Files
unease/engine/render/renderdevice.cpp
2025-02-28 04:43:17 +03:00

193 lines
4.6 KiB
C++

#include <assert.h>
#include <stdio.h>
// OpenGL
#include "render/gl_shared.h"
// VERTEX AND INDEX OBJECTS
#include "render/vertexbuffer.h"
#include "render/indexbuffer.h"
//#include "render/rendertarget.h"
#include "render/renderdevice.h"
RenderDevice* g_renderDevice = NULL;
RenderDevice::RenderDevice()
{
m_activeVB = NULL;
m_activeIB = NULL;
m_blending = false;
m_activeReadRT = NULL;
m_activeWriteRT = NULL;
}
RenderDevice::~RenderDevice()
{
}
VertexBuffer* RenderDevice::CreateVertexBuffer(void* data, size_t size, bool isStream)
{
return new VertexBuffer(data, size, isStream);
}
IndexBuffer* RenderDevice::CreateIndexBuffer(void* data, size_t size, bool isStream)
{
return new IndexBuffer(data, size, isStream);
}
void RenderDevice::SetVerticesBuffer(VertexBuffer* buffer)
{
if (buffer) {
if (m_activeVB != buffer) {
m_activeVB = buffer;
m_activeVB->Bind();
}
} else { // unbind buffer
glBindBuffer(GL_ARRAY_BUFFER, 0);
}
}
void RenderDevice::SetIndicesBuffer(IndexBuffer* buffer)
{
if (buffer) {
if (m_activeIB != buffer) {
m_activeIB = buffer;
m_activeIB->Bind();
}
} else { // unbind buffer
glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, 0);
}
}
void RenderDevice::SetDepthTest(bool enable)
{
enable ? glEnable(GL_DEPTH_TEST) : glDisable(GL_DEPTH_TEST);
}
void RenderDevice::SetDepthWrite(bool enable)
{
glDepthMask(enable ? GL_TRUE : GL_FALSE);
}
//void RenderDevice::setVertexFormat(VertexFormat* format)
//{
// assert(format);
//
// if (format->count() == 0) {
// Core::error("RenderDevice::setVertexFormat: failed to set empty vertex format");
// }
//
// size_t appliedOffset = 0;
// for (VertexAttribute* it = format->begin(); it != format->end(); ++it) {
//
// GLenum data_type = get_gl_vertex_attribute_type(it->m_type);
// GLuint data_size = GLuint(get_vertex_attribute_size(it->m_type));
//
// if (appliedOffset > 0)
// glVertexAttribPointer(
// GLuint(it->m_offset),
// GLint(it->m_size),
// data_type,
// GL_FALSE,
// GLsizei(format->size() * data_size),
// (void*)(appliedOffset * sizeof(float))
// );
// else
// glVertexAttribPointer(
// GLuint(it->m_offset),
// GLint(it->m_size),
// data_type,
// GL_FALSE,
// GLsizei(format->size() * data_size),
// (void*)0
// );
//
// glEnableVertexAttribArray(GLuint(it->m_offset));
//
// appliedOffset += it->m_size;
// }
//}
void RenderDevice::SetBlending(bool value)
{
if (m_blending != value) {
m_blending = value;
value ? glEnable(GL_BLEND) : glDisable(GL_BLEND);
}
}
void RenderDevice::SetBlendingFunction(BlendFactor srcFactor, BlendFactor destFactor)
{
// Switch state if one of two blending factors was changed
if (srcFactor != m_srcBlendFactor || destFactor != m_destBlendFactor)
{
m_srcBlendFactor = srcFactor;
m_destBlendFactor = destFactor;
// push to gl state
glBlendFunc(GetGLBlendFactor(srcFactor), GetGLBlendFactor(destFactor));
}
}
void RenderDevice::SetReadRenderTarget(RenderTarget* renderTarget)
{
if (renderTarget) {
if (m_activeReadRT != renderTarget) {
m_activeReadRT = renderTarget;
//glBindFramebuffer(GL_READ_FRAMEBUFFER, renderTarget->m_framebuffer);
}
}
else { // set default rt
// glBindFramebuffer(GL_READ_FRAMEBUFFER, 0);
}
}
void RenderDevice::SetWriteRenderTarget(RenderTarget* renderTarget)
{
if (renderTarget) {
if (m_activeWriteRT != renderTarget) {
m_activeWriteRT = renderTarget;
//glBindFramebuffer(GL_DRAW_FRAMEBUFFER, renderTarget->m_framebuffer);
}
}
else { // set default rt
//glBindFramebuffer(GL_DRAW_FRAMEBUFFER, 0);
}
}
void RenderDevice::SetViewport(int x, int y, int w, int h)
{
glViewport(x, y, w, h);
}
void RenderDevice::BlitRenderTarget(int srcX, int srcY, int srcWidth, int srcHeight, int destX, int destY, int destWidth, int destHeight, TextureSurfaceType surfaceType)
{
GLbitfield mask = 0;
if (surfaceType & TST_COLOR)
mask |= GL_COLOR_BUFFER_BIT;
if (surfaceType & TST_DEPTH)
mask |= GL_DEPTH_BUFFER_BIT;
if (surfaceType & TST_STENCIL)
mask |= GL_STENCIL_BUFFER_BIT;
//glBlitFramebuffer(srcX, srcY, srcWidth, srcHeight, destX, destY, destWidth, destHeight, mask, GL_LINEAR);
}
static GLenum g_glPrimitiveMode[PT_TRIANGLES + 1] = {
GL_POINTS,
GL_LINES,
GL_TRIANGLES
};
void RenderDevice::DrawArrays(PrimitiveType primType, uint startOf, size_t verticesCount)
{
glDrawArrays(g_glPrimitiveMode[primType], startOf, GLsizei(verticesCount));
}
void RenderDevice::DrawElements(PrimitiveType primType, size_t elementsCount, bool is16bitIndices)
{
glDrawElements(g_glPrimitiveMode[primType], GLsizei(elementsCount), is16bitIndices ? GL_UNSIGNED_SHORT : GL_UNSIGNED_INT, NULL);
}