#include "data/nescart.h"

const unsigned char nescart_palette_bg [16]={ 0x0f,0x22,0x32,0x30,0x0f,0x13,0x23,0x33,0x0f,0x29,0x28,0x30,0x0f,0x13,0x24,0x15 };
const unsigned char nescart_palette_spr[16]={ 0x0f,0x0f,0x0f,0x0f,0x0f,0x0f,0x0f,0x00,0x0f,0x0f,0x00,0x10,0x0f,0x0f,0x10,0x30 };

#define NC_SCENE_DURATION	(60*13)
#define NC_START_ROTATE		(60*3)
#define NC_LABEL_DURATION	(60*3-20)
#define NC_LABEL1_FRAME		(60*4+20)
#define NC_LABEL2_FRAME		(60*9-10)

const unsigned char nescart_metasprite1[]={
	-32,-16,0x01,0,
	-24,-16,0x03,0,
	-16,-16,0x05,0,
	- 8,-16,0x07,0,
	  0,-16,0x09,0,
	  8,-16,0x0b,0,
	 16,-16,0x0d,0,
	 24,-16,0x0f,0,
	-32,  0,0x21,0,
	-24,  0,0x23,0,
	-16,  0,0x25,0,
	- 8,  0,0x27,0,
	  0,  0,0x29,0,
	  8,  0,0x2b,0,
	 16,  0,0x2d,0,
	 24,  0,0x2f,0,
	128
};


const unsigned char nescart_metasprite2[]={
	- 8,-16,0x17,0,
	  0,-16,0x19,0,
	  8,-16,0x1b,0,
	 16,-16,0x1d,0,
	 24,-16,0x1f,0,
	-24,  0,0x33,0,
	-16,  0,0x35,0,
	- 8,  0,0x37,0,
	  0,  0,0x39,0,
	  8,  0,0x3b,0,
	 16,  0,0x3d,0,
	 24,  0,0x3f,0,
	128
};


const unsigned char nescart_sinetable[32]={
	0,1,3,4,5,6,7,7,
	8,7,7,6,5,4,3,1,
	0,-1,-3,-4,-5,-6,-7,-7,
	-8,-7,-7,-6,-5,-4,-3,-1,
};

unsigned char nescart_bank_prg;
unsigned int  nescart_bank_off;

#define NC_FP	7



void e_nescart(void)
{
	unsigned char chr,bright;
	unsigned char label1_bright,label2_bright;
	unsigned int frame,label1_cnt,label2_cnt,label_anim,cart_frame;
	signed int cart_frame_fp,cart_frame_dx;;

	oam_clear_fast();
	oam_size(1);

	chr=CHR_NESCART;
	
	mmc3_chr_bank(chr+0,0);
	mmc3_chr_bank(chr+2,1);
	
	chr=CHR_NESCART_TEXT;
	
	mmc3_chr_bank(chr+0,2);
	mmc3_chr_bank(chr+1,3);
	mmc3_chr_bank(chr+2,4);
	mmc3_chr_bank(chr+3,5);

	mmc3_set_mirroring(M_HORIZONTAL);
	
	set_irq_handler(IRQ_EMPTY);
	set_nmi_handler(NMI_NORMAL);
	
	pal_bg (nescart_palette_bg);
	pal_spr(nescart_palette_spr);
	pal_bright(0);
	
	vram_adr(NAMETABLE_A);
	vram_unrle(nescart);
	vram_adr(NAMETABLE_C);
	vram_fill(0,1024);
	
	memfill(split_list,0,sizeof(split_list));
	
	label1_cnt=0;
	label2_cnt=0;	
	label1_bright=0;
	label2_bright=0;
	label_anim=0;
	frame=0;
	bright=0;
	cart_frame_fp=2<<NC_FP;
	cart_frame_dx=0;
	nescart_bank_prg=0;
	nescart_bank_off=0;
	
	set_irq_handler(IRQ_NESCART);
	mmc3_irq_enable(32);
	
	scroll(0,-1);
	
	ppu_on_all();

	while(1)
	{
		cart_frame=(cart_frame_fp>>NC_FP)&255;
		
		nescart_bank_prg=PRG_NESCART_ROTATE+(cart_frame/93);
		nescart_bank_off=(cart_frame%93)*176;
		
		cart_frame_fp+=cart_frame_dx;
		
		if(frame>NC_START_ROTATE)
		{
			if(frame<NC_SCENE_DURATION/2)
			{
				++cart_frame_dx;
			}
			else
			{
				cart_frame_dx-=2;
			}
		}
		
		oam_clear_fast();
		
		oam_off=0;
		oam_step=4;
		
		if(label1_cnt)
		{
			if(!(frame&3))
			{
				if(label1_cnt>3*8)
				{
					if(label1_bright<3) ++label1_bright;
				}
				else
				{
					if(label1_bright>0) --label1_bright;
				}
			}
		
			oam_meta_clip_x(56,40+nescart_sinetable[label_anim&31],label1_bright,nescart_metasprite1);
		
			--label1_cnt;
		}
		
		if(label2_cnt)
		{
			if(!(frame&3))
			{
				if(label2_cnt>3*8)
				{
					if(label2_bright<3) ++label2_bright;
				}
				else
				{
					if(label2_bright>0) --label2_bright;
				}
			}
		
			oam_meta_clip_x(200,200+nescart_sinetable[label_anim&31],label2_bright,nescart_metasprite2);
		
			--label2_cnt;
		}
		
		oam_update();
		
		ppu_wait_nmi();
		
		if(frame<100)
		{
			if(!(frame&7))
			{
				if(bright<4) ++bright;
				
				pal_bright(bright);
			}
		}
		
		if(frame>=NC_SCENE_DURATION)
		{
			if(!(frame&7))
			{
				if(bright) --bright; else break;
				
				pal_bright(bright);
			}
		}
		
		if(frame==NC_LABEL1_FRAME)
		{
			label1_cnt=NC_LABEL_DURATION;
			label_anim=0;
		}
		
		if(frame==NC_LABEL2_FRAME)
		{
			label2_cnt=NC_LABEL_DURATION;
			label_anim=0;
		}
		
		++frame;
		++label_anim;
	}
	
	ppu_off();
	
	mmc3_irq_enable(0);
}