#include "WimpLib:Sprites.h"

#include <stdio.h>

#include "WimpLib:Exception.h"
#include "WimpLib:mem.h"
#include "swis.h"

CSpriteArea* throw_Sprites_LoadFile(const char* filename)
{
	FILE* file;
	int ext;
	CSpriteArea* pArea;


	file = fopen(filename, "rb");

	if (file == NULL)
		throw_last_oserror();

	// Get sprite file size
	fseek(file, 0, SEEK_END);
	ext = 16 + (int) ftell(file);
	fclose(file);

	// Allocate sprite area
	pArea = throw_mem_alloc(ext);

	try
	{
		// Init sprite area
		pArea->size = ext;
		pArea->sproff = sizeof(CSpriteArea);
		_swi(OS_SpriteOp, _INR(0,1), 0x109, pArea);

		// Load sprites
		_swi(OS_SpriteOp, _INR(0,2), 0x10A, pArea, filename);
	}
	catch
	{
		mem_free(pArea);
		throw_current();
	}
	catch_end

	return pArea;
}

CSpriteHdr* Sprites_SelectSprite(const CSpriteArea* pSpriteArea, const char* pSpriteName)
{
	CSpriteHdr* pSprite;

	// User Area, Select sprite
	if (_swix(OS_SpriteOp, _INR(0,2)|_OUT(2)
			, 0x100 + 24, pSpriteArea, pSpriteName
			, &pSprite))
		return NULL;

	return pSprite;
}
CSpriteHdr* Sprites_FirstSprite(const CSpriteArea* pSpriteArea)
{
	char* p = (char*) pSpriteArea;

	if (pSpriteArea->sproff == pSpriteArea->freeoff)
		return NULL;

	p += pSpriteArea->sproff;

	return (CSpriteHdr*) p;
}

CSpriteHdr* Sprites_NextSprite(const CSpriteArea* pSpriteArea, const CSpriteHdr* pSprite)
{
	char* pf = (char*) pSpriteArea;
	char* p  = (char*) pSprite;

	pf += pSpriteArea->freeoff;
	p += pSprite->next;
	if (p >= pf) return NULL;

	return (CSpriteHdr*) p;
}

CSize Sprite_GetSize(const CSpriteHdr* pSprite)
{
	CSize size = {0, 0};

	// Get sprite pixel sizes
	_swix(OS_SpriteOp, _INR(0,2)|_OUTR(3,4)
		, 0x200 + 40, 0x100, pSprite
		, &size.cx, &size.cy);

	return size;
}
