diff --git a/src/rendering/polyrenderer/drawers/screen_triangle.cpp b/src/rendering/polyrenderer/drawers/screen_triangle.cpp index 66f3c98694..9e3e3a202c 100644 --- a/src/rendering/polyrenderer/drawers/screen_triangle.cpp +++ b/src/rendering/polyrenderer/drawers/screen_triangle.cpp @@ -833,1727 +833,3 @@ void(*ScreenTriangle::TestSpanOpts[])(int y, int x0, int x1, const TriDrawTriang &TestSpan, &TestSpan }; - -#if 0 - -static void SortVertices(const TriDrawTriangleArgs *args, ScreenTriVertex **sortedVertices) -{ - sortedVertices[0] = args->v1; - sortedVertices[1] = args->v2; - sortedVertices[2] = args->v3; - - if (sortedVertices[1]->y < sortedVertices[0]->y) - std::swap(sortedVertices[0], sortedVertices[1]); - if (sortedVertices[2]->y < sortedVertices[0]->y) - std::swap(sortedVertices[0], sortedVertices[2]); - if (sortedVertices[2]->y < sortedVertices[1]->y) - std::swap(sortedVertices[1], sortedVertices[2]); -} - -void ScreenTriangle::Draw(const TriDrawTriangleArgs *args, PolyTriangleThreadData *thread) -{ - using namespace TriScreenDrawerModes; - - // Sort vertices by Y position - ScreenTriVertex *sortedVertices[3]; - SortVertices(args, sortedVertices); - - int clipleft = thread->clip.left; - int cliptop = MAX(thread->clip.top, thread->numa_start_y); - int clipright = thread->clip.right; - int clipbottom = MIN(thread->clip.bottom, thread->numa_end_y); - - int topY = (int)(sortedVertices[0]->y + 0.5f); - int midY = (int)(sortedVertices[1]->y + 0.5f); - int bottomY = (int)(sortedVertices[2]->y + 0.5f); - - topY = MAX(topY, cliptop); - midY = MIN(midY, clipbottom); - bottomY = MIN(bottomY, clipbottom); - - if (topY >= bottomY) - return; - - topY += thread->skipped_by_thread(topY); - int num_cores = thread->num_cores; - - // Find start/end X positions for each line covered by the triangle: - - int16_t edges[MAXHEIGHT * 2]; - - int y = topY; - - float longDX = sortedVertices[2]->x - sortedVertices[0]->x; - float longDY = sortedVertices[2]->y - sortedVertices[0]->y; - float longStep = longDX / longDY; - float longPos = sortedVertices[0]->x + longStep * (y + 0.5f - sortedVertices[0]->y) + 0.5f; - longStep *= num_cores; - - if (y < midY) - { - float shortDX = sortedVertices[1]->x - sortedVertices[0]->x; - float shortDY = sortedVertices[1]->y - sortedVertices[0]->y; - float shortStep = shortDX / shortDY; - float shortPos = sortedVertices[0]->x + shortStep * (y + 0.5f - sortedVertices[0]->y) + 0.5f; - shortStep *= num_cores; - - while (y < midY) - { - int x0 = (int)shortPos; - int x1 = (int)longPos; - if (x1 < x0) std::swap(x0, x1); - x0 = clamp(x0, clipleft, clipright); - x1 = clamp(x1, clipleft, clipright); - - edges[y << 1] = x0; - edges[(y << 1) + 1] = x1; - - shortPos += shortStep; - longPos += longStep; - y += num_cores; - } - } - - if (y < bottomY) - { - float shortDX = sortedVertices[2]->x - sortedVertices[1]->x; - float shortDY = sortedVertices[2]->y - sortedVertices[1]->y; - float shortStep = shortDX / shortDY; - float shortPos = sortedVertices[1]->x + shortStep * (y + 0.5f - sortedVertices[1]->y) + 0.5f; - shortStep *= num_cores; - - while (y < bottomY) - { - int x0 = (int)shortPos; - int x1 = (int)longPos; - if (x1 < x0) std::swap(x0, x1); - x0 = clamp(x0, clipleft, clipright); - x1 = clamp(x1, clipleft, clipright); - - edges[y << 1] = x0; - edges[(y << 1) + 1] = x1; - - shortPos += shortStep; - longPos += longStep; - y += num_cores; - } - } - - int opt = 0; - if (thread->drawargs.DepthTest()) opt |= SWTRI_DepthTest; - if (thread->drawargs.StencilTest()) opt |= SWTRI_StencilTest; - if (thread->drawargs.WriteColor()) opt |= SWTRI_WriteColor; - if (thread->drawargs.WriteDepth()) opt |= SWTRI_WriteDepth; - if (thread->drawargs.WriteStencil()) opt |= SWTRI_WriteStencil; - - TriangleDrawers[opt](args, thread, edges, topY, bottomY); -} - -static void FillDepthValues(float *depthvalues, float posXW, float stepXW, int count, float depthbias) -{ -#ifndef NO_SSE - __m128 mstepXW = _mm_set1_ps(stepXW * 4.0f); - __m128 mfirstStepXW = _mm_setr_ps(0.0f, stepXW, stepXW + stepXW, stepXW + stepXW + stepXW); - __m128 mposXW = _mm_add_ps(_mm_set1_ps(posXW), mfirstStepXW); - __m128 mdepthbias = _mm_set1_ps(depthbias); - while (count > 0) - { - _mm_storeu_ps(depthvalues, _mm_add_ps(_mm_rcp_ps(mposXW), mdepthbias)); - mposXW = _mm_add_ps(mposXW, mstepXW); - depthvalues += 4; - count -= 4; - } -#else - while (count > 0) - { - *(depthvalues++) = 1.0f / posXW + depthbias; - posXW += stepXW; - count--; - } -#endif -} - -template -void DrawTriangle(const TriDrawTriangleArgs *args, PolyTriangleThreadData *thread, int16_t *edges, int topY, int bottomY) -{ - using namespace TriScreenDrawerModes; - - void(*drawfunc)(int y, int x0, int x1, const TriDrawTriangleArgs *args, PolyTriangleThreadData *thread); - float stepXW, v1X, v1Y, v1W; - uint8_t stencilTestValue, stencilWriteValue; - float *zbuffer; - float *zbufferLine; - uint8_t *stencilbuffer; - uint8_t *stencilLine; - int pitch; - - bool alphatest = thread->AlphaTest; - uint8_t *alphatestbuf = thread->alphatestbuffer; - - if (OptT::Flags & SWTRI_WriteColor) - { - int bmode = (int)thread->drawargs.BlendMode(); - drawfunc = thread->dest_bgra ? ScreenTriangle::SpanDrawers32[bmode] : ScreenTriangle::SpanDrawers8[bmode]; - } - - if ((OptT::Flags & SWTRI_DepthTest) || (OptT::Flags & SWTRI_WriteDepth)) - { - stepXW = args->gradientX.W; - v1X = args->v1->x; - v1Y = args->v1->y; - v1W = args->v1->w; - zbuffer = thread->depthstencil->DepthValues(); - } - - if ((OptT::Flags & SWTRI_StencilTest) || (OptT::Flags & SWTRI_WriteStencil)) - { - stencilbuffer = thread->depthstencil->StencilValues(); - } - - if ((OptT::Flags & SWTRI_StencilTest) || (OptT::Flags & SWTRI_WriteStencil) || (OptT::Flags & SWTRI_DepthTest) || (OptT::Flags & SWTRI_WriteDepth)) - pitch = thread->depthstencil->Width(); - - if (OptT::Flags & SWTRI_StencilTest) - stencilTestValue = thread->drawargs.StencilTestValue(); - - if (OptT::Flags & SWTRI_WriteStencil) - stencilWriteValue = thread->drawargs.StencilWriteValue(); - - float depthbias; - if ((OptT::Flags & SWTRI_DepthTest) || (OptT::Flags & SWTRI_WriteDepth)) - { - depthbias = thread->depthbias; - } - - float *depthvalues = thread->depthvalues; - - int num_cores = thread->num_cores; - for (int y = topY; y < bottomY; y += num_cores) - { - int x = edges[y << 1]; - int xend = edges[(y << 1) + 1]; - - if ((OptT::Flags & SWTRI_StencilTest) || (OptT::Flags & SWTRI_WriteStencil)) - stencilLine = stencilbuffer + pitch * y; - - if ((OptT::Flags & SWTRI_DepthTest) || (OptT::Flags & SWTRI_WriteDepth)) - { - zbufferLine = zbuffer + pitch * y; - - float startX = x + (0.5f - v1X); - float startY = y + (0.5f - v1Y); - float posXW = v1W + stepXW * startX + args->gradientY.W * startY; - FillDepthValues(depthvalues + x, posXW, stepXW, xend - x, depthbias); - } - -#ifndef NO_SSE - while (x < xend) - { - int xstart = x; - - if ((OptT::Flags & SWTRI_DepthTest) && (OptT::Flags & SWTRI_StencilTest)) - { - int xendsse = x + ((xend - x) / 4); - __m128 mposXW; - while (x < xendsse && - _mm_movemask_ps(_mm_cmpge_ps(_mm_loadu_ps(zbufferLine + x), mposXW = _mm_loadu_ps(depthvalues + x))) == 15 && - stencilLine[x] == stencilTestValue && - stencilLine[x + 1] == stencilTestValue && - stencilLine[x + 2] == stencilTestValue && - stencilLine[x + 3] == stencilTestValue) - { - if (!alphatest && (OptT::Flags & SWTRI_WriteDepth)) - _mm_storeu_ps(zbufferLine + x, mposXW); - x += 4; - } - - while (zbufferLine[x] >= depthvalues[x] && stencilLine[x] == stencilTestValue && x < xend) - { - if (!alphatest && (OptT::Flags & SWTRI_WriteDepth)) - zbufferLine[x] = depthvalues[x]; - x++; - } - } - else if (OptT::Flags & SWTRI_DepthTest) - { - int xendsse = x + ((xend - x) / 4); - __m128 mposXW; - while (x < xendsse && _mm_movemask_ps(_mm_cmpge_ps(_mm_loadu_ps(zbufferLine + x), mposXW = _mm_loadu_ps(depthvalues + x))) == 15) - { - if (!alphatest && (OptT::Flags & SWTRI_WriteDepth)) - _mm_storeu_ps(zbufferLine + x, mposXW); - x += 4; - } - - while (zbufferLine[x] >= depthvalues[x] && x < xend) - { - if (!alphatest && (OptT::Flags & SWTRI_WriteDepth)) - zbufferLine[x] = depthvalues[x]; - x++; - } - } - else if (OptT::Flags & SWTRI_StencilTest) - { - int xendsse = x + ((xend - x) / 16); - while (x < xendsse && _mm_movemask_epi8(_mm_cmpeq_epi8(_mm_loadu_si128((const __m128i*)&stencilLine[x]), _mm_set1_epi8(stencilTestValue))) == 0xffff) - { - x += 16; - } - - while (stencilLine[x] == stencilTestValue && x < xend) - x++; - } - else - { - x = xend; - } - - if (x > xstart) - { - if (OptT::Flags & SWTRI_WriteColor) - drawfunc(y, xstart, x, args, thread); - - if (alphatest) - { - if (OptT::Flags & SWTRI_WriteStencil) - { - for (int i = xstart; i < x; i++) - { - if (alphatestbuf[i] > 127) - stencilLine[i++] = stencilWriteValue; - } - } - - if (OptT::Flags & SWTRI_WriteDepth) - { - for (int i = xstart; i < x; i++) - { - if (alphatestbuf[i] > 127) - zbufferLine[i] = depthvalues[i]; - } - } - } - else - { - if (OptT::Flags & SWTRI_WriteStencil) - { - int i = xstart; - int xendsse = xstart + ((x - xstart) / 16); - while (i < xendsse) - { - _mm_storeu_si128((__m128i*)&stencilLine[i], _mm_set1_epi8(stencilWriteValue)); - i += 16; - } - - while (i < x) - stencilLine[i++] = stencilWriteValue; - } - - if (!(OptT::Flags & SWTRI_DepthTest) && (OptT::Flags & SWTRI_WriteDepth)) - { - for (int i = xstart; i < x; i++) - { - zbufferLine[i] = depthvalues[i]; - } - } - } - } - - if ((OptT::Flags & SWTRI_DepthTest) && (OptT::Flags & SWTRI_StencilTest)) - { - int xendsse = x + ((xend - x) / 4); - __m128 mposXW; - while (x < xendsse && - (_mm_movemask_ps(_mm_cmpge_ps(_mm_loadu_ps(zbufferLine + x), mposXW = _mm_loadu_ps(depthvalues + x))) == 0 || - stencilLine[x] != stencilTestValue || - stencilLine[x + 1] != stencilTestValue || - stencilLine[x + 2] != stencilTestValue || - stencilLine[x + 3] != stencilTestValue)) - { - x += 4; - } - - while ((zbufferLine[x] < depthvalues[x] || stencilLine[x] != stencilTestValue) && x < xend) - { - x++; - } - } - else if (OptT::Flags & SWTRI_DepthTest) - { - int xendsse = x + ((xend - x) / 4); - __m128 mposXW; - while (x < xendsse && _mm_movemask_ps(_mm_cmpge_ps(_mm_loadu_ps(zbufferLine + x), mposXW = _mm_loadu_ps(depthvalues + x))) == 0) - { - x += 4; - } - - while (zbufferLine[x] < depthvalues[x] && x < xend) - { - x++; - } - } - else if (OptT::Flags & SWTRI_StencilTest) - { - int xendsse = x + ((xend - x) / 16); - while (x < xendsse && _mm_movemask_epi8(_mm_cmpeq_epi8(_mm_loadu_si128((const __m128i*)&stencilLine[x]), _mm_set1_epi8(stencilTestValue))) == 0) - { - x += 16; - } - - while (stencilLine[x] != stencilTestValue && x < xend) - { - x++; - } - } - } -#else - while (x < xend) - { - int xstart = x; - - if ((OptT::Flags & SWTRI_DepthTest) && (OptT::Flags & SWTRI_StencilTest)) - { - while (zbufferLine[x] >= depthvalues[x] && stencilLine[x] == stencilTestValue && x < xend) - { - if (!alphatest && (OptT::Flags & SWTRI_WriteDepth)) - zbufferLine[x] = depthvalues[x]; - x++; - } - } - else if (OptT::Flags & SWTRI_DepthTest) - { - while (zbufferLine[x] >= depthvalues[x] && x < xend) - { - if (!alphatest && (OptT::Flags & SWTRI_WriteDepth)) - zbufferLine[x] = depthvalues[x]; - x++; - } - } - else if (OptT::Flags & SWTRI_StencilTest) - { - while (stencilLine[x] == stencilTestValue && x < xend) - x++; - } - else - { - x = xend; - } - - if (x > xstart) - { - if (OptT::Flags & SWTRI_WriteColor) - drawfunc(y, xstart, x, args, thread); - - if (alphatest) - { - if (OptT::Flags & SWTRI_WriteStencil) - { - for (int i = xstart; i < x; i++) - { - if (alphatestbuf[i] > 127) - stencilLine[i++] = stencilWriteValue; - } - } - - if (OptT::Flags & SWTRI_WriteDepth) - { - for (int i = xstart; i < x; i++) - { - if (alphatestbuf[i] > 127) - zbufferLine[i] = depthvalues[i]; - } - } - } - else - { - if (OptT::Flags & SWTRI_WriteStencil) - { - for (int i = xstart; i < x; i++) - stencilLine[i] = stencilWriteValue; - } - - if (!(OptT::Flags & SWTRI_DepthTest) && (OptT::Flags & SWTRI_WriteDepth)) - { - for (int i = xstart; i < x; i++) - { - zbufferLine[i] = depthvalues[i]; - } - } - } - } - - if ((OptT::Flags & SWTRI_DepthTest) && (OptT::Flags & SWTRI_StencilTest)) - { - while ((zbufferLine[x] < depthvalues[x] || stencilLine[x] != stencilTestValue) && x < xend) - { - x++; - } - } - else if (OptT::Flags & SWTRI_DepthTest) - { - while (zbufferLine[x] < depthvalues[x] && x < xend) - { - x++; - } - } - else if (OptT::Flags & SWTRI_StencilTest) - { - while (stencilLine[x] != stencilTestValue && x < xend) - { - x++; - } - } - } -#endif - } -} - -template -void StepSpan(int y, int x0, int x1, const TriDrawTriangleArgs *args, PolyTriangleThreadData *thread) -{ - using namespace TriScreenDrawerModes; - - float v1X, v1Y, v1W, v1U, v1V, v1WorldX, v1WorldY, v1WorldZ; - float startX, startY; - float stepW, stepU, stepV, stepWorldX, stepWorldY, stepWorldZ; - float posW, posU, posV, posWorldX, posWorldY, posWorldZ; - int texWidth, texHeight; - uint32_t light; - fixed_t shade, lightpos, lightstep; - - float *worldposX = thread->worldposX; - float *worldposY = thread->worldposY; - float *worldposZ = thread->worldposZ; - uint32_t *texel = thread->texel; - int32_t *texelV = thread->texelV; - uint16_t *lightarray = thread->lightarray; - uint32_t *dynlights = thread->dynlights; - - v1X = args->v1->x; - v1Y = args->v1->y; - v1W = args->v1->w; - v1U = args->v1->u * v1W; - v1V = args->v1->v * v1W; - startX = x0 + (0.5f - v1X); - startY = y + (0.5f - v1Y); - stepW = args->gradientX.W; - stepU = args->gradientX.U; - stepV = args->gradientX.V; - posW = v1W + stepW * startX + args->gradientY.W * startY; - posU = v1U + stepU * startX + args->gradientY.U * startY; - posV = v1V + stepV * startX + args->gradientY.V * startY; - - if (!(ModeT::SWFlags & SWSTYLEF_Fill) && !(ModeT::SWFlags & SWSTYLEF_FogBoundary)) - { - texWidth = thread->drawargs.TextureWidth(); - texHeight = thread->drawargs.TextureHeight(); - } - - if (OptT::Flags & SWOPT_DynLights) - { - v1WorldX = args->v1->worldX * v1W; - v1WorldY = args->v1->worldY * v1W; - v1WorldZ = args->v1->worldZ * v1W; - stepWorldX = args->gradientX.WorldX; - stepWorldY = args->gradientX.WorldY; - stepWorldZ = args->gradientX.WorldZ; - posWorldX = v1WorldX + stepWorldX * startX + args->gradientY.WorldX * startY; - posWorldY = v1WorldY + stepWorldY * startX + args->gradientY.WorldY * startY; - posWorldZ = v1WorldZ + stepWorldZ * startX + args->gradientY.WorldZ * startY; - } - - if (!(OptT::Flags & SWOPT_FixedLight)) - { - float globVis = thread->drawargs.GlobVis() * (1.0f / 32.0f); - - light = thread->drawargs.Light(); - shade = (fixed_t)((2.0f - (light + 12.0f) / 128.0f) * (float)FRACUNIT); - lightpos = (fixed_t)(globVis * posW * (float)FRACUNIT); - lightstep = (fixed_t)(globVis * stepW * (float)FRACUNIT); - - fixed_t maxvis = 24 * FRACUNIT / 32; - fixed_t maxlight = 31 * FRACUNIT / 32; - - fixed_t lightend = lightpos + lightstep * (x1 - x0); - if (lightpos < maxvis && shade >= lightpos && shade - lightpos <= maxlight && - lightend < maxvis && shade >= lightend && shade - lightend <= maxlight) - { - if (BitsPerPixel == 32) - { - lightpos += FRACUNIT - shade; - for (int x = x0; x < x1; x++) - { - lightarray[x] = lightpos >> 8; - lightpos += lightstep; - } - } - else - { - lightpos = shade - lightpos; - for (int x = x0; x < x1; x++) - { - lightarray[x] = (lightpos >> 3) & 0xffffff00; - lightpos -= lightstep; - } - } - } - else - { - if (BitsPerPixel == 32) - { - for (int x = x0; x < x1; x++) - { - lightarray[x] = (FRACUNIT - clamp(shade - MIN(maxvis, lightpos), 0, maxlight)) >> 8; - lightpos += lightstep; - } - } - else - { - for (int x = x0; x < x1; x++) - { - lightarray[x] = (clamp(shade - MIN(maxvis, lightpos), 0, maxlight) >> 3) & 0xffffff00; - lightpos += lightstep; - } - } - } - } - -#ifndef NO_SSE - __m128 mposW, mposU, mposV, mstepW, mstepU, mstepV; - __m128 mposWorldX, mposWorldY, mposWorldZ, mstepWorldX, mstepWorldY, mstepWorldZ; - __m128i mtexMul1, mtexMul2; - - #define SETUP_STEP_SSE(mpos,mstep,pos,step) \ - mstep = _mm_load_ss(&step); \ - mpos = _mm_load_ss(&pos); \ - mpos = _mm_shuffle_ps(mpos, mpos, _MM_SHUFFLE(2, 1, 0, 0)); \ - mpos = _mm_add_ss(mpos, mstep); \ - mpos = _mm_shuffle_ps(mpos, mpos, _MM_SHUFFLE(2, 1, 0, 0)); \ - mpos = _mm_add_ss(mpos, mstep); \ - mpos = _mm_shuffle_ps(mpos, mpos, _MM_SHUFFLE(2, 1, 0, 0)); \ - mpos = _mm_add_ss(mpos, mstep); \ - mpos = _mm_shuffle_ps(mpos, mpos, _MM_SHUFFLE(0, 1, 2, 3)); \ - mstep = _mm_mul_ss(mstep, _mm_set1_ps(4.0f)); \ - mstep = _mm_shuffle_ps(mstep, mstep, _MM_SHUFFLE(0, 0, 0, 0)); - - SETUP_STEP_SSE(mposW, mstepW, posW, stepW); - - if (OptT::Flags & SWOPT_DynLights) - { - SETUP_STEP_SSE(mposWorldX, mstepWorldX, posWorldX, stepWorldX); - SETUP_STEP_SSE(mposWorldY, mstepWorldY, posWorldY, stepWorldY); - SETUP_STEP_SSE(mposWorldZ, mstepWorldZ, posWorldZ, stepWorldZ); - } - - if (!(ModeT::SWFlags & SWSTYLEF_Fill) && !(ModeT::SWFlags & SWSTYLEF_FogBoundary)) - { - SETUP_STEP_SSE(mposU, mstepU, posU, stepU); - SETUP_STEP_SSE(mposV, mstepV, posV, stepV); - - mtexMul1 = _mm_setr_epi16(texWidth, texWidth, texWidth, texWidth, texHeight, texHeight, texHeight, texHeight); - mtexMul2 = _mm_setr_epi16(texHeight, texHeight, texHeight, texHeight, 1, 1, 1, 1); - } - - #undef SETUP_STEP_SSE - - for (int x = x0; x < x1; x += 4) - { - __m128 rcp_posW = _mm_div_ps(_mm_set1_ps(1.0f), mposW); // precision of _mm_rcp_ps(mposW) is terrible! - - if (OptT::Flags & SWOPT_DynLights) - { - _mm_storeu_ps(&worldposX[x], _mm_mul_ps(mposWorldX, rcp_posW)); - _mm_storeu_ps(&worldposY[x], _mm_mul_ps(mposWorldY, rcp_posW)); - _mm_storeu_ps(&worldposZ[x], _mm_mul_ps(mposWorldZ, rcp_posW)); - mposWorldX = _mm_add_ps(mposWorldX, mstepWorldX); - mposWorldY = _mm_add_ps(mposWorldY, mstepWorldY); - mposWorldZ = _mm_add_ps(mposWorldZ, mstepWorldZ); - } - if (!(ModeT::SWFlags & SWSTYLEF_Fill) && !(ModeT::SWFlags & SWSTYLEF_FogBoundary)) - { - __m128 rcpW = _mm_mul_ps(_mm_set1_ps(0x01000000), rcp_posW); - __m128i u = _mm_cvtps_epi32(_mm_mul_ps(mposU, rcpW)); - __m128i v = _mm_cvtps_epi32(_mm_mul_ps(mposV, rcpW)); - _mm_storeu_si128((__m128i*)&texelV[x], v); - - __m128i texelX = _mm_srli_epi32(_mm_slli_epi32(u, 8), 17); - __m128i texelY = _mm_srli_epi32(_mm_slli_epi32(v, 8), 17); - __m128i texelXY = _mm_mulhi_epu16(_mm_slli_epi16(_mm_packs_epi32(texelX, texelY), 1), mtexMul1); - __m128i texlo = _mm_mullo_epi16(texelXY, mtexMul2); - __m128i texhi = _mm_mulhi_epi16(texelXY, mtexMul2); - texelX = _mm_unpacklo_epi16(texlo, texhi); - texelY = _mm_unpackhi_epi16(texlo, texhi); - _mm_storeu_si128((__m128i*)&texel[x], _mm_add_epi32(texelX, texelY)); - - mposU = _mm_add_ps(mposU, mstepU); - mposV = _mm_add_ps(mposV, mstepV); - } - - mposW = _mm_add_ps(mposW, mstepW); - } -#else - for (int x = x0; x < x1; x++) - { - if (OptT::Flags & SWOPT_DynLights) - { - float rcp_posW = 1.0f / posW; - worldposX[x] = posWorldX * rcp_posW; - worldposY[x] = posWorldY * rcp_posW; - worldposZ[x] = posWorldZ * rcp_posW; - posWorldX += stepWorldX; - posWorldY += stepWorldY; - posWorldZ += stepWorldZ; - } - if (!(ModeT::SWFlags & SWSTYLEF_Fill) && !(ModeT::SWFlags & SWSTYLEF_FogBoundary)) - { - float rcpW = 0x01000000 / posW; - int32_t u = (int32_t)(posU * rcpW); - int32_t v = (int32_t)(posV * rcpW); - uint32_t texelX = ((((uint32_t)u << 8) >> 16) * texWidth) >> 16; - uint32_t texelY = ((((uint32_t)v << 8) >> 16) * texHeight) >> 16; - texel[x] = texelX * texHeight + texelY; - texelV[x] = v; - posU += stepU; - posV += stepV; - } - - posW += stepW; - } -#endif - - if (OptT::Flags & SWOPT_DynLights) - { - PolyLight *lights; - int num_lights; - float worldnormalX, worldnormalY, worldnormalZ; - uint32_t dynlightcolor; - - lights = thread->drawargs.Lights(); - num_lights = thread->drawargs.NumLights(); - worldnormalX = thread->drawargs.Normal().X; - worldnormalY = thread->drawargs.Normal().Y; - worldnormalZ = thread->drawargs.Normal().Z; - dynlightcolor = thread->drawargs.DynLightColor(); - - // The normal vector cannot be uniform when drawing models. Calculate and use the face normal: - if (worldnormalX == 0.0f && worldnormalY == 0.0f && worldnormalZ == 0.0f) - { - float dx1 = args->v2->worldX - args->v1->worldX; - float dy1 = args->v2->worldY - args->v1->worldY; - float dz1 = args->v2->worldZ - args->v1->worldZ; - float dx2 = args->v3->worldX - args->v1->worldX; - float dy2 = args->v3->worldY - args->v1->worldY; - float dz2 = args->v3->worldZ - args->v1->worldZ; - worldnormalX = dy1 * dz2 - dz1 * dy2; - worldnormalY = dz1 * dx2 - dx1 * dz2; - worldnormalZ = dx1 * dy2 - dy1 * dx2; - float lensqr = worldnormalX * worldnormalX + worldnormalY * worldnormalY + worldnormalZ * worldnormalZ; -#ifndef NO_SSE - float rcplen = _mm_cvtss_f32(_mm_rsqrt_ss(_mm_set_ss(lensqr))); -#else - float rcplen = 1.0f / sqrt(lensqr); -#endif - worldnormalX *= rcplen; - worldnormalY *= rcplen; - worldnormalZ *= rcplen; - } - -#ifndef NO_SSE - __m128 mworldnormalX = _mm_set1_ps(worldnormalX); - __m128 mworldnormalY = _mm_set1_ps(worldnormalY); - __m128 mworldnormalZ = _mm_set1_ps(worldnormalZ); - for (int x = x0; x < x1; x += 4) - { - __m128i litlo = _mm_shuffle_epi32(_mm_unpacklo_epi8(_mm_cvtsi32_si128(dynlightcolor), _mm_setzero_si128()), _MM_SHUFFLE(1, 0, 1, 0)); - __m128i lithi = litlo; - - for (int i = 0; i < num_lights; i++) - { - __m128 lightposX = _mm_set1_ps(lights[i].x); - __m128 lightposY = _mm_set1_ps(lights[i].y); - __m128 lightposZ = _mm_set1_ps(lights[i].z); - __m128 light_radius = _mm_set1_ps(lights[i].radius); - __m128i light_color = _mm_shuffle_epi32(_mm_unpacklo_epi8(_mm_cvtsi32_si128(lights[i].color), _mm_setzero_si128()), _MM_SHUFFLE(1, 0, 1, 0)); - - __m128 is_attenuated = _mm_cmplt_ps(light_radius, _mm_setzero_ps()); - light_radius = _mm_andnot_ps(_mm_set1_ps(-0.0f), light_radius); // clear sign bit - - // L = light-pos - // dist = sqrt(dot(L, L)) - // distance_attenuation = 1 - MIN(dist * (1/radius), 1) - __m128 Lx = _mm_sub_ps(lightposX, _mm_loadu_ps(&worldposX[x])); - __m128 Ly = _mm_sub_ps(lightposY, _mm_loadu_ps(&worldposY[x])); - __m128 Lz = _mm_sub_ps(lightposZ, _mm_loadu_ps(&worldposZ[x])); - __m128 dist2 = _mm_add_ps(_mm_mul_ps(Lx, Lx), _mm_add_ps(_mm_mul_ps(Ly, Ly), _mm_mul_ps(Lz, Lz))); - __m128 rcp_dist = _mm_rsqrt_ps(dist2); - __m128 dist = _mm_mul_ps(dist2, rcp_dist); - __m128 distance_attenuation = _mm_sub_ps(_mm_set1_ps(256.0f), _mm_min_ps(_mm_mul_ps(dist, light_radius), _mm_set1_ps(256.0f))); - - // The simple light type - __m128 simple_attenuation = distance_attenuation; - - // The point light type - // diffuse = max(dot(N,normalize(L)),0) * attenuation - Lx = _mm_mul_ps(Lx, rcp_dist); - Ly = _mm_mul_ps(Ly, rcp_dist); - Lz = _mm_mul_ps(Lz, rcp_dist); - __m128 dotNL = _mm_add_ps(_mm_add_ps(_mm_mul_ps(mworldnormalX, Lx), _mm_mul_ps(mworldnormalY, Ly)), _mm_mul_ps(mworldnormalZ, Lz)); - __m128 point_attenuation = _mm_mul_ps(_mm_max_ps(dotNL, _mm_setzero_ps()), distance_attenuation); - - __m128i attenuation = _mm_cvtps_epi32(_mm_or_ps(_mm_and_ps(is_attenuated, point_attenuation), _mm_andnot_ps(is_attenuated, simple_attenuation))); - - attenuation = _mm_shufflehi_epi16(_mm_shufflelo_epi16(attenuation, _MM_SHUFFLE(2, 2, 0, 0)), _MM_SHUFFLE(2, 2, 0, 0)); - __m128i attenlo = _mm_shuffle_epi32(attenuation, _MM_SHUFFLE(1, 1, 0, 0)); - __m128i attenhi = _mm_shuffle_epi32(attenuation, _MM_SHUFFLE(3, 3, 2, 2)); - - litlo = _mm_add_epi16(litlo, _mm_srli_epi16(_mm_mullo_epi16(light_color, attenlo), 8)); - lithi = _mm_add_epi16(lithi, _mm_srli_epi16(_mm_mullo_epi16(light_color, attenhi), 8)); - } - - _mm_storeu_si128((__m128i*)&dynlights[x], _mm_packus_epi16(litlo, lithi)); - } -#else - for (int x = x0; x < x1; x++) - { - uint32_t lit_r = RPART(dynlightcolor); - uint32_t lit_g = GPART(dynlightcolor); - uint32_t lit_b = BPART(dynlightcolor); - - for (int i = 0; i < num_lights; i++) - { - float lightposX = lights[i].x; - float lightposY = lights[i].y; - float lightposZ = lights[i].z; - float light_radius = lights[i].radius; - uint32_t light_color = lights[i].color; - - bool is_attenuated = light_radius < 0.0f; - if (is_attenuated) - light_radius = -light_radius; - - // L = light-pos - // dist = sqrt(dot(L, L)) - // distance_attenuation = 1 - MIN(dist * (1/radius), 1) - float Lx = lightposX - worldposX[x]; - float Ly = lightposY - worldposY[x]; - float Lz = lightposZ - worldposZ[x]; - float dist2 = Lx * Lx + Ly * Ly + Lz * Lz; -#ifdef NO_SSE - //float rcp_dist = 1.0f / sqrt(dist2); - float rcp_dist = 1.0f / (dist2 * 0.01f); -#else - float rcp_dist = _mm_cvtss_f32(_mm_rsqrt_ss(_mm_set_ss(dist2))); -#endif - float dist = dist2 * rcp_dist; - float distance_attenuation = 256.0f - MIN(dist * light_radius, 256.0f); - - // The simple light type - float simple_attenuation = distance_attenuation; - - // The point light type - // diffuse = max(dot(N,normalize(L)),0) * attenuation - Lx *= rcp_dist; - Ly *= rcp_dist; - Lz *= rcp_dist; - float dotNL = worldnormalX * Lx + worldnormalY * Ly + worldnormalZ * Lz; - float point_attenuation = MAX(dotNL, 0.0f) * distance_attenuation; - - uint32_t attenuation = (uint32_t)(is_attenuated ? (int32_t)point_attenuation : (int32_t)simple_attenuation); - - lit_r += (RPART(light_color) * attenuation) >> 8; - lit_g += (GPART(light_color) * attenuation) >> 8; - lit_b += (BPART(light_color) * attenuation) >> 8; - } - - lit_r = MIN(lit_r, 255); - lit_g = MIN(lit_g, 255); - lit_b = MIN(lit_b, 255); - dynlights[x] = MAKEARGB(255, lit_r, lit_g, lit_b); - } -#endif - } -} - -template -void DrawSpanOpt32(int y, int x0, int x1, const TriDrawTriangleArgs *args, PolyTriangleThreadData *thread) -{ - using namespace TriScreenDrawerModes; - - StepSpan(y, x0, x1, args, thread); - - uint32_t fixedlight; - uint32_t shade_fade_r, shade_fade_g, shade_fade_b, shade_light_r, shade_light_g, shade_light_b, desaturate, inv_desaturate; - fixed_t fuzzscale; - int _fuzzpos; - const uint32_t *texPixels, *translation; - uint32_t fillcolor; - int actoralpha; - uint8_t *alphatestbuf; - - uint32_t *texel = thread->texel; - int32_t *texelV = thread->texelV; - uint16_t *lightarray = thread->lightarray; - uint32_t *dynlights = thread->dynlights; - - if (!(ModeT::SWFlags & SWSTYLEF_Fill) && !(ModeT::SWFlags & SWSTYLEF_FogBoundary)) - { - texPixels = (const uint32_t*)thread->drawargs.TexturePixels(); - } - - if (ModeT::SWFlags & SWSTYLEF_Translated) - { - translation = (const uint32_t*)thread->drawargs.Translation(); - } - - if ((ModeT::SWFlags & SWSTYLEF_Fill) || (ModeT::SWFlags & SWSTYLEF_Skycap) || (ModeT::Flags & STYLEF_ColorIsFixed)) - { - fillcolor = thread->drawargs.Color(); - } - - if (!(ModeT::Flags & STYLEF_Alpha1)) - { - actoralpha = thread->drawargs.Alpha(); - } - - if (OptT::Flags & SWOPT_FixedLight) - { - fixedlight = thread->drawargs.Light(); - fixedlight += fixedlight >> 7; // 255 -> 256 - } - - if (OptT::Flags & SWOPT_ColoredFog) - { - shade_fade_r = thread->drawargs.ShadeFadeRed(); - shade_fade_g = thread->drawargs.ShadeFadeGreen(); - shade_fade_b = thread->drawargs.ShadeFadeBlue(); - shade_light_r = thread->drawargs.ShadeLightRed(); - shade_light_g = thread->drawargs.ShadeLightGreen(); - shade_light_b = thread->drawargs.ShadeLightBlue(); - desaturate = thread->drawargs.ShadeDesaturate(); - inv_desaturate = 256 - desaturate; - } - - if (ModeT::BlendOp == STYLEOP_Fuzz) - { - fuzzscale = (200 << FRACBITS) / thread->dest_height; - _fuzzpos = swrenderer::fuzzpos; - } - - if (ModeT::SWFlags & SWSTYLEF_AlphaTest) - { - alphatestbuf = thread->alphatestbuffer; - } - - uint32_t *dest = (uint32_t*)thread->dest; - uint32_t *destLine = dest + thread->dest_pitch * y; - - int sseend = x0; -#ifndef NO_SSE - if (ModeT::BlendOp == STYLEOP_Add && - ModeT::BlendSrc == STYLEALPHA_One && - ModeT::BlendDest == STYLEALPHA_Zero && - (ModeT::Flags & STYLEF_Alpha1) && - !(OptT::Flags & SWOPT_ColoredFog) && - !(ModeT::Flags & STYLEF_RedIsAlpha) && - !(ModeT::SWFlags & SWSTYLEF_Skycap) && - !(ModeT::SWFlags & SWSTYLEF_FogBoundary) && - !(ModeT::SWFlags & SWSTYLEF_Fill) && - !(ModeT::SWFlags & SWSTYLEF_AlphaTest)) - { - sseend += (x1 - x0) / 2 * 2; - - __m128i mlightshade; - if (OptT::Flags & SWOPT_FixedLight) - mlightshade = _mm_set1_epi16(fixedlight); - - __m128i alphamask = _mm_set1_epi32(0xff000000); - - for (int x = x0; x < sseend; x += 2) - { - __m128i mfg = _mm_unpacklo_epi8(_mm_setr_epi32(texPixels[texel[x]], texPixels[texel[x + 1]], 0, 0), _mm_setzero_si128()); - - if (!(OptT::Flags & SWOPT_FixedLight)) - mlightshade = _mm_shuffle_epi32(_mm_shufflelo_epi16(_mm_cvtsi32_si128(*(int*)&lightarray[x]), _MM_SHUFFLE(1, 1, 0, 0)), _MM_SHUFFLE(1, 1, 0, 0)); - - if (OptT::Flags & SWOPT_DynLights) - { - __m128i mdynlight = _mm_unpacklo_epi8(_mm_loadl_epi64((const __m128i*)&dynlights[x]), _mm_setzero_si128()); - mfg = _mm_srli_epi16(_mm_mullo_epi16(_mm_min_epi16(_mm_add_epi16(mdynlight, mlightshade), _mm_set1_epi16(256)), mfg), 8); - } - else - { - mfg = _mm_srli_epi16(_mm_mullo_epi16(mlightshade, mfg), 8); - } - - _mm_storel_epi64((__m128i*)&destLine[x], _mm_or_si128(_mm_packus_epi16(mfg, _mm_setzero_si128()), alphamask)); - } - } -#endif - - for (int x = sseend; x < x1; x++) - { - if (ModeT::BlendOp == STYLEOP_Fuzz) - { - using namespace swrenderer; - - unsigned int sampleshadeout = APART(texPixels[texel[x]]); - sampleshadeout += sampleshadeout >> 7; // 255 -> 256 - - int scaled_x = (x * fuzzscale) >> FRACBITS; - int fuzz_x = fuzz_random_x_offset[scaled_x % FUZZ_RANDOM_X_SIZE] + _fuzzpos; - - fixed_t fuzzcount = FUZZTABLE << FRACBITS; - fixed_t fuzz = ((fuzz_x << FRACBITS) + y * fuzzscale) % fuzzcount; - unsigned int alpha = fuzzoffset[fuzz >> FRACBITS]; - - sampleshadeout = (sampleshadeout * alpha) >> 5; - - uint32_t a = 256 - sampleshadeout; - - uint32_t dest = destLine[x]; - uint32_t out_r = (RPART(dest) * a) >> 8; - uint32_t out_g = (GPART(dest) * a) >> 8; - uint32_t out_b = (BPART(dest) * a) >> 8; - destLine[x] = MAKEARGB(255, out_r, out_g, out_b); - } - else if (ModeT::SWFlags & SWSTYLEF_Skycap) - { - uint32_t fg = texPixels[texel[x]]; - - int v = texelV[x]; - int start_fade = 2; // How fast it should fade out - int alpha_top = clamp(v >> (16 - start_fade), 0, 256); - int alpha_bottom = clamp(((2 << 24) - v) >> (16 - start_fade), 0, 256); - int a = MIN(alpha_top, alpha_bottom); - int inv_a = 256 - a; - - if (a == 256) - { - destLine[x] = fg; - } - else - { - uint32_t r = RPART(fg); - uint32_t g = GPART(fg); - uint32_t b = BPART(fg); - uint32_t fg_a = APART(fg); - uint32_t bg_red = RPART(fillcolor); - uint32_t bg_green = GPART(fillcolor); - uint32_t bg_blue = BPART(fillcolor); - r = (r * a + bg_red * inv_a + 127) >> 8; - g = (g * a + bg_green * inv_a + 127) >> 8; - b = (b * a + bg_blue * inv_a + 127) >> 8; - - destLine[x] = MAKEARGB(255, r, g, b); - } - } - else if (ModeT::SWFlags & SWSTYLEF_FogBoundary) - { - uint32_t fg = destLine[x]; - - int lightshade; - if (OptT::Flags & SWOPT_FixedLight) - { - lightshade = fixedlight; - } - else - { - lightshade = lightarray[x]; - } - - uint32_t shadedfg_r, shadedfg_g, shadedfg_b; - if (OptT::Flags & SWOPT_ColoredFog) - { - uint32_t fg_r = RPART(fg); - uint32_t fg_g = GPART(fg); - uint32_t fg_b = BPART(fg); - uint32_t intensity = ((fg_r * 77 + fg_g * 143 + fg_b * 37) >> 8) * desaturate; - int inv_light = 256 - lightshade; - shadedfg_r = (((shade_fade_r * inv_light + ((fg_r * inv_desaturate + intensity) >> 8) * lightshade) >> 8) * shade_light_r) >> 8; - shadedfg_g = (((shade_fade_g * inv_light + ((fg_g * inv_desaturate + intensity) >> 8) * lightshade) >> 8) * shade_light_g) >> 8; - shadedfg_b = (((shade_fade_b * inv_light + ((fg_b * inv_desaturate + intensity) >> 8) * lightshade) >> 8) * shade_light_b) >> 8; - } - else - { - shadedfg_r = (RPART(fg) * lightshade) >> 8; - shadedfg_g = (GPART(fg) * lightshade) >> 8; - shadedfg_b = (BPART(fg) * lightshade) >> 8; - } - - destLine[x] = MAKEARGB(255, shadedfg_r, shadedfg_g, shadedfg_b); - } - else - { - uint32_t fg = 0; - - if (ModeT::SWFlags & SWSTYLEF_Fill) - { - fg = fillcolor; - } - else if (ModeT::SWFlags & SWSTYLEF_Translated) - { - fg = translation[((const uint8_t*)texPixels)[texel[x]]]; - } - else if (ModeT::Flags & STYLEF_RedIsAlpha) - { - fg = ((const uint8_t*)texPixels)[texel[x]]; - } - else - { - fg = texPixels[texel[x]]; - } - - if ((ModeT::Flags & STYLEF_ColorIsFixed) && !(ModeT::SWFlags & SWSTYLEF_Fill)) - { - if (ModeT::Flags & STYLEF_RedIsAlpha) - fg = (fg << 24) | (fillcolor & 0x00ffffff); - else - fg = (fg & 0xff000000) | (fillcolor & 0x00ffffff); - } - - uint32_t fgalpha = fg >> 24; - - if (!(ModeT::Flags & STYLEF_Alpha1)) - { - fgalpha = (fgalpha * actoralpha) >> 8; - } - - if (ModeT::SWFlags & SWSTYLEF_AlphaTest) - { - alphatestbuf[x] = fgalpha; - } - - uint32_t lightshade; - if (OptT::Flags & SWOPT_FixedLight) - { - lightshade = fixedlight; - } - else - { - lightshade = lightarray[x]; - } - - uint32_t shadedfg_r, shadedfg_g, shadedfg_b; - if (OptT::Flags & SWOPT_ColoredFog) - { - uint32_t fg_r = RPART(fg); - uint32_t fg_g = GPART(fg); - uint32_t fg_b = BPART(fg); - uint32_t intensity = ((fg_r * 77 + fg_g * 143 + fg_b * 37) >> 8) * desaturate; - int inv_light = 256 - lightshade; - shadedfg_r = (((shade_fade_r * inv_light + ((fg_r * inv_desaturate + intensity) >> 8) * lightshade) >> 8) * shade_light_r) >> 8; - shadedfg_g = (((shade_fade_g * inv_light + ((fg_g * inv_desaturate + intensity) >> 8) * lightshade) >> 8) * shade_light_g) >> 8; - shadedfg_b = (((shade_fade_b * inv_light + ((fg_b * inv_desaturate + intensity) >> 8) * lightshade) >> 8) * shade_light_b) >> 8; - - if (OptT::Flags & SWOPT_DynLights) - { - shadedfg_r = MIN(shadedfg_r + ((fg_r * RPART(dynlights[x])) >> 8), (uint32_t)255); - shadedfg_g = MIN(shadedfg_g + ((fg_g * GPART(dynlights[x])) >> 8), (uint32_t)255); - shadedfg_b = MIN(shadedfg_b + ((fg_b * BPART(dynlights[x])) >> 8), (uint32_t)255); - } - } - else - { - if (OptT::Flags & SWOPT_DynLights) - { - shadedfg_r = (RPART(fg) * MIN(lightshade + RPART(dynlights[x]), (uint32_t)256)) >> 8; - shadedfg_g = (GPART(fg) * MIN(lightshade + GPART(dynlights[x]), (uint32_t)256)) >> 8; - shadedfg_b = (BPART(fg) * MIN(lightshade + BPART(dynlights[x]), (uint32_t)256)) >> 8; - } - else - { - shadedfg_r = (RPART(fg) * lightshade) >> 8; - shadedfg_g = (GPART(fg) * lightshade) >> 8; - shadedfg_b = (BPART(fg) * lightshade) >> 8; - } - } - - if (ModeT::BlendSrc == STYLEALPHA_One && ModeT::BlendDest == STYLEALPHA_Zero) - { - destLine[x] = MAKEARGB(255, shadedfg_r, shadedfg_g, shadedfg_b); - } - else if (ModeT::BlendSrc == STYLEALPHA_One && ModeT::BlendDest == STYLEALPHA_One) - { - uint32_t dest = destLine[x]; - - if (ModeT::BlendOp == STYLEOP_Add) - { - uint32_t out_r = MIN(RPART(dest) + shadedfg_r, 255); - uint32_t out_g = MIN(GPART(dest) + shadedfg_g, 255); - uint32_t out_b = MIN(BPART(dest) + shadedfg_b, 255); - destLine[x] = MAKEARGB(255, out_r, out_g, out_b); - } - else if (ModeT::BlendOp == STYLEOP_RevSub) - { - uint32_t out_r = MAX(RPART(dest) - shadedfg_r, 0); - uint32_t out_g = MAX(GPART(dest) - shadedfg_g, 0); - uint32_t out_b = MAX(BPART(dest) - shadedfg_b, 0); - destLine[x] = MAKEARGB(255, out_r, out_g, out_b); - } - else //if (ModeT::BlendOp == STYLEOP_Sub) - { - uint32_t out_r = MAX(shadedfg_r - RPART(dest), 0); - uint32_t out_g = MAX(shadedfg_g - GPART(dest), 0); - uint32_t out_b = MAX(shadedfg_b - BPART(dest), 0); - destLine[x] = MAKEARGB(255, out_r, out_g, out_b); - } - } - else if (ModeT::SWFlags & SWSTYLEF_SrcColorOneMinusSrcColor) - { - uint32_t dest = destLine[x]; - - uint32_t sfactor_r = shadedfg_r; sfactor_r += sfactor_r >> 7; // 255 -> 256 - uint32_t sfactor_g = shadedfg_g; sfactor_g += sfactor_g >> 7; // 255 -> 256 - uint32_t sfactor_b = shadedfg_b; sfactor_b += sfactor_b >> 7; // 255 -> 256 - uint32_t sfactor_a = fgalpha; sfactor_a += sfactor_a >> 7; // 255 -> 256 - uint32_t dfactor_r = 256 - sfactor_r; - uint32_t dfactor_g = 256 - sfactor_g; - uint32_t dfactor_b = 256 - sfactor_b; - uint32_t out_r = (RPART(dest) * dfactor_r + shadedfg_r * sfactor_r + 128) >> 8; - uint32_t out_g = (GPART(dest) * dfactor_g + shadedfg_g * sfactor_g + 128) >> 8; - uint32_t out_b = (BPART(dest) * dfactor_b + shadedfg_b * sfactor_b + 128) >> 8; - - destLine[x] = MAKEARGB(255, out_r, out_g, out_b); - } - else if (ModeT::BlendSrc == STYLEALPHA_Src && ModeT::BlendDest == STYLEALPHA_InvSrc && fgalpha == 255) - { - destLine[x] = MAKEARGB(255, shadedfg_r, shadedfg_g, shadedfg_b); - } - else if (ModeT::BlendSrc != STYLEALPHA_Src || ModeT::BlendDest != STYLEALPHA_InvSrc || fgalpha != 0) - { - uint32_t dest = destLine[x]; - - uint32_t sfactor = fgalpha; sfactor += sfactor >> 7; // 255 -> 256 - uint32_t src_r = shadedfg_r * sfactor; - uint32_t src_g = shadedfg_g * sfactor; - uint32_t src_b = shadedfg_b * sfactor; - uint32_t dest_r = RPART(dest); - uint32_t dest_g = GPART(dest); - uint32_t dest_b = BPART(dest); - if (ModeT::BlendDest == STYLEALPHA_One) - { - dest_r <<= 8; - dest_g <<= 8; - dest_b <<= 8; - } - else - { - uint32_t dfactor = 256 - sfactor; - dest_r *= dfactor; - dest_g *= dfactor; - dest_b *= dfactor; - } - - uint32_t out_r, out_g, out_b; - if (ModeT::BlendOp == STYLEOP_Add) - { - if (ModeT::BlendDest == STYLEALPHA_One) - { - out_r = MIN((dest_r + src_r + 128) >> 8, 255); - out_g = MIN((dest_g + src_g + 128) >> 8, 255); - out_b = MIN((dest_b + src_b + 128) >> 8, 255); - } - else - { - out_r = (dest_r + src_r + 128) >> 8; - out_g = (dest_g + src_g + 128) >> 8; - out_b = (dest_b + src_b + 128) >> 8; - } - } - else if (ModeT::BlendOp == STYLEOP_RevSub) - { - out_r = MAX(static_cast(dest_r - src_r + 128) >> 8, 0); - out_g = MAX(static_cast(dest_g - src_g + 128) >> 8, 0); - out_b = MAX(static_cast(dest_b - src_b + 128) >> 8, 0); - } - else //if (ModeT::BlendOp == STYLEOP_Sub) - { - out_r = MAX(static_cast(src_r - dest_r + 128) >> 8, 0); - out_g = MAX(static_cast(src_g - dest_g + 128) >> 8, 0); - out_b = MAX(static_cast(src_b - dest_b + 128) >> 8, 0); - } - - destLine[x] = MAKEARGB(255, out_r, out_g, out_b); - } - } - } -} - -template -void DrawSpan32(int y, int x0, int x1, const TriDrawTriangleArgs *args, PolyTriangleThreadData *thread) -{ - using namespace TriScreenDrawerModes; - - if (thread->drawargs.NumLights() == 0 && thread->drawargs.DynLightColor() == 0) - { - if (!thread->drawargs.FixedLight()) - { - if (thread->drawargs.SimpleShade()) - DrawSpanOpt32(y, x0, x1, args, thread); - else - DrawSpanOpt32(y, x0, x1, args, thread); - } - else - { - if (thread->drawargs.SimpleShade()) - DrawSpanOpt32(y, x0, x1, args, thread); - else - DrawSpanOpt32(y, x0, x1, args, thread); - } - } - else - { - if (!thread->drawargs.FixedLight()) - { - if (thread->drawargs.SimpleShade()) - DrawSpanOpt32(y, x0, x1, args, thread); - else - DrawSpanOpt32(y, x0, x1, args, thread); - } - else - { - if (thread->drawargs.SimpleShade()) - DrawSpanOpt32(y, x0, x1, args, thread); - else - DrawSpanOpt32(y, x0, x1, args, thread); - } - } -} - -template -void DrawSpanOpt8(int y, int x0, int x1, const TriDrawTriangleArgs *args, PolyTriangleThreadData *thread) -{ - using namespace TriScreenDrawerModes; - - StepSpan(y, x0, x1, args, thread); - - uint32_t fixedlight, capcolor; - fixed_t fuzzscale; - int _fuzzpos; - const uint8_t *colormaps, *texPixels, *translation; - uint32_t fillcolor; - int actoralpha; - - uint32_t *texel = thread->texel; - int32_t *texelV = thread->texelV; - uint16_t *lightarray = thread->lightarray; - uint32_t *dynlights = thread->dynlights; - - colormaps = thread->drawargs.BaseColormap(); - - if (!(ModeT::SWFlags & SWSTYLEF_Fill) && !(ModeT::SWFlags & SWSTYLEF_FogBoundary)) - { - texPixels = thread->drawargs.TexturePixels(); - } - - if (ModeT::SWFlags & SWSTYLEF_Translated) - { - translation = thread->drawargs.Translation(); - } - - if ((ModeT::SWFlags & SWSTYLEF_Fill) || (ModeT::SWFlags & SWSTYLEF_Skycap) || (ModeT::Flags & STYLEF_ColorIsFixed)) - { - fillcolor = thread->drawargs.Color(); - } - - if (!(ModeT::Flags & STYLEF_Alpha1)) - { - actoralpha = thread->drawargs.Alpha(); - } - - if (ModeT::SWFlags & SWSTYLEF_Skycap) - capcolor = GPalette.BaseColors[fillcolor].d; - - if (OptT::Flags & SWOPT_FixedLight) - { - fixedlight = thread->drawargs.Light(); - fixedlight += fixedlight >> 7; // 255 -> 256 - fixedlight = ((256 - fixedlight) * NUMCOLORMAPS) & 0xffffff00; - } - - if (ModeT::BlendOp == STYLEOP_Fuzz) - { - fuzzscale = (200 << FRACBITS) / thread->dest_height; - _fuzzpos = swrenderer::fuzzpos; - } - - uint8_t *dest = (uint8_t*)thread->dest; - uint8_t *destLine = dest + thread->dest_pitch * y; - - for (int x = x0; x < x1; x++) - { - if (ModeT::BlendOp == STYLEOP_Fuzz) - { - using namespace swrenderer; - - unsigned int sampleshadeout = (texPixels[texel[x]] != 0) ? 256 : 0; - - int scaled_x = (x * fuzzscale) >> FRACBITS; - int fuzz_x = fuzz_random_x_offset[scaled_x % FUZZ_RANDOM_X_SIZE] + _fuzzpos; - - fixed_t fuzzcount = FUZZTABLE << FRACBITS; - fixed_t fuzz = ((fuzz_x << FRACBITS) + y * fuzzscale) % fuzzcount; - unsigned int alpha = fuzzoffset[fuzz >> FRACBITS]; - - sampleshadeout = (sampleshadeout * alpha) >> 5; - - uint32_t a = 256 - sampleshadeout; - - uint32_t dest = GPalette.BaseColors[destLine[x]].d; - uint32_t r = (RPART(dest) * a) >> 8; - uint32_t g = (GPART(dest) * a) >> 8; - uint32_t b = (BPART(dest) * a) >> 8; - destLine[x] = RGB256k.All[((r >> 2) << 12) | ((g >> 2) << 6) | (b >> 2)]; - } - else if (ModeT::SWFlags & SWSTYLEF_Skycap) - { - int32_t v = texelV[x]; - int fg = texPixels[texel[x]]; - - int start_fade = 2; // How fast it should fade out - int alpha_top = clamp(v >> (16 - start_fade), 0, 256); - int alpha_bottom = clamp(((2 << 24) - v) >> (16 - start_fade), 0, 256); - int a = MIN(alpha_top, alpha_bottom); - int inv_a = 256 - a; - - if (a == 256) - { - destLine[x] = fg; - } - else - { - uint32_t texelrgb = GPalette.BaseColors[fg].d; - - uint32_t r = RPART(texelrgb); - uint32_t g = GPART(texelrgb); - uint32_t b = BPART(texelrgb); - uint32_t fg_a = APART(texelrgb); - uint32_t bg_red = RPART(capcolor); - uint32_t bg_green = GPART(capcolor); - uint32_t bg_blue = BPART(capcolor); - r = (r * a + bg_red * inv_a + 127) >> 8; - g = (g * a + bg_green * inv_a + 127) >> 8; - b = (b * a + bg_blue * inv_a + 127) >> 8; - - destLine[x] = RGB256k.All[((r >> 2) << 12) | ((g >> 2) << 6) | (b >> 2)]; - } - } - else if (ModeT::SWFlags & SWSTYLEF_FogBoundary) - { - int fg = destLine[x]; - - uint8_t shadedfg; - if (OptT::Flags & SWOPT_FixedLight) - { - shadedfg = colormaps[fixedlight + fg]; - } - else - { - shadedfg = colormaps[lightarray[x] + fg]; - } - - destLine[x] = shadedfg; - } - else - { - int fg; - if (ModeT::SWFlags & SWSTYLEF_Fill) - { - fg = fillcolor; - } - else - { - fg = texPixels[texel[x]]; - } - - int fgalpha = 255; - - if (ModeT::BlendDest == STYLEALPHA_InvSrc) - { - if (fg == 0) - fgalpha = 0; - } - - if ((ModeT::Flags & STYLEF_ColorIsFixed) && !(ModeT::SWFlags & SWSTYLEF_Fill)) - { - if (ModeT::Flags & STYLEF_RedIsAlpha) - fgalpha = fg; - fg = fillcolor; - } - - if (!(ModeT::Flags & STYLEF_Alpha1)) - { - fgalpha = (fgalpha * actoralpha) >> 8; - } - - if (ModeT::SWFlags & SWSTYLEF_Translated) - fg = translation[fg]; - - uint8_t shadedfg; - if (OptT::Flags & SWOPT_FixedLight) - { - shadedfg = colormaps[fixedlight + fg]; - } - else - { - shadedfg = colormaps[lightarray[x] + fg]; - } - - if (OptT::Flags & SWOPT_DynLights) - { - uint32_t lit = dynlights[x]; - if (lit & 0x00ffffff) - { - uint32_t fgrgb = GPalette.BaseColors[fg]; - uint32_t shadedfgrgb = GPalette.BaseColors[shadedfg]; - - uint32_t out_r = MIN(((RPART(fgrgb) * RPART(lit)) >> 8) + RPART(shadedfgrgb), (uint32_t)255); - uint32_t out_g = MIN(((GPART(fgrgb) * GPART(lit)) >> 8) + GPART(shadedfgrgb), (uint32_t)255); - uint32_t out_b = MIN(((BPART(fgrgb) * BPART(lit)) >> 8) + BPART(shadedfgrgb), (uint32_t)255); - shadedfg = RGB256k.All[((out_r >> 2) << 12) | ((out_g >> 2) << 6) | (out_b >> 2)]; - } - } - - if (ModeT::BlendSrc == STYLEALPHA_One && ModeT::BlendDest == STYLEALPHA_Zero) - { - destLine[x] = shadedfg; - } - else if (ModeT::BlendSrc == STYLEALPHA_One && ModeT::BlendDest == STYLEALPHA_One) - { - uint32_t src = GPalette.BaseColors[shadedfg]; - uint32_t dest = GPalette.BaseColors[destLine[x]]; - - if (ModeT::BlendOp == STYLEOP_Add) - { - uint32_t out_r = MIN(RPART(dest) + RPART(src), 255); - uint32_t out_g = MIN(GPART(dest) + GPART(src), 255); - uint32_t out_b = MIN(BPART(dest) + BPART(src), 255); - destLine[x] = RGB256k.All[((out_r >> 2) << 12) | ((out_g >> 2) << 6) | (out_b >> 2)]; - } - else if (ModeT::BlendOp == STYLEOP_RevSub) - { - uint32_t out_r = MAX(RPART(dest) - RPART(src), 0); - uint32_t out_g = MAX(GPART(dest) - GPART(src), 0); - uint32_t out_b = MAX(BPART(dest) - BPART(src), 0); - destLine[x] = RGB256k.All[((out_r >> 2) << 12) | ((out_g >> 2) << 6) | (out_b >> 2)]; - } - else //if (ModeT::BlendOp == STYLEOP_Sub) - { - uint32_t out_r = MAX(RPART(src) - RPART(dest), 0); - uint32_t out_g = MAX(GPART(src) - GPART(dest), 0); - uint32_t out_b = MAX(BPART(src) - BPART(dest), 0); - destLine[x] = RGB256k.All[((out_r >> 2) << 12) | ((out_g >> 2) << 6) | (out_b >> 2)]; - } - } - else if (ModeT::SWFlags & SWSTYLEF_SrcColorOneMinusSrcColor) - { - uint32_t src = GPalette.BaseColors[shadedfg]; - uint32_t dest = GPalette.BaseColors[destLine[x]]; - - uint32_t sfactor_r = RPART(src); sfactor_r += sfactor_r >> 7; // 255 -> 256 - uint32_t sfactor_g = GPART(src); sfactor_g += sfactor_g >> 7; // 255 -> 256 - uint32_t sfactor_b = BPART(src); sfactor_b += sfactor_b >> 7; // 255 -> 256 - uint32_t sfactor_a = fgalpha; sfactor_a += sfactor_a >> 7; // 255 -> 256 - uint32_t dfactor_r = 256 - sfactor_r; - uint32_t dfactor_g = 256 - sfactor_g; - uint32_t dfactor_b = 256 - sfactor_b; - uint32_t out_r = (RPART(dest) * dfactor_r + RPART(src) * sfactor_r + 128) >> 8; - uint32_t out_g = (GPART(dest) * dfactor_g + GPART(src) * sfactor_g + 128) >> 8; - uint32_t out_b = (BPART(dest) * dfactor_b + BPART(src) * sfactor_b + 128) >> 8; - - destLine[x] = RGB256k.All[((out_r >> 2) << 12) | ((out_g >> 2) << 6) | (out_b >> 2)]; - } - else if (ModeT::BlendSrc == STYLEALPHA_Src && ModeT::BlendDest == STYLEALPHA_InvSrc && fgalpha == 255) - { - destLine[x] = shadedfg; - } - else if (ModeT::BlendSrc != STYLEALPHA_Src || ModeT::BlendDest != STYLEALPHA_InvSrc || fgalpha != 0) - { - uint32_t src = GPalette.BaseColors[shadedfg]; - uint32_t dest = GPalette.BaseColors[destLine[x]]; - - uint32_t sfactor = fgalpha; sfactor += sfactor >> 7; // 255 -> 256 - uint32_t dfactor = 256 - sfactor; - uint32_t src_r = RPART(src) * sfactor; - uint32_t src_g = GPART(src) * sfactor; - uint32_t src_b = BPART(src) * sfactor; - uint32_t dest_r = RPART(dest); - uint32_t dest_g = GPART(dest); - uint32_t dest_b = BPART(dest); - if (ModeT::BlendDest == STYLEALPHA_One) - { - dest_r <<= 8; - dest_g <<= 8; - dest_b <<= 8; - } - else - { - uint32_t dfactor = 256 - sfactor; - dest_r *= dfactor; - dest_g *= dfactor; - dest_b *= dfactor; - } - - uint32_t out_r, out_g, out_b; - if (ModeT::BlendOp == STYLEOP_Add) - { - if (ModeT::BlendDest == STYLEALPHA_One) - { - out_r = MIN((dest_r + src_r + 128) >> 8, 255); - out_g = MIN((dest_g + src_g + 128) >> 8, 255); - out_b = MIN((dest_b + src_b + 128) >> 8, 255); - } - else - { - out_r = (dest_r + src_r + 128) >> 8; - out_g = (dest_g + src_g + 128) >> 8; - out_b = (dest_b + src_b + 128) >> 8; - } - } - else if (ModeT::BlendOp == STYLEOP_RevSub) - { - out_r = MAX(static_cast(dest_r - src_r + 128) >> 8, 0); - out_g = MAX(static_cast(dest_g - src_g + 128) >> 8, 0); - out_b = MAX(static_cast(dest_b - src_b + 128) >> 8, 0); - } - else //if (ModeT::BlendOp == STYLEOP_Sub) - { - out_r = MAX(static_cast(src_r - dest_r + 128) >> 8, 0); - out_g = MAX(static_cast(src_g - dest_g + 128) >> 8, 0); - out_b = MAX(static_cast(src_b - dest_b + 128) >> 8, 0); - } - - destLine[x] = RGB256k.All[((out_r >> 2) << 12) | ((out_g >> 2) << 6) | (out_b >> 2)]; - } - } - } -} - -template -void DrawSpan8(int y, int x0, int x1, const TriDrawTriangleArgs *args, PolyTriangleThreadData *thread) -{ - using namespace TriScreenDrawerModes; - - if (thread->drawargs.NumLights() == 0 && thread->drawargs.DynLightColor() == 0) - { - if (!thread->drawargs.FixedLight()) - DrawSpanOpt8(y, x0, x1, args, thread); - else - DrawSpanOpt8(y, x0, x1, args, thread); - } - else - { - if (!thread->drawargs.FixedLight()) - DrawSpanOpt8(y, x0, x1, args, thread); - else - DrawSpanOpt8(y, x0, x1, args, thread); - } -} - -void(*ScreenTriangle::SpanDrawers8[])(int, int, int, const TriDrawTriangleArgs *, PolyTriangleThreadData *) = -{ - &DrawSpan8, - &DrawSpan8, - &DrawSpan8, - &DrawSpan8, - &DrawSpan8, - &DrawSpan8, - &DrawSpan8, - &DrawSpan8, - &DrawSpan8, - &DrawSpan8, - &DrawSpan8, - &DrawSpan8, - &DrawSpan8, - &DrawSpan8, - &DrawSpan8, - &DrawSpan8, - &DrawSpan8, - &DrawSpan8, - &DrawSpan8, - &DrawSpan8, - &DrawSpan8, - &DrawSpan8, - &DrawSpan8, - &DrawSpan8, - &DrawSpan8, - &DrawSpan8, - &DrawSpan8, - &DrawSpan8, - &DrawSpan8, - &DrawSpan8 -}; - -void(*ScreenTriangle::SpanDrawers32[])(int, int, int, const TriDrawTriangleArgs *, PolyTriangleThreadData *) = -{ - &DrawSpan32, - &DrawSpan32, - &DrawSpan32, - &DrawSpan32, - &DrawSpan32, - &DrawSpan32, - &DrawSpan32, - &DrawSpan32, - &DrawSpan32, - &DrawSpan32, - &DrawSpan32, - &DrawSpan32, - &DrawSpan32, - &DrawSpan32, - &DrawSpan32, - &DrawSpan32, - &DrawSpan32, - &DrawSpan32, - &DrawSpan32, - &DrawSpan32, - &DrawSpan32, - &DrawSpan32, - &DrawSpan32, - &DrawSpan32, - &DrawSpan32, - &DrawSpan32, - &DrawSpan32, - &DrawSpan32, - &DrawSpan32, - &DrawSpan32 -}; - -void(*ScreenTriangle::TriangleDrawers[])(const TriDrawTriangleArgs *args, PolyTriangleThreadData *thread, int16_t *edges, int topY, int bottomY) = -{ - &DrawTriangle, - &DrawTriangle, - &DrawTriangle, - &DrawTriangle, - &DrawTriangle, - &DrawTriangle, - &DrawTriangle, - &DrawTriangle, - &DrawTriangle, - &DrawTriangle, - &DrawTriangle, - &DrawTriangle, - &DrawTriangle, - &DrawTriangle, - &DrawTriangle, - &DrawTriangle, - &DrawTriangle, - &DrawTriangle, - &DrawTriangle, - &DrawTriangle, - &DrawTriangle, - &DrawTriangle, - &DrawTriangle, - &DrawTriangle, - &DrawTriangle, - &DrawTriangle, - &DrawTriangle, - &DrawTriangle, - &DrawTriangle, - &DrawTriangle, - &DrawTriangle, - &DrawTriangle -}; - -int ScreenTriangle::FuzzStart = 0; - -#endif diff --git a/src/rendering/polyrenderer/drawers/screen_triangle.h b/src/rendering/polyrenderer/drawers/screen_triangle.h index 8da0eca89c..9deee30cd1 100644 --- a/src/rendering/polyrenderer/drawers/screen_triangle.h +++ b/src/rendering/polyrenderer/drawers/screen_triangle.h @@ -149,133 +149,3 @@ namespace TriScreenDrawerModes struct TestSpanOpt2 { static const int Flags = 2; }; struct TestSpanOpt3 { static const int Flags = 3; }; } - -#if 0 - -class ScreenTriangle -{ -public: - static void Draw(const TriDrawTriangleArgs *args, PolyTriangleThreadData *thread); - - static void(*TriangleDrawers[])(const TriDrawTriangleArgs *args, PolyTriangleThreadData *thread, int16_t *edges, int topY, int bottomY); - - static void(*SpanDrawers8[])(int y, int x0, int x1, const TriDrawTriangleArgs *args, PolyTriangleThreadData *thread); - static void(*SpanDrawers32[])(int y, int x0, int x1, const TriDrawTriangleArgs *args, PolyTriangleThreadData *thread); - - static int FuzzStart; -}; - -namespace TriScreenDrawerModes -{ - enum SWStyleFlags - { - SWSTYLEF_Translated = 1, - SWSTYLEF_Skycap = 2, - SWSTYLEF_FogBoundary = 4, - SWSTYLEF_Fill = 8, - SWSTYLEF_SrcColorOneMinusSrcColor = 16, - SWSTYLEF_AlphaTest = 32 - }; - - struct StyleOpaque { static const int BlendOp = STYLEOP_Add, BlendSrc = STYLEALPHA_One, BlendDest = STYLEALPHA_Zero, Flags = STYLEF_Alpha1, SWFlags = 0; }; - struct StyleSkycap { static const int BlendOp = STYLEOP_Add, BlendSrc = STYLEALPHA_One, BlendDest = STYLEALPHA_Zero, Flags = STYLEF_Alpha1, SWFlags = SWSTYLEF_Skycap; }; - struct StyleFogBoundary { static const int BlendOp = STYLEOP_Add, BlendSrc = STYLEALPHA_One, BlendDest = STYLEALPHA_Zero, Flags = STYLEF_Alpha1, SWFlags = SWSTYLEF_FogBoundary; }; - struct StyleSrcColor { static const int BlendOp = STYLEOP_Add, BlendSrc = STYLEALPHA_Src, BlendDest = STYLEALPHA_InvSrc, Flags = STYLEF_Alpha1, SWFlags = SWSTYLEF_SrcColorOneMinusSrcColor; }; - struct StyleFill { static const int BlendOp = STYLEOP_Add, BlendSrc = STYLEALPHA_One, BlendDest = STYLEALPHA_Zero, Flags = STYLEF_Alpha1, SWFlags = SWSTYLEF_Fill; }; - struct StyleFillTranslucent { static const int BlendOp = STYLEOP_Add, BlendSrc = STYLEALPHA_Src, BlendDest = STYLEALPHA_InvSrc, Flags = STYLEF_Alpha1, SWFlags = SWSTYLEF_Fill; }; - - struct StyleNormal { static const int BlendOp = STYLEOP_Add, BlendSrc = STYLEALPHA_Src, BlendDest = STYLEALPHA_InvSrc, Flags = STYLEF_Alpha1, SWFlags = 0; }; - struct StyleAlphaTest { static const int BlendOp = STYLEOP_Add, BlendSrc = STYLEALPHA_Src, BlendDest = STYLEALPHA_InvSrc, Flags = STYLEF_Alpha1, SWFlags = SWSTYLEF_AlphaTest; }; - struct StyleFuzzy { static const int BlendOp = STYLEOP_Fuzz, BlendSrc = STYLEALPHA_Src, BlendDest = STYLEALPHA_InvSrc, Flags = 0, SWFlags = 0; }; - struct StyleStencil { static const int BlendOp = STYLEOP_Add, BlendSrc = STYLEALPHA_Src, BlendDest = STYLEALPHA_InvSrc, Flags = STYLEF_Alpha1 | STYLEF_ColorIsFixed, SWFlags = 0; }; - struct StyleTranslucent { static const int BlendOp = STYLEOP_Add, BlendSrc = STYLEALPHA_Src, BlendDest = STYLEALPHA_InvSrc, Flags = 0, SWFlags = 0; }; - struct StyleAdd { static const int BlendOp = STYLEOP_Add, BlendSrc = STYLEALPHA_Src, BlendDest = STYLEALPHA_One, Flags = 0, SWFlags = 0; }; - struct StyleShaded { static const int BlendOp = STYLEOP_Add, BlendSrc = STYLEALPHA_Src, BlendDest = STYLEALPHA_InvSrc, Flags = STYLEF_RedIsAlpha | STYLEF_ColorIsFixed, SWFlags = 0; }; - struct StyleTranslucentStencil { static const int BlendOp = STYLEOP_Add, BlendSrc = STYLEALPHA_Src, BlendDest = STYLEALPHA_InvSrc, Flags = STYLEF_ColorIsFixed, SWFlags = 0; }; - struct StyleShadow { static const int BlendOp = STYLEOP_Shadow, BlendSrc = STYLEALPHA_Src, BlendDest = STYLEALPHA_InvSrc, Flags = 0, SWFlags = 0; }; - struct StyleSubtract { static const int BlendOp = STYLEOP_RevSub, BlendSrc = STYLEALPHA_Src, BlendDest = STYLEALPHA_One, Flags = 0, SWFlags = 0; }; - struct StyleAddStencil { static const int BlendOp = STYLEOP_Add, BlendSrc = STYLEALPHA_Src, BlendDest = STYLEALPHA_One, Flags = STYLEF_ColorIsFixed, SWFlags = 0; }; - struct StyleAddShaded { static const int BlendOp = STYLEOP_Add, BlendSrc = STYLEALPHA_Src, BlendDest = STYLEALPHA_One, Flags = STYLEF_RedIsAlpha | STYLEF_ColorIsFixed, SWFlags = 0; }; - - struct StyleOpaqueTranslated { static const int BlendOp = STYLEOP_Add, BlendSrc = STYLEALPHA_One, BlendDest = STYLEALPHA_Zero, Flags = STYLEF_Alpha1, SWFlags = SWSTYLEF_Translated; }; - struct StyleSrcColorTranslated { static const int BlendOp = STYLEOP_Add, BlendSrc = STYLEALPHA_Src, BlendDest = STYLEALPHA_InvSrc, Flags = STYLEF_Alpha1, SWFlags = SWSTYLEF_Translated|SWSTYLEF_SrcColorOneMinusSrcColor; }; - struct StyleNormalTranslated { static const int BlendOp = STYLEOP_Add, BlendSrc = STYLEALPHA_Src, BlendDest = STYLEALPHA_InvSrc, Flags = STYLEF_Alpha1, SWFlags = SWSTYLEF_Translated; }; - struct StyleStencilTranslated { static const int BlendOp = STYLEOP_Add, BlendSrc = STYLEALPHA_Src, BlendDest = STYLEALPHA_InvSrc, Flags = STYLEF_Alpha1 | STYLEF_ColorIsFixed, SWFlags = SWSTYLEF_Translated; }; - struct StyleTranslucentTranslated { static const int BlendOp = STYLEOP_Add, BlendSrc = STYLEALPHA_Src, BlendDest = STYLEALPHA_InvSrc, Flags = 0, SWFlags = SWSTYLEF_Translated; }; - struct StyleAddTranslated { static const int BlendOp = STYLEOP_Add, BlendSrc = STYLEALPHA_Src, BlendDest = STYLEALPHA_One, Flags = 0, SWFlags = SWSTYLEF_Translated; }; - struct StyleShadedTranslated { static const int BlendOp = STYLEOP_Add, BlendSrc = STYLEALPHA_Src, BlendDest = STYLEALPHA_InvSrc, Flags = STYLEF_RedIsAlpha | STYLEF_ColorIsFixed, SWFlags = SWSTYLEF_Translated; }; - struct StyleTranslucentStencilTranslated { static const int BlendOp = STYLEOP_Add, BlendSrc = STYLEALPHA_Src, BlendDest = STYLEALPHA_InvSrc, Flags = STYLEF_ColorIsFixed, SWFlags = SWSTYLEF_Translated; }; - struct StyleShadowTranslated { static const int BlendOp = STYLEOP_Shadow, BlendSrc = STYLEALPHA_Src, BlendDest = STYLEALPHA_InvSrc, Flags = 0, SWFlags = SWSTYLEF_Translated; }; - struct StyleSubtractTranslated { static const int BlendOp = STYLEOP_RevSub, BlendSrc = STYLEALPHA_Src, BlendDest = STYLEALPHA_One, Flags = 0, SWFlags = SWSTYLEF_Translated; }; - struct StyleAddStencilTranslated { static const int BlendOp = STYLEOP_Add, BlendSrc = STYLEALPHA_Src, BlendDest = STYLEALPHA_One, Flags = STYLEF_ColorIsFixed, SWFlags = SWSTYLEF_Translated; }; - struct StyleAddShadedTranslated { static const int BlendOp = STYLEOP_Add, BlendSrc = STYLEALPHA_Src, BlendDest = STYLEALPHA_One, Flags = STYLEF_RedIsAlpha | STYLEF_ColorIsFixed, SWFlags = SWSTYLEF_Translated; }; - - enum SWOptFlags - { - SWOPT_DynLights = 1, - SWOPT_ColoredFog = 2, - SWOPT_FixedLight = 4 - }; - - struct DrawerOpt { static const int Flags = 0; }; - struct DrawerOptF { static const int Flags = SWOPT_FixedLight; }; - struct DrawerOptC { static const int Flags = SWOPT_ColoredFog; }; - struct DrawerOptCF { static const int Flags = SWOPT_ColoredFog | SWOPT_FixedLight; }; - struct DrawerOptL { static const int Flags = SWOPT_DynLights; }; - struct DrawerOptLC { static const int Flags = SWOPT_DynLights | SWOPT_ColoredFog; }; - struct DrawerOptLF { static const int Flags = SWOPT_DynLights | SWOPT_FixedLight; }; - struct DrawerOptLCF { static const int Flags = SWOPT_DynLights | SWOPT_ColoredFog | SWOPT_FixedLight; }; - - static const int fuzzcolormap[FUZZTABLE] = - { - 6, 11, 6, 11, 6, 6, 11, 6, 6, 11, - 6, 6, 6, 11, 6, 6, 6, 11, 15, 18, - 21, 6, 11, 15, 6, 6, 6, 6, 11, 6, - 11, 6, 6, 11, 15, 6, 6, 11, 15, 18, - 21, 6, 6, 6, 6, 11, 6, 6, 11, 6, - }; - - enum SWTriangleFlags - { - SWTRI_DepthTest = 1, - SWTRI_StencilTest = 2, - SWTRI_WriteColor = 4, - SWTRI_WriteDepth = 8, - SWTRI_WriteStencil = 16 - }; - - struct TriangleOpt0 { static const int Flags = 0; }; - struct TriangleOpt1 { static const int Flags = 1; }; - struct TriangleOpt2 { static const int Flags = 2; }; - struct TriangleOpt3 { static const int Flags = 3; }; - struct TriangleOpt4 { static const int Flags = 4; }; - struct TriangleOpt5 { static const int Flags = 5; }; - struct TriangleOpt6 { static const int Flags = 6; }; - struct TriangleOpt7 { static const int Flags = 7; }; - struct TriangleOpt8 { static const int Flags = 8; }; - struct TriangleOpt9 { static const int Flags = 9; }; - struct TriangleOpt10 { static const int Flags = 10; }; - struct TriangleOpt11 { static const int Flags = 11; }; - struct TriangleOpt12 { static const int Flags = 12; }; - struct TriangleOpt13 { static const int Flags = 13; }; - struct TriangleOpt14 { static const int Flags = 14; }; - struct TriangleOpt15 { static const int Flags = 15; }; - struct TriangleOpt16 { static const int Flags = 16; }; - struct TriangleOpt17 { static const int Flags = 17; }; - struct TriangleOpt18 { static const int Flags = 18; }; - struct TriangleOpt19 { static const int Flags = 19; }; - struct TriangleOpt20 { static const int Flags = 20; }; - struct TriangleOpt21 { static const int Flags = 21; }; - struct TriangleOpt22 { static const int Flags = 22; }; - struct TriangleOpt23 { static const int Flags = 23; }; - struct TriangleOpt24 { static const int Flags = 24; }; - struct TriangleOpt25 { static const int Flags = 25; }; - struct TriangleOpt26 { static const int Flags = 26; }; - struct TriangleOpt27 { static const int Flags = 27; }; - struct TriangleOpt28 { static const int Flags = 28; }; - struct TriangleOpt29 { static const int Flags = 29; }; - struct TriangleOpt30 { static const int Flags = 30; }; - struct TriangleOpt31 { static const int Flags = 31; }; -} - -#endif