From 9f13ded5025f0cfcd9187dbed021d7565235609e Mon Sep 17 00:00:00 2001 From: Flyinghead Date: Fri, 4 May 2018 18:18:04 +0200 Subject: [PATCH] Enable Modifier Volumes. Fix modtrig buffer overflow and stencil reset. --- core/hw/pvr/ta_ctx.h | 2 +- core/rend/gles/gldraw.cpp | 30 +++++++++++++++++------------- core/rend/gles/gles.cpp | 10 ++++------ core/rend/gles/gles.h | 1 + 4 files changed, 23 insertions(+), 20 deletions(-) diff --git a/core/hw/pvr/ta_ctx.h b/core/hw/pvr/ta_ctx.h index 46d6aeeda..cbc7e1f4e 100644 --- a/core/hw/pvr/ta_ctx.h +++ b/core/hw/pvr/ta_ctx.h @@ -166,7 +166,7 @@ struct TA_context rend.global_param_mvo.Init(4096,&rend.Overrun); rend.global_param_tr.Init(4096,&rend.Overrun); - rend.modtrig.Init(4096,&rend.Overrun); + rend.modtrig.Init(8192,&rend.Overrun); Reset(); } diff --git a/core/rend/gles/gldraw.cpp b/core/rend/gles/gldraw.cpp index 03e0396f8..5540ba8be 100644 --- a/core/rend/gles/gldraw.cpp +++ b/core/rend/gles/gldraw.cpp @@ -15,7 +15,7 @@ Takes vertex, textures and renders to the currently set up target //Uncomment this to disable the stencil work around //Seems like there's a bug either on the wrapper, or nvogl making //stencil not work properly (requiring some double calls to get proper results) -//#define NO_STENCIL_WORKAROUND +#define NO_STENCIL_WORKAROUND const static u32 CullMode[]= @@ -147,10 +147,10 @@ s32 SetTileClip(u32 val, bool set) cey = 480 - cey; float dc2s_scale_h = screen_height / 480.0f; float ds2s_offs_x = (screen_width - dc2s_scale_h * 640) / 2; - csx = csx * dc2s_scale_h + ds2s_offs_x; - cex = cex * dc2s_scale_h + ds2s_offs_x; - csy = csy * dc2s_scale_h; - cey = cey * dc2s_scale_h; + csx = csx * dc2s_scale_h * scale_x + ds2s_offs_x; + cex = cex * dc2s_scale_h * scale_x + ds2s_offs_x; + csy = csy * dc2s_scale_h * scale_y; + cey = cey * dc2s_scale_h * scale_y; glUniform4f(CurrentShader->pp_ClipTest, csx, cey, cex, csy); } @@ -843,8 +843,11 @@ void SetMVS_Mode(u32 mv_mode,ISP_Modvol ispc) glStencilMask(2); //no stencil testing glStencilFunc(GL_ALWAYS,0,2); - //count the number of pixels in front of the Z buffer (and only keep the lower bit of the count) + //count the number of pixels in front of the Z buffer (xor zpass) glStencilOp(GL_KEEP,GL_KEEP,GL_INVERT); + + //zfail would be better when camera is in the volume but it doesn't work for open volumes + //glStencilOp(GL_KEEP, GL_INVERT, GL_KEEP); #ifndef NO_STENCIL_WORKAROUND //this needs to be done .. twice ? looks like //a bug somewhere, on gles/nvgl ? @@ -862,8 +865,6 @@ void SetMVS_Mode(u32 mv_mode,ISP_Modvol ispc) //no depth test glDisable(GL_DEPTH_TEST); - //write bits 1:0 - glStencilMask(3); if (mv_mode==1) { @@ -873,7 +874,8 @@ void SetMVS_Mode(u32 mv_mode,ISP_Modvol ispc) //1 : 0 : 01 //1 : 1 : 01 - + //write bits 1:0 + glStencilMask(3); //if (1<=st) st=1; else st=0; glStencilFunc(GL_LEQUAL,1,3); glStencilOp(GL_ZERO,GL_ZERO,GL_REPLACE); @@ -904,8 +906,10 @@ void SetMVS_Mode(u32 mv_mode,ISP_Modvol ispc) //1 : 0 : 00 //1 : 1 : 01 - //if (2>st) st=1; else st=0; //can't be done with a single pass - glStencilFunc(GL_GREATER,1,3); + // Write to bit 0 + glStencilMask(1); // FIXME bit 1 is not reset. Need other pass + //if (3==st) st=1; else st=0; //can't be done with a single pass + glStencilFunc(GL_EQUAL, 3, 3); glStencilOp(GL_ZERO,GL_KEEP,GL_REPLACE); #ifndef NO_STENCIL_WORKAROUND //Look @ comment above -- this looks like a driver bug @@ -997,7 +1001,7 @@ void DrawModVols() */ glColorMask(GL_FALSE,GL_FALSE,GL_FALSE,GL_FALSE); - glDepthFunc(GL_GREATER); + if ( 0 /* || GetAsyncKeyState(VK_F6)*/ ) { //simple single level stencil @@ -1118,7 +1122,7 @@ void DrawStrips() /*if (!GetAsyncKeyState(VK_F1))*/ DrawList(pvrrc.global_param_op); - //DrawModVols(); + DrawModVols(); //Alpha tested //setup alpha test state diff --git a/core/rend/gles/gles.cpp b/core/rend/gles/gles.cpp index 542a93cd6..28e020a4e 100755 --- a/core/rend/gles/gles.cpp +++ b/core/rend/gles/gles.cpp @@ -61,6 +61,7 @@ Tile clip void GenSorted(); float fb_scale_x,fb_scale_y; +float scale_x, scale_y; #ifndef GLES #define attr "in" @@ -1554,8 +1555,6 @@ bool RenderFrame() if (!is_rtt) { gcflip=0; - dc_width=640; - dc_height=480; } else { @@ -1568,12 +1567,10 @@ bool RenderFrame() dc_height=FB_Y_CLIP.max-FB_Y_CLIP.min+1; u32 pvr_stride=(FB_W_LINESTRIDE.stride)*8; */ - - dc_width=640; - dc_height=480; } - float scale_x=1, scale_y=1; + scale_x = 1; + scale_y = 1; float scissoring_scale_x = 1; @@ -1768,6 +1765,7 @@ bool RenderFrame() glClearColor(0,0,0,1.0f); glClearDepthf(0.f); glCheck(); + glStencilMask(0xFF); glCheck(); glClear(GL_COLOR_BUFFER_BIT|GL_STENCIL_BUFFER_BIT|GL_DEPTH_BUFFER_BIT); glCheck(); diff --git a/core/rend/gles/gles.h b/core/rend/gles/gles.h index c77e67f5b..f42069e8a 100755 --- a/core/rend/gles/gles.h +++ b/core/rend/gles/gles.h @@ -43,6 +43,7 @@ //vertex types extern u32 gcflip; +extern float scale_x, scale_y; void DrawStrips();