Hello,
Here you’ll find two routines for fading to black, an incorrect and a correct
one, separated by conditional compiles. The one that is currently enabled is
incorrect–and I can’t figure out why. The correct version is very slow with
those 3 divides per pixel. The basic idea with the incorrect version is to
just setup a delta buffer and apply it iteratively… but for some reason the
colors are screwy and it doesn’t fade enough. Any ideas?
The delta buffer is called originals because that’s what it stores in the
correct version–the original pixel values.
void ZVideo::fadeToBlack( Uint8 numSteps )
{
Uint32 numCells = screenWidth * screenHeight;
Uint16* pixels = 0;
Uint16 color = 0;
Uint32 redMask = screen->format->Rmask;
Uint32 greenMask = screen->format->Gmask;
Uint32 blueMask = screen->format->Bmask;
Uint16* originals = 0;
if( SDL_MUSTLOCK( screen ) && ( SDL_LockSurface( screen ) < 0 ) )
{
cerr << “zelda: could not lock surface for buffer copy in
ZVideo::fadeToBlack()\n”;
return;
}
else
{
// Allow for the fact that a lock might shuffle addresses in screen.
pixels = (Uint16*) screen->pixels;
originals = new Uint16[ screenWidth * screenHeight ];
if( originals == 0 )
{
cerr << "zelda: could not allocate color buffer in
ZVideo::fadeToBlack()\n";
return;
}
#if 1
for( unsigned int i = 0; i < numCells; i++ )
{
if( pixels[i] > 0 )
{
color = pixels[i] & redMask;
originals[i] &= ~redMask;
originals[i] |= color / numSteps;
color = pixels[i] & greenMask;
originals[i] &= ~greenMask;
originals[i] |= color / numSteps;
color = pixels[i] & blueMask;
originals[i] &= ~blueMask;
originals[i] |= color / numSteps;
}
else
{
originals[i] = 0;
}
}
#else
memcpy( originals, pixels, numCells * 2 );
#endif
SDL_UnlockSurface( screen );
}
for( int i = numSteps - 1; i >= 0; --i )
{
if( SDL_MUSTLOCK( screen ) && ( SDL_LockSurface( screen ) < 0 ) )
{
cerr << "zelda: failed to lock surface in ZVideo::ditherToBlack()\n";
delete[] originals;
return;
}
pixels = (Uint16*) screen->pixels;
for( unsigned int j = 0; j < numCells; j++ )
{
#if 1
if( pixels[j] < originals[j] )
{
pixels[j] = 0;
}
else if( pixels[j] > 0 )
{
pixels[j] -= originals[j];
}
#else
if( pixels[j] > 0 )
{
color = originals[j] & redMask;
pixels[j] &= ~redMask;
pixels[j] |= ( color * i ) / numSteps;
color = originals[j] & greenMask;
pixels[j] &= ~greenMask;
pixels[j] |= ( color * i ) / numSteps;
color = originals[j] & blueMask;
pixels[j] &= ~blueMask;
pixels[j] |= ( color * i ) / numSteps;
}
#endif
}
if( SDL_MUSTLOCK( screen ) )
{
SDL_UnlockSurface( screen );
}
flip( );
}
delete[] originals;
}
m.–
“Plausibility is just what it does have, Crito, rather than truth.”
– Socrates, Euthydemus