summaryrefslogtreecommitdiffstatshomepage
path: root/src/mame/video/ladybug.c
diff options
context:
space:
mode:
Diffstat (limited to 'src/mame/video/ladybug.c')
-rw-r--r--src/mame/video/ladybug.c475
1 files changed, 475 insertions, 0 deletions
diff --git a/src/mame/video/ladybug.c b/src/mame/video/ladybug.c
new file mode 100644
index 00000000000..08a4f6b77bc
--- /dev/null
+++ b/src/mame/video/ladybug.c
@@ -0,0 +1,475 @@
+/***************************************************************************
+
+ video.c
+
+ Functions to emulate the video hardware of the machine.
+
+***************************************************************************/
+
+#include "driver.h"
+
+/* Use the Zero Hour star generator board */
+extern void redclash_set_stars_enable( UINT8 on );
+extern void redclash_update_stars_state(void);
+extern void redclash_set_stars_speed( UINT8 speed );
+extern void redclash_draw_stars(running_machine *machine, mame_bitmap *bitmap, const rectangle *cliprect, UINT8 palette_offset, UINT8 sraider, UINT8 firstx, UINT8 lastx);
+
+static tilemap *bg_tilemap;
+static tilemap *grid_tilemap;
+
+/***************************************************************************
+
+ Convert the color PROMs into a more useable format.
+
+ Lady Bug has a 32 bytes palette PROM and a 32 bytes sprite color lookup
+ table PROM.
+ The palette PROM is connected to the RGB output this way:
+
+ bit 7 -- inverter -- 220 ohm resistor -- BLUE
+ -- inverter -- 220 ohm resistor -- GREEN
+ -- inverter -- 220 ohm resistor -- RED
+ -- inverter -- 470 ohm resistor -- BLUE
+ -- unused
+ -- inverter -- 470 ohm resistor -- GREEN
+ -- unused
+ bit 0 -- inverter -- 470 ohm resistor -- RED
+
+***************************************************************************/
+PALETTE_INIT( ladybug )
+{
+ int i;
+
+ for (i = 0;i < 32;i++)
+ {
+ int bit1,bit2,r,g,b;
+
+
+ bit1 = (~color_prom[i] >> 0) & 0x01;
+ bit2 = (~color_prom[i] >> 5) & 0x01;
+ r = 0x47 * bit1 + 0x97 * bit2;
+ bit1 = (~color_prom[i] >> 2) & 0x01;
+ bit2 = (~color_prom[i] >> 6) & 0x01;
+ g = 0x47 * bit1 + 0x97 * bit2;
+ bit1 = (~color_prom[i] >> 4) & 0x01;
+ bit2 = (~color_prom[i] >> 7) & 0x01;
+ b = 0x47 * bit1 + 0x97 * bit2;
+ palette_set_color(machine,i,MAKE_RGB(r,g,b));
+ }
+
+ /* characters */
+ for (i = 0;i < 8;i++)
+ {
+ colortable[4 * i] = 0;
+ colortable[4 * i + 1] = i + 0x08;
+ colortable[4 * i + 2] = i + 0x10;
+ colortable[4 * i + 3] = i + 0x18;
+ }
+
+ /* sprites */
+ for (i = 0;i < 4 * 8;i++)
+ {
+ int bit0,bit1,bit2,bit3;
+
+
+ /* low 4 bits are for sprite n */
+ bit0 = (color_prom[i + 32] >> 3) & 0x01;
+ bit1 = (color_prom[i + 32] >> 2) & 0x01;
+ bit2 = (color_prom[i + 32] >> 1) & 0x01;
+ bit3 = (color_prom[i + 32] >> 0) & 0x01;
+ colortable[i + 4 * 8] = 1 * bit0 + 2 * bit1 + 4 * bit2 + 8 * bit3;
+
+ /* high 4 bits are for sprite n + 8 */
+ bit0 = (color_prom[i + 32] >> 7) & 0x01;
+ bit1 = (color_prom[i + 32] >> 6) & 0x01;
+ bit2 = (color_prom[i + 32] >> 5) & 0x01;
+ bit3 = (color_prom[i + 32] >> 4) & 0x01;
+ colortable[i + 4 * 16] = 1 * bit0 + 2 * bit1 + 4 * bit2 + 8 * bit3;
+ }
+}
+
+PALETTE_INIT( sraider )
+{
+ int i;
+
+ for (i = 0;i < 32;i++)
+ {
+ int bit1,bit2,r,g,b;
+
+
+ bit1 = (~color_prom[i] >> 3) & 0x01;
+ bit2 = (~color_prom[i] >> 0) & 0x01;
+ r = 0x47 * bit1 + 0x97 * bit2;
+ bit1 = (~color_prom[i] >> 5) & 0x01;
+ bit2 = (~color_prom[i] >> 4) & 0x01;
+ g = 0x47 * bit1 + 0x97 * bit2;
+ bit1 = (~color_prom[i] >> 7) & 0x01;
+ bit2 = (~color_prom[i] >> 6) & 0x01;
+ b = 0x47 * bit1 + 0x97 * bit2;
+ palette_set_color(machine,i,MAKE_RGB(r,g,b));
+ }
+
+ /* This is for the stars colors */
+ for (i = 32;i < 64;i++)
+ {
+ int bit1,bit2,r,g,b;
+
+
+ bit2 = (i >> 4) & 0x01;
+ bit1 = (i >> 3) & 0x01;
+ b = 0x47 * bit1 + 0x97 * bit2;
+ bit2 = (i >> 2) & 0x01;
+ bit1 = (i >> 1) & 0x01;
+ g = 0x47 * bit1 + 0x97 * bit2;
+ bit1 = i & 0x01;
+ r = 0x47 * bit1;
+ palette_set_color(machine,i,MAKE_RGB(r,g,b));
+ }
+
+ /* This is reserved for the grid color */
+ palette_set_color(machine,64,MAKE_RGB(0,0,0));
+
+ /* characters */
+ for (i = 0;i < 8;i++)
+ {
+ colortable[4 * i] = 0;
+ colortable[4 * i + 1] = i + 0x08;
+ colortable[4 * i + 2] = i + 0x10;
+ colortable[4 * i + 3] = i + 0x18;
+ }
+
+ /* sprites */
+ for (i = 0;i < 4 * 8;i++)
+ {
+ int bit0,bit1,bit2,bit3;
+
+
+ /* low 4 bits are for sprite n */
+ bit0 = (color_prom[i + 32] >> 3) & 0x01;
+ bit1 = (color_prom[i + 32] >> 2) & 0x01;
+ bit2 = (color_prom[i + 32] >> 1) & 0x01;
+ bit3 = (color_prom[i + 32] >> 0) & 0x01;
+ colortable[i + 4 * 8] = 1 * bit0 + 2 * bit1 + 4 * bit2 + 8 * bit3;
+
+ /* high 4 bits are for sprite n + 8 */
+ bit0 = (color_prom[i + 32] >> 7) & 0x01;
+ bit1 = (color_prom[i + 32] >> 6) & 0x01;
+ bit2 = (color_prom[i + 32] >> 5) & 0x01;
+ bit3 = (color_prom[i + 32] >> 4) & 0x01;
+ colortable[i + 4 * 16] = 1 * bit0 + 2 * bit1 + 4 * bit2 + 8 * bit3;
+ }
+
+ /* stationary part of grid */
+ colortable[32 + 64] = 0;
+ colortable[32 + 64 + 1] = 64;
+}
+
+WRITE8_HANDLER( ladybug_videoram_w )
+{
+ videoram[offset] = data;
+ tilemap_mark_tile_dirty(bg_tilemap, offset);
+}
+
+WRITE8_HANDLER( ladybug_colorram_w )
+{
+ colorram[offset] = data;
+ tilemap_mark_tile_dirty(bg_tilemap, offset);
+}
+
+WRITE8_HANDLER( ladybug_flipscreen_w )
+{
+ if (flip_screen != (data & 0x01))
+ {
+ flip_screen_set(data & 0x01);
+ tilemap_mark_all_tiles_dirty(ALL_TILEMAPS);
+ }
+}
+
+////////////////////////////////////////////////
+/* All this should probably go somewhere else */
+
+/* Sound comm between CPU's */
+static UINT8 sraider_sound_low;
+
+READ8_HANDLER( sraider_sound_low_r )
+{
+ return sraider_sound_low;
+}
+
+static UINT8 sraider_sound_high;
+
+READ8_HANDLER( sraider_sound_high_r )
+{
+ return sraider_sound_high;
+}
+
+WRITE8_HANDLER( sraider_sound_low_w )
+{
+ sraider_sound_low = data;
+}
+
+WRITE8_HANDLER( sraider_sound_high_w )
+{
+ sraider_sound_high = data;
+}
+
+/* Protection? */
+
+READ8_HANDLER( sraider_8005_r )
+{
+ /* This must return X011111X or cpu #1 will hang */
+ /* see code at rst $10 */
+ return 0x3e;
+}
+
+/* Unknown IO */
+
+static UINT8 sraider_wierd_value[8];
+static UINT8 sraider_0x30, sraider_0x38;
+
+WRITE8_HANDLER( sraider_misc_w )
+{
+ switch(offset)
+ {
+ /* These 8 bits are stored in the latch at A7 */
+ case 0x00:
+ case 0x01:
+ case 0x02:
+ case 0x03:
+ case 0x04:
+ case 0x05:
+ case 0x06:
+ case 0x07:
+ sraider_wierd_value[offset&7] = data&1;
+ break;
+ /* These 6 bits are stored in the latch at N7 */
+ case 0x08:
+ sraider_0x30 = data&0x3f;
+ break;
+ /* These 6 bits are stored in the latch at N8 */
+ case 0x10:
+ sraider_0x38 = data&0x3f;
+ break;
+ default:
+ mame_printf_debug("(%04X) write to %02X\n",activecpu_get_pc(),offset);
+ break;
+ }
+}
+
+////////////////////////////////////////////////////
+
+static UINT8 gridline[256];
+
+WRITE8_HANDLER( sraider_grid_data_w )
+{
+ static int x = 0;
+
+ if (x == 0)
+ {
+ tilemap_mark_all_tiles_dirty(grid_tilemap);
+ x = 1;
+ }
+ gridline[offset] = data;
+
+}
+
+WRITE8_HANDLER( sraider_io_w )
+{
+ // bit7 = flip
+ // bit6 = grid red
+ // bit5 = grid green
+ // bit4 = grid blue
+ // bit3 = enable stars
+ // bit210 = stars speed/dir
+
+ if (flip_screen != (data & 0x80))
+ {
+ flip_screen_set(data & 0x80);
+ tilemap_mark_all_tiles_dirty(ALL_TILEMAPS);
+ }
+
+ palette_set_color_rgb(Machine,64,
+ ((data&0x40)>>6)*0xff,
+ ((data&0x20)>>5)*0xff,
+ ((data&0x10)>>4)*0xff);
+
+ redclash_set_stars_enable((data&0x08)>>3);
+
+ /*
+ * There must be a subtle clocking difference between
+ * Space Raider and the other games using this star generator,
+ * hence the -1 here
+ */
+
+ redclash_set_stars_speed((data&0x07) - 1);
+}
+
+static TILE_GET_INFO( get_bg_tile_info )
+{
+ int code = videoram[tile_index] + 32 * (colorram[tile_index] & 0x08);
+ int color = colorram[tile_index] & 0x07;
+
+ SET_TILE_INFO(0, code, color, 0);
+}
+
+static TILE_GET_INFO( get_grid_tile_info )
+{
+ if (tile_index < 512)
+ SET_TILE_INFO(3, tile_index, 0, 0);
+ else
+ {
+ int temp = tile_index/32;
+ tile_index = (31 - temp) * 32 + (tile_index % 32);
+ SET_TILE_INFO(4, tile_index, 0, 0);
+ }
+}
+
+VIDEO_START( ladybug )
+{
+ bg_tilemap = tilemap_create(get_bg_tile_info, tilemap_scan_rows,
+ TILEMAP_TYPE_PEN, 8, 8, 32, 32);
+
+ tilemap_set_scroll_rows(bg_tilemap, 32);
+}
+
+VIDEO_START( sraider )
+{
+ grid_tilemap = tilemap_create(get_grid_tile_info, tilemap_scan_rows,
+ TILEMAP_TYPE_PEN, 8, 8, 32, 32);
+
+ tilemap_set_scroll_rows(grid_tilemap, 32);
+
+ bg_tilemap = tilemap_create(get_bg_tile_info, tilemap_scan_rows,
+ TILEMAP_TYPE_PEN, 8, 8, 32, 32);
+
+ tilemap_set_scroll_rows(bg_tilemap, 32);
+
+ tilemap_set_transparent_pen(grid_tilemap, 0);
+ tilemap_set_transparent_pen(bg_tilemap, 0);
+}
+
+static void draw_sprites(running_machine *machine, mame_bitmap *bitmap, const rectangle *cliprect)
+{
+ int offs;
+
+ for (offs = spriteram_size - 2*0x40;offs >= 2*0x40;offs -= 0x40)
+ {
+ int i = 0;
+
+ while (i < 0x40 && spriteram[offs + i] != 0)
+ i += 4;
+
+ while (i > 0)
+ {
+/*
+ abccdddd eeeeeeee fffghhhh iiiiiiii
+
+ a enable?
+ b size (0 = 8x8, 1 = 16x16)
+ cc flip
+ dddd y offset
+ eeeeeeee sprite code (shift right 2 bits for 16x16 sprites)
+ fff unknown
+ g sprite bank
+ hhhh color
+ iiiiiiii x position
+*/
+ i -= 4;
+
+ if (spriteram[offs + i] & 0x80)
+ {
+ if (spriteram[offs + i] & 0x40) /* 16x16 */
+ drawgfx(bitmap,machine->gfx[1],
+ (spriteram[offs + i + 1] >> 2) + 4 * (spriteram[offs + i + 2] & 0x10),
+ spriteram[offs + i + 2] & 0x0f,
+ spriteram[offs + i] & 0x20,spriteram[offs + i] & 0x10,
+ spriteram[offs + i + 3],
+ offs / 4 - 8 + (spriteram[offs + i] & 0x0f),
+ cliprect,TRANSPARENCY_PEN,0);
+ else /* 8x8 */
+ drawgfx(bitmap,machine->gfx[2],
+ spriteram[offs + i + 1] + 16 * (spriteram[offs + i + 2] & 0x10),
+ spriteram[offs + i + 2] & 0x0f,
+ spriteram[offs + i] & 0x20,spriteram[offs + i] & 0x10,
+ spriteram[offs + i + 3],
+ offs / 4 + (spriteram[offs + i] & 0x0f),
+ cliprect,TRANSPARENCY_PEN,0);
+ }
+ }
+ }
+}
+
+VIDEO_UPDATE( ladybug )
+{
+ int offs;
+
+ for (offs = 0; offs < 32; offs++)
+ {
+ int sx = offs % 4;
+ int sy = offs / 4;
+
+ if (flip_screen)
+ tilemap_set_scrollx(bg_tilemap, offs, -videoram[32 * sx + sy]);
+ else
+ tilemap_set_scrollx(bg_tilemap, offs, videoram[32 * sx + sy]);
+ }
+
+ tilemap_draw(bitmap, cliprect, bg_tilemap, 0, 0);
+ draw_sprites(machine, bitmap, cliprect);
+ return 0;
+}
+
+VIDEO_EOF( sraider ) /* update starfield position */
+{
+ redclash_update_stars_state();
+}
+
+VIDEO_UPDATE( sraider )
+{
+ // this part is boilerplate from ladybug, not sure if hardware does this,
+ // since it's not used
+
+ int offs;
+ int i;
+
+ for (offs = 0; offs < 32; offs++)
+ {
+ int sx = offs % 4;
+ int sy = offs / 4;
+
+ if (flip_screen)
+ tilemap_set_scrollx(bg_tilemap, offs, -videoram[32 * sx + sy]);
+ else
+ tilemap_set_scrollx(bg_tilemap, offs, videoram[32 * sx + sy]);
+ }
+
+ // clear the bg bitmap
+ fillbitmap(bitmap,machine->pens[0],cliprect);
+
+ // draw the stars
+ if (flip_screen)
+ redclash_draw_stars(machine,bitmap,cliprect,32,1,0x27,0xff);
+ else
+ redclash_draw_stars(machine,bitmap,cliprect,32,1,0x00,0xd8);
+
+ // draw the horizontal gridlines
+ tilemap_draw(bitmap, cliprect, grid_tilemap, 0, flip_screen);
+ for(i=0;i<256;i++)
+ {
+ if (gridline[i] != 0)
+ {
+ if (flip_screen)
+ plot_box(bitmap,i^0xff,0,1,255,machine->pens[64]);
+ else
+ plot_box(bitmap,i,0,1,255,machine->pens[64]);
+ }
+ }
+
+ // now the chars
+ tilemap_draw(bitmap, cliprect, bg_tilemap, 0, flip_screen);
+
+ // now the sprites
+ draw_sprites(machine, bitmap, cliprect);
+
+ return 0;
+}
+