//
/***  スプライト制御  ***/

#define PALSTK_MAX		( 256 * 16 )

#define BAK0_IDX	  0		/* インデックス格納オフセット	*/
#define MAIN_IDX	 16
#define BAK1_IDX	272
#define BACK_IDX	288

#define	SCR_WC		18
#define	SCR_WD		( SCR_WC * 16 )
#define SCR_OFSX	-16
#define SCR_OFSY	-16

#define IDX_MAX		896
#define B_WHITE		 32
#define B_DARK		-32
#define	BLV_PART	0
#define	BLV_ALL		1
#define	BLV_FREE	2

#define FRM_CX		( map_dtx - SCR_OFSX + 128 & 4095 )
#define FRM_CY		( map_dty - SCR_OFSY + 128 & 4095 )
/* FRAME_X = map_frx ? */

#define IMGMAP_WDX		imgmap_wdx
#define IMGMAP_WDY		imgmap_wdy
#define IMGMAP_BUF(x,y)	imgmap_p[ (x) + imgmap_wx * (y) ]

extern	unsigned short	palstk_buf[], gradpal_stk[], *imgmap_p ;

extern	int	pattern_idx[];
extern	int	imgmap_wx, imgmap_wy, imgmap_wdx, imgmap_wdy ;
extern	int	map_dtx, map_dty, map_chx, map_chy, map_frx, map_fry ;
extern	int	scr_chx, scr_chy ;
extern	int	bright_lv, bright_slv, bright_zero, bright_lmt, brlv_lmt ;
extern	int	gradpal_ofs, gradpal_n, gradpal_step ;
extern	int	gradpal_div, gradpal_siz ;
extern	int	spr_swi[];

void	sprite_end(), sprite_init();
void	scroll( int xm, int ym );
int		scroll_x( int move_x ), scroll_y( int move_y );
int		load_imagemap( char *fname, int buf_swi );
int		load_sprite( char *fname, int spr_ofs, int pal_ofs );
int		load_data( char *nam, char *adr, int offset, int size );
void	map_init( void ), map_reset( int x, int y );
void	bright_level(int level,int step,int wait_c,int all,unsigned long mask);
void	bright_down( int step, int wait_c, unsigned long mask );
void	wait_sprtime( int c );

/***  キャラクター制御  ***/

#define CHR_MAX		15
#define BULLET_MAX	64
#define REQ			-1

#define OPT		0x001
#define MUL		0x004
#define FLY		0x008
#define TAL		0x010
#define VSZ		0x10000000
#define VPT		0x20000000
#define POV		0x40000000

#define CHRX( n )	chr[n].x.HL.H
#define CHRY( n )	chr[n].y.HL.H
#define CHR_X		chr[PLAYER].x.HL.H
#define CHR_Y		chr[PLAYER].y.HL.H
#define CHX			cp->x.HL.H
#define CHY			cp->y.HL.H
#define XH			x.HL.H
#define YH			y.HL.H
#define CP_SIZE		(( cp->size & 255 )*( cp->size>> 8 & 255 ))
#define CPFLAG(f)	( cp->set_flag & (f) )
#define SCR_X		( CHR_X - map_frx )
#define SCR_Y		( CHR_Y - map_fry )
#define CH_OPT		cp->opt
#define CH_EFX		cp->efx
#define PPOS(p)		(( (p)->ang +(1<<(p)->ang_sft-1)& 255 )>> (p)->ang_sft )
#define SETCP_ANG(a)	\
	cp->ang = (a),(cp->ppos = (cp->ang+(1<<cp->ang_sft-1)&255)>> cp->ang_sft)

union	long_HL {
	struct	{ unsigned short L ; signed short H; } HL ;
	long	all ;
};

typedef struct { int x, y ;} QUAD ; 
typedef struct { int x1, y1, x2, y2 ;} D_QUAD ;
typedef struct { int pat, swi, x, y ;} DCPOS_S ;

typedef struct {
	short			pat, pal ;
	int 			size ;
	short			swi, c ;
	union long_HL	x, y ;
	short			ac, type, cn, ang ;
} EFFECT_S ;

typedef struct {
	union			long_HL x, y ;
	int				idx, pat, pal, dir, ajst ;
	int				slant, c ;
	short			swi, res1 ;
} BULLET_S ;

typedef struct {
	short idx, pat, pal, swi, ajst, x, y, slant, c, psc ;
} OPTION_S ;

typedef struct {
	union			long_HL x, y ;
	int				size, idx, pat, pal, ppos, ajst ;
	int				MC_idx, stk_n, pat_ofs, c ;
	unsigned long	set_flag ;
	short			ang, ang_sft ;
	int				swi, res1, through, connect ;
	int				efx_n ;
	short			psn, psc ;
	OPTION_S		opt ;
} DSPCH_S ;

extern	DSPCH_S			chr[];
extern	DCPOS_S			chr_pos[];
extern	BULLET_S		bullet[];
extern	EFFECT_S		effect_ch[];
extern	int				show_max, bullet_vol ;
extern	int				efxch_c, efxch_spc ;
extern	unsigned short	spr_dir[];

int		chrs_entry( int swi );
int		chrs_put( int max, int xm, int ym );

/***  パターンストック  ***/

#define PPOS_BLMT	( 32 * 8 )
#define PHIT_BLMT	( 32 * 8 )

typedef struct {
	short		pat, opt ;
	char		*buf ;
} PTENT_S ;

extern PTENT_S	patstk_ent[];
extern QUAD		pat_pos[], opt_pos[], efx_pos[];
extern D_QUAD	pat_hit[], opt_hit[];
