; /*
sc RESOPT IGNORE=73 DATA=NEAR NMINC UCHAR CONSTLIB STREQ STRMERGE NOSTKCHK NOSTDIO OPTIMIZE OPTSIZE fadescreen.c
slink from lib:c.o fadescreen.o to //Clients/FadeScreen lib /lib/client.lib lib:sc.lib lib:amiga.lib SC SD STRIPDEBUG NOICONS
delete fadescreen.o
quit

 FadeScreen 1.3  (Client for BServer)

 Copyright © 1994-1995 Stefano Reksten of 3AM - The Three Amigos!!!
 All rights reserved.
*/

#include <exec/memory.h>
#include <intuition/intuition.h>
#include <intuition/intuitionbase.h>
#include <graphics/gfxbase.h>

#include <proto/exec.h>
#include <proto/graphics.h>
#include <proto/icon.h>
#include <stdlib.h>

#include "/include/client.h"

char *ver = "$VER: FadeScreen 1.3 "__AMIGADATE__;

struct IntuitionBase *IntuitionBase;
struct GfxBase *GfxBase;
struct Library *BitMapBase, *IconBase;

struct Screen *scr;
UWORD scrdepth, darkness_percent;

struct DisplayIDInformation *dinfo;
ULONG command;


UWORD GetDarknessPercent( void )
{
struct DiskObject *dobj;
char **ttypes;
char *pstr;
UWORD percent = 0;

if ( IconBase = OpenLibrary( "icon.library", 0L ) )
	{
	if ( dobj = GetDiskObject( "FadeScreen" ) )
		{
		ttypes = dobj->do_ToolTypes;

		if ( pstr = FindToolType( ttypes, "BRIGHTNESS" ) )
			percent = atoi( pstr );

		FreeDiskObject( dobj );
		}
	CloseLibrary( IconBase );
	}
return percent;
}


void FadeOut( void )
{
UWORD n;
ULONG color;
BOOL still_fading, blanking;
ULONG *current, *colors, *copy_of_colors, *faded, colorsize = (257 * 3 + 1) * sizeof(ULONG);
ULONG r, g, b;
BOOL result = FALSE;
UBYTE fadecount = 0;

scr = IntuitionBase->FirstScreen;
scrdepth = scr->RastPort.BitMap->Depth;

if ( colors = AllocVec( colorsize, MEMF_ANY|MEMF_CLEAR ) )
	{
	if ( faded = AllocVec( colorsize, MEMF_ANY|MEMF_CLEAR ) )
		{
		if ( CheckAA() )
			{
			current = colors;
			current++;
			GetRGB32( scr->ViewPort.ColorMap, 0, 1<<scrdepth, current );
			*colors = (1L<<scrdepth)<<16;
			CopyMem( colors, faded, colorsize );
			}
		else
			{
			current = colors;
			current++;
			for ( n = 0; n < 1<<scrdepth; n++ )
				{
				color = GetRGB4( scr->ViewPort.ColorMap, n );
				*current++ = color >> 8;
				*current++ = (color & 0xF0) >> 4;
				*current++ = color & 0xF;
				CopyMem( colors, faded, colorsize );
				}
			}

		result = TRUE;
		SpritesOff();

		blanking = TRUE;
		still_fading = TRUE;

		while( blanking )
			{
			if ( still_fading )
				command = GetServerCommand();
			else
				command = WaitServerCommand();

			if ( command == COMMAND_QUIT )
				blanking = FALSE;
			else
			if ( still_fading )
				{
				current = faded;
				current++;
				copy_of_colors = colors;
				copy_of_colors++;

				still_fading = FALSE;
				if ( CheckAA() )
					{
					for ( n = 0; n < 1<<scrdepth; n++ )
						{
						if ( *current>>24 > (*copy_of_colors++>>24)*darkness_percent/100 )
							{
							still_fading = TRUE;
							*current -= 0x01000000;
							}
						current++;
						if ( *current>>24 > (*copy_of_colors++>>24)*darkness_percent/100 )
							{
							still_fading = TRUE;
							*current -= 0x01000000;
							}
						current++;
						if ( *current>>24 > (*copy_of_colors++>>24)*darkness_percent/100 )
							{
							still_fading = TRUE;
							*current -= 0x01000000;
							}
						current++;
						}

					WaitTOF();
					LoadRGB32( &scr->ViewPort, faded );
					}
				else
					{
					WaitTOF();
					if ( ++fadecount == 16 )
						{
						fadecount = 0;
						for ( n = 0; n < 1<<scrdepth; n++ )
							{
							if ( *current > (*copy_of_colors++)*darkness_percent/100 )
								{
								*current -= 0x01;
								still_fading = TRUE;
								}
							r = *current++;

							if ( *current > (*copy_of_colors++)*darkness_percent/100 )
								{
								*current -= 0x01;
								still_fading = TRUE;
								}
							g = *current++;

							if ( *current > (*copy_of_colors++)*darkness_percent/100 )
								{
								*current -= 0x01;
								still_fading = TRUE;
								}
							b = *current++;

							SetRGB4( &scr->ViewPort, n, r, g, b );
							}
						}
					else still_fading = TRUE;
					}
				}
			}

		SpritesOn();

		if ( CheckAA() )
			LoadRGB32( &scr->ViewPort, colors );
		else
			{
			current = colors;
			current++;
			for ( n = 0; n < 1<<scrdepth; n++ )
				{
				r = *current++;
				g = *current++;
				b = *current++;
				SetRGB4( &scr->ViewPort, n, r, g, b );
				}
			}

		FreeVec( faded );
		}
	FreeVec( colors );
	}

if ( !result )
	SendClientMsg( ACTION_FAILED );
}


void __main( char *line )
{
if ( IntuitionBase = (struct IntuitionBase *)OpenLibrary( "intuition.library", 36L ) )
	{
	if ( GfxBase = (struct GfxBase *)OpenLibrary( "graphics.library",0L ) )
		{
		if ( dinfo = OpenCommunication() )
			{
			darkness_percent = GetDarknessPercent();

			FadeOut();
			CloseCommunication( dinfo );
			}
		CloseLibrary( (struct Library *)GfxBase );
		}
	CloseLibrary( (struct Library *)IntuitionBase );
	}
}
