/*************************************************************************** Cinematronics vector hardware ***************************************************************************/ #include "driver.h" #include "video/vector.h" #include "cpu/ccpu/ccpu.h" #include "cinemat.h" /************************************* * * Constants * *************************************/ enum { COLOR_BILEVEL, COLOR_16LEVEL, COLOR_64LEVEL, COLOR_RGB, COLOR_QB3 }; /************************************* * * Local variables * *************************************/ static int color_mode; static rgb_t vector_color; static INT16 lastx, lasty; static UINT8 last_control; /************************************* * * Vector rendering * *************************************/ void cinemat_vector_callback(INT16 sx, INT16 sy, INT16 ex, INT16 ey, UINT8 shift) { int intensity = 0xff; /* adjust for slop */ sx = sx - Machine->screen[0].visarea.min_x; ex = ex - Machine->screen[0].visarea.min_x; sy = sy - Machine->screen[0].visarea.min_y; ey = ey - Machine->screen[0].visarea.min_y; /* point intensity is determined by the shift value */ if (sx == ex && sy == ey) intensity = 0x1ff * shift / 8; /* move to the starting position if we're not there already */ if (sx != lastx || sy != lasty) vector_add_point(sx << 16, sy << 16, 0, 0); /* draw the vector */ vector_add_point(ex << 16, ey << 16, vector_color, intensity); /* remember the last point */ lastx = ex; lasty = ey; } /************************************* * * Vector color handling * *************************************/ WRITE8_HANDLER(cinemat_vector_control_w) { int r, g, b, i; switch (color_mode) { case COLOR_BILEVEL: /* color is either bright or dim, selected by the value sent to the port */ vector_color = (data & 1) ? MAKE_RGB(0x80,0x80,0x80) : MAKE_RGB(0xff,0xff,0xff); break; case COLOR_16LEVEL: /* on the rising edge of the data value, latch bits 0-3 of the */ /* X register as the intensity */ if (data != last_control && data) { int xval = cpunum_get_reg(0, CCPU_X) & 0x0f; i = (xval + 1) * 255 / 16; vector_color = MAKE_RGB(i,i,i); } break; case COLOR_64LEVEL: /* on the rising edge of the data value, latch bits 2-7 of the */ /* X register as the intensity */ if (data != last_control && data) { int xval = cpunum_get_reg(0, CCPU_X); xval = (~xval >> 2) & 0x3f; i = (xval + 1) * 255 / 64; vector_color = MAKE_RGB(i,i,i); } break; case COLOR_RGB: /* on the rising edge of the data value, latch the X register */ /* as 4-4-4 BGR values */ if (data != last_control && data) { int xval = cpunum_get_reg(0, CCPU_X); r = (~xval >> 0) & 0x0f; r = r * 255 / 15; g = (~xval >> 4) & 0x0f; g = g * 255 / 15; b = (~xval >> 8) & 0x0f; b = b * 255 / 15; vector_color = MAKE_RGB(r,g,b); } break; case COLOR_QB3: { static int lastx, lasty; /* on the falling edge of the data value, remember the original X,Y values */ /* they will be restored on the rising edge; this is to simulate the fact */ /* that the Rockola color hardware did not overwrite the beam X,Y position */ /* on an IV instruction if data == 0 here */ if (data != last_control && !data) { lastx = cpunum_get_reg(0, CCPU_X); lasty = cpunum_get_reg(0, CCPU_Y); } /* on the rising edge of the data value, latch the Y register */ /* as 2-3-3 BGR values */ if (data != last_control && data) { int yval = cpunum_get_reg(0, CCPU_Y); r = (~yval >> 0) & 0x07; r = r * 255 / 7; g = (~yval >> 3) & 0x07; g = g * 255 / 7; b = (~yval >> 6) & 0x03; b = b * 255 / 3; vector_color = MAKE_RGB(r,g,b); /* restore the original X,Y values */ cpunum_set_reg(0, CCPU_X, lastx); cpunum_set_reg(0, CCPU_Y, lasty); } } break; } /* remember the last value */ last_control = data; } /************************************* * * Video startup * *************************************/ VIDEO_START( cinemat_bilevel ) { color_mode = COLOR_BILEVEL; video_start_vector(machine); } VIDEO_START( cinemat_16level ) { color_mode = COLOR_16LEVEL; video_start_vector(machine); } VIDEO_START( cinemat_64level ) { color_mode = COLOR_64LEVEL; video_start_vector(machine); } VIDEO_START( cinemat_color ) { color_mode = COLOR_RGB; video_start_vector(machine); } VIDEO_START( cinemat_qb3color ) { color_mode = COLOR_QB3; video_start_vector(machine); } /************************************* * * End-of-frame * *************************************/ VIDEO_EOF( cinemat ) { vector_clear_list(); } /************************************* * * Space War update * *************************************/ VIDEO_UPDATE( spacewar ) { int sw_option = readinputportbytag("INPUTS"); video_update_vector(machine, screen, bitmap, cliprect); /* set the state of the artwork */ output_set_value("pressed3", (~sw_option >> 0) & 1); output_set_value("pressed8", (~sw_option >> 1) & 1); output_set_value("pressed4", (~sw_option >> 2) & 1); output_set_value("pressed9", (~sw_option >> 3) & 1); output_set_value("pressed1", (~sw_option >> 4) & 1); output_set_value("pressed6", (~sw_option >> 5) & 1); output_set_value("pressed2", (~sw_option >> 6) & 1); output_set_value("pressed7", (~sw_option >> 7) & 1); output_set_value("pressed5", (~sw_option >> 10) & 1); output_set_value("pressed0", (~sw_option >> 11) & 1); return 0; }