/* >c.ChooseRes
 * Automatically select the correct sprite/template files for the current
 * screen mode / CMOS settings (taking into account file availability!)
 *
 *  Musus Umbra, 1996
 */

#include <string.h>
#include "kernel.h"

#define SPRITEFILE_TYPE 0xff9
#define TEMPLATE_TYPE   0xfec
#define OS_ReadModeVariable  0x35
#define MODEVAR_NCOL 3
#define MODEVAR_XEIG 4
#define MODEVAR_YEIG 5


/**************************************************************************
 STATIC file_exists
 --------------------------------------------------------------------------
 * Arguments:
 *	char	*pathname		The pathname of the file to test
 *	int		filetype		Required filetype
 * Returns:
 *	true iff the file exists and is a spritefile
 **************************************************************************/

static int file_exists(char *pathname, unsigned int filetype)
{
	_kernel_osfile_block block;

	filetype = (filetype << 8) | 0xfff00000;
	if ( _kernel_osfile(17, pathname, &block) !=1 ) { return 0; }
	return ( (block.load & 0xffffff00) == filetype );
}



/*static*/ char* leafname(char* source)
{
  char* ret;
  char* search;
  for (search=source; *search!=0; search++); /* find terminator */
  for (ret=search; *ret!='.' && ret>=source && *ret!=':'; ret--); /*find leaf*/
  return(ret+1);
}




/**************************************************************************
 STATIC mode_type
 --------------------------------------------------------------------------
 * Arguments:
 *	none
 * Returns:
 *	The generic type of the current screen mode:
 *		0 => tv-res mono mode     (ie. 0 suffix)
 *		1 => tv-res colour mode   (ie. 24, or no suffix)
 *		2 => high-res colour mode (ie. 22 suffix)
 *		3 => high-res mono mode   (ie. 23 suffix)
 **************************************************************************/

static int mode_type( void )
{
	_kernel_swi_regs r;
	int xeig, yeig, ncols;

	r.r[0] = -1;			/* screen mode to read info for */
	r.r[1] = MODEVAR_NCOL;
	_kernel_swi( OS_ReadModeVariable, &r, &r );
	ncols = r.r[2];
	r.r[1] = MODEVAR_XEIG;
	_kernel_swi( OS_ReadModeVariable, &r, &r );
	xeig = r.r[2];
	r.r[1] = MODEVAR_YEIG;
	_kernel_swi( OS_ReadModeVariable, &r, &r );
	yeig = r.r[2];

	/* High Res: */
	if ( (xeig == yeig) && (yeig <= 2) ) { return ncols>1 ? 2 : 3; }

	/* Low Res: */
	return ncols ? 1 : 0;
}


/**************************************************************************
 EXTERN choose_sprites()
 --------------------------------------------------------------------------
 * Arguments:
 *	char *stub	Stub to append ""/0/22/23/24 to (NULL=>"<obey$dir>.Sprites")
 * Returns:
 *	->the selected file's pathname (or NULL if no spritefile)
 **************************************************************************/

char *choose_sprites(char *stub)
{
	static char	spritefile[64];
	char	*suffixes[]	= { 0, "", "24", "0", "", "24", "22", "23" };
	char	*suffix_pos;
	int		mode;

	if ( !stub ) { stub = "<obey$dir>.Sprites"; }	/* Default stub */

	strcpy(spritefile,stub);				/* Copy stub into buffer */
	suffix_pos = spritefile + strlen(spritefile);

	mode = mode_type();					/* get type of current mode */
	if ( mode > 1 ) { mode +=1; }		/* suffix 4 is a mung! */
	mode += 3;							/* as are the first three */

	for ( ; mode ; mode-- )
	{
		strcpy( suffix_pos, suffixes[mode] );
		if ( file_exists( spritefile, SPRITEFILE_TYPE ) )
		{
			return spritefile;
		}
	}

	/* Couldn't choose a suitable sprite file! */
	return NULL;
}




/**************************************************************************
 STATIC use_newlook
 --------------------------------------------------------------------------
 * Arguments:
 *	none
 * Returns:
 *	true if NewLook is configured on in the CMOS RAM, false otherwise
 **************************************************************************/

static int use_newlook( void )
{
	return ( (_kernel_osbyte( 161, 140, 0 ) & 0x100) != 0 );
}


/**************************************************************************
 EXTERN choose_templates
 --------------------------------------------------------------------------
 * Arguments:
 *	char *stub	Stub to append "2D", "3D" or "" to
 * Returns:
 *	selected template's LEAF name (NULL => no templates)
 **************************************************************************/

char *choose_templates( char *stub )
{
	static char	template_file[64];
	char	*suffixes[] = { 0, "", "2", "2D", "3", "3D" };
	char	*suffix_pos;
	int		suffix_try;

	strcpy(template_file, stub);
	suffix_pos = template_file + strlen(template_file);
	suffix_try = use_newlook() ? 5 : 3;

	for ( ; suffix_try ; suffix_try-- )
	{
		strcpy(suffix_pos,suffixes[suffix_try]);
		if ( file_exists(template_file,TEMPLATE_TYPE) )
		{
			return leafname(template_file);
		}
	}

	return NULL;
}

