mirror of
https://github.com/melonDS-emu/melonDS.git
synced 2025-07-25 15:19:53 -06:00
get somewhere with this
hahahahahahhhhh except it's still upside-down
This commit is contained in:
14
src/GPU.h
14
src/GPU.h
@ -422,6 +422,20 @@ void SetDispStat(u32 cpu, u16 val);
|
||||
|
||||
void SetVCount(u16 val);
|
||||
|
||||
namespace GLCompositor
|
||||
{
|
||||
|
||||
bool Init();
|
||||
void DeInit();
|
||||
void Reset();
|
||||
|
||||
void UpdateDisplaySettings();
|
||||
|
||||
void RenderFrame();
|
||||
void BindOutputTexture();
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
#endif
|
||||
|
@ -371,11 +371,19 @@ bool Init()
|
||||
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_NEAREST);
|
||||
glTexImage2D(GL_TEXTURE_2D, 0, GL_RGB5_A1, 1024, 48, 0, GL_RGBA, GL_UNSIGNED_SHORT_1_5_5_5_REV, NULL);
|
||||
|
||||
if (!GPU::GLCompositor::Init())
|
||||
{
|
||||
// TODO: clean up things? fail more gracefully??
|
||||
return false;
|
||||
}
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
void DeInit()
|
||||
{
|
||||
GPU::GLCompositor::DeInit();
|
||||
|
||||
glDeleteTextures(1, &TexMemID);
|
||||
glDeleteTextures(1, &TexPalMemID);
|
||||
|
||||
@ -398,6 +406,7 @@ void DeInit()
|
||||
|
||||
void Reset()
|
||||
{
|
||||
GPU::GLCompositor::Reset();
|
||||
}
|
||||
|
||||
void UpdateDisplaySettings()
|
||||
@ -480,6 +489,8 @@ void UpdateDisplaySettings()
|
||||
|
||||
//glLineWidth(scale);
|
||||
//glLineWidth(1.5);
|
||||
|
||||
GPU::GLCompositor::UpdateDisplaySettings();
|
||||
}
|
||||
|
||||
|
||||
|
@ -26,7 +26,171 @@
|
||||
|
||||
namespace GPU
|
||||
{
|
||||
namespace GLCompositor
|
||||
{
|
||||
|
||||
// shit goes here
|
||||
int Scale;
|
||||
int ScreenH, ScreenW;
|
||||
|
||||
GLuint CompShader[1][3];
|
||||
GLuint CompScaleLoc[1];
|
||||
|
||||
GLuint CompVertexBufferID;
|
||||
GLuint CompVertexArrayID;
|
||||
float CompVertices[2 * 3*2 * 2]; // position
|
||||
|
||||
GLuint CompScreenInputTex;
|
||||
GLuint CompScreenOutputTex;
|
||||
GLuint CompScreenOutputFB;
|
||||
|
||||
|
||||
bool Init()
|
||||
{
|
||||
if (!OpenGL_BuildShaderProgram(kCompositorVS, kCompositorFS_Nearest, CompShader[0], "CompositorShader"))
|
||||
return false;
|
||||
|
||||
for (int i = 0; i < 1; i++)
|
||||
{
|
||||
glBindAttribLocation(CompShader[i][2], 0, "vPosition");
|
||||
glBindFragDataLocation(CompShader[i][2], 0, "oColor");
|
||||
|
||||
if (!OpenGL_LinkShaderProgram(CompShader[i]))
|
||||
return false;
|
||||
|
||||
CompScaleLoc[i] = glGetUniformLocation(CompShader[i][2], "u3DScale");
|
||||
}
|
||||
|
||||
#define SETVERTEX(i, x, y) \
|
||||
CompVertices[2*(i) + 0] = x; \
|
||||
CompVertices[2*(i) + 1] = y;
|
||||
|
||||
// top screen
|
||||
SETVERTEX(0, -1, 1);
|
||||
SETVERTEX(1, 1, 0);
|
||||
SETVERTEX(2, 1, 1);
|
||||
SETVERTEX(3, -1, 1);
|
||||
SETVERTEX(4, -1, 0);
|
||||
SETVERTEX(5, 1, 0);
|
||||
|
||||
// bottom screen
|
||||
SETVERTEX(6, -1, 0);
|
||||
SETVERTEX(7, 1, -1);
|
||||
SETVERTEX(8, 1, 0);
|
||||
SETVERTEX(9, -1, 0);
|
||||
SETVERTEX(10, -1, -1);
|
||||
SETVERTEX(11, 1, -1);
|
||||
|
||||
#undef SETVERTEX
|
||||
|
||||
glGenBuffers(1, &CompVertexBufferID);
|
||||
glBindBuffer(GL_ARRAY_BUFFER, CompVertexBufferID);
|
||||
glBufferData(GL_ARRAY_BUFFER, sizeof(CompVertices), CompVertices, GL_STATIC_DRAW);
|
||||
|
||||
glGenVertexArrays(1, &CompVertexArrayID);
|
||||
glBindVertexArray(CompVertexArrayID);
|
||||
glEnableVertexAttribArray(0); // position
|
||||
glVertexAttribPointer(0, 2, GL_FLOAT, GL_FALSE, 2*4, (void*)(0));
|
||||
|
||||
glGenFramebuffers(1, &CompScreenOutputFB);
|
||||
|
||||
glGenTextures(1, &CompScreenInputTex);
|
||||
glActiveTexture(GL_TEXTURE0);
|
||||
glBindTexture(GL_TEXTURE_2D, CompScreenInputTex);
|
||||
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_CLAMP_TO_EDGE);
|
||||
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_CLAMP_TO_EDGE);
|
||||
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_NEAREST);
|
||||
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_NEAREST);
|
||||
glTexImage2D(GL_TEXTURE_2D, 0, GL_RGBA8UI, 256*3 + 1, 192*2, 0, GL_RGBA_INTEGER, GL_UNSIGNED_BYTE, NULL);
|
||||
|
||||
glGenTextures(1, &CompScreenOutputTex);
|
||||
glBindTexture(GL_TEXTURE_2D, CompScreenOutputTex);
|
||||
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_CLAMP_TO_EDGE);
|
||||
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_CLAMP_TO_EDGE);
|
||||
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_NEAREST);
|
||||
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_NEAREST);
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
void DeInit()
|
||||
{
|
||||
glDeleteFramebuffers(1, &CompScreenOutputFB);
|
||||
glDeleteTextures(1, &CompScreenInputTex);
|
||||
glDeleteTextures(1, &CompScreenOutputTex);
|
||||
|
||||
glDeleteVertexArrays(1, &CompVertexArrayID);
|
||||
glDeleteBuffers(1, &CompVertexBufferID);
|
||||
|
||||
for (int i = 0; i < 1; i++)
|
||||
OpenGL_DeleteShaderProgram(CompShader[i]);
|
||||
}
|
||||
|
||||
void Reset()
|
||||
{
|
||||
}
|
||||
|
||||
|
||||
void UpdateDisplaySettings()
|
||||
{
|
||||
int scale = Config::GL_ScaleFactor;
|
||||
|
||||
Scale = scale;
|
||||
ScreenW = 256 * scale;
|
||||
ScreenH = 384 * scale;
|
||||
|
||||
glBindTexture(GL_TEXTURE_2D, CompScreenOutputTex);
|
||||
glTexImage2D(GL_TEXTURE_2D, 0, GL_RGBA, ScreenW, ScreenH, 0, GL_RGBA, GL_UNSIGNED_BYTE, NULL);
|
||||
|
||||
GLenum fbassign[] = {GL_COLOR_ATTACHMENT0};
|
||||
glBindFramebuffer(GL_FRAMEBUFFER, CompScreenOutputFB);
|
||||
glFramebufferTexture(GL_FRAMEBUFFER, GL_COLOR_ATTACHMENT0, CompScreenOutputTex, 0);
|
||||
glDrawBuffers(1, fbassign);
|
||||
}
|
||||
|
||||
|
||||
void RenderFrame()
|
||||
{printf("0: error %04X\n", glGetError());
|
||||
glBindFramebuffer(GL_FRAMEBUFFER, CompScreenOutputFB);
|
||||
printf("1: error %04X\n", glGetError());
|
||||
glDisable(GL_DEPTH_TEST);
|
||||
glDisable(GL_STENCIL_TEST);
|
||||
glDisable(GL_BLEND);
|
||||
glColorMaski(0, GL_TRUE, GL_TRUE, GL_TRUE, GL_TRUE);
|
||||
|
||||
glViewport(0, 0, ScreenW, ScreenH);
|
||||
printf("2: error %04X\n", glGetError());
|
||||
// TODO: select more shaders (filtering, etc)
|
||||
OpenGL_UseShaderProgram(CompShader[0]);
|
||||
glUniform1ui(CompScaleLoc[0], Scale);
|
||||
printf("3: error %04X\n", glGetError());
|
||||
//if (RunningSomething)
|
||||
{
|
||||
int frontbuf = GPU::FrontBuffer;
|
||||
glActiveTexture(GL_TEXTURE0);
|
||||
glBindTexture(GL_TEXTURE_2D, CompScreenInputTex);
|
||||
printf("4: error %04X\n", glGetError());
|
||||
if (GPU::Framebuffer[frontbuf][0] && GPU::Framebuffer[frontbuf][1])
|
||||
{
|
||||
glTexSubImage2D(GL_TEXTURE_2D, 0, 0, 0, 256*3 + 1, 192, GL_RGBA_INTEGER,
|
||||
GL_UNSIGNED_BYTE, GPU::Framebuffer[frontbuf][0]);
|
||||
glTexSubImage2D(GL_TEXTURE_2D, 0, 0, 192, 256*3 + 1, 192, GL_RGBA_INTEGER,
|
||||
GL_UNSIGNED_BYTE, GPU::Framebuffer[frontbuf][1]);
|
||||
}
|
||||
printf("5: error %04X\n", glGetError());
|
||||
glActiveTexture(GL_TEXTURE1);
|
||||
GPU3D::GLRenderer::SetupAccelFrame();
|
||||
printf("6: error %04X\n", glGetError());
|
||||
glBindBuffer(GL_ARRAY_BUFFER, CompVertexBufferID);
|
||||
glBindVertexArray(CompVertexArrayID);
|
||||
glDrawArrays(GL_TRIANGLES, 0, 4*3);
|
||||
printf("7: error %04X\n", glGetError());
|
||||
}
|
||||
}
|
||||
|
||||
void BindOutputTexture()
|
||||
{
|
||||
glBindTexture(GL_TEXTURE_2D, CompScreenOutputTex);
|
||||
}
|
||||
|
||||
}
|
||||
}
|
||||
|
@ -19,9 +19,144 @@
|
||||
#ifndef GPU_OPENGL_SHADERS_H
|
||||
#define GPU_OPENGL_SHADERS_H
|
||||
|
||||
#define kShaderHeader "#version 140"
|
||||
const char* kCompositorVS = R"(#version 140
|
||||
|
||||
in vec2 vPosition;
|
||||
|
||||
// shader shit goes here
|
||||
smooth out vec2 fTexcoord;
|
||||
|
||||
void main()
|
||||
{
|
||||
vec4 fpos;
|
||||
fpos.xy = vPosition;
|
||||
fpos.z = 0.0;
|
||||
fpos.w = 1.0;
|
||||
|
||||
gl_Position = fpos;
|
||||
fTexcoord = (vPosition + vec2(1.0, -1.0)) * (vec2(256.0, -384.0) / 2.0);
|
||||
}
|
||||
)";
|
||||
|
||||
const char* kCompositorFS_Nearest = R"(#version 140
|
||||
|
||||
uniform uint u3DScale;
|
||||
|
||||
uniform usampler2D ScreenTex;
|
||||
uniform sampler2D _3DTex;
|
||||
|
||||
smooth in vec2 fTexcoord;
|
||||
|
||||
out vec4 oColor;
|
||||
|
||||
void main()
|
||||
{
|
||||
ivec4 pixel = ivec4(texelFetch(ScreenTex, ivec2(fTexcoord), 0));
|
||||
|
||||
ivec4 mbright = ivec4(texelFetch(ScreenTex, ivec2(256*3, int(fTexcoord.y)), 0));
|
||||
int dispmode = mbright.b & 0x3;
|
||||
|
||||
if (dispmode == 1)
|
||||
{
|
||||
ivec4 val1 = pixel;
|
||||
ivec4 val2 = ivec4(texelFetch(ScreenTex, ivec2(fTexcoord) + ivec2(256,0), 0));
|
||||
ivec4 val3 = ivec4(texelFetch(ScreenTex, ivec2(fTexcoord) + ivec2(512,0), 0));
|
||||
|
||||
int compmode = val3.a & 0xF;
|
||||
int eva, evb, evy;
|
||||
|
||||
if (compmode == 4)
|
||||
{
|
||||
// 3D on top, blending
|
||||
|
||||
float xpos = val3.r + fract(fTexcoord.x);
|
||||
float ypos = mod(fTexcoord.y, 192);
|
||||
ivec4 _3dpix = ivec4(texelFetch(_3DTex, ivec2(vec2(xpos, ypos)*u3DScale), 0).bgra
|
||||
* vec4(63,63,63,31));
|
||||
|
||||
if (_3dpix.a > 0)
|
||||
{
|
||||
eva = (_3dpix.a & 0x1F) + 1;
|
||||
evb = 32 - eva;
|
||||
|
||||
val1 = ((_3dpix * eva) + (val1 * evb)) >> 5;
|
||||
if (eva <= 16) val1 += ivec4(1,1,1,0);
|
||||
val1 = min(val1, 0x3F);
|
||||
}
|
||||
else
|
||||
val1 = val2;
|
||||
}
|
||||
else if (compmode == 1)
|
||||
{
|
||||
// 3D on bottom, blending
|
||||
|
||||
float xpos = val3.r + fract(fTexcoord.x);
|
||||
float ypos = mod(fTexcoord.y, 192);
|
||||
ivec4 _3dpix = ivec4(texelFetch(_3DTex, ivec2(vec2(xpos, ypos)*u3DScale), 0).bgra
|
||||
* vec4(63,63,63,31));
|
||||
|
||||
if (_3dpix.a > 0)
|
||||
{
|
||||
eva = val3.g;
|
||||
evb = val3.b;
|
||||
|
||||
val1 = ((val1 * eva) + (_3dpix * evb)) >> 4;
|
||||
val1 = min(val1, 0x3F);
|
||||
}
|
||||
else
|
||||
val1 = val2;
|
||||
}
|
||||
else if (compmode <= 3)
|
||||
{
|
||||
// 3D on top, normal/fade
|
||||
|
||||
float xpos = val3.r + fract(fTexcoord.x);
|
||||
float ypos = mod(fTexcoord.y, 192);
|
||||
ivec4 _3dpix = ivec4(texelFetch(_3DTex, ivec2(vec2(xpos, ypos)*u3DScale), 0).bgra
|
||||
* vec4(63,63,63,31));
|
||||
|
||||
if (_3dpix.a > 0)
|
||||
{
|
||||
evy = val3.g;
|
||||
|
||||
val1 = _3dpix;
|
||||
if (compmode == 2) val1 += ((ivec4(0x3F,0x3F,0x3F,0) - val1) * evy) >> 4;
|
||||
else if (compmode == 3) val1 -= (val1 * evy) >> 4;
|
||||
}
|
||||
else
|
||||
val1 = val2;
|
||||
}
|
||||
|
||||
pixel = val1;
|
||||
}
|
||||
|
||||
if (dispmode != 0)
|
||||
{
|
||||
int brightmode = mbright.g >> 6;
|
||||
if (brightmode == 1)
|
||||
{
|
||||
// up
|
||||
int evy = mbright.r & 0x1F;
|
||||
if (evy > 16) evy = 16;
|
||||
|
||||
pixel += ((ivec4(0x3F,0x3F,0x3F,0) - pixel) * evy) >> 4;
|
||||
}
|
||||
else if (brightmode == 2)
|
||||
{
|
||||
// down
|
||||
int evy = mbright.r & 0x1F;
|
||||
if (evy > 16) evy = 16;
|
||||
|
||||
pixel -= (pixel * evy) >> 4;
|
||||
}
|
||||
}
|
||||
|
||||
pixel.rgb <<= 2;
|
||||
pixel.rgb |= (pixel.rgb >> 6);
|
||||
|
||||
// TODO: filters
|
||||
|
||||
oColor = vec4(vec3(pixel.rgb) / 255.0, 1.0);
|
||||
}
|
||||
)";
|
||||
|
||||
#endif // GPU_OPENGL_SHADERS_H
|
||||
|
@ -319,6 +319,11 @@ void GLScreen_DrawScreen()
|
||||
uiGLSetVSync(vsync);
|
||||
}
|
||||
|
||||
if (GPU3D::Renderer != 0)
|
||||
{
|
||||
GPU::GLCompositor::RenderFrame();
|
||||
}
|
||||
|
||||
float scale = uiGLGetFramebufferScale(GLContext);
|
||||
|
||||
glBindFramebuffer(GL_FRAMEBUFFER, uiGLGetFramebuffer(GLContext));
|
||||
@ -353,8 +358,8 @@ void GLScreen_DrawScreen()
|
||||
x1 = TopScreenRect.X + TopScreenRect.Width;
|
||||
y1 = TopScreenRect.Y + TopScreenRect.Height;
|
||||
|
||||
scwidth = 256;
|
||||
scheight = 192;
|
||||
scwidth = 256 * GL_3DScale;
|
||||
scheight = 192 * GL_3DScale;
|
||||
|
||||
switch (ScreenRotation)
|
||||
{
|
||||
@ -399,8 +404,8 @@ void GLScreen_DrawScreen()
|
||||
x1 = BottomScreenRect.X + BottomScreenRect.Width;
|
||||
y1 = BottomScreenRect.Y + BottomScreenRect.Height;
|
||||
|
||||
scwidth = 256;
|
||||
scheight = 192;
|
||||
scwidth = 256 * GL_3DScale;
|
||||
scheight = 192 * GL_3DScale;
|
||||
|
||||
switch (ScreenRotation)
|
||||
{
|
||||
@ -453,10 +458,10 @@ void GLScreen_DrawScreen()
|
||||
|
||||
glViewport(0, 0, WindowWidth*scale, WindowHeight*scale);
|
||||
|
||||
if (GPU3D::Renderer == 0)
|
||||
//if (GPU3D::Renderer == 0)
|
||||
OpenGL_UseShaderProgram(GL_ScreenShader);
|
||||
else
|
||||
OpenGL_UseShaderProgram(GL_ScreenShaderAccel);
|
||||
//else
|
||||
// OpenGL_UseShaderProgram(GL_ScreenShaderAccel);
|
||||
|
||||
glClearColor(0, 0, 0, 1);
|
||||
glClear(GL_COLOR_BUFFER_BIT);
|
||||
@ -465,12 +470,12 @@ void GLScreen_DrawScreen()
|
||||
{
|
||||
int frontbuf = GPU::FrontBuffer;
|
||||
glActiveTexture(GL_TEXTURE0);
|
||||
glBindTexture(GL_TEXTURE_2D, GL_ScreenTexture);
|
||||
|
||||
if (GPU::Framebuffer[frontbuf][0] && GPU::Framebuffer[frontbuf][1])
|
||||
{
|
||||
if (GPU3D::Renderer == 0)
|
||||
{
|
||||
glBindTexture(GL_TEXTURE_2D, GL_ScreenTexture);
|
||||
glTexSubImage2D(GL_TEXTURE_2D, 0, 0, 0, 256, 192, GL_RGBA_INTEGER,
|
||||
GL_UNSIGNED_BYTE, GPU::Framebuffer[frontbuf][0]);
|
||||
glTexSubImage2D(GL_TEXTURE_2D, 0, 0, 192, 256, 192, GL_RGBA_INTEGER,
|
||||
@ -478,16 +483,17 @@ void GLScreen_DrawScreen()
|
||||
}
|
||||
else
|
||||
{
|
||||
glTexSubImage2D(GL_TEXTURE_2D, 0, 0, 0, 256*3 + 1, 192, GL_RGBA_INTEGER,
|
||||
GPU::GLCompositor::BindOutputTexture();
|
||||
/*glTexSubImage2D(GL_TEXTURE_2D, 0, 0, 0, 256*3 + 1, 192, GL_RGBA_INTEGER,
|
||||
GL_UNSIGNED_BYTE, GPU::Framebuffer[frontbuf][0]);
|
||||
glTexSubImage2D(GL_TEXTURE_2D, 0, 0, 192, 256*3 + 1, 192, GL_RGBA_INTEGER,
|
||||
GL_UNSIGNED_BYTE, GPU::Framebuffer[frontbuf][1]);
|
||||
GL_UNSIGNED_BYTE, GPU::Framebuffer[frontbuf][1]);*/
|
||||
}
|
||||
}
|
||||
|
||||
glActiveTexture(GL_TEXTURE1);
|
||||
if (GPU3D::Renderer != 0)
|
||||
GPU3D::GLRenderer::SetupAccelFrame();
|
||||
//glActiveTexture(GL_TEXTURE1);
|
||||
//if (GPU3D::Renderer != 0)
|
||||
// GPU3D::GLRenderer::SetupAccelFrame();
|
||||
|
||||
glBindBuffer(GL_ARRAY_BUFFER, GL_ScreenVertexBufferID);
|
||||
glBindVertexArray(GL_ScreenVertexArrayID);
|
||||
|
@ -55,7 +55,7 @@ layout(std140) uniform uConfig
|
||||
uint uFilterMode;
|
||||
};
|
||||
|
||||
uniform usampler2D ScreenTex;
|
||||
uniform sampler2D ScreenTex;
|
||||
|
||||
smooth in vec2 fTexcoord;
|
||||
|
||||
@ -68,6 +68,7 @@ void main()
|
||||
// TODO: filters
|
||||
|
||||
oColor = vec4(vec3(pixel.bgr) / 255.0, 1.0);
|
||||
oColor = texelFetch(ScreenTex, ivec2(fTexcoord), 0);
|
||||
}
|
||||
)";
|
||||
|
||||
|
Reference in New Issue
Block a user