fix hyprduel to boot [Hau]

This commit is contained in:
Yasuhiro Ogawa 2009-03-28 16:26:45 +00:00
parent dc169055da
commit d15c4e0d3f
3 changed files with 155 additions and 153 deletions

View File

@ -23,7 +23,7 @@ Imagetek Inc 14220 071
-- --
Written by Hau Written by Hau
03/27/2009 03/28/2009
based on driver from drivers/metro.c by Luca Elia based on driver from drivers/metro.c by Luca Elia
spthx to kikur,Cha,teioh,kokkyu,teruchu,aya,sgo spthx to kikur,Cha,teioh,kokkyu,teruchu,aya,sgo
--- ---
@ -43,7 +43,6 @@ fix comms so it boots, it's a bit of a hack for hyperduel at the moment ;-)
#include "includes/hyprduel.h" #include "includes/hyprduel.h"
int rastersplit;
static int blitter_bit; static int blitter_bit;
static int requested_int; static int requested_int;
static UINT16 *hypr_irq_enable; static UINT16 *hypr_irq_enable;
@ -81,10 +80,8 @@ static INTERRUPT_GEN( hyprduel_interrupt )
cpu_set_input_line(device->machine->cpu[1], 1, HOLD_LINE); cpu_set_input_line(device->machine->cpu[1], 1, HOLD_LINE);
/* the duration is a guess */ /* the duration is a guess */
timer_set(device->machine, ATTOTIME_IN_USEC(2500), NULL, 0x20, vblank_end_callback); timer_set(device->machine, ATTOTIME_IN_USEC(2500), NULL, 0x20, vblank_end_callback);
rastersplit = 0;
} else { } else {
requested_int |= 0x12; /* hsync */ requested_int |= 0x12; /* hsync */
rastersplit = line + 1;
} }
update_irq_state(device->machine); update_irq_state(device->machine);
@ -165,14 +162,12 @@ static UINT16 *hyprduel_rombank;
static READ16_HANDLER( hyprduel_bankedrom_r ) static READ16_HANDLER( hyprduel_bankedrom_r )
{ {
const char *region = "gfx1"; UINT8 *ROM = memory_region( space->machine, "gfx1" );
size_t len = memory_region_length( space->machine, "gfx1" );
UINT8 *ROM = memory_region( space->machine, region );
size_t len = memory_region_length( space->machine, region );
offset = offset * 2 + 0x10000 * (*hyprduel_rombank); offset = offset * 2 + 0x10000 * (*hyprduel_rombank);
if ( offset < len ) return ((ROM[offset+0]<<8)+ROM[offset+1])^0xffff; if ( offset < len ) return ((ROM[offset+0]<<8)+ROM[offset+1]);
else return 0xffff; else return 0xffff;
} }
@ -230,7 +225,7 @@ static TIMER_CALLBACK( hyprduel_blit_done )
INLINE int blt_read(const UINT8 *ROM, const int offs) INLINE int blt_read(const UINT8 *ROM, const int offs)
{ {
return ROM[offs] ^ 0xff; return ROM[offs];
} }
INLINE void blt_write(const address_space *space, const int tmap, const offs_t offs, const UINT16 data, const UINT16 mask) INLINE void blt_write(const address_space *space, const int tmap, const offs_t offs, const UINT16 data, const UINT16 mask)
@ -251,10 +246,8 @@ static WRITE16_HANDLER( hyprduel_blitter_w )
if (offset == 0xC/2) if (offset == 0xC/2)
{ {
const char *region = "gfx1"; UINT8 *src = memory_region(space->machine, "gfx1");
size_t src_len = memory_region_length(space->machine, "gfx1");
UINT8 *src = memory_region(space->machine, region);
size_t src_len = memory_region_length(space->machine, region);
UINT32 tmap = (hyprduel_blitter_regs[ 0x00 / 2 ] << 16 ) + UINT32 tmap = (hyprduel_blitter_regs[ 0x00 / 2 ] << 16 ) +
hyprduel_blitter_regs[ 0x02 / 2 ]; hyprduel_blitter_regs[ 0x02 / 2 ];
@ -264,7 +257,7 @@ static WRITE16_HANDLER( hyprduel_blitter_w )
hyprduel_blitter_regs[ 0x0a / 2 ]; hyprduel_blitter_regs[ 0x0a / 2 ];
int shift = (dst_offs & 0x80) ? 0 : 8; int shift = (dst_offs & 0x80) ? 0 : 8;
UINT16 mask = (dst_offs & 0x80) ? 0xff00 : 0x00ff; UINT16 mask = (dst_offs & 0x80) ? 0x00ff : 0xff00;
// logerror("CPU #0 PC %06X : Blitter regs %08X, %08X, %08X\n",cpu_get_pc(space->cpu),tmap,src_offs,dst_offs); // logerror("CPU #0 PC %06X : Blitter regs %08X, %08X, %08X\n",cpu_get_pc(space->cpu),tmap,src_offs,dst_offs);
@ -395,8 +388,8 @@ static ADDRESS_MAP_START( hyprduel_map, ADDRESS_SPACE_PROGRAM, 16 )
AM_RANGE(0x478000, 0x4787ff) AM_RAM AM_BASE(&hyprduel_tiletable) AM_SIZE(&hyprduel_tiletable_size) /* Tiles Set */ AM_RANGE(0x478000, 0x4787ff) AM_RAM AM_BASE(&hyprduel_tiletable) AM_SIZE(&hyprduel_tiletable_size) /* Tiles Set */
AM_RANGE(0x478840, 0x47884d) AM_WRITE(hyprduel_blitter_w) AM_BASE(&hyprduel_blitter_regs) /* Tiles Blitter */ AM_RANGE(0x478840, 0x47884d) AM_WRITE(hyprduel_blitter_w) AM_BASE(&hyprduel_blitter_regs) /* Tiles Blitter */
AM_RANGE(0x478860, 0x47886b) AM_WRITE(hyprduel_window_w) AM_BASE(&hyprduel_window) /* Tilemap Window */ AM_RANGE(0x478860, 0x47886b) AM_WRITE(hyprduel_window_w) AM_BASE(&hyprduel_window) /* Tilemap Window */
AM_RANGE(0x478870, 0x47887b) AM_WRITE(hypr_scrollreg_w) /* Scroll Regs */ AM_RANGE(0x478870, 0x47887b) AM_RAM_WRITE(hyprduel_scrollreg_w) AM_BASE(&hyprduel_scroll) /* Scroll Regs */
AM_RANGE(0x47887c, 0x47887d) AM_WRITE(hypr_scrollreg_init_w) AM_RANGE(0x47887c, 0x47887d) AM_WRITE(hyprduel_scrollreg_init_w)
AM_RANGE(0x478880, 0x478881) AM_WRITENOP AM_RANGE(0x478880, 0x478881) AM_WRITENOP
AM_RANGE(0x478890, 0x478891) AM_WRITENOP AM_RANGE(0x478890, 0x478891) AM_WRITENOP
AM_RANGE(0x4788a0, 0x4788a1) AM_WRITENOP AM_RANGE(0x4788a0, 0x4788a1) AM_WRITENOP
@ -442,8 +435,8 @@ static ADDRESS_MAP_START( magerror_map, ADDRESS_SPACE_PROGRAM, 16 )
AM_RANGE(0x878000, 0x8787ff) AM_RAM AM_BASE(&hyprduel_tiletable) AM_SIZE(&hyprduel_tiletable_size) /* Tiles Set */ AM_RANGE(0x878000, 0x8787ff) AM_RAM AM_BASE(&hyprduel_tiletable) AM_SIZE(&hyprduel_tiletable_size) /* Tiles Set */
AM_RANGE(0x878840, 0x87884d) AM_WRITE(hyprduel_blitter_w) AM_BASE(&hyprduel_blitter_regs) /* Tiles Blitter */ AM_RANGE(0x878840, 0x87884d) AM_WRITE(hyprduel_blitter_w) AM_BASE(&hyprduel_blitter_regs) /* Tiles Blitter */
AM_RANGE(0x878860, 0x87886b) AM_WRITE(hyprduel_window_w) AM_BASE(&hyprduel_window) /* Tilemap Window */ AM_RANGE(0x878860, 0x87886b) AM_WRITE(hyprduel_window_w) AM_BASE(&hyprduel_window) /* Tilemap Window */
AM_RANGE(0x878870, 0x87887b) AM_WRITE(hypr_scrollreg_w) /* Scroll Regs */ AM_RANGE(0x878870, 0x87887b) AM_RAM_WRITE(hyprduel_scrollreg_w) AM_BASE(&hyprduel_scroll) /* Scroll Regs */
AM_RANGE(0x87887c, 0x87887d) AM_WRITE(hypr_scrollreg_init_w) AM_RANGE(0x87887c, 0x87887d) AM_WRITE(hyprduel_scrollreg_init_w)
AM_RANGE(0x878880, 0x878881) AM_WRITENOP AM_RANGE(0x878880, 0x878881) AM_WRITENOP
AM_RANGE(0x878890, 0x878891) AM_WRITENOP AM_RANGE(0x878890, 0x878891) AM_WRITENOP
AM_RANGE(0x8788a0, 0x8788a1) AM_WRITENOP AM_RANGE(0x8788a0, 0x8788a1) AM_WRITENOP
@ -598,11 +591,15 @@ static MACHINE_RESET( hyprduel )
/* start with cpu2 halted */ /* start with cpu2 halted */
cpu_set_input_line(machine->cpu[1], INPUT_LINE_RESET, ASSERT_LINE); cpu_set_input_line(machine->cpu[1], INPUT_LINE_RESET, ASSERT_LINE);
subcpu_resetline = 1; subcpu_resetline = 1;
requested_int = 0x00;
blitter_bit = 2;
*hypr_irq_enable = 0xff;
} }
static MACHINE_START( magerror ) static MACHINE_START( magerror )
{ {
timer_adjust_periodic(magerror_irq_timer, attotime_zero, 0, ATTOTIME_IN_HZ(896)); /* ? */ timer_adjust_periodic(magerror_irq_timer, attotime_zero, 0, ATTOTIME_IN_HZ(968)); /* ? */
} }
static MACHINE_DRIVER_START( hyprduel ) static MACHINE_DRIVER_START( hyprduel )
@ -618,6 +615,8 @@ static MACHINE_DRIVER_START( hyprduel )
MDRV_MACHINE_RESET(hyprduel) MDRV_MACHINE_RESET(hyprduel)
/* video hardware */ /* video hardware */
MDRV_VIDEO_ATTRIBUTES(VIDEO_UPDATE_SCANLINE)
MDRV_SCREEN_ADD("screen", RASTER) MDRV_SCREEN_ADD("screen", RASTER)
MDRV_SCREEN_REFRESH_RATE(60) MDRV_SCREEN_REFRESH_RATE(60)
MDRV_SCREEN_VBLANK_TIME(ATTOSECONDS_IN_USEC(0)) MDRV_SCREEN_VBLANK_TIME(ATTOSECONDS_IN_USEC(0))
@ -660,6 +659,8 @@ static MACHINE_DRIVER_START( magerror )
MDRV_MACHINE_RESET(hyprduel) MDRV_MACHINE_RESET(hyprduel)
/* video hardware */ /* video hardware */
MDRV_VIDEO_ATTRIBUTES(VIDEO_UPDATE_SCANLINE)
MDRV_SCREEN_ADD("screen", RASTER) MDRV_SCREEN_ADD("screen", RASTER)
MDRV_SCREEN_REFRESH_RATE(60) MDRV_SCREEN_REFRESH_RATE(60)
MDRV_SCREEN_VBLANK_TIME(ATTOSECONDS_IN_USEC(0)) MDRV_SCREEN_VBLANK_TIME(ATTOSECONDS_IN_USEC(0))
@ -738,28 +739,11 @@ ROM_END
static DRIVER_INIT( hyprduel ) static DRIVER_INIT( hyprduel )
{ {
int i, len = memory_region_length(machine, "gfx1");
UINT8 *ROM = memory_region(machine, "gfx1");
/*
Tiles can be either 4-bit or 8-bit, and both depths can be used at the same
time. The transparent pen is the last one, that is 15 or 255. To make
tilemap.c handle that, we invert gfx data so the transparent pen becomes 0
for both tile depths.
*/
for (i=0; i<len; i++)
ROM[i] ^= 0xff;
requested_int = 0x00;
blitter_bit = 2;
*hypr_irq_enable = 0xff;
int_num = 0x02; int_num = 0x02;
memory_install_read16_handler(cpu_get_address_space(machine->cpu[0], ADDRESS_SPACE_PROGRAM), 0xc00408, 0xc0040b, 0, 0, hypr_cpusync_r); memory_install_read16_handler(cpu_get_address_space(machine->cpu[0], ADDRESS_SPACE_PROGRAM), 0xc00408, 0xc0040b, 0, 0, hypr_cpusync_r);
/* Set up save state */ /* Set up save state */
state_save_register_global(machine, rastersplit);
state_save_register_global(machine, blitter_bit); state_save_register_global(machine, blitter_bit);
state_save_register_global(machine, requested_int); state_save_register_global(machine, requested_int);
state_save_register_global(machine, subcpu_resetline); state_save_register_global(machine, subcpu_resetline);

View File

@ -2,10 +2,6 @@
#define FIRST_VISIBLE_LINE 0 #define FIRST_VISIBLE_LINE 0
#define LAST_VISIBLE_LINE 223 #define LAST_VISIBLE_LINE 223
/*----------- defined in drivers/hyprduel.c -----------*/
extern int rastersplit;
/*----------- defined in video/hyprduel.c -----------*/ /*----------- defined in video/hyprduel.c -----------*/
extern UINT16 *hyprduel_videoregs; extern UINT16 *hyprduel_videoregs;
@ -14,13 +10,15 @@ extern UINT16 *hyprduel_tiletable;
extern size_t hyprduel_tiletable_size; extern size_t hyprduel_tiletable_size;
extern UINT16 *hyprduel_vram_0, *hyprduel_vram_1, *hyprduel_vram_2; extern UINT16 *hyprduel_vram_0, *hyprduel_vram_1, *hyprduel_vram_2;
extern UINT16 *hyprduel_window; extern UINT16 *hyprduel_window;
extern UINT16 *hyprduel_scroll;
WRITE16_HANDLER( hyprduel_paletteram_w ); WRITE16_HANDLER( hyprduel_paletteram_w );
WRITE16_HANDLER( hyprduel_window_w ); WRITE16_HANDLER( hyprduel_window_w );
WRITE16_HANDLER( hyprduel_vram_0_w ); WRITE16_HANDLER( hyprduel_vram_0_w );
WRITE16_HANDLER( hyprduel_vram_1_w ); WRITE16_HANDLER( hyprduel_vram_1_w );
WRITE16_HANDLER( hyprduel_vram_2_w ); WRITE16_HANDLER( hyprduel_vram_2_w );
WRITE16_HANDLER( hypr_scrollreg_w ); WRITE16_HANDLER( hyprduel_scrollreg_w );
WRITE16_HANDLER( hypr_scrollreg_init_w ); WRITE16_HANDLER( hyprduel_scrollreg_init_w );
VIDEO_START( hyprduel_14220 ); VIDEO_START( hyprduel_14220 );
VIDEO_UPDATE( hyprduel ); VIDEO_UPDATE( hyprduel );

View File

@ -65,15 +65,14 @@ UINT16 *hyprduel_tiletable;
size_t hyprduel_tiletable_size; size_t hyprduel_tiletable_size;
UINT16 *hyprduel_vram_0,*hyprduel_vram_1,*hyprduel_vram_2; UINT16 *hyprduel_vram_0,*hyprduel_vram_1,*hyprduel_vram_2;
UINT16 *hyprduel_window; UINT16 *hyprduel_window;
UINT16 *hyprduel_scroll;
static UINT16 hyprduel_scrollx[3][RASTER_LINES+1]; static UINT16 *hyprduel_tiletable_old;
static UINT16 hyprduel_scrolly[3][RASTER_LINES+1];
static UINT16 *hypr_tiletable_old;
static UINT8 *dirtyindex; static UINT8 *dirtyindex;
static int hyprduel_sprite_xoffs; static int hyprduel_sprite_xoffs;
static int hyprduel_sprite_yoffs; static int hyprduel_sprite_yoffs;
static int hyprduel_sprite_yoffs_magerror; static int hyprduel_sprite_yoffs_sub;
/*************************************************************************** /***************************************************************************
Palette GGGGGRRRRRBBBBBx Palette GGGGGRRRRRBBBBBx
@ -82,8 +81,7 @@ static int hyprduel_sprite_yoffs_magerror;
WRITE16_HANDLER( hyprduel_paletteram_w ) WRITE16_HANDLER( hyprduel_paletteram_w )
{ {
data = COMBINE_DATA(&paletteram16[offset]); data = COMBINE_DATA(&paletteram16[offset]);
/* We need the ^0xff because we had to invert the pens in the gfx */ palette_set_color_rgb(space->machine,offset,pal5bit(data >> 6),pal5bit(data >> 11),pal5bit(data >> 1));
palette_set_color_rgb(space->machine,offset^0xff,pal5bit(data >> 6),pal5bit(data >> 11),pal5bit(data >> 1));
} }
@ -125,7 +123,6 @@ static UINT8 *empty_tiles;
/* 8x8x4 tiles only */ /* 8x8x4 tiles only */
#ifdef UNUSED_FUNCTION
INLINE void get_tile_info(running_machine *machine,tile_data *tileinfo,int tile_index,int layer,UINT16 *vram) INLINE void get_tile_info(running_machine *machine,tile_data *tileinfo,int tile_index,int layer,UINT16 *vram)
{ {
UINT16 code; UINT16 code;
@ -148,17 +145,20 @@ INLINE void get_tile_info(running_machine *machine,tile_data *tileinfo,int tile_
{ {
int _code = code & 0x000f; int _code = code & 0x000f;
tileinfo->pen_data = empty_tiles + _code*16*16; tileinfo->pen_data = empty_tiles + _code*16*16;
tileinfo->palette_base = ((code & 0x0ff0) ^ 0x0f0) + 0x1000; tileinfo->palette_base = ((code & 0x0ff0)) + 0x1000;
tileinfo->flags = 0; tileinfo->flags = 0;
tileinfo->group = 0;
} }
else else
{
tileinfo->group = 0;
SET_TILE_INFO( SET_TILE_INFO(
0, 0,
(tile & 0xfffff) + (code & 0xf), (tile & 0xfffff) + (code & 0xf),
(((tile & 0x0ff00000) >> 20) ^ 0x0f) + 0x100, (((tile & 0x0ff00000) >> 20)) + 0x100,
TILE_FLIPXY((code & 0x6000) >> 13)); TILE_FLIPXY((code & 0x6000) >> 13));
}
} }
#endif
/* 8x8x4 or 8x8x8 tiles. It's the tile's color that decides: if its low 4 /* 8x8x4 or 8x8x8 tiles. It's the tile's color that decides: if its low 4
bits are high ($f,$1f,$2f etc) the tile is 8bpp, otherwise it's 4bpp */ bits are high ($f,$1f,$2f etc) the tile is 8bpp, otherwise it's 4bpp */
@ -184,26 +184,32 @@ INLINE void get_tile_info_8bit(running_machine *machine,tile_data *tileinfo,int
{ {
int _code = code & 0x000f; int _code = code & 0x000f;
tileinfo->pen_data = empty_tiles + _code*16*16; tileinfo->pen_data = empty_tiles + _code*16*16;
tileinfo->palette_base = ((code & 0x0ff0) ^ 0x0f0) + 0x1000; tileinfo->palette_base = ((code & 0x0ff0)) + 0x1000;
tileinfo->flags = 0; tileinfo->flags = 0;
tileinfo->group = 0;
} }
else if ((tile & 0x00f00000)==0x00f00000) /* draw tile as 8bpp */ else if ((tile & 0x00f00000)==0x00f00000) /* draw tile as 8bpp */
{
tileinfo->group = 1;
SET_TILE_INFO( SET_TILE_INFO(
1, 1,
(tile & 0xfffff) + 2*(code & 0xf), (tile & 0xfffff) + 2*(code & 0xf),
((tile & 0x0f000000) >> 24) + 0x10, ((tile & 0x0f000000) >> 24) + 0x10,
TILE_FLIPXY((code & 0x6000) >> 13)); TILE_FLIPXY((code & 0x6000) >> 13));
}
else else
{
tileinfo->group = 0;
SET_TILE_INFO( SET_TILE_INFO(
0, 0,
(tile & 0xfffff) + (code & 0xf), (tile & 0xfffff) + (code & 0xf),
(((tile & 0x0ff00000) >> 20) ^ 0x0f) + 0x100, (((tile & 0x0ff00000) >> 20)) + 0x100,
TILE_FLIPXY((code & 0x6000) >> 13)); TILE_FLIPXY((code & 0x6000) >> 13));
}
} }
/* 16x16x4 or 16x16x8 tiles. It's the tile's color that decides: if its low 4 /* 16x16x4 or 16x16x8 tiles. It's the tile's color that decides: if its low 4
bits are high ($f,$1f,$2f etc) the tile is 8bpp, otherwise it's 4bpp */ bits are high ($f,$1f,$2f etc) the tile is 8bpp, otherwise it's 4bpp */
#ifdef UNUSED_FUNCTION
INLINE void get_tile_info_16x16_8bit(running_machine *machine,tile_data *tileinfo,int tile_index,int layer,UINT16 *vram) INLINE void get_tile_info_16x16_8bit(running_machine *machine,tile_data *tileinfo,int tile_index,int layer,UINT16 *vram)
{ {
UINT16 code; UINT16 code;
@ -226,28 +232,34 @@ INLINE void get_tile_info_16x16_8bit(running_machine *machine,tile_data *tileinf
{ {
int _code = code & 0x000f; int _code = code & 0x000f;
tileinfo->pen_data = empty_tiles + _code*16*16; tileinfo->pen_data = empty_tiles + _code*16*16;
tileinfo->palette_base = ((code & 0x0ff0) ^ 0x0f0) + 0x1000; tileinfo->palette_base = ((code & 0x0ff0)) + 0x1000;
tileinfo->flags = 0; tileinfo->flags = 0;
tileinfo->group = 0;
} }
else if ((tile & 0x00f00000)==0x00f00000) /* draw tile as 8bpp */ else if ((tile & 0x00f00000)==0x00f00000) /* draw tile as 8bpp */
{
tileinfo->group = 1;
SET_TILE_INFO( SET_TILE_INFO(
3, 3,
(tile & 0xfffff) + 8*(code & 0xf), (tile & 0xfffff) + 8*(code & 0xf),
((tile & 0x0f000000) >> 24) + 0x10, ((tile & 0x0f000000) >> 24) + 0x10,
TILE_FLIPXY((code & 0x6000) >> 13)); TILE_FLIPXY((code & 0x6000) >> 13));
}
else else
{
tileinfo->group = 0;
SET_TILE_INFO( SET_TILE_INFO(
2, 2,
(tile & 0xfffff) + 4*(code & 0xf), (tile & 0xfffff) + 4*(code & 0xf),
(((tile & 0x0ff00000) >> 20) ^ 0x0f) + 0x100, (((tile & 0x0ff00000) >> 20)) + 0x100,
TILE_FLIPXY((code & 0x6000) >> 13)); TILE_FLIPXY((code & 0x6000) >> 13));
}
} }
#endif
INLINE void hyprduel_vram_w(offs_t offset,UINT16 data,UINT16 mem_mask,int layer,UINT16 *vram) INLINE void hyprduel_vram_w(offs_t offset,UINT16 data,UINT16 mem_mask,int layer,UINT16 *vram)
{ {
COMBINE_DATA(&vram[offset]); COMBINE_DATA(&vram[offset]);
{ {
/* Account for the window */ /* Account for the window */
int col = (offset % BIG_NX) - ((hyprduel_window[layer * 2 + 1] / 8) % BIG_NX); int col = (offset % BIG_NX) - ((hyprduel_window[layer * 2 + 1] / 8) % BIG_NX);
@ -285,7 +297,6 @@ WRITE16_HANDLER( hyprduel_window_w )
} }
} }
/*************************************************************************** /***************************************************************************
Video Init Routines Video Init Routines
***************************************************************************/ ***************************************************************************/
@ -306,42 +317,60 @@ static void alloc_empty_tiles(void)
for (code = 0;code < 0x10;code++) for (code = 0;code < 0x10;code++)
for (i = 0;i < 16*16;i++) for (i = 0;i < 16*16;i++)
empty_tiles[16*16*code + i] = code ^ 0x0f; empty_tiles[16*16*code + i] = code;
} }
static STATE_POSTLOAD( hyprduel_postload )
{
int i;
for (i=0; i<3; i++)
{
UINT16 wx = hyprduel_window[i * 2 + 1];
UINT16 wy = hyprduel_window[i * 2 + 0];
tilemap_set_scrollx(bg_tilemap[i], 0, hyprduel_scroll[i * 2 + 1] - wx - (wx & 7));
tilemap_set_scrolly(bg_tilemap[i], 0, hyprduel_scroll[i * 2 + 0] - wy - (wy & 7));
tilemap_mark_all_tiles_dirty(bg_tilemap[i]);
}
}
VIDEO_START( hyprduel_14220 ) VIDEO_START( hyprduel_14220 )
{ {
alloc_empty_tiles(); alloc_empty_tiles();
hypr_tiletable_old = auto_malloc(hyprduel_tiletable_size); hyprduel_tiletable_old = auto_malloc(hyprduel_tiletable_size);
dirtyindex = auto_malloc(hyprduel_tiletable_size/4); dirtyindex = auto_malloc(hyprduel_tiletable_size/4);
bg_tilemap[0] = tilemap_create(machine, get_tile_info_0_8bit,tilemap_scan_rows,8,8,WIN_NX,WIN_NY); bg_tilemap[0] = tilemap_create(machine, get_tile_info_0_8bit,tilemap_scan_rows,8,8,WIN_NX,WIN_NY);
bg_tilemap[1] = tilemap_create(machine, get_tile_info_1_8bit,tilemap_scan_rows,8,8,WIN_NX,WIN_NY); bg_tilemap[1] = tilemap_create(machine, get_tile_info_1_8bit,tilemap_scan_rows,8,8,WIN_NX,WIN_NY);
bg_tilemap[2] = tilemap_create(machine, get_tile_info_2_8bit,tilemap_scan_rows,8,8,WIN_NX,WIN_NY); bg_tilemap[2] = tilemap_create(machine, get_tile_info_2_8bit,tilemap_scan_rows,8,8,WIN_NX,WIN_NY);
tilemap_set_transparent_pen(bg_tilemap[0],0); tilemap_map_pen_to_layer(bg_tilemap[0], 0, 15, TILEMAP_PIXEL_TRANSPARENT);
tilemap_set_transparent_pen(bg_tilemap[1],0); tilemap_map_pen_to_layer(bg_tilemap[0], 1, 255, TILEMAP_PIXEL_TRANSPARENT);
tilemap_set_transparent_pen(bg_tilemap[2],0);
tilemap_map_pen_to_layer(bg_tilemap[1], 0, 15, TILEMAP_PIXEL_TRANSPARENT);
tilemap_map_pen_to_layer(bg_tilemap[1], 1, 255, TILEMAP_PIXEL_TRANSPARENT);
tilemap_map_pen_to_layer(bg_tilemap[2], 0, 15, TILEMAP_PIXEL_TRANSPARENT);
tilemap_map_pen_to_layer(bg_tilemap[2], 1, 255, TILEMAP_PIXEL_TRANSPARENT);
tilemap_set_scrolldx(bg_tilemap[0], 0, 0); tilemap_set_scrolldx(bg_tilemap[0], 0, 0);
tilemap_set_scrolldx(bg_tilemap[1], 0, 0); tilemap_set_scrolldx(bg_tilemap[1], 0, 0);
tilemap_set_scrolldx(bg_tilemap[2], 0, 0); tilemap_set_scrolldx(bg_tilemap[2], 0, 0);
if (!strcmp(machine->gamedrv->name, "magerror")) if (!strcmp(machine->gamedrv->name, "magerror"))
hyprduel_sprite_yoffs_magerror = 2; hyprduel_sprite_yoffs_sub = 0;
else else
hyprduel_sprite_yoffs_magerror = 0; hyprduel_sprite_yoffs_sub = 2;
/* Set up save state */ /* Set up save state */
state_save_register_global_array(machine, hyprduel_scrollx[0]);
state_save_register_global_array(machine, hyprduel_scrollx[1]);
state_save_register_global_array(machine, hyprduel_scrollx[2]);
state_save_register_global_array(machine, hyprduel_scrolly[0]);
state_save_register_global_array(machine, hyprduel_scrolly[1]);
state_save_register_global_array(machine, hyprduel_scrolly[2]);
state_save_register_global(machine, hyprduel_sprite_xoffs); state_save_register_global(machine, hyprduel_sprite_xoffs);
state_save_register_global(machine, hyprduel_sprite_yoffs); state_save_register_global(machine, hyprduel_sprite_yoffs);
state_save_register_global(machine, hyprduel_sprite_yoffs_magerror); state_save_register_global(machine, hyprduel_sprite_yoffs_sub);
state_save_register_postload(machine, hyprduel_postload, NULL);
} }
/*************************************************************************** /***************************************************************************
@ -373,35 +402,6 @@ VIDEO_START( hyprduel_14220 )
***************************************************************************/ ***************************************************************************/
WRITE16_HANDLER( hypr_scrollreg_w )
{
int i;
if (offset & 0x01)
{
for (i = rastersplit; i < RASTER_LINES; i++)
hyprduel_scrollx[offset>>1][i] = data;
} else {
for (i = rastersplit; i < RASTER_LINES; i++)
hyprduel_scrolly[offset>>1][i] = data;
}
}
WRITE16_HANDLER( hypr_scrollreg_init_w )
{
int i;
for (i = 0; i < RASTER_LINES; i++)
{
hyprduel_scrollx[0][i] = data;
hyprduel_scrollx[1][i] = data;
hyprduel_scrollx[2][i] = data;
hyprduel_scrolly[0][i] = data;
hyprduel_scrolly[1][i] = data;
hyprduel_scrolly[2][i] = data;
}
}
/*************************************************************************** /***************************************************************************
Sprites Drawing Sprites Drawing
@ -430,12 +430,10 @@ WRITE16_HANDLER( hypr_scrollreg_init_w )
/* Draw sprites */ /* Draw sprites */
static void draw_sprites(running_machine *machine, bitmap_t *bitmap, const rectangle *cliprect) void draw_sprites(running_machine *machine, bitmap_t *bitmap, const rectangle *cliprect)
{ {
const char * region = "gfx1"; UINT8 *base_gfx = memory_region(machine, "gfx1");
UINT8 *gfx_max = base_gfx + memory_region_length(machine, "gfx1");
UINT8 *base_gfx = memory_region(machine, region);
UINT8 *gfx_max = base_gfx + memory_region_length(machine, region);
int max_x = video_screen_get_width(machine->primary_screen); int max_x = video_screen_get_width(machine->primary_screen);
int max_y = video_screen_get_height(machine->primary_screen); int max_y = video_screen_get_height(machine->primary_screen);
@ -445,18 +443,31 @@ static void draw_sprites(running_machine *machine, bitmap_t *bitmap, const recta
int color_start = ((hyprduel_videoregs[0x08/2] & 0xf) << 4 ) + 0x100; int color_start = ((hyprduel_videoregs[0x08/2] & 0xf) << 4 ) + 0x100;
int i, pri; int i, j, pri;
static const int primask[4] = { 0x0000, 0xff00, 0xff00|0xf0f0, 0xff00|0xf0f0|0xcccc }; static const int primask[4] = { 0x0000, 0xff00, 0xff00|0xf0f0, 0xff00|0xf0f0|0xcccc };
UINT16 *src;
int inc;
if (sprites == 0)
return;
for (i=0; i<0x20; i++) for (i=0; i<0x20; i++)
{ {
UINT16 *src = spriteram16 + (sprites - 1) * (8/2); gfx_element gfx;
UINT16 *end = spriteram16;
for ( ; src >= end; src -= 8/2 ) if (!(hyprduel_videoregs[0x02/2] & 0x8000))
{
src = spriteram16 + (sprites - 1) * (8/2);
inc = -(8/2);
} else {
src = spriteram16;
inc = (8/2);
}
for (j=0; j<sprites; j++)
{ {
int x,y, attr,code,color,flipx,flipy, zoom, curr_pri,width,height; int x,y, attr,code,color,flipx,flipy, zoom, curr_pri,width,height;
gfx_element gfx;
UINT8 *gfxdata; UINT8 *gfxdata;
/* Exponential zoom table extracted from daitoride */ /* Exponential zoom table extracted from daitoride */
@ -472,7 +483,12 @@ static void draw_sprites(running_machine *machine, bitmap_t *bitmap, const recta
x = src[ 0 ]; x = src[ 0 ];
curr_pri = (x & 0xf800) >> 11; curr_pri = (x & 0xf800) >> 11;
if ((curr_pri == 0x1f) || (curr_pri != i)) continue;
if ((curr_pri == 0x1f) || (curr_pri != i))
{
src += inc;
continue;
}
pri = (hyprduel_videoregs[0x02/2] & 0x0300) >> 8; pri = (hyprduel_videoregs[0x02/2] & 0x0300) >> 8;
@ -493,7 +509,7 @@ static void draw_sprites(running_machine *machine, bitmap_t *bitmap, const recta
zoom = zoomtable[(y & 0xfc00) >> 10] << (16-8); zoom = zoomtable[(y & 0xfc00) >> 10] << (16-8);
x = (x & 0x07ff) - hyprduel_sprite_xoffs; x = (x & 0x07ff) - hyprduel_sprite_xoffs;
y = (y & 0x03ff) - hyprduel_sprite_yoffs +2; y = (y & 0x03ff) - hyprduel_sprite_yoffs;
width = (( (attr >> 11) & 0x7 ) + 1 ) * 8; width = (( (attr >> 11) & 0x7 ) + 1 ) * 8;
height = (( (attr >> 8) & 0x7 ) + 1 ) * 8; height = (( (attr >> 8) & 0x7 ) + 1 ) * 8;
@ -519,7 +535,7 @@ static void draw_sprites(running_machine *machine, bitmap_t *bitmap, const recta
color_start >> 4, color_start >> 4,
flipx, flipy, flipx, flipy,
x, y, x, y,
cliprect, TRANSPARENCY_PEN, 0, cliprect, TRANSPARENCY_PEN, 255,
zoom, zoom, zoom, zoom,
primask[pri]); primask[pri]);
} }
@ -533,10 +549,10 @@ static void draw_sprites(running_machine *machine, bitmap_t *bitmap, const recta
pdrawgfxzoom( bitmap,&gfx, pdrawgfxzoom( bitmap,&gfx,
0, 0,
(color ^ 0x0f) + color_start, color + color_start,
flipx, flipy, flipx, flipy,
x, y, x, y,
cliprect, TRANSPARENCY_PEN, 0, cliprect, TRANSPARENCY_PEN, 15,
zoom, zoom, zoom, zoom,
primask[pri]); primask[pri]);
} }
@ -547,54 +563,61 @@ static void draw_sprites(running_machine *machine, bitmap_t *bitmap, const recta
ui_draw_text(buf, x, y); ui_draw_text(buf, x, y);
} }
#endif #endif
src += inc;
} }
} }
} }
/*************************************************************************** /***************************************************************************
Screen Drawing Screen Drawing
***************************************************************************/ ***************************************************************************/
/* Draw all the layers that match the given priority */ WRITE16_HANDLER( hyprduel_scrollreg_w )
{
UINT16 window = hyprduel_window[offset];
COMBINE_DATA(&hyprduel_scroll[offset]);
if (offset & 0x01)
tilemap_set_scrollx(bg_tilemap[offset / 2], 0, hyprduel_scroll[offset] - window - (window & 7));
else
tilemap_set_scrolly(bg_tilemap[offset / 2], 0, hyprduel_scroll[offset] - window - (window & 7));
}
WRITE16_HANDLER( hyprduel_scrollreg_init_w )
{
int i;
for (i=0; i<3; i++)
{
UINT16 wx = hyprduel_window[i * 2 + 1];
UINT16 wy = hyprduel_window[i * 2 + 0];
hyprduel_scroll[i * 2 + 1] = data;
hyprduel_scroll[i * 2 + 0] = data;
tilemap_set_scrollx(bg_tilemap[i], 0, data - wx - (wx & 7));
tilemap_set_scrolly(bg_tilemap[i], 0, data - wy - (wy & 7));
}
}
static void draw_layers(bitmap_t *bitmap, const rectangle *cliprect, int pri, int layers_ctrl) static void draw_layers(bitmap_t *bitmap, const rectangle *cliprect, int pri, int layers_ctrl)
{ {
UINT16 layers_pri = hyprduel_videoregs[0x10/2]; UINT16 layers_pri = hyprduel_videoregs[0x10/2];
int layer; int layer;
int offs;
rectangle clip;
clip.min_x = 0;
clip.max_x = 319;
/* Draw all the layers with priority == pri */ /* Draw all the layers with priority == pri */
for (layer = 2; layer >= 0; layer--) // tilemap[2] below? for (layer = 2; layer >= 0; layer--) // tilemap[2] below?
{ {
if ( pri == ((layers_pri >> (layer*2)) & 3) ) if ( pri == ((layers_pri >> (layer*2)) & 3) )
{ {
/* Scroll and Window values */ if (layers_ctrl & (1<<layer)) // for debug
UINT16 wx = hyprduel_window[layer * 2 + 1]; tilemap_draw(bitmap,cliprect,bg_tilemap[layer], 0, 1<<(3-pri));
UINT16 wy = hyprduel_window[layer * 2 + 0];
wx = wx - (wx & 7);
wy = wy - (wy & 7);
if (layers_ctrl & (1<<layer))
{
for (offs = cliprect->min_y; offs <= cliprect->max_y; offs++)
{
clip.min_y = offs;
clip.max_y = offs;
tilemap_set_scrollx(bg_tilemap[layer], 0, hyprduel_scrollx[layer][offs+RASTER_LINES-(LAST_VISIBLE_LINE+1)] - wx);
tilemap_set_scrolly(bg_tilemap[layer], 0, hyprduel_scrolly[layer][offs+RASTER_LINES-(LAST_VISIBLE_LINE+1)] - wy);
tilemap_draw(bitmap,&clip,bg_tilemap[layer], 0, 1<<(3-pri));
}
}
} }
} }
} }
/* Dirty tilemaps when the tiles set changes */ /* Dirty tilemaps when the tiles set changes */
static void dirty_tiles(int layer,UINT16 *vram) static void dirty_tiles(int layer,UINT16 *vram)
{ {
@ -627,7 +650,7 @@ VIDEO_UPDATE( hyprduel )
for (i = 0;i < hyprduel_tiletable_size/4;i++) for (i = 0;i < hyprduel_tiletable_size/4;i++)
{ {
UINT32 tile_new = (hyprduel_tiletable[2*i + 0] << 16 ) + hyprduel_tiletable[2*i + 1]; UINT32 tile_new = (hyprduel_tiletable[2*i + 0] << 16 ) + hyprduel_tiletable[2*i + 1];
UINT32 tile_old = (hypr_tiletable_old[2*i + 0] << 16 ) + hypr_tiletable_old[2*i + 1]; UINT32 tile_old = (hyprduel_tiletable_old[2*i + 0] << 16 ) + hyprduel_tiletable_old[2*i + 1];
if ((tile_new ^ tile_old) & 0x0fffffff) if ((tile_new ^ tile_old) & 0x0fffffff)
{ {
@ -635,7 +658,7 @@ VIDEO_UPDATE( hyprduel )
dirty = 1; dirty = 1;
} }
} }
memcpy(hypr_tiletable_old,hyprduel_tiletable,hyprduel_tiletable_size); memcpy(hyprduel_tiletable_old,hyprduel_tiletable,hyprduel_tiletable_size);
if (dirty) if (dirty)
{ {
@ -646,11 +669,11 @@ VIDEO_UPDATE( hyprduel )
} }
hyprduel_sprite_xoffs = hyprduel_videoregs[0x06/2] - video_screen_get_width(screen) / 2; hyprduel_sprite_xoffs = hyprduel_videoregs[0x06/2] - video_screen_get_width(screen) / 2;
hyprduel_sprite_yoffs = hyprduel_videoregs[0x04/2] - video_screen_get_height(screen) / 2 + hyprduel_sprite_yoffs_magerror; hyprduel_sprite_yoffs = hyprduel_videoregs[0x04/2] - video_screen_get_height(screen) / 2 - hyprduel_sprite_yoffs_sub;
/* The background color is selected by a register */ /* The background color is selected by a register */
bitmap_fill(priority_bitmap,cliprect,0); bitmap_fill(priority_bitmap,cliprect,0);
bitmap_fill(bitmap,cliprect,((hyprduel_videoregs[0x12/2] & 0x0fff) ^ 0x0ff) + 0x1000); bitmap_fill(bitmap,cliprect,((hyprduel_videoregs[0x12/2] & 0x0fff)) + 0x1000);
/* Screen Control Register: /* Screen Control Register:
@ -666,10 +689,6 @@ VIDEO_UPDATE( hyprduel )
if (screenctrl & 2) return 0; if (screenctrl & 2) return 0;
flip_screen_set(screen->machine, screenctrl & 1); flip_screen_set(screen->machine, screenctrl & 1);
/* If the game supports 16x16 tiles, make sure that the
16x16 and 8x8 tilemaps of a given layer are not simultaneously
enabled! */
#if 0 #if 0
if (input_code_pressed(KEYCODE_Z)) if (input_code_pressed(KEYCODE_Z))
{ int msk = 0; { int msk = 0;
@ -692,5 +711,6 @@ if (input_code_pressed(KEYCODE_Z))
if (layers_ctrl & 0x08) if (layers_ctrl & 0x08)
draw_sprites(screen->machine,bitmap,cliprect); draw_sprites(screen->machine,bitmap,cliprect);
return 0; return 0;
} }