#include	<stdlib.h>
#include    <string.h>
#include    <stdio.h>
#include    <time.h>
#include	"GB.h"
#include	"system.h"
#include	"method2.h"
#include	"gfxfunc.h"
#include	"prefs.h"

void RefreshLineSub(byte Y);


//#define WIDTH  176
//#define HEIGHT 160

#define WIDTH  256
#define HEIGHT 256

#define	XOFFSET	((WIDTH-160)/2)

byte	*XBuf, XPal[16];
byte DefaultPalette[]={	0,0,0,                 /* Overscan colour */
						0xFF,0xFF,0xFF,        /* Background colours */
						0xB0,0xB0,0xB0,
						0x60,0x60,0x60,
						0x00,0x00,0x00,
						0xFF,0xFF,0xFF,        /* Sprite colours */
						0xB0,0xB0,0xB0,
						0x60,0x60,0x60,
						0x00,0x00,0x00,
						0xFF,0xFF,0xFF,        /* Window colours */
						0xB0,0xB0,0xB0,
						0x60,0x60,0x60,
						0x00,0x00,0x00 };
byte	Palette[256];

byte	SourceColor2(int n)
{
	return n;
}


int InitMachine2(void)
{
	char	*error;
	int		i;

	//	INITIALIZE WORK BUFFER
	XBuf=(byte *)GXGetMem(sizeof(byte)*HEIGHT*WIDTH, MEMF_ZERO|MEMF_ABORT);
    for (i=0; i<16; ++i){
		XPal[i]=i+16;
	}
	return 1;
}
void TrashMachine2(void)
{
	if(XBuf){
		GXFreeMem(XBuf);
		XBuf=0;
	}
}

void RefreshScreen2(void)
{
	CopyToScreen(XBuf+XOFFSET, 160, 144, WIDTH);
}


void RefreshLine2(byte Y)
{
  byte Offset,*P,*T,*R,D0,X1,X2;
  unsigned D1;
  byte Pal[4];
  int	MyScroll;
  int	n;
  byte  *map;
  int   nmap;

  R=XBuf+WIDTH*Y+XOFFSET;
  Pal[0]=XPal[BPal[0]];Pal[1]=XPal[BPal[1]];
  Pal[2]=XPal[BPal[2]];Pal[3]=XPal[BPal[3]];

	if( ((LCDCONT&0x81)!=0x81) || (!BackgroundOn) ) { 
	memset(R,XPal[0],160);R+=160; 
  }else{
	MyScroll=SCROLLX;		
    Offset=Y+SCROLLY;
    T=BgdTab+((word)(Offset&0xF8)<<2);
    Offset=(Offset&0x07)<<1;

    R-=(MyScroll&0x07);
	X1=(MyScroll/8);

    for(n=21; n; n--)
    {
      D0=*(T+( X1 & 31));
      if( !(LCDCONT&0x10)  ) D0+=0x80;
      P=ChrGen+(((int)D0)<<4)+Offset;
      D0=*P;D1=(word)*(P+1)<<1;
      R[0]=Pal[((D1&0x100)|(D0&0x80))>>7];
      R[1]=Pal[((D1&0x080)|(D0&0x40))>>6];
      R[2]=Pal[((D1&0x040)|(D0&0x20))>>5];
      R[3]=Pal[((D1&0x020)|(D0&0x10))>>4];
      R[4]=Pal[((D1&0x010)|(D0&0x08))>>3];
      R[5]=Pal[((D1&0x008)|(D0&0x04))>>2];
      R[6]=Pal[((D1&0x004)|(D0&0x02))>>1];
      R[7]=Pal[((D1&0x002)|(D0&0x01))];
      R+=8;
      X1++;
    }
    R+=(MyScroll&0x07)-8;
  }
//	R+=160;
  X1=(WNDPOSX>7)? WNDPOSX-7:0;

	if(!WindowOn)return;

  if(((LCDCONT&0xA0)==0xA0)&&(WNDPOSY<=Y)&&(X1<160))
  {
    R-=160-X1;
    Offset=Y-WNDPOSY;
    T=WndTab+((word)(Offset&0xF8)<<2);
    Offset=(Offset&0x07)<<1;
    Pal[0]=XPal[BPal[0]+8];Pal[1]=XPal[BPal[1]+8];
    Pal[2]=XPal[BPal[2]+8];Pal[3]=XPal[BPal[3]+8];
    {
     for(X1>>=3;X1<(160>>3);X1++)
     {
//	QuitCode("Plotting window\n");
      D0=*(T++)+0x80;
      P=RAM+0x8800+((word)D0<<4)+Offset;
      D0=*P;D1=(word)*(P+1)<<1;
      R[0]=Pal[((D1&0x100)|(D0&0x80))>>7];
      R[1]=Pal[((D1&0x080)|(D0&0x40))>>6];
      R[2]=Pal[((D1&0x040)|(D0&0x20))>>5];
      R[3]=Pal[((D1&0x020)|(D0&0x10))>>4];
      R[4]=Pal[((D1&0x010)|(D0&0x08))>>3];
      R[5]=Pal[((D1&0x008)|(D0&0x04))>>2];
      R[6]=Pal[((D1&0x004)|(D0&0x02))>>1];
      R[7]=Pal[((D1&0x002)|(D0&0x01))];
      R+=8;
     }
    }
  }
}

