trunk/src/mess/drivers/hh_pic16.c
| r244945 | r244946 | |
| 59 | 59 | int m_display_maxx; // display matrix number of columns |
| 60 | 60 | |
| 61 | 61 | UINT32 m_display_state[0x20]; // display matrix rows data |
| 62 | | UINT16 m_7seg_mask[0x20]; // if not 0, display matrix row is a 7seg, mask indicates connected segments |
| 62 | UINT16 m_display_segmask[0x20]; // if not 0, display matrix row is a digit, mask indicates connected segments |
| 63 | 63 | UINT32 m_display_cache[0x20]; // (internal use) |
| 64 | 64 | UINT8 m_display_decay[0x20][0x20]; // (internal use) |
| 65 | 65 | |
| r244945 | r244946 | |
| 78 | 78 | memset(m_display_state, 0, sizeof(m_display_state)); |
| 79 | 79 | memset(m_display_cache, 0, sizeof(m_display_cache)); |
| 80 | 80 | memset(m_display_decay, 0, sizeof(m_display_decay)); |
| 81 | | memset(m_7seg_mask, 0, sizeof(m_7seg_mask)); |
| 81 | memset(m_display_segmask, 0, sizeof(m_display_segmask)); |
| 82 | 82 | |
| 83 | 83 | m_b = 0; |
| 84 | 84 | m_c = 0; |
| r244945 | r244946 | |
| 91 | 91 | save_item(NAME(m_display_state)); |
| 92 | 92 | save_item(NAME(m_display_cache)); |
| 93 | 93 | save_item(NAME(m_display_decay)); |
| 94 | | save_item(NAME(m_7seg_mask)); |
| 94 | save_item(NAME(m_display_segmask)); |
| 95 | 95 | |
| 96 | 96 | save_item(NAME(m_b)); |
| 97 | 97 | save_item(NAME(m_c)); |
| r244945 | r244946 | |
| 132 | 132 | for (int y = 0; y < m_display_maxy; y++) |
| 133 | 133 | if (m_display_cache[y] != active_state[y]) |
| 134 | 134 | { |
| 135 | | if (m_7seg_mask[y] != 0) |
| 136 | | output_set_digit_value(y, active_state[y] & m_7seg_mask[y]); |
| 135 | if (m_display_segmask[y] != 0) |
| 136 | output_set_digit_value(y, active_state[y] & m_display_segmask[y]); |
| 137 | 137 | |
| 138 | 138 | const int mul = (m_display_maxx <= 10) ? 10 : 100; |
| 139 | 139 | for (int x = 0; x < m_display_maxx; x++) |
| r244945 | r244946 | |
| 199 | 199 | m_display_maxx = 7; |
| 200 | 200 | m_display_maxy = 2; |
| 201 | 201 | |
| 202 | | m_7seg_mask[offset] = 0x7f; |
| 202 | m_display_segmask[offset] = 0x7f; |
| 203 | 203 | m_display_state[offset] = ~data & 0x7f; |
| 204 | 204 | display_update(); |
| 205 | 205 | } |
trunk/src/mess/drivers/hh_tms1k.c
| r244945 | r244946 | |
| 126 | 126 | int m_display_maxx; // display matrix number of columns |
| 127 | 127 | |
| 128 | 128 | UINT32 m_display_state[0x20]; // display matrix rows data |
| 129 | | UINT16 m_7seg_mask[0x20]; // if not 0, display matrix row is a 7seg, mask indicates connected segments |
| 129 | UINT16 m_display_segmask[0x20]; // if not 0, display matrix row is a digit, mask indicates connected segments |
| 130 | 130 | UINT32 m_display_cache[0x20]; // (internal use) |
| 131 | 131 | UINT8 m_display_decay[0x20][0x20]; // (internal use) |
| 132 | 132 | |
| r244945 | r244946 | |
| 215 | 215 | memset(m_display_state, 0, sizeof(m_display_state)); |
| 216 | 216 | memset(m_display_cache, 0, sizeof(m_display_cache)); |
| 217 | 217 | memset(m_display_decay, 0, sizeof(m_display_decay)); |
| 218 | | memset(m_7seg_mask, 0, sizeof(m_7seg_mask)); |
| 218 | memset(m_display_segmask, 0, sizeof(m_display_segmask)); |
| 219 | 219 | |
| 220 | 220 | m_o = 0; |
| 221 | 221 | m_r = 0; |
| r244945 | r244946 | |
| 230 | 230 | save_item(NAME(m_display_state)); |
| 231 | 231 | save_item(NAME(m_display_cache)); |
| 232 | 232 | save_item(NAME(m_display_decay)); |
| 233 | | save_item(NAME(m_7seg_mask)); |
| 233 | save_item(NAME(m_display_segmask)); |
| 234 | 234 | |
| 235 | 235 | save_item(NAME(m_o)); |
| 236 | 236 | save_item(NAME(m_r)); |
| r244945 | r244946 | |
| 291 | 291 | for (int y = 0; y < m_display_maxy; y++) |
| 292 | 292 | if (m_display_cache[y] != active_state[y]) |
| 293 | 293 | { |
| 294 | | if (m_7seg_mask[y] != 0) |
| 295 | | output_set_digit_value(y, active_state[y] & m_7seg_mask[y]); |
| 294 | if (m_display_segmask[y] != 0) |
| 295 | output_set_digit_value(y, active_state[y] & m_display_segmask[y]); |
| 296 | 296 | |
| 297 | 297 | const int mul = (m_display_maxx <= 10) ? 10 : 100; |
| 298 | 298 | for (int x = 0; x < m_display_maxx; x++) |
| r244945 | r244946 | |
| 395 | 395 | // R0-R7: 7seg leds |
| 396 | 396 | for (int y = 0; y < 8; y++) |
| 397 | 397 | { |
| 398 | | m_7seg_mask[y] = 0x7f; |
| 398 | m_display_segmask[y] = 0x7f; |
| 399 | 399 | m_display_state[y] = (m_r >> y & 1) ? (m_o >> 1) : 0; |
| 400 | 400 | } |
| 401 | 401 | |
| r244945 | r244946 | |
| 558 | 558 | // R8,R9: select digit |
| 559 | 559 | for (int y = 0; y < 2; y++) |
| 560 | 560 | { |
| 561 | | m_7seg_mask[y] = 0x7f; |
| 561 | m_display_segmask[y] = 0x7f; |
| 562 | 562 | m_display_state[y] = (m_r >> (y + 8) & 1) ? m_o : 0; |
| 563 | 563 | } |
| 564 | 564 | |
| r244945 | r244946 | |
| 705 | 705 | // R5,7,8,9 are 7segs |
| 706 | 706 | for (int y = 0; y < 10; y++) |
| 707 | 707 | if (y >= 5 && y <= 9 && y != 6) |
| 708 | | m_7seg_mask[y] = 0x7f; |
| 708 | m_display_segmask[y] = 0x7f; |
| 709 | 709 | |
| 710 | 710 | // update current state (note: R6 as extra column!) |
| 711 | 711 | display_matrix(9, 10, (m_o | (m_r << 2 & 0x100)), m_r); |
| r244945 | r244946 | |
| 848 | 848 | void hh_tms1k_state::ebball_display() |
| 849 | 849 | { |
| 850 | 850 | // R8 is a 7seg |
| 851 | | m_7seg_mask[8] = 0x7f; |
| 851 | m_display_segmask[8] = 0x7f; |
| 852 | 852 | |
| 853 | 853 | display_matrix(7, 9, ~m_o, m_r); |
| 854 | 854 | } |
| r244945 | r244946 | |
| 979 | 979 | m_display_state[y] = (m_r >> y & 1) ? m_o : 0; |
| 980 | 980 | |
| 981 | 981 | // R0,R1 are normal 7segs |
| 982 | | m_7seg_mask[0] = m_7seg_mask[1] = 0x7f; |
| 982 | m_display_segmask[0] = m_display_segmask[1] = 0x7f; |
| 983 | 983 | |
| 984 | 984 | // R4,R7 contain segments(only F and B) for the two other digits |
| 985 | 985 | m_display_state[10] = (m_display_state[4] & 0x20) | (m_display_state[7] & 0x02); |
| 986 | 986 | m_display_state[11] = ((m_display_state[4] & 0x10) | (m_display_state[7] & 0x01)) << 1; |
| 987 | | m_7seg_mask[10] = m_7seg_mask[11] = 0x22; |
| 987 | m_display_segmask[10] = m_display_segmask[11] = 0x22; |
| 988 | 988 | |
| 989 | 989 | display_update(); |
| 990 | 990 | } |
| r244945 | r244946 | |
| 1126 | 1126 | |
| 1127 | 1127 | // R0-R6: select digit |
| 1128 | 1128 | for (int y = 0; y < 7; y++) |
| 1129 | | m_7seg_mask[y] = 0x7f; |
| 1129 | m_display_segmask[y] = 0x7f; |
| 1130 | 1130 | |
| 1131 | 1131 | display_matrix(7, 7, BITSWAP8(m_o,7,5,2,1,4,0,6,3), data); |
| 1132 | 1132 | } |
| r244945 | r244946 | |
| 1228 | 1228 | void hh_tms1k_state::starwbc_display() |
| 1229 | 1229 | { |
| 1230 | 1230 | // R6,R8 are 7segs |
| 1231 | | m_7seg_mask[6] = m_7seg_mask[8] = 0x7f; |
| 1231 | m_display_segmask[6] = m_display_segmask[8] = 0x7f; |
| 1232 | 1232 | |
| 1233 | 1233 | display_matrix(8, 10, m_o, m_r); |
| 1234 | 1234 | } |
| r244945 | r244946 | |
| 1527 | 1527 | // R0-R5: select digit (right-to-left) |
| 1528 | 1528 | for (int y = 0; y < 6; y++) |
| 1529 | 1529 | { |
| 1530 | | m_7seg_mask[y] = 0xff; |
| 1530 | m_display_segmask[y] = 0xff; |
| 1531 | 1531 | m_display_state[y] = (data >> y & 1) ? m_o : 0; |
| 1532 | 1532 | } |
| 1533 | 1533 | |
| r244945 | r244946 | |
| 1731 | 1731 | UINT8 o = BITSWAP8(m_o,3,5,2,1,4,0,6,7) & 0x7f; |
| 1732 | 1732 | for (int y = 0; y < m_display_maxy; y++) |
| 1733 | 1733 | { |
| 1734 | | m_7seg_mask[y] = 0x7f; |
| 1734 | m_display_segmask[y] = 0x7f; |
| 1735 | 1735 | m_display_state[y] = (data >> y & 1) ? o : 0; |
| 1736 | 1736 | } |
| 1737 | 1737 | |
trunk/src/mess/drivers/hh_ucom4.c
| r244945 | r244946 | |
| 69 | 69 | UINT32 m_plate; // VFD current column data |
| 70 | 70 | |
| 71 | 71 | UINT32 m_display_state[0x20]; // display matrix rows data |
| 72 | | UINT16 m_7seg_mask[0x20]; // if not 0, display matrix row is a 7seg, mask indicates connected segments |
| 72 | UINT16 m_display_segmask[0x20]; // if not 0, display matrix row is a digit, mask indicates connected segments |
| 73 | 73 | UINT32 m_display_cache[0x20]; // (internal use) |
| 74 | 74 | UINT8 m_display_decay[0x20][0x20]; // (internal use) |
| 75 | 75 | |
| r244945 | r244946 | |
| 118 | 118 | memset(m_display_state, 0, sizeof(m_display_state)); |
| 119 | 119 | memset(m_display_cache, 0, sizeof(m_display_cache)); |
| 120 | 120 | memset(m_display_decay, 0, sizeof(m_display_decay)); |
| 121 | | memset(m_7seg_mask, 0, sizeof(m_7seg_mask)); |
| 121 | memset(m_display_segmask, 0, sizeof(m_display_segmask)); |
| 122 | 122 | |
| 123 | 123 | memset(m_port, 0, sizeof(m_port)); |
| 124 | 124 | m_inp_mux = 0; |
| r244945 | r244946 | |
| 133 | 133 | save_item(NAME(m_display_state)); |
| 134 | 134 | save_item(NAME(m_display_cache)); |
| 135 | 135 | save_item(NAME(m_display_decay)); |
| 136 | | save_item(NAME(m_7seg_mask)); |
| 136 | save_item(NAME(m_display_segmask)); |
| 137 | 137 | |
| 138 | 138 | save_item(NAME(m_port)); |
| 139 | 139 | save_item(NAME(m_inp_mux)); |
| r244945 | r244946 | |
| 176 | 176 | for (int y = 0; y < m_display_maxy; y++) |
| 177 | 177 | if (m_display_cache[y] != active_state[y]) |
| 178 | 178 | { |
| 179 | | if (m_7seg_mask[y] != 0) |
| 180 | | output_set_digit_value(y, active_state[y] & m_7seg_mask[y]); |
| 179 | if (m_display_segmask[y] != 0) |
| 180 | output_set_digit_value(y, active_state[y] & m_display_segmask[y]); |
| 181 | 181 | |
| 182 | 182 | const int mul = (m_display_maxx <= 10) ? 10 : 100; |
| 183 | 183 | for (int x = 0; x < m_display_maxx; x++) |
trunk/src/mess/drivers/ticalc1x.c
| r244945 | r244946 | |
| 61 | 61 | int m_display_maxx; // display matrix number of columns |
| 62 | 62 | |
| 63 | 63 | UINT32 m_display_state[0x20]; // display matrix rows data |
| 64 | | UINT16 m_7seg_mask[0x20]; // if not 0, display matrix row is a 7seg, mask indicates connected segments |
| 64 | UINT16 m_display_segmask[0x20]; // if not 0, display matrix row is a digit, mask indicates connected segments |
| 65 | 65 | UINT32 m_display_cache[0x20]; // (internal use) |
| 66 | 66 | UINT8 m_display_decay[0x20][0x20]; // (internal use) |
| 67 | 67 | |
| 68 | 68 | TIMER_DEVICE_CALLBACK_MEMBER(display_decay_tick); |
| 69 | 69 | void display_update(); |
| 70 | | void display_matrix_7seg(int maxx, int maxy, UINT32 setx, UINT32 sety, UINT16 _7segmask); |
| 70 | void display_matrix_seg(int maxx, int maxy, UINT32 setx, UINT32 sety, UINT16 segmask); |
| 71 | 71 | |
| 72 | 72 | // calculator-specific handlers |
| 73 | 73 | DECLARE_READ8_MEMBER(tisr16_read_k); |
| r244945 | r244946 | |
| 101 | 101 | memset(m_display_state, 0, sizeof(m_display_state)); |
| 102 | 102 | memset(m_display_cache, 0, sizeof(m_display_cache)); |
| 103 | 103 | memset(m_display_decay, 0, sizeof(m_display_decay)); |
| 104 | | memset(m_7seg_mask, ~0, sizeof(m_7seg_mask)); // ! |
| 104 | memset(m_display_segmask, ~0, sizeof(m_display_segmask)); // ! |
| 105 | 105 | |
| 106 | 106 | m_o = 0; |
| 107 | 107 | m_r = 0; |
| r244945 | r244946 | |
| 116 | 116 | save_item(NAME(m_display_state)); |
| 117 | 117 | save_item(NAME(m_display_cache)); |
| 118 | 118 | save_item(NAME(m_display_decay)); |
| 119 | | save_item(NAME(m_7seg_mask)); |
| 119 | save_item(NAME(m_display_segmask)); |
| 120 | 120 | |
| 121 | 121 | save_item(NAME(m_o)); |
| 122 | 122 | save_item(NAME(m_r)); |
| r244945 | r244946 | |
| 164 | 164 | for (int y = 0; y < m_display_maxy; y++) |
| 165 | 165 | if (m_display_cache[y] != active_state[y]) |
| 166 | 166 | { |
| 167 | | if (m_7seg_mask[y] != 0) |
| 168 | | output_set_digit_value(y, active_state[y] & m_7seg_mask[y]); |
| 167 | if (m_display_segmask[y] != 0) |
| 168 | output_set_digit_value(y, active_state[y] & m_display_segmask[y]); |
| 169 | 169 | |
| 170 | 170 | const int mul = (m_display_maxx <= 10) ? 10 : 100; |
| 171 | 171 | for (int x = 0; x < m_display_maxx; x++) |
| r244945 | r244946 | |
| 186 | 186 | display_update(); |
| 187 | 187 | } |
| 188 | 188 | |
| 189 | | void ticalc1x_state::display_matrix_7seg(int maxx, int maxy, UINT32 setx, UINT32 sety, UINT16 _7segmask) |
| 189 | void ticalc1x_state::display_matrix_seg(int maxx, int maxy, UINT32 setx, UINT32 sety, UINT16 segmask) |
| 190 | 190 | { |
| 191 | 191 | m_display_maxx = maxx; |
| 192 | 192 | m_display_maxy = maxy; |
| r244945 | r244946 | |
| 195 | 195 | UINT32 colmask = (1 << maxx) - 1; |
| 196 | 196 | for (int y = 0; y < maxy; y++) |
| 197 | 197 | { |
| 198 | | m_7seg_mask[y] &= _7segmask; |
| 198 | m_display_segmask[y] &= segmask; |
| 199 | 199 | m_display_state[y] = (sety >> y & 1) ? (setx & colmask) : 0; |
| 200 | 200 | } |
| 201 | 201 | |
| r244945 | r244946 | |
| 387 | 387 | WRITE16_MEMBER(ticalc1x_state::ti1270_write_r) |
| 388 | 388 | { |
| 389 | 389 | // R0-R7: select digit (right-to-left) |
| 390 | | display_matrix_7seg(8, 8, m_o, data, 0xff); |
| 390 | display_matrix_seg(8, 8, m_o, data, 0xff); |
| 391 | 391 | } |
| 392 | 392 | |
| 393 | 393 | WRITE16_MEMBER(ticalc1x_state::ti1270_write_o) |
| r244945 | r244946 | |
| 474 | 474 | { |
| 475 | 475 | // note: 6th digit is custom(not 7seg), for math symbols, and 3rd digit |
| 476 | 476 | // only has A and G for =, though some newer revisions use a custom digit too. |
| 477 | | m_7seg_mask[3] = 0x41; |
| 477 | m_display_segmask[3] = 0x41; |
| 478 | 478 | |
| 479 | 479 | // R0-R8: select digit (right-to-left) |
| 480 | | display_matrix_7seg(8, 9, m_o, data, 0x7f); |
| 480 | display_matrix_seg(8, 9, m_o, data, 0x7f); |
| 481 | 481 | } |
| 482 | 482 | |
| 483 | 483 | WRITE16_MEMBER(ticalc1x_state::wizatron_write_o) |
| r244945 | r244946 | |
| 651 | 651 | WRITE16_MEMBER(ticalc1x_state::ti30_write_r) |
| 652 | 652 | { |
| 653 | 653 | // note: 1st digit only has segments B,F,G,DP |
| 654 | | m_7seg_mask[0] = 0xe2; |
| 654 | m_display_segmask[0] = 0xe2; |
| 655 | 655 | |
| 656 | 656 | // R0-R8: select digit |
| 657 | | display_matrix_7seg(8, 9, BITSWAP8(m_o,7,5,2,1,4,0,6,3), data, 0xff); |
| 657 | display_matrix_seg(8, 9, BITSWAP8(m_o,7,5,2,1,4,0,6,3), data, 0xff); |
| 658 | 658 | } |
| 659 | 659 | |
| 660 | 660 | WRITE16_MEMBER(ticalc1x_state::ti30_write_o) |
trunk/src/mess/drivers/tispeak.c
| r244945 | r244946 | |
| 303 | 303 | m_tms5100(*this, "tms5100"), |
| 304 | 304 | m_tms6100(*this, "tms6100"), |
| 305 | 305 | m_cart(*this, "cartslot"), |
| 306 | | m_button_matrix(*this, "IN") |
| 306 | m_button_matrix(*this, "IN"), |
| 307 | m_display_wait(33), |
| 308 | m_display_maxy(1), |
| 309 | m_display_maxx(0) |
| 307 | 310 | { } |
| 308 | 311 | |
| 312 | // devices |
| 309 | 313 | required_device<tms0270_cpu_device> m_maincpu; |
| 310 | 314 | required_device<tms5100_device> m_tms5100; |
| 311 | 315 | required_device<tms6100_device> m_tms6100; |
| 312 | 316 | optional_device<generic_slot_device> m_cart; |
| 313 | 317 | required_ioport_array<9> m_button_matrix; |
| 314 | 318 | |
| 315 | | UINT16 m_r; |
| 316 | | UINT16 m_o; |
| 319 | // misc common |
| 320 | UINT16 m_r; // MCU R-pins data |
| 321 | UINT16 m_o; // MCU O-pins data |
| 317 | 322 | int m_power_on; |
| 323 | int m_filament_on; |
| 318 | 324 | |
| 319 | | UINT16 m_display_state[0x10]; |
| 320 | | UINT16 m_display_cache[0x10]; |
| 321 | | UINT8 m_display_decay[0x100]; |
| 325 | // display common |
| 326 | int m_display_wait; // led/lamp off-delay in microseconds (default 33ms) |
| 327 | int m_display_maxy; // display matrix number of rows |
| 328 | int m_display_maxx; // display matrix number of columns |
| 329 | |
| 330 | UINT32 m_display_state[0x20]; // display matrix rows data |
| 331 | UINT16 m_display_segmask[0x20]; // if not 0, display matrix row is a digit, mask indicates connected segments |
| 332 | UINT32 m_display_cache[0x20]; // (internal use) |
| 333 | UINT8 m_display_decay[0x20][0x20]; // (internal use) |
| 334 | |
| 335 | TIMER_DEVICE_CALLBACK_MEMBER(display_decay_tick); |
| 322 | 336 | void display_update(); |
| 323 | | TIMER_DEVICE_CALLBACK_MEMBER(display_decay_tick); |
| 337 | void display_matrix_seg(int maxx, int maxy, UINT32 setx, UINT32 sety, UINT16 segmask); |
| 324 | 338 | |
| 339 | // cartridge |
| 325 | 340 | UINT32 m_cart_max_size; |
| 326 | 341 | UINT8* m_cart_base; |
| 327 | 342 | DECLARE_DEVICE_IMAGE_LOAD_MEMBER(tispeak_cartridge); |
| r244945 | r244946 | |
| 386 | 401 | |
| 387 | 402 | ***************************************************************************/ |
| 388 | 403 | |
| 389 | | // The device strobes the filament-enable very fast, it is unnoticeable to the user. |
| 404 | // The device may strobe the outputs very fast, it is unnoticeable to the user. |
| 390 | 405 | // To prevent flickering here, we need to simulate a decay. |
| 391 | 406 | |
| 392 | | // decay time, in steps of 1ms |
| 393 | | #define DISPLAY_DECAY_TIME 40 |
| 394 | | |
| 395 | 407 | void tispeak_state::display_update() |
| 396 | 408 | { |
| 397 | | int filament_on = (m_r & 0x8000) ? 1 : 0; |
| 398 | | UINT16 active_state[0x10]; |
| 409 | UINT32 active_state[0x20]; |
| 399 | 410 | |
| 400 | | for (int i = 0; i < 0x10; i++) |
| 411 | for (int y = 0; y < m_display_maxy; y++) |
| 401 | 412 | { |
| 402 | | // update current state |
| 403 | | m_display_state[i] = (m_r >> i & 1) ? m_o : 0; |
| 413 | active_state[y] = 0; |
| 404 | 414 | |
| 405 | | active_state[i] = 0; |
| 406 | | |
| 407 | | for (int j = 0; j < 0x10; j++) |
| 415 | for (int x = 0; x < m_display_maxx; x++) |
| 408 | 416 | { |
| 409 | | int di = j << 4 | i; |
| 410 | | |
| 411 | 417 | // turn on powered segments |
| 412 | | if (m_power_on && filament_on && m_display_state[i] >> j & 1) |
| 413 | | m_display_decay[di] = DISPLAY_DECAY_TIME; |
| 418 | if (m_power_on && m_filament_on && m_display_state[y] >> x & 1) |
| 419 | m_display_decay[y][x] = m_display_wait; |
| 414 | 420 | |
| 415 | 421 | // determine active state |
| 416 | | int ds = (m_display_decay[di] != 0) ? 1 : 0; |
| 417 | | active_state[i] |= (ds << j); |
| 422 | int ds = (m_display_decay[y][x] != 0) ? 1 : 0; |
| 423 | active_state[y] |= (ds << x); |
| 418 | 424 | } |
| 419 | 425 | } |
| 420 | 426 | |
| 421 | 427 | // on difference, send to output |
| 422 | | for (int i = 0; i < 0x10; i++) |
| 423 | | if (m_display_cache[i] != active_state[i]) |
| 428 | for (int y = 0; y < m_display_maxy; y++) |
| 429 | if (m_display_cache[y] != active_state[y]) |
| 424 | 430 | { |
| 425 | | output_set_digit_value(i, active_state[i] & 0x3fff); |
| 431 | if (m_display_segmask[y] != 0) |
| 432 | output_set_digit_value(y, active_state[y] & m_display_segmask[y]); |
| 426 | 433 | |
| 427 | | // lampxyy where x=digit, y=segment |
| 428 | | for (int j = 0; j < 0x10; j++) |
| 429 | | output_set_lamp_value(i*100 + j, active_state[i] >> j & 1); |
| 434 | const int mul = (m_display_maxx <= 10) ? 10 : 100; |
| 435 | for (int x = 0; x < m_display_maxx; x++) |
| 436 | output_set_lamp_value(y * mul + x, active_state[y] >> x & 1); |
| 430 | 437 | } |
| 431 | 438 | |
| 432 | 439 | memcpy(m_display_cache, active_state, sizeof(m_display_cache)); |
| r244945 | r244946 | |
| 435 | 442 | TIMER_DEVICE_CALLBACK_MEMBER(tispeak_state::display_decay_tick) |
| 436 | 443 | { |
| 437 | 444 | // slowly turn off unpowered segments |
| 438 | | for (int i = 0; i < 0x100; i++) |
| 439 | | if (!(m_display_state[i & 0xf] >> (i>>4) & 1) && m_display_decay[i]) |
| 440 | | m_display_decay[i]--; |
| 445 | for (int y = 0; y < m_display_maxy; y++) |
| 446 | for (int x = 0; x < m_display_maxx; x++) |
| 447 | if (m_display_decay[y][x] != 0) |
| 448 | m_display_decay[y][x]--; |
| 449 | |
| 450 | display_update(); |
| 451 | } |
| 441 | 452 | |
| 453 | void tispeak_state::display_matrix_seg(int maxx, int maxy, UINT32 setx, UINT32 sety, UINT16 segmask) |
| 454 | { |
| 455 | m_display_maxx = maxx; |
| 456 | m_display_maxy = maxy; |
| 457 | |
| 458 | // update current state |
| 459 | UINT32 colmask = (1 << maxx) - 1; |
| 460 | for (int y = 0; y < maxy; y++) |
| 461 | { |
| 462 | m_display_segmask[y] &= segmask; |
| 463 | m_display_state[y] = (sety >> y & 1) ? (setx & colmask) : 0; |
| 464 | } |
| 465 | |
| 442 | 466 | display_update(); |
| 443 | 467 | } |
| 444 | 468 | |
| r244945 | r244946 | |
| 467 | 491 | |
| 468 | 492 | WRITE16_MEMBER(tispeak_state::snspell_write_r) |
| 469 | 493 | { |
| 470 | | // R0-R7: input mux and select digit (+R8 if the device has 9 digits) |
| 471 | | // R15: filament on (handled in leds_update) |
| 494 | // R15: filament on |
| 495 | m_filament_on = data & 0x8000; |
| 496 | |
| 472 | 497 | // R13: power-off request, on falling edge |
| 473 | 498 | if ((m_r >> 13 & 1) && !(data >> 13 & 1)) |
| 474 | 499 | power_off(); |
| 475 | 500 | |
| 501 | // R0-R7: input mux and select digit (+R8 if the device has 9 digits) |
| 476 | 502 | // other bits: MCU internal use |
| 477 | | m_r = data; |
| 478 | | display_update(); |
| 503 | m_r = data & 0x21ff; |
| 504 | display_matrix_seg(16, 16, m_o, m_r, 0x3fff); |
| 479 | 505 | } |
| 480 | 506 | |
| 481 | 507 | WRITE16_MEMBER(tispeak_state::snspell_write_o) |
| r244945 | r244946 | |
| 483 | 509 | // reorder opla to led14seg, plus DP as d14 and AP as d15: |
| 484 | 510 | // E,D,C,G,B,A,I,M,L,K,N,J,[AP],H,F,[DP] (sidenote: TI KLMN = MAME MLNK) |
| 485 | 511 | m_o = BITSWAP16(data,12,15,10,7,8,9,11,6,13,3,14,0,1,2,4,5); |
| 486 | | |
| 487 | | display_update(); |
| 512 | display_matrix_seg(16, 16, m_o, m_r, 0x3fff); |
| 488 | 513 | } |
| 489 | 514 | |
| 490 | 515 | |
| r244945 | r244946 | |
| 505 | 530 | // reorder opla to led14seg, plus DP as d14 and AP as d15: |
| 506 | 531 | // [DP],D,C,H,F,B,I,M,L,K,N,J,[AP],E,G,A (sidenote: TI KLMN = MAME MLNK) |
| 507 | 532 | m_o = BITSWAP16(data,12,0,10,7,8,9,11,6,3,14,4,13,1,2,5,15); |
| 508 | | |
| 509 | | display_update(); |
| 533 | display_matrix_seg(16, 16, m_o, m_r, 0x3fff); |
| 510 | 534 | } |
| 511 | 535 | |
| 512 | 536 | |
| r244945 | r244946 | |
| 515 | 539 | WRITE16_MEMBER(tispeak_state::lantutor_write_r) |
| 516 | 540 | { |
| 517 | 541 | // same as default, except R13 is used for an extra digit |
| 518 | | m_r = data; |
| 519 | | display_update(); |
| 542 | m_filament_on = data & 0x8000; |
| 543 | m_r = data & 0x21ff; |
| 544 | display_matrix_seg(16, 16, m_o, m_r, 0x3fff); |
| 520 | 545 | } |
| 521 | 546 | |
| 522 | 547 | |
| r244945 | r244946 | |
| 708 | 733 | memset(m_display_state, 0, sizeof(m_display_state)); |
| 709 | 734 | memset(m_display_cache, 0, sizeof(m_display_cache)); |
| 710 | 735 | memset(m_display_decay, 0, sizeof(m_display_decay)); |
| 736 | memset(m_display_segmask, ~0, sizeof(m_display_segmask)); // ! |
| 711 | 737 | |
| 712 | 738 | m_r = 0; |
| 713 | 739 | m_o = 0; |
| 714 | 740 | m_power_on = 0; |
| 741 | m_filament_on = 0; |
| 715 | 742 | |
| 716 | 743 | // register for savestates |
| 717 | 744 | save_item(NAME(m_display_state)); |
| 718 | 745 | save_item(NAME(m_display_cache)); |
| 719 | 746 | save_item(NAME(m_display_decay)); |
| 747 | save_item(NAME(m_display_segmask)); |
| 720 | 748 | |
| 721 | 749 | save_item(NAME(m_r)); |
| 722 | 750 | save_item(NAME(m_o)); |
| 723 | 751 | save_item(NAME(m_power_on)); |
| 752 | save_item(NAME(m_filament_on)); |
| 724 | 753 | |
| 725 | 754 | // init cartridge |
| 726 | 755 | if (m_cart != NULL && m_cart->exists()) |