/****************************************************************************
*
* VERSION
*	$VER: timer.c 1.72 (30.12.93)
*
* DESCRIPTION
*	Handle code for clock timer...
*
* AUTHOR
*	Rune Johnsrud
*
* COPYRIGHT
*	(c) 1993 Amiga Freelancers
*
*****************************************************************************/

#define INTUI_V36_NAMES_ONLY

#include <intuition/intuition.h>
#include <exec/types.h>
#include <exec/io.h>
#include <exec/memory.h>
#include <devices/timer.h>
#include <utility/date.h>

#include <clib/alib_stdio_protos.h>

#include <proto/intuition.h>
#include <proto/exec.h>
#include <proto/dos.h>
#include <proto/timer.h>
#include <proto/utility.h>

#include "global.h"

/************************************************************************/

extern struct GlobalData *gd;
extern struct ClockInfo  *ci;
extern struct Library *TimerBase;
extern UBYTE  *Months[];
extern UBYTE  *Days[];

/************************************************************************/

UBYTE *DateFmtStr[] =
{
	"%02ld%s%s%s%04ld",
	"%02ld%s%s%s%s",
	"%02ld%s%02ld%s%04ld",
	"%02ld%s%02ld%s%s",
};

UBYTE *TimeFmtStr[] =
{
	"%02ld%s%02ld%s%02ld",
	"%02ld%s%02ld",
};

/************************************************************************/

UBYTE strbuff[10];

/************************************************************************/

static UBYTE *GetShortYear(UWORD year);

/************************************************************************/


BOOL OpenTimerDevice(VOID)
{
	gd->TimerPort = CreateMsgPort();
	if (!gd->TimerPort) return FALSE;

	gd->TReq = (struct timerequest *) CreateExtIO(gd->TimerPort, sizeof(struct timerequest));
	if (!gd->TReq) return FALSE;

	if (!OpenDevice("timer.device", UNIT_VBLANK, (struct IORequest *) gd->TReq, 0))
	{
		TimerBase = (struct Library *) gd->TReq->tr_node.io_Device;

		gd->TReq->tr_node.io_Message.mn_ReplyPort = gd->TimerPort;
		gd->TReq->tr_node.io_Command              = TR_ADDREQUEST;
		gd->TReq->tr_node.io_Flags                = NULL;
		gd->TReq->tr_node.io_Error                = NULL;
		gd->TReq->tr_time.tv_secs				  = 1;
		gd->TReq->tr_time.tv_micro				  = 0;

		SendIO((struct IORequest *) gd->TReq);
	}
	else
		return FALSE;

	return TRUE;
}


VOID CloseTimerDevice(VOID)
{
	if (gd->TReq)
	{
		AbortIO((struct IORequest *) gd->TReq);
		WaitIO((struct IORequest *) gd->TReq);
		CloseDevice((struct IORequest *) gd->TReq);
		DeleteExtIO((struct IORequest *) gd->TReq);
	}

	if (gd->TimerPort) DeleteMsgPort(gd->TimerPort);
}


VOID GetCurrSysTime(VOID)
{
	static struct ClockData cd;

	GetSysTime(&gd->TVal);
	Amiga2Date(gd->TVal.tv_secs, &cd);

	if (ci->ClockType == CT_ANALOG)
	{
		if (cd.min != gd->CData.min)
		{
			gd->NewTime = TRUE;
			gd->NewMin  = TRUE;
			gd->NewHour = TRUE;
		}
	}
	else
	{
		if (ci->ShowDate)
		{
			if ((cd.mday  != gd->CData.mday ) ||
				(cd.month != gd->CData.month) ||
				(cd.year  != gd->CData.year ))
			{
				switch (ci->DateFormat)
				{
				case 0:
					sprintf(gd->DateStr, DateFmtStr[0],
						cd.mday, ci->DateSep, Months[cd.month - 1], ci->DateSep, cd.year);
					break;
				case 1:
					sprintf(gd->DateStr, DateFmtStr[1],
						cd.mday, ci->DateSep, Months[cd.month - 1], ci->DateSep, GetShortYear(cd.year));
					break;
				case 2:
					sprintf(gd->DateStr, DateFmtStr[2],
						cd.mday, ci->DateSep, cd.month, ci->DateSep, cd.year);
					break;
				case 3:
					sprintf(gd->DateStr, DateFmtStr[3],
						cd.mday, ci->DateSep, cd.month, ci->DateSep, GetShortYear(cd.year));
					break;
				}	

				gd->NewDate = TRUE;
			}
		}

		if (ci->ShowSec)
		{
			sprintf(gd->TimeStr, TimeFmtStr[0],
				cd.hour, ci->TimeSep, cd.min, ci->TimeSep, cd.sec);

				gd->NewTime = TRUE;
		}
		else
		{
			if (cd.min != gd->CData.min)
			{
				sprintf(gd->TimeStr, TimeFmtStr[1],
					cd.hour, ci->TimeSep, cd.min);

					gd->NewTime = TRUE;
			}
		}
	}

	gd->CData = cd;
}


static UBYTE *GetShortYear(UWORD year)
{
	UBYTE *p = (UBYTE *) &strbuff;

	sprintf(strbuff, "%04ld\0", year);

	return (p + 2);
}


/* End Of File */
