2 CASIO PV-1000 Emulator 'ePV-1000'
4 Author : Takeda.Toshiya
12 static const scrntype_t palette_pc[8] = {
13 RGB_COLOR( 0, 0, 0), RGB_COLOR(255, 0, 0), RGB_COLOR( 0,255, 0), RGB_COLOR(255,255, 0),
14 RGB_COLOR( 0, 0,255), RGB_COLOR(255, 0,255), RGB_COLOR( 0,255,255), RGB_COLOR(255,255,255)
16 static const uint8_t plane[4] = {0, 1, 2, 4};
18 void VDP::initialize()
20 // register event to interrupt
21 register_vline_event(this);
26 force_pattern = false;
29 void VDP::write_io8(uint32_t addr, uint32_t data)
33 vram = base + (data << 8);
34 pcg = base + (data << 8) + 0x400;
37 pattern = base + ((data & 0x20) << 8);
38 force_pattern = ((data & 0x10) != 0);
43 void VDP::event_callback(int event_id, int err)
45 d_cpu->write_signal(SIG_CPU_BUSREQ, 0, 1);
48 void VDP::event_vline(int v, int clock)
50 if(v < LINES_PER_HBLANK) {
51 d_cpu->write_signal(SIG_CPU_BUSREQ, 1, 1);
52 register_event_by_clock(this, 0, 800, false, NULL);
54 // hsync interrupt (not pending ???)
55 d_cpu->set_intr_line(true, false, 0);
59 void VDP::draw_screen()
61 memset(bg, 0, sizeof(bg));
63 for(int y = 0; y < 24; y++) {
64 int y8 = y << 3, y32 = y << 5;
66 for(int x = 2; x < 30; x++) {
68 uint8_t code = vram[y32 + x];
70 if(code < 0xe0 || force_pattern) {
71 draw_pattern(x8, y8, code << 5);
73 draw_pcg(x8, y8, (code & 0x1f) << 5);
77 for(int y = 0; y < 192; y++) {
78 scrntype_t* dest = emu->get_screen_buffer(y);
79 for(int x = 0; x < 256; x++) {
80 dest[x] = palette_pc[bg[y][x] & 7];
85 void VDP::draw_pattern(int x8, int y8, uint16_t top)
87 // draw pattern on rom
88 for(int p = 1; p < 4; p++) {
89 uint8_t col = plane[p];
90 uint16_t p8 = top + (p << 3);
92 for(int l = 0; l < 8; l++) {
93 uint8_t* dest = &bg[y8 + l][x8];
94 uint8_t pat = pattern[p8 + l];
96 if(pat & 0x80) dest[0] |= col;
97 if(pat & 0x40) dest[1] |= col;
98 if(pat & 0x20) dest[2] |= col;
99 if(pat & 0x10) dest[3] |= col;
100 if(pat & 0x08) dest[4] |= col;
101 if(pat & 0x04) dest[5] |= col;
102 if(pat & 0x02) dest[6] |= col;
103 if(pat & 0x01) dest[7] |= col;
108 void VDP::draw_pcg(int x8, int y8, uint16_t top)
110 // draw pattern on ram
111 for(int p = 1; p < 4; p++) {
112 uint8_t col = plane[p];
113 uint16_t p8 = top + (p << 3);
115 for(int l = 0; l < 8; l++) {
116 uint8_t* dest = &bg[y8 + l][x8];
117 uint8_t pat = pcg[p8 + l];
119 if(pat & 0x80) dest[0] |= col;
120 if(pat & 0x40) dest[1] |= col;
121 if(pat & 0x20) dest[2] |= col;
122 if(pat & 0x10) dest[3] |= col;
123 if(pat & 0x08) dest[4] |= col;
124 if(pat & 0x04) dest[5] |= col;
125 if(pat & 0x02) dest[6] |= col;
126 if(pat & 0x01) dest[7] |= col;
131 #define STATE_VERSION 1
133 #include "../../statesub.h"
135 void VDP::decl_state()
137 enter_decl_state(STATE_VERSION);
139 DECL_STATE_ENTRY_INT32(tmp_vram_size); // (int)(vram - base);
140 DECL_STATE_ENTRY_INT32(tmp_pcg_size); // (int)(pcg - base);
141 DECL_STATE_ENTRY_INT32(tmp_pattern_size); // (int)(pattern - base);
142 DECL_STATE_ENTRY_BOOL(force_pattern);
147 void VDP::save_state(FILEIO* state_fio)
149 tmp_vram_size = (int)(vram - base);
150 tmp_pcg_size = (int)(pcg - base);
151 tmp_pattern_size = (int)(pattern - base);
153 if(state_entry != NULL) {
154 state_entry->save_state(state_fio);
156 // state_fio->FputUint32(STATE_VERSION);
157 // state_fio->FputInt32(this_device_id);
159 // state_fio->FputInt32((int)(vram - base));
160 // state_fio->FputInt32((int)(pcg - base));
161 // state_fio->FputInt32((int)(pattern - base));
162 // state_fio->FputBool(force_pattern);
165 bool VDP::load_state(FILEIO* state_fio)
168 if(state_entry != NULL) {
169 mb = state_entry->load_state(state_fio);
174 // if(state_fio->FgetUint32() != STATE_VERSION) {
177 // if(state_fio->FgetInt32() != this_device_id) {
180 // vram = base + state_fio->FgetInt32();
181 // pcg = base + state_fio->FgetInt32();
182 // pattern = base + state_fio->FgetInt32();
183 // force_pattern = state_fio->FgetBool();
184 vram = base + tmp_vram_size;
185 pcg = base + tmp_pcg_size;
186 pattern = base + tmp_pattern_size;
190 bool VDP::process_state(FILEIO* state_fio, bool loading)
192 if(!state_fio->StateCheckUint32(STATE_VERSION)) {
195 if(!state_fio->StateCheckInt32(this_device_id)) {
199 vram = base + state_fio->FgetInt32_LE();
200 pcg = base + state_fio->FgetInt32_LE();
201 pattern = base + state_fio->FgetInt32_LE();
203 state_fio->FputInt32_LE((int)(vram - base));
204 state_fio->FputInt32_LE((int)(pcg - base));
205 state_fio->FputInt32_LE((int)(pattern - base));
207 state_fio->StateBool(force_pattern);