#include <stdio.h>
#include "egb.h"
#include "stdlib.h"
#include <msdos.cf>
#include "FMCFRB.H"

#define	 GBUF_SIZE16	(321 * 241 * 2)
#define	 GBUF_SIZE8	(640 * 480 * 1)
#define  KBUF_SIZE      (640 * 480 * 2)
#define  UPAGE		0x80	/*  ユーザページ */
#define  BITR(p1)	( (p1 & 0x03e0) >>  5 )
#define  BITG(p1)	( (p1 & 0x7c00) >> 10 )
#define  BITB(p1)	(  p1 & 0x1f )


extern short int gwork[];
extern int mode;		/* 1=2色 4=16色 8=256色 16=32k色 */
extern int ovr; 		/* 重ね合わせ濃度	*/
extern int aflg;		/* 加算フラグ	*/
extern int sx,sy;		/* ズ−ム大きさ	*/
extern int ix,iy;		/* 読み込み位置	*/

int Gradate( value, kbuf )
int 	value;
short int *kbuf;
{
	int bx,by;
	unsigned int vbeta, bbeta;
	int i;
	unsigned char *mbuf;
	short int *tbuf;
	int r,g,b;
	int ovr2;
	int x1, y1, x2, y2;
	int n;

	char *reswork;
	int  worksize;
	char rpara[20];

	char tmp[20];

trace("Gradate start");
	mbuf = (unsigned char *)malloc( GBUF_SIZE8 );
	tbuf = (short int *)malloc( KBUF_SIZE );	
sprintf(tmp, "ovr=%d",ovr);
trace(tmp);
/*********************************************
  マスク作成
********************************************/
	GvramToBuf( tbuf );
	MakeMask(tbuf, mbuf);
 
/*********************************************
  作業用バッファ作成
********************************************/
	memcpy( tbuf, kbuf, KBUF_SIZE );
	GvramToBuf( tbuf );

        /*	作業用バッファぼかす準備	*/
        EGB_resolutionRam( gwork,UPAGE,16,640,480,tbuf );
        EGB_writePage( gwork,UPAGE );
        n = 0;
        WORD( rpara     ) = 4;
        WORD( rpara + 2 ) = 0;
        WORD( rpara + 4 ) = 0;
        WORD( rpara + 6 ) = 639;
        WORD( rpara + 8 ) = 0;
        WORD( rpara + 10) = 639;
        WORD( rpara + 12) = 479;
        WORD( rpara + 14) = 0;
        WORD( rpara + 16) = 479;
        EGB_region( gwork, &n, &worksize, &x1, &y1, &x2, &y2, rpara );

	reswork = (char *)malloc( worksize );
	for(i=0; i <= value; i ++){
	   /*	マスクぼかす	*/
	   MaskGrade( mbuf );

           /*	作業用バッファぼかす */
	   EGB_resolve( gwork, reswork );
	}
	free( reswork );

/* 
memcpy( kbuf, tbuf, KBUF_SIZE );
free( tbuf );
free( mbuf );
trace("Gradate end");
return 0;
*/

/*********************************************
  保存用バッファに重ねる
********************************************/
	if (aflg != 0){	/* 加算合成	*/
	   for( by=0; by < 480; by ++){
		  for( bx=0; bx < 640; bx ++){
			 vbeta = *(tbuf + bx + by * 640);
			 ovr2  = *(mbuf + bx + by * 640);
			 if( ovr2 != 0 && vbeta != 0){	/* 透明色以外なら書き込み */
				bbeta = *(kbuf + bx + by*640);
				r = _min( (BITR(bbeta)*256 + BITR(vbeta) * ovr2), 31*256 )/256;
				g = _min( (BITG(bbeta)*256 + BITG(vbeta) * ovr2), 31*256 )/256;
				b = _min( (BITB(bbeta)*256 + BITB(vbeta) * ovr2), 31*256 )/256;
				*(kbuf + bx + by*640) = ( ((r << 5)&0x3e0) | ((g << 10)&0x7c00) | (b&0x1f));
			 }
		  }
	   }
	}else{
	  for( by=0; by < 480; by ++){
		 for( bx=0; bx < 640; bx ++){
			vbeta = *(tbuf + bx + by * 640);
			ovr2 = *(mbuf + bx + by * 640);
			if( ovr2 != 0 && vbeta != 0 ){	/* 透明色以外なら書き込み */
			   bbeta  = *(kbuf + bx + by*640);
			   r = _min( ((BITR(vbeta) - BITR(bbeta) ) * ovr2 + BITR(bbeta)*256), 31*256 )/256;
			   g = _min( ((BITG(vbeta) - BITG(bbeta) ) * ovr2 + BITG(bbeta)*256), 31*256 )/256;
			   b = _min( ((BITB(vbeta) - BITB(bbeta) ) * ovr2 + BITB(bbeta)*256), 31*256 )/256;
			   *(kbuf + bx + by*640) = ( ((r << 5)&0x3e0) | ((g << 10)&0x7c00) | (b&0x1f));
			}
		 }
	  }
	}

	free( tbuf );
	free( mbuf );
trace("Gradate end");
	return 0;
 }

int MakeMask( kbuf, mbuf )
short int *kbuf;	/* VRAMバッファ(INPUT)	*/
unsigned char *mbuf;	/* αマスクバッファ(OUTPUT)*/
{
	unsigned char	mask;
	int bx,by;
	unsigned int bbeta;
	char tmp[20];

trace("MakeMask start");
/***********************************************************
	重ね合わせ用バッファを参照してαマスク作成
*************************************************************/

	mask = 255;
//	mask = ovr / 255;
sprintf(tmp, "mask=%d, ovr=%d", mask,ovr);
trace(tmp);
	memset( mbuf, 0, GBUF_SIZE8);
	for( by=0; by < 480; by ++){
	   for( bx=0; bx < 640; bx ++){
		  bbeta  = *(kbuf + bx + by*640);
		  if( bbeta != -258 ){	/* 透明色以外なら書き込み */
//printf("%d", bbeta);
			 *(mbuf + bx + by*640) = mask;
		  }
	   }
	}

trace("MakeMask end");
	return 0;
}

/***********************************************************
	αマスクをぼかす
*************************************************************/
int MaskGrade( mbuf )
unsigned char	*mbuf;
{
	int bx,by;
	unsigned char *tmpbuf;
	unsigned int newmask;

trace("MaskGrade start");
	tmpbuf = (unsigned char *)malloc( GBUF_SIZE8 );
	memcpy( tmpbuf, mbuf, GBUF_SIZE8 );

	for( by=1; by < 479; by ++){
	   for( bx=1; bx < 639; bx ++){
		  newmask = (*(tmpbuf + bx-1 + (by-1)*640) + *(tmpbuf + bx + (by-1)*640) + *(tmpbuf + bx+1 + (by-1)*640)  + *(tmpbuf + bx-1 + by*640) + *(tmpbuf + bx + by*640)*3 + *(tmpbuf + bx+1 + by*640)  + *(tmpbuf + bx-1 + (by+1)*640) + *(tmpbuf + bx + (by+1)*640) + *(tmpbuf + bx+1 + (by+1)*640) ) / 11;
		  *(mbuf+bx+by*640) = newmask;
	   }
	}

	free(tmpbuf);
trace("MaskGrade end");
	return 0;
}