void RefreshSprites2(void)
{
  register byte *P,*T,*S,I,J,K,N,D0;
  register offset DY;
  register unsigned D1;
  byte Pal[4];

	if(!SpritesOn)return;

  N=LCDCONT&0x04? 16:8;

  for(S=RAM+0xFE9C,J=40;J;S-=4,J--)
    if(S[0]&&(S[0]<160)&&S[1]&&(S[1]<168))
    {
      if(S[0]<16){ 
      	D0=0;
      	K=16-S[0];
      	I=(K<N)? N-K:0; 
      }else{ 
      	D0=S[0]-16;						//start y coordinate
      	K=0;
      	I=(160-S[0]<N)? 160-S[0]:N; 	//lines to draw??
      }
      P=XBuf+D0*WIDTH+XOFFSET+S[1]-(S[3]&0x20? 1:8);
      DY=2;
      if(S[3]&0x40){	//if tiles y flipped, moved to end of data and read 
      	DY=-DY;			//backwards
      	K=N-K-1; 		//=tile height - 1 normally	
      }

      //T=S[3]&0x10? SPal1:SPal0;
      //Pal[0]=XPal[T[0]+4];Pal[1]=XPal[T[1]+4];
      //Pal[2]=XPal[T[2]+4];Pal[3]=XPal[T[3]+4];

	  if(S[3]&0x10){
	  	Pal[0]=SPal1[0]+12;
	  	Pal[1]=SPal1[1]+12;
	  	Pal[2]=SPal1[2]+12;
	  	Pal[3]=SPal1[3]+12;
	  }else{
	  	Pal[0]=SPal0[0]+8;
	  	Pal[1]=SPal0[1]+8;
	  	Pal[2]=SPal0[2]+8;
	  	Pal[3]=SPal0[3]+8;
	  }
	

      T=RAM+0x8000+((long)((N>8)? S[2]&0xFE:S[2])<<4)+(K<<1);

      if(S[3]&0x20)
        for(;I;I--,P+=WIDTH,T+=DY)	//i=height to draw
        {						
          D0=*T;D1=*(T+1);K=D0|D1;D1<<=1;
          if(K&0x80) P[0]=Pal[((D1&0x100)|(D0&0x80))>>7];
          if(K&0x40) P[-1]=Pal[((D1&0x080)|(D0&0x40))>>6];
          if(K&0x20) P[-2]=Pal[((D1&0x040)|(D0&0x20))>>5];
          if(K&0x10) P[-3]=Pal[((D1&0x020)|(D0&0x10))>>4];
          if(K&0x08) P[-4]=Pal[((D1&0x010)|(D0&0x08))>>3];
          if(K&0x04) P[-5]=Pal[((D1&0x008)|(D0&0x04))>>2];
          if(K&0x02) P[-6]=Pal[((D1&0x004)|(D0&0x02))>>1];
          if(K&0x01) P[-7]=Pal[((D1&0x002)|(D0&0x01))];
        }
      else
        for(;I;I--,P+=WIDTH,T+=DY)
        {
          D0=*T;D1=*(T+1);K=D0|D1;D1<<=1;
          if(K&0x80) P[0]=Pal[((D1&0x100)|(D0&0x80))>>7];
          if(K&0x40) P[1]=Pal[((D1&0x080)|(D0&0x40))>>6];
          if(K&0x20) P[2]=Pal[((D1&0x040)|(D0&0x20))>>5];
          if(K&0x10) P[3]=Pal[((D1&0x020)|(D0&0x10))>>4];
          if(K&0x08) P[4]=Pal[((D1&0x010)|(D0&0x08))>>3];
          if(K&0x04) P[5]=Pal[((D1&0x008)|(D0&0x04))>>2];
          if(K&0x02) P[6]=Pal[((D1&0x004)|(D0&0x02))>>1];
          if(K&0x01) P[7]=Pal[((D1&0x002)|(D0&0x01))];
        }
    }
}
void Sound2(byte R,byte V){}
byte SIOSend2(byte V){return 0;}
byte SIOReceive2(byte *V){return 0;}


