116 lines
3.0 KiB
C++
116 lines
3.0 KiB
C++
#include "Canvas.h"
|
|
#include "EngineCore/Game.h"
|
|
#include "EngineFrame/Render/RenderManager.h"
|
|
Canvas::Canvas(VecSize size)
|
|
{
|
|
m_size = size;
|
|
m_renderRect = {0, 0, size.width, size.height};
|
|
m_rect = {0, 0, (float)size.width, (float)size.height};
|
|
m_texture = new Texture();
|
|
m_texture->Init(VecSize(Game::GetInstance().Screen_W, Game::GetInstance().Screen_H));
|
|
|
|
Actor::Init();
|
|
|
|
glGenFramebuffers(1, &m_fbo);
|
|
glBindFramebuffer(GL_FRAMEBUFFER, m_fbo);
|
|
// 将目标纹理附加到FBO的颜色附着点
|
|
glFramebufferTexture2D(
|
|
GL_FRAMEBUFFER, // 帧缓冲类型
|
|
GL_COLOR_ATTACHMENT0, // 颜色附着点(可多个,这里用第一个)
|
|
GL_TEXTURE_2D, // 纹理类型
|
|
m_texture->getID(), // 目标纹理ID
|
|
0 // 多级渐远纹理级别
|
|
);
|
|
glBindFramebuffer(GL_FRAMEBUFFER, 0); // 解绑FBO
|
|
}
|
|
|
|
void Canvas::PreRender()
|
|
{
|
|
m_rect.x = GetWorldPos().x;
|
|
m_rect.y = GetWorldPos().y;
|
|
}
|
|
|
|
void Canvas::Render()
|
|
{
|
|
RenderManager *renderer = Game::GetInstance().GetRenderer();
|
|
SDL_FPoint AnchorPos = {0, 0};
|
|
if (m_dirty)
|
|
{
|
|
glBindFramebuffer(GL_FRAMEBUFFER, m_fbo); // 绑定FBO
|
|
glClearColor(0.0f, 0.0f, 0.0f, 0.0f);
|
|
glClear(GL_COLOR_BUFFER_BIT);
|
|
for (auto &info : m_drawQueue)
|
|
{
|
|
renderer->DrawTexture(m_imgMap[info.texture], nullptr, &info.rect, 0.f, &AnchorPos, SDL_FLIP_NONE);
|
|
}
|
|
glBindFramebuffer(GL_FRAMEBUFFER, 0); // 解绑FBO
|
|
m_dirty = false;
|
|
}
|
|
|
|
renderer->SetCurrentShaderProgram("flip_y");
|
|
// 混合
|
|
if (this->_BlendMode != NONE)
|
|
Blend();
|
|
renderer->DrawTexture(m_texture, &m_renderRect, &m_rect, 0.f, &AnchorPos, SDL_FLIP_NONE);
|
|
// 还原混合
|
|
if (this->_BlendMode != NONE)
|
|
glBlendFunc(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA);
|
|
renderer->SetCurrentShaderProgram("normal");
|
|
}
|
|
|
|
void Canvas::DrawImg(std::string img, int index, Vec2 pos)
|
|
{
|
|
m_dirty = true;
|
|
ImgKey key = {img, index};
|
|
DrawInfo info;
|
|
info.rect.x = pos.x;
|
|
info.rect.y = pos.y;
|
|
info.texture = key;
|
|
|
|
if (m_imgMap.find(key) == m_imgMap.end())
|
|
{
|
|
RefPtr<Texture> tex = new Texture();
|
|
tex->Init(img, index);
|
|
m_imgMap[key] = tex;
|
|
}
|
|
|
|
info.rect.w = m_imgMap[key]->getSize().width;
|
|
info.rect.h = m_imgMap[key]->getSize().height;
|
|
|
|
m_drawQueue.push_back(info);
|
|
}
|
|
|
|
void Canvas::DrawImg(std::string img, int index, SDL_FRect rect)
|
|
{
|
|
m_dirty = true;
|
|
ImgKey key = {img, index};
|
|
DrawInfo info;
|
|
info.rect = rect;
|
|
info.texture = key;
|
|
|
|
if (m_imgMap.find(key) == m_imgMap.end())
|
|
{
|
|
RefPtr<Texture> tex = new Texture();
|
|
tex->Init(img, index);
|
|
m_imgMap[key] = tex;
|
|
}
|
|
|
|
m_drawQueue.push_back(info);
|
|
}
|
|
|
|
void Canvas::Clear()
|
|
{
|
|
m_drawQueue.clear();
|
|
m_dirty = true;
|
|
}
|
|
|
|
void Canvas::Blend()
|
|
{
|
|
switch (this->_BlendMode)
|
|
{
|
|
case LINEARDODGE:
|
|
glBlendFuncSeparate(GL_SRC_ALPHA, GL_ONE, GL_ZERO, GL_ONE);
|
|
break;
|
|
}
|
|
}
|