From 6e59afa0473c5815da5bfccbb3bf2824f7c4a837 Mon Sep 17 00:00:00 2001 From: hap Date: Wed, 12 Jun 2019 02:35:52 +0200 Subject: add screenless base class (nw) --- scripts/target/mame/mess.lua | 54 ++++---- src/mame/drivers/fidel_chesster.cpp | 16 +-- src/mame/drivers/hh_amis2k.cpp | 130 ++----------------- src/mame/drivers/hh_cop400.cpp | 140 ++------------------- src/mame/drivers/hh_hmcs40.cpp | 245 ++++++------------------------------ src/mame/drivers/hh_melps4.cpp | 122 ++---------------- src/mame/drivers/hh_pic16.cpp | 140 ++------------------- src/mame/drivers/hh_tms1k.cpp | 175 ++------------------------ src/mame/drivers/hh_ucom4.cpp | 166 +++--------------------- src/mame/drivers/mattelchess.cpp | 2 +- src/mame/drivers/tb303.cpp | 2 - src/mame/drivers/ticalc1x.cpp | 11 -- src/mame/drivers/tispeak.cpp | 5 +- src/mame/drivers/tispellb.cpp | 4 +- src/mame/drivers/tr606.cpp | 1 - src/mame/includes/hh_tms1k.h | 40 ++---- src/mame/includes/hh_ucom4.h | 38 ++---- src/mame/includes/screenless.h | 75 +++++++++++ src/mame/layout/wildfire.lay | 3 +- src/mame/machine/chessbase.cpp | 3 + src/mame/machine/screenless.cpp | 205 ++++++++++++++++++++++++++++++ 21 files changed, 439 insertions(+), 1138 deletions(-) create mode 100644 src/mame/includes/screenless.h create mode 100644 src/mame/machine/screenless.cpp diff --git a/scripts/target/mame/mess.lua b/scripts/target/mame/mess.lua index 61441c002cc..f9657c0f7ea 100644 --- a/scripts/target/mame/mess.lua +++ b/scripts/target/mame/mess.lua @@ -1028,7 +1028,6 @@ function linkProjects_mame_mess(_target, _subtarget) "akai", "alesis", "altos", - "ami", "amiga", "ampro", "amstrad", @@ -1093,7 +1092,6 @@ function linkProjects_mame_mess(_target, _subtarget) "funtech", "galaxy", "gamepark", - "gi", "gridcomp", "grundy", "hartung", @@ -1153,7 +1151,6 @@ function linkProjects_mame_mess(_target, _subtarget) "nokia", "northstar", "novag", - "ns", "olivetti", "olympia", "omnibyte", @@ -1185,6 +1182,7 @@ function linkProjects_mame_mess(_target, _subtarget) "samsung", "sanyo", "saturn", + "screenless", "segacons", "sequential", "sgi", @@ -1523,11 +1521,6 @@ files { MAME_DIR .. "src/mame/machine/acs8600_ics.cpp", } -createMESSProjects(_target, _subtarget, "ami") -files { - MAME_DIR .. "src/mame/drivers/hh_amis2k.cpp", -} - createMESSProjects(_target, _subtarget, "amiga") files { MAME_DIR .. "src/mame/drivers/amiga.cpp", @@ -2225,11 +2218,6 @@ files { MAME_DIR .. "src/mame/includes/gp32.h", } -createMESSProjects(_target, _subtarget, "gi") -files { - MAME_DIR .. "src/mame/drivers/hh_pic16.cpp", -} - createMESSProjects(_target, _subtarget, "gridcomp") files { MAME_DIR .. "src/mame/drivers/gridcomp.cpp", @@ -2276,7 +2264,6 @@ files { MAME_DIR .. "src/mame/drivers/b16.cpp", MAME_DIR .. "src/mame/drivers/bmjr.cpp", MAME_DIR .. "src/mame/drivers/bml3.cpp", - MAME_DIR .. "src/mame/drivers/hh_hmcs40.cpp", } createMESSProjects(_target, _subtarget, "homebrew") @@ -2600,7 +2587,6 @@ files { createMESSProjects(_target, _subtarget, "mitsubishi") files { - MAME_DIR .. "src/mame/drivers/hh_melps4.cpp", MAME_DIR .. "src/mame/drivers/multi8.cpp", MAME_DIR .. "src/mame/drivers/multi16.cpp", } @@ -2700,8 +2686,6 @@ files { MAME_DIR .. "src/mame/machine/pc9801_cd.cpp", MAME_DIR .. "src/mame/machine/pc9801_cd.h", MAME_DIR .. "src/mame/drivers/tk80bs.cpp", - MAME_DIR .. "src/mame/drivers/hh_ucom4.cpp", - MAME_DIR .. "src/mame/includes/hh_ucom4.h", } createMESSProjects(_target, _subtarget, "netronic") @@ -2801,11 +2785,6 @@ files { MAME_DIR .. "src/mame/drivers/peoplepc.cpp", } -createMESSProjects(_target, _subtarget, "ns") -files { - MAME_DIR .. "src/mame/drivers/hh_cop400.cpp", -} - createMESSProjects(_target, _subtarget, "omnibyte") files { MAME_DIR .. "src/mame/drivers/msbc1.cpp", @@ -3002,8 +2981,6 @@ files { MAME_DIR .. "src/mame/drivers/rmt32.cpp", MAME_DIR .. "src/mame/drivers/rd110.cpp", MAME_DIR .. "src/mame/drivers/rsc55.cpp", - MAME_DIR .. "src/mame/drivers/tb303.cpp", - MAME_DIR .. "src/mame/drivers/tr606.cpp", } createMESSProjects(_target, _subtarget, "rolm") @@ -3056,11 +3033,31 @@ files { MAME_DIR .. "src/mame/machine/mbc55x_kbd.h", } +-- for drivers that are subclass of screenless_state +createMESSProjects(_target, _subtarget, "screenless") +files { + MAME_DIR .. "src/mame/machine/screenless.cpp", + MAME_DIR .. "src/mame/includes/screenless.h", + MAME_DIR .. "src/mame/drivers/hh_amis2k.cpp", + MAME_DIR .. "src/mame/drivers/hh_cop400.cpp", + MAME_DIR .. "src/mame/drivers/hh_hmcs40.cpp", + MAME_DIR .. "src/mame/drivers/hh_pic16.cpp", + MAME_DIR .. "src/mame/drivers/hh_ucom4.cpp", + MAME_DIR .. "src/mame/includes/hh_ucom4.h", + MAME_DIR .. "src/mame/drivers/tb303.cpp", + MAME_DIR .. "src/mame/drivers/tr606.cpp", + MAME_DIR .. "src/mame/drivers/hh_melps4.cpp", + MAME_DIR .. "src/mame/drivers/hh_tms1k.cpp", + MAME_DIR .. "src/mame/includes/hh_tms1k.h", + MAME_DIR .. "src/mame/drivers/ticalc1x.cpp", + MAME_DIR .. "src/mame/drivers/tispeak.cpp", + MAME_DIR .. "src/mame/drivers/tispellb.cpp", +} + -- Don't call this project "sega" or it collides with the arcade one -- and merges with it, which ends up with libsega.a linked after -- libshared.a. The link then fails on linux because SEGAM1AUDIO and RAX -- are in shared while model* and stv are in sega. - createMESSProjects(_target, _subtarget, "segacons") files { MAME_DIR .. "src/mame/drivers/dccons.cpp", @@ -3129,6 +3126,7 @@ createMESSProjects(_target, _subtarget, "sharp") files { MAME_DIR .. "src/mame/drivers/hh_sm510.cpp", MAME_DIR .. "src/mame/includes/hh_sm510.h", + MAME_DIR .. "src/mame/drivers/rzone.cpp", -- subdriver of hh_sm510 MAME_DIR .. "src/mame/video/mz700.cpp", MAME_DIR .. "src/mame/drivers/mz700.cpp", MAME_DIR .. "src/mame/includes/mz700.h", @@ -3421,9 +3419,6 @@ files { MAME_DIR .. "src/mame/drivers/evmbug.cpp", MAME_DIR .. "src/mame/drivers/exelv.cpp", MAME_DIR .. "src/mame/drivers/geneve.cpp", - MAME_DIR .. "src/mame/drivers/ticalc1x.cpp", - MAME_DIR .. "src/mame/drivers/tispeak.cpp", - MAME_DIR .. "src/mame/drivers/tispellb.cpp", MAME_DIR .. "src/mame/drivers/ti74.cpp", MAME_DIR .. "src/mame/drivers/ti85.cpp", MAME_DIR .. "src/mame/includes/ti85.h", @@ -3445,8 +3440,6 @@ files { MAME_DIR .. "src/mame/video/911_vdt.h", MAME_DIR .. "src/mame/video/911_chr.h", MAME_DIR .. "src/mame/video/911_key.h", - MAME_DIR .. "src/mame/drivers/hh_tms1k.cpp", - MAME_DIR .. "src/mame/includes/hh_tms1k.h", } createMESSProjects(_target, _subtarget, "tiger") @@ -3456,7 +3449,6 @@ files { MAME_DIR .. "src/mame/machine/gamecom.cpp", MAME_DIR .. "src/mame/video/gamecom.cpp", MAME_DIR .. "src/mame/drivers/k28.cpp", - MAME_DIR .. "src/mame/drivers/rzone.cpp", } createMESSProjects(_target, _subtarget, "tigertel") diff --git a/src/mame/drivers/fidel_chesster.cpp b/src/mame/drivers/fidel_chesster.cpp index 8ca546e5eb3..3a87fd3ece5 100644 --- a/src/mame/drivers/fidel_chesster.cpp +++ b/src/mame/drivers/fidel_chesster.cpp @@ -196,20 +196,20 @@ ROM_START( chesstera ) // model 6120, PCB label 510.1141C01 ROM_LOAD("101-1091a02.ic10", 0x0000, 0x20000, CRC(2b4d243c) SHA1(921e51978facb502b207b4f64a73b1e74127e826) ) // AMI, 27C010 or equivalent ROM_END -ROM_START( kishon ) // possibly Mephisto brand?, PCB label 510.1141C01 +ROM_START( kishon ) // model 6120G or 6127(same), PCB label 510.1141C01 ROM_REGION( 0x10000, "maincpu", 0 ) - ROM_LOAD("german_chesster_v2.2.ic9", 0x8000, 0x8000, CRC(43e0cfcd) SHA1(961c7335f562b19fa96324c429ab70e8ab4d7647) ) // 27C256, 15.1.91 + ROM_LOAD("gc_2.3.ic9", 0x8000, 0x8000, CRC(121c007f) SHA1(652e9ea47b6bb1632d10eb0fcd7f98cdba22fce7) ) // 27C256, GC 2.3 on sticker, also seen without label ROM_REGION( 0x80000, "rombank", 0 ) - ROM_LOAD("kishon_chesster_v2.6.ic10", 0x0000, 0x80000, CRC(50598869) SHA1(2087e0c2f40a2408fe217a6502c8c3a247bdd063) ) // Toshiba TC544000P-12 + ROM_LOAD("kishon_chesster_v2.6.ic10", 0x0000, 0x80000, CRC(50598869) SHA1(2087e0c2f40a2408fe217a6502c8c3a247bdd063) ) // Toshiba TC544000P-12, 1-14-91, aka 101-1094A01 on 6127 ROM_END -ROM_START( kishona ) // model 6120G or 6127(same), PCB label 510.1141C01 +ROM_START( kishona ) // possibly Mephisto brand?, PCB label 510.1141C01 ROM_REGION( 0x10000, "maincpu", 0 ) - ROM_LOAD("kishon.ic9", 0x8000, 0x8000, CRC(121c007f) SHA1(652e9ea47b6bb1632d10eb0fcd7f98cdba22fce7) ) // 27C256, no label + ROM_LOAD("german_chesster_v2.2.ic9", 0x8000, 0x8000, CRC(43e0cfcd) SHA1(961c7335f562b19fa96324c429ab70e8ab4d7647) ) // 27C256, 15.1.91 ROM_REGION( 0x80000, "rombank", 0 ) - ROM_LOAD("kishon_chesster_v2.6.ic10", 0x0000, 0x80000, CRC(50598869) SHA1(2087e0c2f40a2408fe217a6502c8c3a247bdd063) ) // Toshiba TC544000P-12, 1-14-91, aka 101-1094A01 on 6127 + ROM_LOAD("kishon_chesster_v2.6.ic10", 0x0000, 0x80000, CRC(50598869) SHA1(2087e0c2f40a2408fe217a6502c8c3a247bdd063) ) // Toshiba TC544000P-12 ROM_END } // anonymous namespace @@ -223,5 +223,5 @@ ROM_END // YEAR NAME PARENT CMP MACHINE INPUT STATE INIT COMPANY, FULLNAME, FLAGS CONS( 1990, chesster, 0, 0, chesster, chesster, chesster_state, init_chesster, "Fidelity Electronics", "Chesster Challenger (v1.3)", MACHINE_SUPPORTS_SAVE | MACHINE_CLICKABLE_ARTWORK | MACHINE_IMPERFECT_CONTROLS ) CONS( 1990, chesstera, chesster, 0, chesster, chesster, chesster_state, init_chesster, "Fidelity Electronics", "Chesster Challenger", MACHINE_SUPPORTS_SAVE | MACHINE_CLICKABLE_ARTWORK | MACHINE_IMPERFECT_CONTROLS ) -CONS( 1991, kishon, chesster, 0, kishon, chesster, chesster_state, init_chesster, "Fidelity Electronics", "Kishon Chesster (v2.2)", MACHINE_SUPPORTS_SAVE | MACHINE_CLICKABLE_ARTWORK | MACHINE_IMPERFECT_CONTROLS ) -CONS( 1991, kishona, chesster, 0, kishon, chesster, chesster_state, init_chesster, "Fidelity Electronics", "Kishon Chesster", MACHINE_SUPPORTS_SAVE | MACHINE_CLICKABLE_ARTWORK | MACHINE_IMPERFECT_CONTROLS ) +CONS( 1991, kishon, chesster, 0, kishon, chesster, chesster_state, init_chesster, "Fidelity Electronics", "Kishon Chesster (v2.3)", MACHINE_SUPPORTS_SAVE | MACHINE_CLICKABLE_ARTWORK | MACHINE_IMPERFECT_CONTROLS ) +CONS( 1991, kishona, chesster, 0, kishon, chesster, chesster_state, init_chesster, "Fidelity Electronics", "Kishon Chesster (v2.2)", MACHINE_SUPPORTS_SAVE | MACHINE_CLICKABLE_ARTWORK | MACHINE_IMPERFECT_CONTROLS ) diff --git a/src/mame/drivers/hh_amis2k.cpp b/src/mame/drivers/hh_amis2k.cpp index 4eb4046608f..8d4bdddb745 100644 --- a/src/mame/drivers/hh_amis2k.cpp +++ b/src/mame/drivers/hh_amis2k.cpp @@ -9,12 +9,11 @@ - were any other handhelds with this MCU released? - wildfire sound can be improved, volume decay should be more steep at the start, and the pitch sounds wrong too (latter is an MCU emulation problem) - - leds are sometimes strobed faster/longer to appear at a different brightness, - eg. wildfire bumpers ***************************************************************************/ #include "emu.h" +#include "includes/screenless.h" #include "cpu/amis2000/amis2000.h" #include "machine/timer.h" @@ -27,28 +26,19 @@ //#include "hh_amis2k_test.lh" // common test-layout - use external artwork -class hh_amis2k_state : public driver_device +class hh_amis2k_state : public screenless_state { public: hh_amis2k_state(const machine_config &mconfig, device_type type, const char *tag) : - driver_device(mconfig, type, tag), + screenless_state(mconfig, type, tag), m_maincpu(*this, "maincpu"), m_inp_matrix(*this, "IN.%u", 0), - m_out_x(*this, "%u.%u", 0U, 0U), - m_out_a(*this, "%u.a", 0U), - m_out_digit(*this, "digit%u", 0U), - m_speaker(*this, "speaker"), - m_display_wait(33), - m_display_maxy(1), - m_display_maxx(0) + m_speaker(*this, "speaker") { } // devices required_device m_maincpu; optional_ioport_array<4> m_inp_matrix; // max 4 - output_finder<0x20, 0x20> m_out_x; - output_finder<0x20> m_out_a; - output_finder<0x20> m_out_digit; optional_device m_speaker; // misc common @@ -59,21 +49,6 @@ public: u8 read_inputs(int columns); - // display common - int m_display_wait; // led/lamp off-delay in milliseconds (default 33ms) - int m_display_maxy; // display matrix number of rows - int m_display_maxx; // display matrix number of columns (max 31 for now) - - u32 m_display_state[0x20]; // display matrix rows data (last bit is used for always-on) - u16 m_display_segmask[0x20]; // if not 0, display matrix row is a digit, mask indicates connected segments - u8 m_display_decay[0x20][0x20]; // (internal use) - - TIMER_DEVICE_CALLBACK_MEMBER(display_decay_tick); - void display_update(); - void set_display_size(int maxx, int maxy); - void set_display_segmask(u32 digits, u32 mask); - void display_matrix(int maxx, int maxy, u32 setx, u32 sety, bool update = true); - protected: virtual void machine_start() override; virtual void machine_reset() override; @@ -84,30 +59,15 @@ protected: void hh_amis2k_state::machine_start() { - // resolve handlers - m_out_x.resolve(); - m_out_a.resolve(); - m_out_digit.resolve(); + screenless_state::machine_start(); // zerofill - memset(m_display_state, 0, sizeof(m_display_state)); - memset(m_display_decay, 0, sizeof(m_display_decay)); - memset(m_display_segmask, 0, sizeof(m_display_segmask)); - m_a = 0; m_d = 0; m_f = 0; m_inp_mux = 0; // register for savestates - save_item(NAME(m_display_maxy)); - save_item(NAME(m_display_maxx)); - save_item(NAME(m_display_wait)); - - save_item(NAME(m_display_state)); - save_item(NAME(m_display_decay)); - save_item(NAME(m_display_segmask)); - save_item(NAME(m_a)); save_item(NAME(m_d)); save_item(NAME(m_f)); @@ -126,80 +86,6 @@ void hh_amis2k_state::machine_reset() ***************************************************************************/ -// The device may strobe the outputs very fast, it is unnoticeable to the user. -// To prevent flickering here, we need to simulate a decay. - -void hh_amis2k_state::display_update() -{ - for (int y = 0; y < m_display_maxy; y++) - { - u32 active_state = 0; - - for (int x = 0; x <= m_display_maxx; x++) - { - // turn on powered segments - if (m_display_state[y] >> x & 1) - m_display_decay[y][x] = m_display_wait; - - // determine active state - u32 ds = (m_display_decay[y][x] != 0) ? 1 : 0; - active_state |= (ds << x); - - // output to y.x, or y.a when always-on - if (x != m_display_maxx) - m_out_x[y][x] = ds; - else - m_out_a[y] = ds; - } - - // output to digity - if (m_display_segmask[y] != 0) - m_out_digit[y] = active_state & m_display_segmask[y]; - } -} - -TIMER_DEVICE_CALLBACK_MEMBER(hh_amis2k_state::display_decay_tick) -{ - // slowly turn off unpowered segments - for (int y = 0; y < m_display_maxy; y++) - for (int x = 0; x <= m_display_maxx; x++) - if (m_display_decay[y][x] != 0) - m_display_decay[y][x]--; - - display_update(); -} - -void hh_amis2k_state::set_display_size(int maxx, int maxy) -{ - m_display_maxx = maxx; - m_display_maxy = maxy; -} - -void hh_amis2k_state::set_display_segmask(u32 digits, u32 mask) -{ - // set a segment mask per selected digit, but leave unselected ones alone - for (int i = 0; i < 0x20; i++) - { - if (digits & 1) - m_display_segmask[i] = mask; - digits >>= 1; - } -} - -void hh_amis2k_state::display_matrix(int maxx, int maxy, u32 setx, u32 sety, bool update) -{ - set_display_size(maxx, maxy); - - // update current state - u32 mask = (1 << maxx) - 1; - for (int y = 0; y < maxy; y++) - m_display_state[y] = (sety >> y & 1) ? ((setx & mask) | (1 << maxx)) : 0; - - if (update) - display_update(); -} - - // generic input handlers u8 hh_amis2k_state::read_inputs(int columns) @@ -258,7 +144,10 @@ class wildfire_state : public hh_amis2k_state public: wildfire_state(const machine_config &mconfig, device_type type, const char *tag) : hh_amis2k_state(mconfig, type, tag) - { } + { + // bumpers are dimmed + set_display_levels(2, 0.015, 0.1); + } void prepare_display(); DECLARE_WRITE8_MEMBER(write_d); @@ -360,7 +249,6 @@ void wildfire_state::wildfire(machine_config &config) m_maincpu->write_a().set(FUNC(wildfire_state::write_a)); m_maincpu->write_f().set(FUNC(wildfire_state::write_f)); - TIMER(config, "display_decay").configure_periodic(FUNC(hh_amis2k_state::display_decay_tick), attotime::from_msec(1)); config.set_default_layout(layout_wildfire); /* sound hardware */ diff --git a/src/mame/drivers/hh_cop400.cpp b/src/mame/drivers/hh_cop400.cpp index ff72e840fcf..8ea108057d7 100644 --- a/src/mame/drivers/hh_cop400.cpp +++ b/src/mame/drivers/hh_cop400.cpp @@ -17,8 +17,9 @@ ***************************************************************************/ #include "emu.h" -#include "cpu/cop400/cop400.h" +#include "includes/screenless.h" +#include "cpu/cop400/cop400.h" #include "machine/timer.h" #include "sound/spkrdev.h" #include "sound/dac.h" @@ -45,28 +46,19 @@ //#include "hh_cop400_test.lh" // common test-layout - use external artwork -class hh_cop400_state : public driver_device +class hh_cop400_state : public screenless_state { public: hh_cop400_state(const machine_config &mconfig, device_type type, const char *tag) : - driver_device(mconfig, type, tag), + screenless_state(mconfig, type, tag), m_maincpu(*this, "maincpu"), m_inp_matrix(*this, "IN.%u", 0), - m_out_x(*this, "%u.%u", 0U, 0U), - m_out_a(*this, "%u.a", 0U), - m_out_digit(*this, "digit%u", 0U), - m_speaker(*this, "speaker"), - m_display_wait(33), - m_display_maxy(1), - m_display_maxx(0) + m_speaker(*this, "speaker") { } // devices required_device m_maincpu; optional_ioport_array<6> m_inp_matrix; // max 6 - output_finder<0x20, 0x20> m_out_x; - output_finder<0x20> m_out_a; - output_finder<0x20> m_out_digit; optional_device m_speaker; // misc common @@ -80,21 +72,6 @@ public: u16 read_inputs(int columns, u16 colmask = ~0); virtual DECLARE_INPUT_CHANGED_MEMBER(reset_button); - // display common - int m_display_wait; // led/lamp off-delay in milliseconds (default 33ms) - int m_display_maxy; // display matrix number of rows - int m_display_maxx; // display matrix number of columns (max 31 for now) - - u32 m_display_state[0x20]; // display matrix rows data (last bit is used for always-on) - u16 m_display_segmask[0x20]; // if not 0, display matrix row is a digit, mask indicates connected segments - u8 m_display_decay[0x20][0x20]; // (internal use) - - TIMER_DEVICE_CALLBACK_MEMBER(display_decay_tick); - void display_update(); - void set_display_size(int maxx, int maxy); - void set_display_segmask(u32 digits, u32 mask); - void display_matrix(int maxx, int maxy, u32 setx, u32 sety, bool update = true); - protected: virtual void machine_start() override; virtual void machine_reset() override; @@ -105,16 +82,9 @@ protected: void hh_cop400_state::machine_start() { - // resolve handlers - m_out_x.resolve(); - m_out_a.resolve(); - m_out_digit.resolve(); + screenless_state::machine_start(); // zerofill - memset(m_display_state, 0, sizeof(m_display_state)); - memset(m_display_decay, 0, sizeof(m_display_decay)); - memset(m_display_segmask, 0, sizeof(m_display_segmask)); - m_l = 0; m_g = 0; m_d = 0; @@ -123,14 +93,6 @@ void hh_cop400_state::machine_start() m_inp_mux = ~0; // register for savestates - save_item(NAME(m_display_maxy)); - save_item(NAME(m_display_maxx)); - save_item(NAME(m_display_wait)); - - save_item(NAME(m_display_state)); - save_item(NAME(m_display_decay)); - save_item(NAME(m_display_segmask)); - save_item(NAME(m_l)); save_item(NAME(m_g)); save_item(NAME(m_d)); @@ -151,80 +113,6 @@ void hh_cop400_state::machine_reset() ***************************************************************************/ -// The device may strobe the outputs very fast, it is unnoticeable to the user. -// To prevent flickering here, we need to simulate a decay. - -void hh_cop400_state::display_update() -{ - for (int y = 0; y < m_display_maxy; y++) - { - u32 active_state = 0; - - for (int x = 0; x <= m_display_maxx; x++) - { - // turn on powered segments - if (m_display_state[y] >> x & 1) - m_display_decay[y][x] = m_display_wait; - - // determine active state - u32 ds = (m_display_decay[y][x] != 0) ? 1 : 0; - active_state |= (ds << x); - - // output to y.x, or y.a when always-on - if (x != m_display_maxx) - m_out_x[y][x] = ds; - else - m_out_a[y] = ds; - } - - // output to digity - if (m_display_segmask[y] != 0) - m_out_digit[y] = active_state & m_display_segmask[y]; - } -} - -TIMER_DEVICE_CALLBACK_MEMBER(hh_cop400_state::display_decay_tick) -{ - // slowly turn off unpowered segments - for (int y = 0; y < m_display_maxy; y++) - for (int x = 0; x <= m_display_maxx; x++) - if (m_display_decay[y][x] != 0) - m_display_decay[y][x]--; - - display_update(); -} - -void hh_cop400_state::set_display_size(int maxx, int maxy) -{ - m_display_maxx = maxx; - m_display_maxy = maxy; -} - -void hh_cop400_state::set_display_segmask(u32 digits, u32 mask) -{ - // set a segment mask per selected digit, but leave unselected ones alone - for (int i = 0; i < 0x20; i++) - { - if (digits & 1) - m_display_segmask[i] = mask; - digits >>= 1; - } -} - -void hh_cop400_state::display_matrix(int maxx, int maxy, u32 setx, u32 sety, bool update) -{ - set_display_size(maxx, maxy); - - // update current state - u32 mask = (1 << maxx) - 1; - for (int y = 0; y < maxy; y++) - m_display_state[y] = (sety >> y & 1) ? ((setx & mask) | (1 << maxx)) : 0; - - if (update) - display_update(); -} - - // generic input handlers u16 hh_cop400_state::read_inputs(int columns, u16 colmask) @@ -332,7 +220,6 @@ void ctstein_state::ctstein(machine_config &config) m_maincpu->write_sk().set(m_speaker, FUNC(speaker_sound_device::level_w)); m_maincpu->read_l().set(FUNC(ctstein_state::read_l)); - TIMER(config, "display_decay").configure_periodic(FUNC(hh_cop400_state::display_decay_tick), attotime::from_msec(1)); config.set_default_layout(layout_ctstein); /* sound hardware */ @@ -409,9 +296,7 @@ WRITE8_MEMBER(h2hbaskbc_state::write_l) set_display_segmask(3, 0x7f); // L0-L6: digit segments A-G, L0-L4: led data - // strobe display display_matrix(7, 16, data, sel); - display_matrix(7, 16, 0, 0); } READ8_MEMBER(h2hbaskbc_state::read_in) @@ -482,7 +367,6 @@ void h2hbaskbc_state::h2hbaskbc(machine_config &config) m_maincpu->read_in().set(FUNC(h2hbaskbc_state::read_in)); m_maincpu->write_so().set(m_speaker, FUNC(speaker_sound_device::level_w)); - TIMER(config, "display_decay").configure_periodic(FUNC(hh_cop400_state::display_decay_tick), attotime::from_msec(1)); config.set_default_layout(layout_h2hbaskbc); /* sound hardware */ @@ -619,11 +503,10 @@ void einvaderc_state::einvaderc(machine_config &config) /* video hardware */ screen_device &screen(SCREEN(config, "screen", SCREEN_TYPE_SVG)); screen.set_svg_region("svg"); - screen.set_refresh_hz(50); + screen.set_refresh_hz(60); screen.set_size(913, 1080); screen.set_visarea_full(); - TIMER(config, "display_decay").configure_periodic(FUNC(hh_cop400_state::display_decay_tick), attotime::from_msec(1)); config.set_default_layout(layout_einvaderc); /* sound hardware */ @@ -751,7 +634,6 @@ void unkeinv_state::unkeinv(machine_config &config) m_maincpu->read_l_tristate().set_constant(0xff); m_maincpu->write_so().set(m_speaker, FUNC(speaker_sound_device::level_w)); - TIMER(config, "display_decay").configure_periodic(FUNC(hh_cop400_state::display_decay_tick), attotime::from_msec(1)); config.set_default_layout(layout_unkeinv); /* sound hardware */ @@ -914,7 +796,6 @@ void lchicken_state::lchicken(machine_config &config) m_maincpu->read_si().set(FUNC(lchicken_state::read_si)); TIMER(config, "chicken_motor").configure_periodic(FUNC(lchicken_state::motor_sim_tick), attotime::from_msec(6000/0x100)); // ~6sec for a full rotation - TIMER(config, "display_decay").configure_periodic(FUNC(hh_cop400_state::display_decay_tick), attotime::from_msec(1)); config.set_default_layout(layout_lchicken); /* sound hardware */ @@ -1028,7 +909,6 @@ void funjacks_state::funjacks(machine_config &config) m_maincpu->read_l().set(FUNC(funjacks_state::read_l)); m_maincpu->read_g().set(FUNC(funjacks_state::read_g)); - TIMER(config, "display_decay").configure_periodic(FUNC(hh_cop400_state::display_decay_tick), attotime::from_msec(1)); config.set_default_layout(layout_funjacks); /* sound hardware */ @@ -1121,7 +1001,6 @@ void funrlgl_state::funrlgl(machine_config &config) m_maincpu->write_g().set(FUNC(funrlgl_state::write_g)); m_maincpu->read_g().set_ioport("IN.0"); - TIMER(config, "display_decay").configure_periodic(FUNC(hh_cop400_state::display_decay_tick), attotime::from_msec(1)); config.set_default_layout(layout_funrlgl); /* sound hardware */ @@ -1263,7 +1142,6 @@ void mdallas_state::mdallas(machine_config &config) m_maincpu->read_in().set(FUNC(mdallas_state::read_in)); m_maincpu->write_so().set(m_speaker, FUNC(speaker_sound_device::level_w)); - TIMER(config, "display_decay").configure_periodic(FUNC(hh_cop400_state::display_decay_tick), attotime::from_msec(1)); config.set_default_layout(layout_mdallas); /* sound hardware */ @@ -1487,7 +1365,6 @@ void lightfgt_state::lightfgt(machine_config &config) m_maincpu->write_sk().set(m_speaker, FUNC(speaker_sound_device::level_w)); m_maincpu->read_g().set(FUNC(lightfgt_state::read_g)); - TIMER(config, "display_decay").configure_periodic(FUNC(hh_cop400_state::display_decay_tick), attotime::from_msec(1)); config.set_default_layout(layout_lightfgt); /* sound hardware */ @@ -1648,7 +1525,6 @@ void bship82_state::bship82(machine_config &config) m_maincpu->write_so().set(FUNC(bship82_state::write_so)); m_maincpu->read_si().set_ioport("IN.4"); - TIMER(config, "display_decay").configure_periodic(FUNC(hh_cop400_state::display_decay_tick), attotime::from_msec(1)); config.set_default_layout(layout_bship82); /* sound hardware */ @@ -1787,7 +1663,6 @@ void qkracer_state::qkracer(machine_config &config) m_maincpu->read_in().set(FUNC(qkracer_state::read_in)); m_maincpu->write_sk().set(FUNC(qkracer_state::write_sk)); - TIMER(config, "display_decay").configure_periodic(FUNC(hh_cop400_state::display_decay_tick), attotime::from_msec(1)); config.set_default_layout(layout_qkracer); /* no sound! */ @@ -1885,7 +1760,6 @@ void vidchal_state::vidchal(machine_config &config) m_maincpu->read_in().set_ioport("IN.0"); m_maincpu->write_sk().set(FUNC(vidchal_state::write_sk)); - TIMER(config, "display_decay").configure_periodic(FUNC(hh_cop400_state::display_decay_tick), attotime::from_msec(1)); config.set_default_layout(layout_vidchal); /* sound hardware */ diff --git a/src/mame/drivers/hh_hmcs40.cpp b/src/mame/drivers/hh_hmcs40.cpp index ad15dc6185a..73bd6f595a5 100644 --- a/src/mame/drivers/hh_hmcs40.cpp +++ b/src/mame/drivers/hh_hmcs40.cpp @@ -80,16 +80,14 @@ - Though very uncommon when compared to games with LED/lamp display, some games may manipulate VFD plate brightness by strobing it longer/shorter, eg. cgalaxn when the player ship explodes. - - Related to the above issue: bultrman sometimes strobes D0/D1/D2 for a very - short duration, causing (unwanted) dimly lit segments on the real machine. - On MAME they will show with full brightness, see eg. building explosions. - Currently there's a workaround in place. - bzaxxon 3D effect is difficult to simulate - improve/redo SVGs of: bzaxxon, bpengo, bbtime ***************************************************************************/ #include "emu.h" +#include "includes/screenless.h" + #include "cpu/hmcs40/hmcs40.h" #include "cpu/cop400/cop400.h" #include "machine/gen_latch.h" @@ -112,28 +110,19 @@ //#include "hh_hmcs40_test.lh" // common test-layout - no svg artwork(yet), use external artwork -class hh_hmcs40_state : public driver_device +class hh_hmcs40_state : public screenless_state { public: hh_hmcs40_state(const machine_config &mconfig, device_type type, const char *tag) : - driver_device(mconfig, type, tag), + screenless_state(mconfig, type, tag), m_maincpu(*this, "maincpu"), m_inp_matrix(*this, "IN.%u", 0), - m_out_x(*this, "%u.%u", 0U, 0U), - m_out_a(*this, "%u.a", 0U), - m_out_digit(*this, "digit%u", 0U), - m_speaker(*this, "speaker"), - m_display_wait(33), - m_display_maxy(1), - m_display_maxx(0) + m_speaker(*this, "speaker") { } // devices required_device m_maincpu; optional_ioport_array<7> m_inp_matrix; // max 7 - output_finder<0x20, 0x40> m_out_x; - output_finder<0x20> m_out_a; - output_finder<0x20> m_out_digit; optional_device m_speaker; // misc common @@ -142,29 +131,14 @@ public: u8 m_int[2]; // MCU INT0/1 pins state u16 m_inp_mux; // multiplexed inputs mask + u32 m_grid; // VFD current row data + u64 m_plate; // VFD current column data + u16 read_inputs(int columns); void refresh_interrupts(void); void set_interrupt(int line, int state); DECLARE_INPUT_CHANGED_MEMBER(single_interrupt_line); - // display common - int m_display_wait; // led/lamp off-delay in milliseconds (default 33ms) - int m_display_maxy; // display matrix number of rows - int m_display_maxx; // display matrix number of columns (max 47 for now) - - u32 m_grid; // VFD current row data - u64 m_plate; // VFD current column data - - u64 m_display_state[0x20]; // display matrix rows data (last bit is used for always-on) - u16 m_display_segmask[0x20]; // if not 0, display matrix row is a digit, mask indicates connected segments - u8 m_display_decay[0x20][0x40]; // (internal use) - - TIMER_DEVICE_CALLBACK_MEMBER(display_decay_tick); - void display_update(); - void set_display_size(int maxx, int maxy); - void set_display_segmask(u32 digits, u32 mask); - void display_matrix(int maxx, int maxy, u64 setx, u32 sety, bool update = true); - protected: virtual void machine_start() override; virtual void machine_reset() override; @@ -175,16 +149,9 @@ protected: void hh_hmcs40_state::machine_start() { - // resolve handlers - m_out_x.resolve(); - m_out_a.resolve(); - m_out_digit.resolve(); + screenless_state::machine_start(); // zerofill - memset(m_display_state, 0, sizeof(m_display_state)); - memset(m_display_decay, 0, sizeof(m_display_decay)); - memset(m_display_segmask, 0, sizeof(m_display_segmask)); - memset(m_r, 0, sizeof(m_r)); memset(m_int, 0, sizeof(m_int)); m_d = 0; @@ -193,14 +160,6 @@ void hh_hmcs40_state::machine_start() m_plate = 0; // register for savestates - save_item(NAME(m_display_maxy)); - save_item(NAME(m_display_maxx)); - save_item(NAME(m_display_wait)); - - save_item(NAME(m_display_state)); - save_item(NAME(m_display_decay)); - save_item(NAME(m_display_segmask)); - save_item(NAME(m_r)); save_item(NAME(m_int)); save_item(NAME(m_d)); @@ -222,80 +181,6 @@ void hh_hmcs40_state::machine_reset() ***************************************************************************/ -// The device may strobe the outputs very fast, it is unnoticeable to the user. -// To prevent flickering here, we need to simulate a decay. - -void hh_hmcs40_state::display_update() -{ - for (int y = 0; y < m_display_maxy; y++) - { - u64 active_state = 0; - - for (int x = 0; x <= m_display_maxx; x++) - { - // turn on powered segments - if (m_display_state[y] >> x & 1) - m_display_decay[y][x] = m_display_wait; - - // determine active state - u64 ds = (m_display_decay[y][x] != 0) ? 1 : 0; - active_state |= (ds << x); - - // output to y.x, or y.a when always-on - if (x != m_display_maxx) - m_out_x[y][x] = ds; - else - m_out_a[y] = ds; - } - - // output to digity - if (m_display_segmask[y] != 0) - m_out_digit[y] = active_state & m_display_segmask[y]; - } -} - -TIMER_DEVICE_CALLBACK_MEMBER(hh_hmcs40_state::display_decay_tick) -{ - // slowly turn off unpowered segments - for (int y = 0; y < m_display_maxy; y++) - for (int x = 0; x <= m_display_maxx; x++) - if (m_display_decay[y][x] != 0) - m_display_decay[y][x]--; - - display_update(); -} - -void hh_hmcs40_state::set_display_size(int maxx, int maxy) -{ - m_display_maxx = maxx; - m_display_maxy = maxy; -} - -void hh_hmcs40_state::set_display_segmask(u32 digits, u32 mask) -{ - // set a segment mask per selected digit, but leave unselected ones alone - for (int i = 0; i < 0x20; i++) - { - if (digits & 1) - m_display_segmask[i] = mask; - digits >>= 1; - } -} - -void hh_hmcs40_state::display_matrix(int maxx, int maxy, u64 setx, u32 sety, bool update) -{ - set_display_size(maxx, maxy); - - // update current state - u64 mask = (u64(1) << maxx) - 1; - for (int y = 0; y < maxy; y++) - m_display_state[y] = (sety >> y & 1) ? ((setx & mask) | (u64(1) << maxx)) : 0; - - if (update) - display_update(); -} - - // generic input handlers u16 hh_hmcs40_state::read_inputs(int columns) @@ -445,11 +330,10 @@ void bambball_state::bambball(machine_config &config) /* video hardware */ screen_device &screen(SCREEN(config, "screen", SCREEN_TYPE_SVG)); screen.set_svg_region("svg"); - screen.set_refresh_hz(50); + screen.set_refresh_hz(60); screen.set_size(1920, 478); screen.set_visarea_full(); - TIMER(config, "display_decay").configure_periodic(FUNC(hh_hmcs40_state::display_decay_tick), attotime::from_msec(1)); config.set_default_layout(layout_bambball); /* sound hardware */ @@ -594,12 +478,10 @@ void bmboxing_state::bmboxing(machine_config &config) /* video hardware */ screen_device &screen(SCREEN(config, "screen", SCREEN_TYPE_SVG)); screen.set_svg_region("svg"); - screen.set_refresh_hz(50); + screen.set_refresh_hz(60); screen.set_size(1920, 529); screen.set_visarea_full(); - TIMER(config, "display_decay").configure_periodic(FUNC(hh_hmcs40_state::display_decay_tick), attotime::from_msec(1)); - /* sound hardware */ SPEAKER(config, "mono").front_center(); SPEAKER_SOUND(config, m_speaker).add_route(ALL_OUTPUTS, "mono", 0.25); @@ -724,12 +606,10 @@ void bfriskyt_state::bfriskyt(machine_config &config) /* video hardware */ screen_device &screen(SCREEN(config, "screen", SCREEN_TYPE_SVG)); screen.set_svg_region("svg"); - screen.set_refresh_hz(50); + screen.set_refresh_hz(60); screen.set_size(1920, 675); screen.set_visarea_full(); - TIMER(config, "display_decay").configure_periodic(FUNC(hh_hmcs40_state::display_decay_tick), attotime::from_msec(1)); - /* sound hardware */ SPEAKER(config, "mono").front_center(); SPEAKER_SOUND(config, m_speaker).add_route(ALL_OUTPUTS, "mono", 0.25); @@ -846,11 +726,10 @@ void packmon_state::packmon(machine_config &config) /* video hardware */ screen_device &screen(SCREEN(config, "screen", SCREEN_TYPE_SVG)); screen.set_svg_region("svg"); - screen.set_refresh_hz(50); + screen.set_refresh_hz(60); screen.set_size(1920, 680); screen.set_visarea_full(); - TIMER(config, "display_decay").configure_periodic(FUNC(hh_hmcs40_state::display_decay_tick), attotime::from_msec(1)); config.set_default_layout(layout_packmon); /* sound hardware */ @@ -975,12 +854,10 @@ void bzaxxon_state::bzaxxon(machine_config &config) /* video hardware */ screen_device &screen(SCREEN(config, "screen", SCREEN_TYPE_SVG)); screen.set_svg_region("svg"); - screen.set_refresh_hz(50); + screen.set_refresh_hz(60); screen.set_size(613, 1080); screen.set_visarea_full(); - TIMER(config, "display_decay").configure_periodic(FUNC(hh_hmcs40_state::display_decay_tick), attotime::from_msec(1)); - /* sound hardware */ SPEAKER(config, "mono").front_center(); SPEAKER_SOUND(config, m_speaker).add_route(ALL_OUTPUTS, "mono", 0.25); @@ -1099,12 +976,10 @@ void zackman_state::zackman(machine_config &config) /* video hardware */ screen_device &screen(SCREEN(config, "screen", SCREEN_TYPE_SVG)); screen.set_svg_region("svg"); - screen.set_refresh_hz(50); + screen.set_refresh_hz(60); screen.set_size(487, 1080); screen.set_visarea_full(); - TIMER(config, "display_decay").configure_periodic(FUNC(hh_hmcs40_state::display_decay_tick), attotime::from_msec(1)); - /* sound hardware */ SPEAKER(config, "mono").front_center(); SPEAKER_SOUND(config, m_speaker).add_route(ALL_OUTPUTS, "mono", 0.25); @@ -1233,12 +1108,10 @@ void bpengo_state::bpengo(machine_config &config) /* video hardware */ screen_device &screen(SCREEN(config, "screen", SCREEN_TYPE_SVG)); screen.set_svg_region("svg"); - screen.set_refresh_hz(50); + screen.set_refresh_hz(60); screen.set_size(1920, 759); screen.set_visarea_full(); - TIMER(config, "display_decay").configure_periodic(FUNC(hh_hmcs40_state::display_decay_tick), attotime::from_msec(1)); - /* sound hardware */ SPEAKER(config, "mono").front_center(); SPEAKER_SOUND(config, m_speaker).add_route(ALL_OUTPUTS, "mono", 0.25); @@ -1363,12 +1236,10 @@ void bbtime_state::bbtime(machine_config &config) /* video hardware */ screen_device &screen(SCREEN(config, "screen", SCREEN_TYPE_SVG)); screen.set_svg_region("svg"); - screen.set_refresh_hz(50); + screen.set_refresh_hz(60); screen.set_size(379, 1080); screen.set_visarea_full(); - TIMER(config, "display_decay").configure_periodic(FUNC(hh_hmcs40_state::display_decay_tick), attotime::from_msec(1)); - /* sound hardware */ SPEAKER(config, "mono").front_center(); SPEAKER_SOUND(config, m_speaker).add_route(ALL_OUTPUTS, "mono", 0.25); @@ -1473,12 +1344,10 @@ void bdoramon_state::bdoramon(machine_config &config) /* video hardware */ screen_device &screen(SCREEN(config, "screen", SCREEN_TYPE_SVG)); screen.set_svg_region("svg"); - screen.set_refresh_hz(50); + screen.set_refresh_hz(60); screen.set_size(1920, 668); screen.set_visarea_full(); - TIMER(config, "display_decay").configure_periodic(FUNC(hh_hmcs40_state::display_decay_tick), attotime::from_msec(1)); - /* sound hardware */ SPEAKER(config, "mono").front_center(); SPEAKER_SOUND(config, m_speaker).add_route(ALL_OUTPUTS, "mono", 0.25); @@ -1543,8 +1412,7 @@ WRITE16_MEMBER(bultrman_state::grid_w) m_grid = data >> 8 & 0xff; // D0-D2: plate 15-17 (update display there) - //plate_w(space, 4, data & 7); - plate_w(space, 4, data & (1 << offset) & 7); + plate_w(space, 4, data & 7); } // config @@ -1576,12 +1444,10 @@ void bultrman_state::bultrman(machine_config &config) /* video hardware */ screen_device &screen(SCREEN(config, "screen", SCREEN_TYPE_SVG)); screen.set_svg_region("svg"); - screen.set_refresh_hz(50); + screen.set_refresh_hz(60); screen.set_size(1920, 673); screen.set_visarea_full(); - TIMER(config, "display_decay").configure_periodic(FUNC(hh_hmcs40_state::display_decay_tick), attotime::from_msec(1)); - /* sound hardware */ SPEAKER(config, "mono").front_center(); SPEAKER_SOUND(config, m_speaker).add_route(ALL_OUTPUTS, "mono", 0.25); @@ -1677,12 +1543,10 @@ void machiman_state::machiman(machine_config &config) /* video hardware */ screen_device &screen(SCREEN(config, "screen", SCREEN_TYPE_SVG)); screen.set_svg_region("svg"); - screen.set_refresh_hz(50); + screen.set_refresh_hz(60); screen.set_size(1534, 1080); screen.set_visarea_full(); - TIMER(config, "display_decay").configure_periodic(FUNC(hh_hmcs40_state::display_decay_tick), attotime::from_msec(1)); - /* sound hardware */ SPEAKER(config, "mono").front_center(); SPEAKER_SOUND(config, m_speaker).add_route(ALL_OUTPUTS, "mono", 0.25); @@ -1845,7 +1709,6 @@ void pairmtch_state::pairmtch(machine_config &config) config.m_perfect_cpu_quantum = subtag("maincpu"); - TIMER(config, "display_decay").configure_periodic(FUNC(hh_hmcs40_state::display_decay_tick), attotime::from_msec(1)); config.set_default_layout(layout_pairmtch); /* sound hardware */ @@ -1971,12 +1834,10 @@ void alnattck_state::alnattck(machine_config &config) /* video hardware */ screen_device &screen(SCREEN(config, "screen", SCREEN_TYPE_SVG)); screen.set_svg_region("svg"); - screen.set_refresh_hz(50); + screen.set_refresh_hz(60); screen.set_size(1920, 700); screen.set_visarea_full(); - TIMER(config, "display_decay").configure_periodic(FUNC(hh_hmcs40_state::display_decay_tick), attotime::from_msec(1)); - /* sound hardware */ SPEAKER(config, "mono").front_center(); SPEAKER_SOUND(config, m_speaker).add_route(ALL_OUTPUTS, "mono", 0.25); @@ -2116,12 +1977,10 @@ void cdkong_state::cdkong(machine_config &config) /* video hardware */ screen_device &screen(SCREEN(config, "screen", SCREEN_TYPE_SVG)); screen.set_svg_region("svg"); - screen.set_refresh_hz(50); + screen.set_refresh_hz(60); screen.set_size(605, 1080); screen.set_visarea_full(); - TIMER(config, "display_decay").configure_periodic(FUNC(hh_hmcs40_state::display_decay_tick), attotime::from_msec(1)); - /* sound hardware */ SPEAKER(config, "mono").front_center(); SPEAKER_SOUND(config, m_speaker).add_route(ALL_OUTPUTS, "mono", 0.25); @@ -2262,12 +2121,10 @@ void cgalaxn_state::cgalaxn(machine_config &config) /* video hardware */ screen_device &screen(SCREEN(config, "screen", SCREEN_TYPE_SVG)); screen.set_svg_region("svg"); - screen.set_refresh_hz(50); + screen.set_refresh_hz(60); screen.set_size(526, 1080); screen.set_visarea_full(); - TIMER(config, "display_decay").configure_periodic(FUNC(hh_hmcs40_state::display_decay_tick), attotime::from_msec(1)); - /* sound hardware */ SPEAKER(config, "mono").front_center(); SPEAKER_SOUND(config, m_speaker).add_route(ALL_OUTPUTS, "mono", 0.25); @@ -2395,12 +2252,10 @@ void cpacman_state::cpacman(machine_config &config) /* video hardware */ screen_device &screen(SCREEN(config, "screen", SCREEN_TYPE_SVG)); screen.set_svg_region("svg"); - screen.set_refresh_hz(50); + screen.set_refresh_hz(60); screen.set_size(484, 1080); screen.set_visarea_full(); - TIMER(config, "display_decay").configure_periodic(FUNC(hh_hmcs40_state::display_decay_tick), attotime::from_msec(1)); - /* sound hardware */ SPEAKER(config, "mono").front_center(); SPEAKER_SOUND(config, m_speaker).add_route(ALL_OUTPUTS, "mono", 0.25); @@ -2532,12 +2387,10 @@ void cmspacmn_state::cmspacmn(machine_config &config) /* video hardware */ screen_device &screen(SCREEN(config, "screen", SCREEN_TYPE_SVG)); screen.set_svg_region("svg"); - screen.set_refresh_hz(50); + screen.set_refresh_hz(60); screen.set_size(481, 1080); screen.set_visarea_full(); - TIMER(config, "display_decay").configure_periodic(FUNC(hh_hmcs40_state::display_decay_tick), attotime::from_msec(1)); - /* sound hardware */ SPEAKER(config, "mono").front_center(); SPEAKER_SOUND(config, m_speaker).add_route(ALL_OUTPUTS, "mono", 0.25); @@ -2685,7 +2538,6 @@ void sag_state::sag(machine_config &config) m_maincpu->write_d().set(FUNC(sag_state::grid_w)); m_maincpu->read_d().set(FUNC(sag_state::input_r)); - TIMER(config, "display_decay").configure_periodic(FUNC(hh_hmcs40_state::display_decay_tick), attotime::from_msec(1)); config.set_default_layout(layout_sag); /* sound hardware */ @@ -2824,12 +2676,10 @@ void egalaxn2_state::egalaxn2(machine_config &config) /* video hardware */ screen_device &screen(SCREEN(config, "screen", SCREEN_TYPE_SVG)); screen.set_svg_region("svg"); - screen.set_refresh_hz(50); + screen.set_refresh_hz(60); screen.set_size(505, 1080); screen.set_visarea_full(); - TIMER(config, "display_decay").configure_periodic(FUNC(hh_hmcs40_state::display_decay_tick), attotime::from_msec(1)); - /* sound hardware */ SPEAKER(config, "mono").front_center(); SPEAKER_SOUND(config, m_speaker).add_route(ALL_OUTPUTS, "mono", 0.25); @@ -3114,12 +2964,10 @@ void eturtles_state::eturtles(machine_config &config) /* video hardware */ screen_device &screen(SCREEN(config, "screen", SCREEN_TYPE_SVG)); screen.set_svg_region("svg"); - screen.set_refresh_hz(50); + screen.set_refresh_hz(60); screen.set_size(484, 1080); screen.set_visarea_full(); - TIMER(config, "display_decay").configure_periodic(FUNC(hh_hmcs40_state::display_decay_tick), attotime::from_msec(1)); - /* sound hardware */ SPEAKER(config, "mono").front_center(); SPEAKER_SOUND(config, m_speaker).add_route(ALL_OUTPUTS, "mono", 0.25); @@ -3237,12 +3085,10 @@ void estargte_state::estargte(machine_config &config) /* video hardware */ screen_device &screen(SCREEN(config, "screen", SCREEN_TYPE_SVG)); screen.set_svg_region("svg"); - screen.set_refresh_hz(50); + screen.set_refresh_hz(60); screen.set_size(1920, 854); screen.set_visarea_full(); - TIMER(config, "display_decay").configure_periodic(FUNC(hh_hmcs40_state::display_decay_tick), attotime::from_msec(1)); - /* sound hardware */ SPEAKER(config, "mono").front_center(); SPEAKER_SOUND(config, m_speaker).add_route(ALL_OUTPUTS, "mono", 0.25); @@ -3367,12 +3213,10 @@ void ghalien_state::ghalien(machine_config &config) /* video hardware */ screen_device &screen(SCREEN(config, "screen", SCREEN_TYPE_SVG)); screen.set_svg_region("svg"); - screen.set_refresh_hz(50); + screen.set_refresh_hz(60); screen.set_size(1920, 699); screen.set_visarea_full(); - TIMER(config, "display_decay").configure_periodic(FUNC(hh_hmcs40_state::display_decay_tick), attotime::from_msec(1)); - /* sound hardware */ SPEAKER(config, "mono").front_center(); SPEAKER_SOUND(config, m_speaker).add_route(ALL_OUTPUTS, "mono", 0.25); @@ -3500,11 +3344,10 @@ void gckong_state::gckong(machine_config &config) /* video hardware */ screen_device &screen(SCREEN(config, "screen", SCREEN_TYPE_SVG)); screen.set_svg_region("svg"); - screen.set_refresh_hz(50); + screen.set_refresh_hz(60); screen.set_size(479, 1080); screen.set_visarea_full(); - TIMER(config, "display_decay").configure_periodic(FUNC(hh_hmcs40_state::display_decay_tick), attotime::from_msec(1)); config.set_default_layout(layout_gckong); /* sound hardware */ @@ -3628,12 +3471,10 @@ void gdigdug_state::gdigdug(machine_config &config) /* video hardware */ screen_device &screen(SCREEN(config, "screen", SCREEN_TYPE_SVG)); screen.set_svg_region("svg"); - screen.set_refresh_hz(50); + screen.set_refresh_hz(60); screen.set_size(476, 1080); screen.set_visarea_full(); - TIMER(config, "display_decay").configure_periodic(FUNC(hh_hmcs40_state::display_decay_tick), attotime::from_msec(1)); - /* sound hardware */ SPEAKER(config, "mono").front_center(); SPEAKER_SOUND(config, m_speaker).add_route(ALL_OUTPUTS, "mono", 0.25); @@ -3800,11 +3641,10 @@ void mwcbaseb_state::mwcbaseb(machine_config &config) /* video hardware */ screen_device &screen(SCREEN(config, "screen", SCREEN_TYPE_SVG)); screen.set_svg_region("svg"); - screen.set_refresh_hz(50); + screen.set_refresh_hz(60); screen.set_size(1920, 478); screen.set_visarea_full(); - TIMER(config, "display_decay").configure_periodic(FUNC(hh_hmcs40_state::display_decay_tick), attotime::from_msec(1)); config.set_default_layout(layout_mwcbaseb); /* sound hardware */ @@ -3940,11 +3780,10 @@ void msthawk_state::msthawk(machine_config &config) /* video hardware */ screen_device &screen(SCREEN(config, "screen", SCREEN_TYPE_SVG)); screen.set_svg_region("svg"); - screen.set_refresh_hz(50); + screen.set_refresh_hz(60); screen.set_size(1920, 696); screen.set_visarea_full(); - TIMER(config, "display_decay").configure_periodic(FUNC(hh_hmcs40_state::display_decay_tick), attotime::from_msec(1)); config.set_default_layout(layout_msthawk); /* sound hardware */ @@ -4041,12 +3880,10 @@ void pbqbert_state::pbqbert(machine_config &config) /* video hardware */ screen_device &screen(SCREEN(config, "screen", SCREEN_TYPE_SVG)); screen.set_svg_region("svg"); - screen.set_refresh_hz(50); + screen.set_refresh_hz(60); screen.set_size(603, 1080); screen.set_visarea_full(); - TIMER(config, "display_decay").configure_periodic(FUNC(hh_hmcs40_state::display_decay_tick), attotime::from_msec(1)); - /* sound hardware */ SPEAKER(config, "mono").front_center(); SPEAKER_SOUND(config, m_speaker).add_route(ALL_OUTPUTS, "mono", 0.25); @@ -4168,12 +4005,10 @@ void kingman_state::kingman(machine_config &config) /* video hardware */ screen_device &screen(SCREEN(config, "screen", SCREEN_TYPE_SVG)); screen.set_svg_region("svg"); - screen.set_refresh_hz(50); + screen.set_refresh_hz(60); screen.set_size(374, 1080); screen.set_visarea_full(); - TIMER(config, "display_decay").configure_periodic(FUNC(hh_hmcs40_state::display_decay_tick), attotime::from_msec(1)); - /* sound hardware */ SPEAKER(config, "mono").front_center(); SPEAKER_SOUND(config, m_speaker).add_route(ALL_OUTPUTS, "mono", 0.25); @@ -4295,12 +4130,10 @@ void tmtron_state::tmtron(machine_config &config) /* video hardware */ screen_device &screen(SCREEN(config, "screen", SCREEN_TYPE_SVG)); screen.set_svg_region("svg"); - screen.set_refresh_hz(50); + screen.set_refresh_hz(60); screen.set_size(1920, 662); screen.set_visarea_full(); - TIMER(config, "display_decay").configure_periodic(FUNC(hh_hmcs40_state::display_decay_tick), attotime::from_msec(1)); - /* sound hardware */ SPEAKER(config, "mono").front_center(); SPEAKER_SOUND(config, m_speaker).add_route(ALL_OUTPUTS, "mono", 0.25); @@ -4401,12 +4234,10 @@ void vinvader_state::vinvader(machine_config &config) /* video hardware */ screen_device &screen(SCREEN(config, "screen", SCREEN_TYPE_SVG)); screen.set_svg_region("svg"); - screen.set_refresh_hz(50); + screen.set_refresh_hz(60); screen.set_size(233, 1080); screen.set_visarea_full(); - TIMER(config, "display_decay").configure_periodic(FUNC(hh_hmcs40_state::display_decay_tick), attotime::from_msec(1)); - /* sound hardware */ SPEAKER(config, "mono").front_center(); SPEAKER_SOUND(config, m_speaker).add_route(ALL_OUTPUTS, "mono", 0.25); diff --git a/src/mame/drivers/hh_melps4.cpp b/src/mame/drivers/hh_melps4.cpp index 4849df8f5d9..6c6a89df39f 100644 --- a/src/mame/drivers/hh_melps4.cpp +++ b/src/mame/drivers/hh_melps4.cpp @@ -9,6 +9,7 @@ ***************************************************************************/ #include "emu.h" +#include "includes/screenless.h" #include "cpu/melps4/m58846.h" #include "machine/timer.h" @@ -20,52 +21,29 @@ //#include "hh_melps4_test.lh" // common test-layout - no svg artwork(yet), use external artwork -class hh_melps4_state : public driver_device +class hh_melps4_state : public screenless_state { public: hh_melps4_state(const machine_config &mconfig, device_type type, const char *tag) : - driver_device(mconfig, type, tag), + screenless_state(mconfig, type, tag), m_maincpu(*this, "maincpu"), m_inp_matrix(*this, "IN.%u", 0), - m_out_x(*this, "%u.%u", 0U, 0U), - m_out_a(*this, "%u.a", 0U), - m_out_digit(*this, "digit%u", 0U), - m_speaker(*this, "speaker"), - m_display_wait(33), - m_display_maxy(1), - m_display_maxx(0) + m_speaker(*this, "speaker") { } // devices required_device m_maincpu; optional_ioport_array<4> m_inp_matrix; // max 4 - output_finder<0x20, 0x20> m_out_x; - output_finder<0x20> m_out_a; - output_finder<0x20> m_out_digit; optional_device m_speaker; // misc common u16 m_inp_mux; // multiplexed inputs mask - u8 read_inputs(int columns); - virtual DECLARE_INPUT_CHANGED_MEMBER(reset_button); - - // display common - int m_display_wait; // led/lamp off-delay in milliseconds (default 33ms) - int m_display_maxy; // display matrix number of rows - int m_display_maxx; // display matrix number of columns (max 31 for now) - u32 m_grid; // VFD current row data u32 m_plate; // VFD current column data - u32 m_display_state[0x20]; // display matrix rows data (last bit is used for always-on) - u16 m_display_segmask[0x20]; // if not 0, display matrix row is a digit, mask indicates connected segments - u8 m_display_decay[0x20][0x20]; // (internal use) - - TIMER_DEVICE_CALLBACK_MEMBER(display_decay_tick); - void display_update(); - void set_display_size(int maxx, int maxy); - void display_matrix(int maxx, int maxy, u32 setx, u32 sety, bool update = true); + u8 read_inputs(int columns); + virtual DECLARE_INPUT_CHANGED_MEMBER(reset_button); protected: virtual void machine_start() override; @@ -77,29 +55,14 @@ protected: void hh_melps4_state::machine_start() { - // resolve handlers - m_out_x.resolve(); - m_out_a.resolve(); - m_out_digit.resolve(); + screenless_state::machine_start(); // zerofill - memset(m_display_state, 0, sizeof(m_display_state)); - memset(m_display_decay, 0, sizeof(m_display_decay)); - memset(m_display_segmask, 0, sizeof(m_display_segmask)); - m_inp_mux = 0; m_grid = 0; m_plate = 0; // register for savestates - save_item(NAME(m_display_maxy)); - save_item(NAME(m_display_maxx)); - save_item(NAME(m_display_wait)); - - save_item(NAME(m_display_state)); - save_item(NAME(m_display_decay)); - save_item(NAME(m_display_segmask)); - save_item(NAME(m_inp_mux)); save_item(NAME(m_grid)); save_item(NAME(m_plate)); @@ -117,69 +80,6 @@ void hh_melps4_state::machine_reset() ***************************************************************************/ -// The device may strobe the outputs very fast, it is unnoticeable to the user. -// To prevent flickering here, we need to simulate a decay. - -void hh_melps4_state::display_update() -{ - for (int y = 0; y < m_display_maxy; y++) - { - u32 active_state = 0; - - for (int x = 0; x <= m_display_maxx; x++) - { - // turn on powered segments - if (m_display_state[y] >> x & 1) - m_display_decay[y][x] = m_display_wait; - - // determine active state - u32 ds = (m_display_decay[y][x] != 0) ? 1 : 0; - active_state |= (ds << x); - - // output to y.x, or y.a when always-on - if (x != m_display_maxx) - m_out_x[y][x] = ds; - else - m_out_a[y] = ds; - } - - // output to digity - if (m_display_segmask[y] != 0) - m_out_digit[y] = active_state & m_display_segmask[y]; - } -} - -TIMER_DEVICE_CALLBACK_MEMBER(hh_melps4_state::display_decay_tick) -{ - // slowly turn off unpowered segments - for (int y = 0; y < m_display_maxy; y++) - for (int x = 0; x <= m_display_maxx; x++) - if (m_display_decay[y][x] != 0) - m_display_decay[y][x]--; - - display_update(); -} - -void hh_melps4_state::set_display_size(int maxx, int maxy) -{ - m_display_maxx = maxx; - m_display_maxy = maxy; -} - -void hh_melps4_state::display_matrix(int maxx, int maxy, u32 setx, u32 sety, bool update) -{ - set_display_size(maxx, maxy); - - // update current state - u32 mask = (1 << maxx) - 1; - for (int y = 0; y < maxy; y++) - m_display_state[y] = (sety >> y & 1) ? ((setx & mask) | (1 << maxx)) : 0; - - if (update) - display_update(); -} - - // generic input handlers u8 hh_melps4_state::read_inputs(int columns) @@ -310,12 +210,10 @@ void cfrogger_state::cfrogger(machine_config &config) /* video hardware */ screen_device &screen(SCREEN(config, "screen", "svg")); - screen.set_refresh_hz(50); + screen.set_refresh_hz(60); screen.set_size(500, 1080); screen.set_visarea_full(); - TIMER(config, "display_decay").configure_periodic(FUNC(hh_melps4_state::display_decay_tick), attotime::from_msec(1)); - /* sound hardware */ SPEAKER(config, "mono").front_center(); SPEAKER_SOUND(config, m_speaker).add_route(ALL_OUTPUTS, "mono", 0.25); @@ -436,12 +334,10 @@ void gjungler_state::gjungler(machine_config &config) /* video hardware */ screen_device &screen(SCREEN(config, "screen", "svg")); - screen.set_refresh_hz(50); + screen.set_refresh_hz(60); screen.set_size(481, 1080); screen.set_visarea_full(); - TIMER(config, "display_decay").configure_periodic(FUNC(hh_melps4_state::display_decay_tick), attotime::from_msec(1)); - /* sound hardware */ SPEAKER(config, "mono").front_center(); SPEAKER_SOUND(config, m_speaker).add_route(ALL_OUTPUTS, "mono", 0.25); diff --git a/src/mame/drivers/hh_pic16.cpp b/src/mame/drivers/hh_pic16.cpp index 3ade8a5655b..1a44dbab5f1 100644 --- a/src/mame/drivers/hh_pic16.cpp +++ b/src/mame/drivers/hh_pic16.cpp @@ -49,6 +49,8 @@ ***************************************************************************/ #include "emu.h" +#include "includes/screenless.h" + #include "cpu/pic16c5x/pic16c5x.h" #include "machine/clock.h" #include "machine/timer.h" @@ -69,28 +71,19 @@ #include "hh_pic16_test.lh" // common test-layout - use external artwork -class hh_pic16_state : public driver_device +class hh_pic16_state : public screenless_state { public: hh_pic16_state(const machine_config &mconfig, device_type type, const char *tag) : - driver_device(mconfig, type, tag), + screenless_state(mconfig, type, tag), m_maincpu(*this, "maincpu"), m_inp_matrix(*this, "IN.%u", 0), - m_out_x(*this, "%u.%u", 0U, 0U), - m_out_a(*this, "%u.a", 0U), - m_out_digit(*this, "digit%u", 0U), - m_speaker(*this, "speaker"), - m_display_wait(33), - m_display_maxy(1), - m_display_maxx(0) + m_speaker(*this, "speaker") { } // devices required_device m_maincpu; optional_ioport_array<6> m_inp_matrix; // max 6 - output_finder<0x20, 0x20> m_out_x; - output_finder<0x20> m_out_a; - output_finder<0x20> m_out_digit; optional_device m_speaker; // misc common @@ -104,21 +97,6 @@ public: u8 read_rotated_inputs(int columns, u8 rowmask = ~0); virtual DECLARE_INPUT_CHANGED_MEMBER(reset_button); - // display common - int m_display_wait; // led/lamp off-delay in milliseconds (default 33ms) - int m_display_maxy; // display matrix number of rows - int m_display_maxx; // display matrix number of columns (max 31 for now) - - u32 m_display_state[0x20]; // display matrix rows data (last bit is used for always-on) - u16 m_display_segmask[0x20]; // if not 0, display matrix row is a digit, mask indicates connected segments - u8 m_display_decay[0x20][0x20]; // (internal use) - - TIMER_DEVICE_CALLBACK_MEMBER(display_decay_tick); - void display_update(); - void set_display_size(int maxx, int maxy); - void set_display_segmask(u32 digits, u32 mask); - void display_matrix(int maxx, int maxy, u32 setx, u32 sety, bool update = true); - protected: virtual void machine_start() override; virtual void machine_reset() override; @@ -129,16 +107,9 @@ protected: void hh_pic16_state::machine_start() { - // resolve handlers - m_out_x.resolve(); - m_out_a.resolve(); - m_out_digit.resolve(); + screenless_state::machine_start(); // zerofill - memset(m_display_state, 0, sizeof(m_display_state)); - memset(m_display_decay, 0, sizeof(m_display_decay)); - memset(m_display_segmask, 0, sizeof(m_display_segmask)); - m_a = 0; m_b = 0; m_c = 0; @@ -146,14 +117,6 @@ void hh_pic16_state::machine_start() m_inp_mux = ~0; // register for savestates - save_item(NAME(m_display_maxy)); - save_item(NAME(m_display_maxx)); - save_item(NAME(m_display_wait)); - - save_item(NAME(m_display_state)); - save_item(NAME(m_display_decay)); - save_item(NAME(m_display_segmask)); - save_item(NAME(m_a)); save_item(NAME(m_b)); save_item(NAME(m_c)); @@ -173,80 +136,6 @@ void hh_pic16_state::machine_reset() ***************************************************************************/ -// The device may strobe the outputs very fast, it is unnoticeable to the user. -// To prevent flickering here, we need to simulate a decay. - -void hh_pic16_state::display_update() -{ - for (int y = 0; y < m_display_maxy; y++) - { - u32 active_state = 0; - - for (int x = 0; x <= m_display_maxx; x++) - { - // turn on powered segments - if (m_display_state[y] >> x & 1) - m_display_decay[y][x] = m_display_wait; - - // determine active state - u32 ds = (m_display_decay[y][x] != 0) ? 1 : 0; - active_state |= (ds << x); - - // output to y.x, or y.a when always-on - if (x != m_display_maxx) - m_out_x[y][x] = ds; - else - m_out_a[y] = ds; - } - - // output to digity - if (m_display_segmask[y] != 0) - m_out_digit[y] = active_state & m_display_segmask[y]; - } -} - -TIMER_DEVICE_CALLBACK_MEMBER(hh_pic16_state::display_decay_tick) -{ - // slowly turn off unpowered segments - for (int y = 0; y < m_display_maxy; y++) - for (int x = 0; x <= m_display_maxx; x++) - if (m_display_decay[y][x] != 0) - m_display_decay[y][x]--; - - display_update(); -} - -void hh_pic16_state::set_display_size(int maxx, int maxy) -{ - m_display_maxx = maxx; - m_display_maxy = maxy; -} - -void hh_pic16_state::set_display_segmask(u32 digits, u32 mask) -{ - // set a segment mask per selected digit, but leave unselected ones alone - for (int i = 0; i < 0x20; i++) - { - if (digits & 1) - m_display_segmask[i] = mask; - digits >>= 1; - } -} - -void hh_pic16_state::display_matrix(int maxx, int maxy, u32 setx, u32 sety, bool update) -{ - set_display_size(maxx, maxy); - - // update current state - u32 mask = (1 << maxx) - 1; - for (int y = 0; y < maxy; y++) - m_display_state[y] = (sety >> y & 1) ? ((setx & mask) | (1 << maxx)) : 0; - - if (update) - display_update(); -} - - // generic input handlers u16 hh_pic16_state::read_inputs(int columns, u16 colmask) @@ -401,7 +290,6 @@ void touchme_state::touchme(machine_config &config) // PIC CLKOUT, tied to RTCC CLOCK(config, "clock", 300000/4).signal_handler().set_inputline("maincpu", PIC16C5x_RTCC); - TIMER(config, "display_decay").configure_periodic(FUNC(hh_pic16_state::display_decay_tick), attotime::from_msec(1)); config.set_default_layout(layout_touchme); /* sound hardware */ @@ -506,7 +394,6 @@ void pabball_state::pabball(machine_config &config) m_maincpu->read_c().set_ioport("IN.1"); m_maincpu->write_c().set(FUNC(pabball_state::write_c)); - TIMER(config, "display_decay").configure_periodic(FUNC(hh_pic16_state::display_decay_tick), attotime::from_msec(1)); config.set_default_layout(layout_hh_pic16_test); /* sound hardware */ @@ -541,7 +428,9 @@ class melodym_state : public hh_pic16_state public: melodym_state(const machine_config &mconfig, device_type type, const char *tag) : hh_pic16_state(mconfig, type, tag) - { } + { + set_display_level(0.9); + } DECLARE_WRITE8_MEMBER(write_b); DECLARE_READ8_MEMBER(read_c); @@ -566,7 +455,6 @@ READ8_MEMBER(melodym_state::read_c) WRITE8_MEMBER(melodym_state::write_c) { // C6: both lamps - m_display_wait = 2; display_matrix(1, 1, ~data >> 6 & 1, 1); // C7: speaker out @@ -627,7 +515,6 @@ void melodym_state::melodym(machine_config &config) m_maincpu->read_c().set(FUNC(melodym_state::read_c)); m_maincpu->write_c().set(FUNC(melodym_state::write_c)); - TIMER(config, "display_decay").configure_periodic(FUNC(hh_pic16_state::display_decay_tick), attotime::from_msec(1)); config.set_default_layout(layout_melodym); /* sound hardware */ @@ -732,7 +619,6 @@ void maniac_state::maniac(machine_config &config) m_maincpu->write_b().set(FUNC(maniac_state::write_b)); m_maincpu->write_c().set(FUNC(maniac_state::write_c)); - TIMER(config, "display_decay").configure_periodic(FUNC(hh_pic16_state::display_decay_tick), attotime::from_msec(1)); config.set_default_layout(layout_maniac); /* sound hardware */ @@ -887,7 +773,6 @@ void matchme_state::matchme(machine_config &config) m_maincpu->read_c().set(FUNC(matchme_state::read_c)); m_maincpu->write_c().set(FUNC(matchme_state::write_c)); - TIMER(config, "display_decay").configure_periodic(FUNC(hh_pic16_state::display_decay_tick), attotime::from_msec(1)); config.set_default_layout(layout_matchme); /* sound hardware */ @@ -1049,7 +934,6 @@ void leboom_state::leboom(machine_config &config) m_maincpu->read_c().set_constant(0xff); m_maincpu->write_c().set(FUNC(leboom_state::write_c)); - TIMER(config, "display_decay").configure_periodic(FUNC(hh_pic16_state::display_decay_tick), attotime::from_msec(1)); config.set_default_layout(layout_leboom); /* sound hardware */ @@ -1165,7 +1049,6 @@ void tbaskb_state::tbaskb(machine_config &config) m_maincpu->read_c().set_constant(0xff); m_maincpu->write_c().set(FUNC(tbaskb_state::write_c)); - TIMER(config, "display_decay").configure_periodic(FUNC(hh_pic16_state::display_decay_tick), attotime::from_msec(1)); config.set_default_layout(layout_tbaskb); /* sound hardware */ @@ -1288,7 +1171,6 @@ void rockpin_state::rockpin(machine_config &config) // PIC CLKOUT, tied to RTCC CLOCK(config, "clock", 450000/4).signal_handler().set_inputline(m_maincpu, PIC16C5x_RTCC); - TIMER(config, "display_decay").configure_periodic(FUNC(hh_pic16_state::display_decay_tick), attotime::from_msec(1)); config.set_default_layout(layout_rockpin); /* sound hardware */ @@ -1406,7 +1288,6 @@ void hccbaskb_state::hccbaskb(machine_config &config) m_maincpu->read_c().set_constant(0xff); m_maincpu->write_c().set(FUNC(hccbaskb_state::write_c)); - TIMER(config, "display_decay").configure_periodic(FUNC(hh_pic16_state::display_decay_tick), attotime::from_msec(1)); config.set_default_layout(layout_hccbaskb); /* sound hardware */ @@ -1564,7 +1445,6 @@ void ttfball_state::ttfball(machine_config &config) m_maincpu->read_c().set_constant(0xff); m_maincpu->write_c().set(FUNC(ttfball_state::write_c)); - TIMER(config, "display_decay").configure_periodic(FUNC(hh_pic16_state::display_decay_tick), attotime::from_msec(1)); config.set_default_layout(layout_ttfball); /* sound hardware */ @@ -1686,7 +1566,6 @@ void uspbball_state::uspbball(machine_config &config) // PIC CLKOUT, tied to RTCC CLOCK(config, "clock", 900000/4).signal_handler().set_inputline("maincpu", PIC16C5x_RTCC); - TIMER(config, "display_decay").configure_periodic(FUNC(hh_pic16_state::display_decay_tick), attotime::from_msec(1)); config.set_default_layout(layout_hh_pic16_test); /* sound hardware */ @@ -1827,7 +1706,6 @@ void us2pfball_state::us2pfball(machine_config &config) // PIC CLKOUT, tied to RTCC CLOCK(config, "clock", 800000/4).signal_handler().set_inputline("maincpu", PIC16C5x_RTCC); - TIMER(config, "display_decay").configure_periodic(FUNC(hh_pic16_state::display_decay_tick), attotime::from_msec(1)); config.set_default_layout(layout_us2pfball); /* sound hardware */ diff --git a/src/mame/drivers/hh_tms1k.cpp b/src/mame/drivers/hh_tms1k.cpp index f381d3ddec9..ad703fe84af 100644 --- a/src/mame/drivers/hh_tms1k.cpp +++ b/src/mame/drivers/hh_tms1k.cpp @@ -241,16 +241,9 @@ void hh_tms1k_state::machine_start() { - // resolve handlers - m_out_x.resolve(); - m_out_a.resolve(); - m_out_digit.resolve(); + screenless_state::machine_start(); // zerofill - memset(m_display_state, 0, sizeof(m_display_state)); - memset(m_display_decay, 0, sizeof(m_display_decay)); - memset(m_display_segmask, 0, sizeof(m_display_segmask)); - m_o = 0; m_r = 0; m_inp_mux = 0; @@ -260,15 +253,7 @@ void hh_tms1k_state::machine_start() m_plate = 0; // register for savestates - save_item(NAME(m_display_maxy)); - save_item(NAME(m_display_maxx)); - save_item(NAME(m_display_wait)); - - save_item(NAME(m_display_state)); /* save_item(NAME(m_power_led)); */ // don't save! - save_item(NAME(m_display_decay)); - save_item(NAME(m_display_segmask)); - save_item(NAME(m_o)); save_item(NAME(m_r)); save_item(NAME(m_inp_mux)); @@ -290,36 +275,11 @@ void hh_tms1k_state::machine_reset() ***************************************************************************/ -// The device may strobe the outputs very fast, it is unnoticeable to the user. -// To prevent flickering here, we need to simulate a decay. +// display update void hh_tms1k_state::display_update() { - for (int y = 0; y < m_display_maxy; y++) - { - u32 active_state = 0; - - for (int x = 0; x <= m_display_maxx; x++) - { - // turn on powered segments - if (m_power_on && m_display_state[y] >> x & 1) - m_display_decay[y][x] = m_display_wait; - - // determine active state - u32 ds = (m_display_decay[y][x] != 0) ? 1 : 0; - active_state |= (ds << x); - - // output to y.x, or y.a when always-on - if (x != m_display_maxx) - m_out_x[y][x] = ds; - else - m_out_a[y] = ds; - } - - // output to digity - if (m_display_segmask[y] != 0) - m_out_digit[y] = active_state & m_display_segmask[y]; - } + screenless_state::display_update(); // output optional power led if (m_power_led != m_power_on) @@ -329,47 +289,6 @@ void hh_tms1k_state::display_update() } } -TIMER_DEVICE_CALLBACK_MEMBER(hh_tms1k_state::display_decay_tick) -{ - // slowly turn off unpowered segments - for (int y = 0; y < m_display_maxy; y++) - for (int x = 0; x <= m_display_maxx; x++) - if (m_display_decay[y][x] != 0) - m_display_decay[y][x]--; - - display_update(); -} - -void hh_tms1k_state::set_display_size(int maxx, int maxy) -{ - m_display_maxx = maxx; - m_display_maxy = maxy; -} - -void hh_tms1k_state::set_display_segmask(u32 digits, u32 mask) -{ - // set a segment mask per selected digit, but leave unselected ones alone - for (int i = 0; i < 0x20; i++) - { - if (digits & 1) - m_display_segmask[i] = mask; - digits >>= 1; - } -} - -void hh_tms1k_state::display_matrix(int maxx, int maxy, u32 setx, u32 sety, bool update) -{ - set_display_size(maxx, maxy); - - // update current state - u32 mask = (1 << maxx) - 1; - for (int y = 0; y < maxy; y++) - m_display_state[y] = (sety >> y & 1) ? ((setx & mask) | (1 << maxx)) : 0; - - if (update) - display_update(); -} - // generic input handlers @@ -561,7 +480,6 @@ void matchnum_state::matchnum(machine_config &config) m_maincpu->r().set(FUNC(matchnum_state::write_r)); m_maincpu->o().set(FUNC(matchnum_state::write_o)); - TIMER(config, "display_decay").configure_periodic(FUNC(hh_tms1k_state::display_decay_tick), attotime::from_msec(1)); config.set_default_layout(layout_matchnum); /* sound hardware */ @@ -673,7 +591,6 @@ void arrball_state::arrball(machine_config &config) m_maincpu->r().set(FUNC(arrball_state::write_r)); m_maincpu->o().set(FUNC(arrball_state::write_o)); - TIMER(config, "display_decay").configure_periodic(FUNC(hh_tms1k_state::display_decay_tick), attotime::from_msec(1)); config.set_default_layout(layout_arrball); /* sound hardware */ @@ -838,7 +755,6 @@ void mathmagi_state::mathmagi(machine_config &config) m_maincpu->r().set(FUNC(mathmagi_state::write_r)); m_maincpu->o().set(FUNC(mathmagi_state::write_o)); - TIMER(config, "display_decay").configure_periodic(FUNC(hh_tms1k_state::display_decay_tick), attotime::from_msec(1)); config.set_default_layout(layout_mathmagi); /* no sound! */ @@ -1094,7 +1010,6 @@ void amaztron_state::amaztron(machine_config &config) m_maincpu->r().set(FUNC(amaztron_state::write_r)); m_maincpu->o().set(FUNC(amaztron_state::write_o)); - TIMER(config, "display_decay").configure_periodic(FUNC(hh_tms1k_state::display_decay_tick), attotime::from_msec(1)); config.set_default_layout(layout_amaztron); /* sound hardware */ @@ -1254,7 +1169,6 @@ void zodiac_state::zodiac(machine_config &config) m_maincpu->r().set(FUNC(zodiac_state::write_r)); m_maincpu->o().set(FUNC(zodiac_state::write_o)); - TIMER(config, "display_decay").configure_periodic(FUNC(hh_tms1k_state::display_decay_tick), attotime::from_msec(1)); config.set_default_layout(layout_zodiac); /* sound hardware */ @@ -1381,7 +1295,6 @@ void cqback_state::cqback(machine_config &config) m_maincpu->r().set(FUNC(cqback_state::write_r)); m_maincpu->o().set(FUNC(cqback_state::write_o)); - TIMER(config, "display_decay").configure_periodic(FUNC(hh_tms1k_state::display_decay_tick), attotime::from_msec(1)); config.set_default_layout(layout_cqback); /* sound hardware */ @@ -1511,7 +1424,6 @@ void h2hfootb_state::h2hfootb(machine_config &config) m_maincpu->r().set(FUNC(h2hfootb_state::write_r)); m_maincpu->o().set(FUNC(h2hfootb_state::write_o)); - TIMER(config, "display_decay").configure_periodic(FUNC(hh_tms1k_state::display_decay_tick), attotime::from_msec(1)); config.set_default_layout(layout_h2hfootb); /* sound hardware */ @@ -1697,7 +1609,6 @@ void h2hbaskb_state::h2hbaskb(machine_config &config) TIMER(config, "cap_empty").configure_generic(FUNC(h2hbaskb_state::cap_empty_callback)); - TIMER(config, "display_decay").configure_periodic(FUNC(hh_tms1k_state::display_decay_tick), attotime::from_msec(1)); config.set_default_layout(layout_h2hbaskb); /* sound hardware */ @@ -1859,7 +1770,6 @@ void h2hbaseb_state::h2hbaseb(machine_config &config) m_maincpu->r().set(FUNC(h2hbaseb_state::write_r)); m_maincpu->o().set(FUNC(h2hbaseb_state::write_o)); - TIMER(config, "display_decay").configure_periodic(FUNC(hh_tms1k_state::display_decay_tick), attotime::from_msec(1)); config.set_default_layout(layout_h2hbaseb); /* sound hardware */ @@ -1983,7 +1893,6 @@ void h2hboxing_state::h2hboxing(machine_config &config) m_maincpu->r().set(FUNC(h2hboxing_state::write_r)); m_maincpu->o().set(FUNC(h2hboxing_state::write_o)); - TIMER(config, "display_decay").configure_periodic(FUNC(hh_tms1k_state::display_decay_tick), attotime::from_msec(1)); config.set_default_layout(layout_h2hboxing); /* sound hardware */ @@ -2166,7 +2075,6 @@ void quizwizc_state::quizwizc(machine_config &config) m_maincpu->r().set(FUNC(quizwizc_state::write_r)); m_maincpu->o().set(FUNC(quizwizc_state::write_o)); - TIMER(config, "display_decay").configure_periodic(FUNC(hh_tms1k_state::display_decay_tick), attotime::from_msec(1)); config.set_default_layout(layout_quizwizc); /* sound hardware */ @@ -2354,7 +2262,6 @@ void tc4_state::tc4(machine_config &config) m_maincpu->r().set(FUNC(tc4_state::write_r)); m_maincpu->o().set(FUNC(tc4_state::write_o)); - TIMER(config, "display_decay").configure_periodic(FUNC(hh_tms1k_state::display_decay_tick), attotime::from_msec(1)); config.set_default_layout(layout_tc4); /* sound hardware */ @@ -2482,7 +2389,6 @@ void cnbaskb_state::cnbaskb(machine_config &config) m_maincpu->r().set(FUNC(cnbaskb_state::write_r)); m_maincpu->o().set(FUNC(cnbaskb_state::write_o)); - TIMER(config, "display_decay").configure_periodic(FUNC(hh_tms1k_state::display_decay_tick), attotime::from_msec(1)); config.set_default_layout(layout_cnbaskb); /* sound hardware */ @@ -2607,7 +2513,6 @@ void cmsport_state::cmsport(machine_config &config) m_maincpu->r().set(FUNC(cmsport_state::write_r)); m_maincpu->o().set(FUNC(cmsport_state::write_o)); - TIMER(config, "display_decay").configure_periodic(FUNC(hh_tms1k_state::display_decay_tick), attotime::from_msec(1)); config.set_default_layout(layout_cmsport); /* sound hardware */ @@ -2745,7 +2650,6 @@ void cnfball_state::cnfball(machine_config &config) m_maincpu->r().set(FUNC(cnfball_state::write_r)); m_maincpu->o().set(FUNC(cnfball_state::write_o)); - TIMER(config, "display_decay").configure_periodic(FUNC(hh_tms1k_state::display_decay_tick), attotime::from_msec(1)); config.set_default_layout(layout_cnfball); /* sound hardware */ @@ -2884,7 +2788,6 @@ void cnfball2_state::cnfball2(machine_config &config) m_maincpu->r().set(FUNC(cnfball2_state::write_r)); m_maincpu->o().set(FUNC(cnfball2_state::write_o)); - TIMER(config, "display_decay").configure_periodic(FUNC(hh_tms1k_state::display_decay_tick), attotime::from_msec(1)); config.set_default_layout(layout_cnfball2); /* sound hardware */ @@ -3029,7 +2932,6 @@ void eleciq_state::eleciq(machine_config &config) m_maincpu->r().set(FUNC(eleciq_state::write_r)); m_maincpu->o().set(FUNC(eleciq_state::write_o)); - TIMER(config, "display_decay").configure_periodic(FUNC(hh_tms1k_state::display_decay_tick), attotime::from_msec(1)); config.set_default_layout(layout_eleciq); /* sound hardware */ @@ -3146,7 +3048,6 @@ void esoccer_state::esoccer(machine_config &config) m_maincpu->r().set(FUNC(esoccer_state::write_r)); m_maincpu->o().set(FUNC(esoccer_state::write_o)); - TIMER(config, "display_decay").configure_periodic(FUNC(hh_tms1k_state::display_decay_tick), attotime::from_msec(1)); config.set_default_layout(layout_esoccer); /* sound hardware */ @@ -3292,7 +3193,6 @@ void ebball_state::ebball(machine_config &config) m_maincpu->r().set(FUNC(ebball_state::write_r)); m_maincpu->o().set(FUNC(ebball_state::write_o)); - TIMER(config, "display_decay").configure_periodic(FUNC(hh_tms1k_state::display_decay_tick), attotime::from_msec(1)); config.set_default_layout(layout_ebball); /* sound hardware */ @@ -3427,7 +3327,6 @@ void ebball2_state::ebball2(machine_config &config) m_maincpu->r().set(FUNC(ebball2_state::write_r)); m_maincpu->o().set(FUNC(ebball2_state::write_o)); - TIMER(config, "display_decay").configure_periodic(FUNC(hh_tms1k_state::display_decay_tick), attotime::from_msec(1)); config.set_default_layout(layout_ebball2); /* sound hardware */ @@ -3614,7 +3513,6 @@ void ebball3_state::ebball3(machine_config &config) m_maincpu->r().set(FUNC(ebball3_state::write_r)); m_maincpu->o().set(FUNC(ebball3_state::write_o)); - TIMER(config, "display_decay").configure_periodic(FUNC(hh_tms1k_state::display_decay_tick), attotime::from_msec(1)); config.set_default_layout(layout_ebball3); /* sound hardware */ @@ -3737,7 +3635,6 @@ void esbattle_state::esbattle(machine_config &config) m_maincpu->r().set(FUNC(esbattle_state::write_r)); m_maincpu->o().set(FUNC(esbattle_state::write_o)); - TIMER(config, "display_decay").configure_periodic(FUNC(hh_tms1k_state::display_decay_tick), attotime::from_msec(1)); config.set_default_layout(layout_esbattle); /* sound hardware */ @@ -3856,11 +3753,10 @@ void einvader_state::einvader(machine_config &config) /* video hardware */ screen_device &screen(SCREEN(config, "screen", SCREEN_TYPE_SVG)); screen.set_svg_region("svg"); - screen.set_refresh_hz(50); + screen.set_refresh_hz(60); screen.set_size(939, 1080); screen.set_visarea_full(); - TIMER(config, "display_decay").configure_periodic(FUNC(hh_tms1k_state::display_decay_tick), attotime::from_msec(1)); config.set_default_layout(layout_einvader); /* sound hardware */ @@ -3990,7 +3886,6 @@ void efootb4_state::efootb4(machine_config &config) m_maincpu->r().set(FUNC(efootb4_state::write_r)); m_maincpu->o().set(FUNC(efootb4_state::write_o)); - TIMER(config, "display_decay").configure_periodic(FUNC(hh_tms1k_state::display_decay_tick), attotime::from_msec(1)); config.set_default_layout(layout_efootb4); /* sound hardware */ @@ -4123,7 +4018,6 @@ void ebaskb2_state::ebaskb2(machine_config &config) m_maincpu->r().set(FUNC(ebaskb2_state::write_r)); m_maincpu->o().set(FUNC(ebaskb2_state::write_o)); - TIMER(config, "display_decay").configure_periodic(FUNC(hh_tms1k_state::display_decay_tick), attotime::from_msec(1)); config.set_default_layout(layout_ebaskb2); /* sound hardware */ @@ -4269,7 +4163,6 @@ void raisedvl_state::raisedvl(machine_config &config) m_maincpu->r().set(FUNC(raisedvl_state::write_r)); m_maincpu->o().set(FUNC(raisedvl_state::write_o)); - TIMER(config, "display_decay").configure_periodic(FUNC(hh_tms1k_state::display_decay_tick), attotime::from_msec(1)); config.set_default_layout(layout_raisedvl); /* sound hardware */ @@ -4404,7 +4297,6 @@ void f2pbball_state::f2pbball(machine_config &config) m_maincpu->r().set(FUNC(f2pbball_state::write_r)); m_maincpu->o().set(FUNC(f2pbball_state::write_o)); - TIMER(config, "display_decay").configure_periodic(FUNC(hh_tms1k_state::display_decay_tick), attotime::from_msec(1)); config.set_default_layout(layout_f2pbball); /* sound hardware */ @@ -4548,7 +4440,6 @@ void f3in1_state::f3in1(machine_config &config) m_maincpu->r().set(FUNC(f3in1_state::write_r)); m_maincpu->o().set(FUNC(f3in1_state::write_o)); - TIMER(config, "display_decay").configure_periodic(FUNC(hh_tms1k_state::display_decay_tick), attotime::from_msec(1)); config.set_default_layout(layout_f3in1); /* sound hardware */ @@ -4709,7 +4600,6 @@ void gpoker_state::gpoker(machine_config &config) m_maincpu->r().set(FUNC(gpoker_state::write_r)); m_maincpu->o().set(FUNC(gpoker_state::write_o)); - TIMER(config, "display_decay").configure_periodic(FUNC(hh_tms1k_state::display_decay_tick), attotime::from_msec(1)); config.set_default_layout(layout_gpoker); /* sound hardware */ @@ -4834,7 +4724,6 @@ void gjackpot_state::gjackpot(machine_config &config) m_maincpu->r().set(FUNC(gjackpot_state::write_r)); m_maincpu->o().set(FUNC(gpoker_state::write_o)); - TIMER(config, "display_decay").configure_periodic(FUNC(hh_tms1k_state::display_decay_tick), attotime::from_msec(1)); config.set_default_layout(layout_gjackpot); /* sound hardware */ @@ -4957,12 +4846,10 @@ void ginv_state::ginv(machine_config &config) /* video hardware */ screen_device &screen(SCREEN(config, "screen", SCREEN_TYPE_SVG)); screen.set_svg_region("svg"); - screen.set_refresh_hz(50); + screen.set_refresh_hz(60); screen.set_size(236, 1080); screen.set_visarea_full(); - TIMER(config, "display_decay").configure_periodic(FUNC(hh_tms1k_state::display_decay_tick), attotime::from_msec(1)); - /* sound hardware */ SPEAKER(config, "mono").front_center(); SPEAKER_SOUND(config, m_speaker); @@ -5083,12 +4970,10 @@ void ginv1000_state::ginv1000(machine_config &config) /* video hardware */ screen_device &screen(SCREEN(config, "screen", SCREEN_TYPE_SVG)); screen.set_svg_region("svg"); - screen.set_refresh_hz(50); + screen.set_refresh_hz(60); screen.set_size(226, 1080); screen.set_visarea_full(); - TIMER(config, "display_decay").configure_periodic(FUNC(hh_tms1k_state::display_decay_tick), attotime::from_msec(1)); - /* sound hardware */ SPEAKER(config, "mono").front_center(); SPEAKER_SOUND(config, m_speaker); @@ -5235,12 +5120,10 @@ void ginv2000_state::ginv2000(machine_config &config) /* video hardware */ screen_device &screen(SCREEN(config, "screen", SCREEN_TYPE_SVG)); screen.set_svg_region("svg"); - screen.set_refresh_hz(50); + screen.set_refresh_hz(60); screen.set_size(364, 1080); screen.set_visarea_full(); - TIMER(config, "display_decay").configure_periodic(FUNC(hh_tms1k_state::display_decay_tick), attotime::from_msec(1)); - /* sound hardware */ SPEAKER(config, "mono").front_center(); SPEAKER_SOUND(config, m_speaker); @@ -5391,7 +5274,6 @@ void fxmcr165_state::fxmcr165(machine_config &config) m_maincpu->r().set(FUNC(fxmcr165_state::write_r)); m_maincpu->o().set(FUNC(fxmcr165_state::write_o)); - TIMER(config, "display_decay").configure_periodic(FUNC(hh_tms1k_state::display_decay_tick), attotime::from_msec(1)); config.set_default_layout(layout_fxmcr165); /* sound hardware */ @@ -5532,7 +5414,6 @@ void elecdet_state::elecdet(machine_config &config) m_maincpu->o().set(FUNC(elecdet_state::write_o)); m_maincpu->power_off().set(FUNC(hh_tms1k_state::auto_power_off)); - TIMER(config, "display_decay").configure_periodic(FUNC(hh_tms1k_state::display_decay_tick), attotime::from_msec(1)); config.set_default_layout(layout_elecdet); /* sound hardware */ @@ -5675,7 +5556,6 @@ void starwbc_state::starwbc(machine_config &config) m_maincpu->r().set(FUNC(starwbc_state::write_r)); m_maincpu->o().set(FUNC(starwbc_state::write_o)); - TIMER(config, "display_decay").configure_periodic(FUNC(hh_tms1k_state::display_decay_tick), attotime::from_msec(1)); config.set_default_layout(layout_starwbc); /* sound hardware */ @@ -5824,7 +5704,6 @@ void astro_state::astro(machine_config &config) m_maincpu->r().set(FUNC(astro_state::write_r)); m_maincpu->o().set(FUNC(astro_state::write_o)); - TIMER(config, "display_decay").configure_periodic(FUNC(hh_tms1k_state::display_decay_tick), attotime::from_msec(1)); config.set_default_layout(layout_astro); /* no sound! */ @@ -5992,7 +5871,6 @@ void elecbowl_state::elecbowl(machine_config &config) m_maincpu->r().set(FUNC(elecbowl_state::write_r)); m_maincpu->o().set(FUNC(elecbowl_state::write_o)); - TIMER(config, "display_decay").configure_periodic(FUNC(hh_tms1k_state::display_decay_tick), attotime::from_msec(1)); config.set_default_layout(layout_elecbowl); /* sound hardware */ @@ -6162,7 +6040,7 @@ void horseran_state::horseran(machine_config &config) /* video hardware */ HLCD0569(config, m_lcd, 1100); // C=0.022uF m_lcd->write_cols().set(FUNC(horseran_state::lcd_output_w)); - TIMER(config, "display_decay").configure_periodic(FUNC(hh_tms1k_state::display_decay_tick), attotime::from_msec(1)); + config.set_default_layout(layout_horseran); /* no sound! */ @@ -6467,7 +6345,6 @@ void comp4_state::comp4(machine_config &config) m_maincpu->r().set(FUNC(comp4_state::write_r)); m_maincpu->o().set(FUNC(comp4_state::write_o)); - TIMER(config, "display_decay").configure_periodic(FUNC(hh_tms1k_state::display_decay_tick), attotime::from_msec(1)); config.set_default_layout(layout_comp4); /* no sound! */ @@ -6633,7 +6510,6 @@ void bship_state::bship(machine_config &config) m_maincpu->r().set(FUNC(bship_state::write_r)); m_maincpu->o().set(FUNC(bship_state::write_o)); - TIMER(config, "display_decay").configure_periodic(FUNC(hh_tms1k_state::display_decay_tick), attotime::from_msec(1)); config.set_default_layout(layout_bship); /* sound hardware */ @@ -6748,7 +6624,6 @@ void bshipb_state::bshipb(machine_config &config) m_maincpu->r().set(FUNC(bshipb_state::write_r)); m_maincpu->o().set(FUNC(bshipb_state::write_o)); - TIMER(config, "display_decay").configure_periodic(FUNC(hh_tms1k_state::display_decay_tick), attotime::from_msec(1)); config.set_default_layout(layout_bship); /* sound hardware */ @@ -6883,7 +6758,6 @@ void simon_state::simon(machine_config &config) m_maincpu->k().set(FUNC(simon_state::read_k)); m_maincpu->r().set(FUNC(simon_state::write_r)); - TIMER(config, "display_decay").configure_periodic(FUNC(hh_tms1k_state::display_decay_tick), attotime::from_msec(1)); config.set_default_layout(layout_simon); /* sound hardware */ @@ -7049,7 +6923,6 @@ void ssimon_state::ssimon(machine_config &config) m_maincpu->k().set(FUNC(ssimon_state::read_k)); m_maincpu->r().set(FUNC(ssimon_state::write_r)); - TIMER(config, "display_decay").configure_periodic(FUNC(hh_tms1k_state::display_decay_tick), attotime::from_msec(1)); config.set_default_layout(layout_ssimon); /* sound hardware */ @@ -7103,7 +6976,7 @@ public: DECLARE_READ8_MEMBER(read_k); int m_gearbox_pos; - bool sensor_state() { return m_gearbox_pos < 0 && m_display_decay[0][0] != 0; } + bool sensor_state() { return m_gearbox_pos < 0 && display_element_on(0, 0); } TIMER_DEVICE_CALLBACK_MEMBER(gearbox_sim_tick); void bigtrak(machine_config &config); @@ -7243,7 +7116,7 @@ void bigtrak_state::bigtrak(machine_config &config) m_maincpu->o().set(FUNC(bigtrak_state::write_o)); TIMER(config, "gearbox").configure_periodic(FUNC(bigtrak_state::gearbox_sim_tick), attotime::from_msec(1)); - TIMER(config, "display_decay").configure_periodic(FUNC(hh_tms1k_state::display_decay_tick), attotime::from_msec(1)); + config.set_default_layout(layout_bigtrak); /* sound hardware */ @@ -7296,7 +7169,7 @@ public: { } void prepare_display(); - bool sensor_led_on() { return m_display_decay[0][0] != 0; } + bool sensor_led_on() { return display_element_on(0, 0); } int m_motor_pos; int m_motor_pos_prev; @@ -7488,7 +7361,7 @@ void mbdtower_state::mbdtower(machine_config &config) m_maincpu->o().set(FUNC(mbdtower_state::write_o)); TIMER(config, "tower_motor").configure_periodic(FUNC(mbdtower_state::motor_sim_tick), attotime::from_msec(3500/0x80)); // ~3.5sec for a full rotation - TIMER(config, "display_decay").configure_periodic(FUNC(hh_tms1k_state::display_decay_tick), attotime::from_msec(1)); + config.set_default_layout(layout_mbdtower); /* sound hardware */ @@ -7610,7 +7483,6 @@ void arcmania_state::arcmania(machine_config &config) m_maincpu->r().set(FUNC(arcmania_state::write_r)); m_maincpu->o().set(FUNC(arcmania_state::write_o)); - TIMER(config, "display_decay").configure_periodic(FUNC(hh_tms1k_state::display_decay_tick), attotime::from_msec(1)); config.set_default_layout(layout_arcmania); /* sound hardware */ @@ -7741,7 +7613,6 @@ void cnsector_state::cnsector(machine_config &config) m_maincpu->r().set(FUNC(cnsector_state::write_r)); m_maincpu->o().set(FUNC(cnsector_state::write_o)); - TIMER(config, "display_decay").configure_periodic(FUNC(hh_tms1k_state::display_decay_tick), attotime::from_msec(1)); config.set_default_layout(layout_cnsector); /* no sound! */ @@ -7871,7 +7742,6 @@ void merlin_state::merlin(machine_config &config) m_maincpu->r().set(FUNC(merlin_state::write_r)); m_maincpu->o().set(FUNC(merlin_state::write_o)); - TIMER(config, "display_decay").configure_periodic(FUNC(hh_tms1k_state::display_decay_tick), attotime::from_msec(1)); config.set_default_layout(layout_merlin); /* sound hardware */ @@ -7948,7 +7818,6 @@ void mmerlin_state::mmerlin(machine_config &config) m_maincpu->r().set(FUNC(mmerlin_state::write_r)); m_maincpu->o().set(FUNC(mmerlin_state::write_o)); - TIMER(config, "display_decay").configure_periodic(FUNC(hh_tms1k_state::display_decay_tick), attotime::from_msec(1)); config.set_default_layout(layout_mmerlin); /* sound hardware */ @@ -8077,7 +7946,6 @@ void stopthief_state::stopthief(machine_config &config) m_maincpu->o().set(FUNC(stopthief_state::write_o)); m_maincpu->power_off().set(FUNC(hh_tms1k_state::auto_power_off)); - TIMER(config, "display_decay").configure_periodic(FUNC(hh_tms1k_state::display_decay_tick), attotime::from_msec(1)); config.set_default_layout(layout_stopthief); /* sound hardware */ @@ -8220,7 +8088,6 @@ void bankshot_state::bankshot(machine_config &config) m_maincpu->r().set(FUNC(bankshot_state::write_r)); m_maincpu->o().set(FUNC(bankshot_state::write_o)); - TIMER(config, "display_decay").configure_periodic(FUNC(hh_tms1k_state::display_decay_tick), attotime::from_msec(1)); config.set_default_layout(layout_bankshot); /* sound hardware */ @@ -8349,7 +8216,6 @@ void splitsec_state::splitsec(machine_config &config) m_maincpu->r().set(FUNC(splitsec_state::write_r)); m_maincpu->o().set(FUNC(splitsec_state::write_o)); - TIMER(config, "display_decay").configure_periodic(FUNC(hh_tms1k_state::display_decay_tick), attotime::from_msec(1)); config.set_default_layout(layout_splitsec); /* sound hardware */ @@ -8479,7 +8345,6 @@ void lostreas_state::lostreas(machine_config &config) m_maincpu->r().set(FUNC(lostreas_state::write_r)); m_maincpu->o().set(FUNC(lostreas_state::write_o)); - TIMER(config, "display_decay").configure_periodic(FUNC(hh_tms1k_state::display_decay_tick), attotime::from_msec(1)); config.set_default_layout(layout_lostreas); /* sound hardware */ @@ -8620,7 +8485,6 @@ void alphie_state::alphie(machine_config &config) m_maincpu->r().set(FUNC(alphie_state::write_r)); m_maincpu->o().set(FUNC(alphie_state::write_o)); - TIMER(config, "display_decay").configure_periodic(FUNC(hh_tms1k_state::display_decay_tick), attotime::from_msec(1)); config.set_default_layout(layout_alphie); /* sound hardware */ @@ -8741,7 +8605,6 @@ void tcfball_state::tcfball(machine_config &config) m_maincpu->r().set(FUNC(tcfball_state::write_r)); m_maincpu->o().set(FUNC(tcfball_state::write_o)); - TIMER(config, "display_decay").configure_periodic(FUNC(hh_tms1k_state::display_decay_tick), attotime::from_msec(1)); config.set_default_layout(layout_tcfball); /* sound hardware */ @@ -8819,7 +8682,6 @@ void tcfballa_state::tcfballa(machine_config &config) m_maincpu->r().set(FUNC(tcfballa_state::write_r)); m_maincpu->o().set(FUNC(tcfballa_state::write_o)); - TIMER(config, "display_decay").configure_periodic(FUNC(hh_tms1k_state::display_decay_tick), attotime::from_msec(1)); config.set_default_layout(layout_tcfballa); /* sound hardware */ @@ -8995,7 +8857,6 @@ void tandy12_state::tandy12(machine_config &config) m_maincpu->r().set(FUNC(tandy12_state::write_r)); m_maincpu->o().set(FUNC(tandy12_state::write_o)); - TIMER(config, "display_decay").configure_periodic(FUNC(hh_tms1k_state::display_decay_tick), attotime::from_msec(1)); config.set_default_layout(layout_tandy12); /* sound hardware */ @@ -9115,7 +8976,6 @@ void monkeysee_state::monkeysee(machine_config &config) m_maincpu->r().set(FUNC(monkeysee_state::write_r)); m_maincpu->o().set(FUNC(monkeysee_state::write_o)); - TIMER(config, "display_decay").configure_periodic(FUNC(hh_tms1k_state::display_decay_tick), attotime::from_msec(1)); config.set_default_layout(layout_monkeysee); /* sound hardware */ @@ -9276,7 +9136,6 @@ void speechp_state::speechp(machine_config &config) m_maincpu->r().set(FUNC(speechp_state::write_r)); m_maincpu->o().set(FUNC(speechp_state::write_o)); - TIMER(config, "display_decay").configure_periodic(FUNC(hh_tms1k_state::display_decay_tick), attotime::from_msec(1)); config.set_default_layout(layout_speechp); /* sound hardware */ @@ -9373,7 +9232,6 @@ void timaze_state::timaze(machine_config &config) m_maincpu->r().set(FUNC(timaze_state::write_r)); m_maincpu->o().set(FUNC(timaze_state::write_o)); - TIMER(config, "display_decay").configure_periodic(FUNC(hh_tms1k_state::display_decay_tick), attotime::from_msec(1)); config.set_default_layout(layout_timaze); /* no sound! */ @@ -9524,7 +9382,6 @@ void tithermos_state::tithermos(machine_config &config) CLOCK(config, "ac_line", 60).signal_handler().set_nop(); - TIMER(config, "display_decay").configure_periodic(FUNC(hh_tms1k_state::display_decay_tick), attotime::from_msec(1)); config.set_default_layout(layout_tithermos); /* no sound! */ @@ -9642,7 +9499,6 @@ void copycat_state::copycat(machine_config &config) m_maincpu->r().set(FUNC(copycat_state::write_r)); m_maincpu->o().set(FUNC(copycat_state::write_o)); - TIMER(config, "display_decay").configure_periodic(FUNC(hh_tms1k_state::display_decay_tick), attotime::from_msec(1)); config.set_default_layout(layout_copycat); /* sound hardware */ @@ -9730,7 +9586,6 @@ void copycatm2_state::copycatm2(machine_config &config) m_maincpu->r().set(FUNC(copycatm2_state::write_r)); m_maincpu->o().set(FUNC(copycatm2_state::write_o)); - TIMER(config, "display_decay").configure_periodic(FUNC(hh_tms1k_state::display_decay_tick), attotime::from_msec(1)); config.set_default_layout(layout_copycatm2); /* sound hardware */ @@ -9813,7 +9668,6 @@ void ditto_state::ditto(machine_config &config) m_maincpu->r().set(FUNC(ditto_state::write_r)); m_maincpu->o().set(FUNC(ditto_state::write_o)); - TIMER(config, "display_decay").configure_periodic(FUNC(hh_tms1k_state::display_decay_tick), attotime::from_msec(1)); config.set_default_layout(layout_ditto); /* sound hardware */ @@ -9941,7 +9795,6 @@ void ss7in1_state::ss7in1(machine_config &config) m_maincpu->r().set(FUNC(ss7in1_state::write_r)); m_maincpu->o().set(FUNC(ss7in1_state::write_o)); - TIMER(config, "display_decay").configure_periodic(FUNC(hh_tms1k_state::display_decay_tick), attotime::from_msec(1)); config.set_default_layout(layout_7in1ss); /* sound hardware */ @@ -10150,7 +10003,6 @@ void tbreakup_state::tbreakup(machine_config &config) m_expander->write_port6_callback().set(FUNC(tbreakup_state::expander_w)); m_expander->write_port7_callback().set(FUNC(tbreakup_state::expander_w)); - TIMER(config, "display_decay").configure_periodic(FUNC(hh_tms1k_state::display_decay_tick), attotime::from_msec(1)); config.set_default_layout(layout_tbreakup); /* sound hardware */ @@ -10281,7 +10133,6 @@ void phpball_state::phpball(machine_config &config) m_maincpu->r().set(FUNC(phpball_state::write_r)); m_maincpu->o().set(FUNC(phpball_state::write_o)); - TIMER(config, "display_decay").configure_periodic(FUNC(hh_tms1k_state::display_decay_tick), attotime::from_msec(1)); config.set_default_layout(layout_phpball); /* sound hardware */ @@ -10429,7 +10280,6 @@ void ssports4_state::ssports4(machine_config &config) m_maincpu->r().set(FUNC(ssports4_state::write_r)); m_maincpu->o().set(FUNC(ssports4_state::write_o)); - TIMER(config, "display_decay").configure_periodic(FUNC(hh_tms1k_state::display_decay_tick), attotime::from_msec(1)); config.set_default_layout(layout_ssports4); /* sound hardware */ @@ -10605,7 +10455,6 @@ void xl25_state::xl25(machine_config &config) m_maincpu->r().set(FUNC(xl25_state::write_r)); m_maincpu->o().set(FUNC(xl25_state::write_o)); - TIMER(config, "display_decay").configure_periodic(FUNC(hh_tms1k_state::display_decay_tick), attotime::from_msec(1)); config.set_default_layout(layout_xl25); /* sound hardware */ diff --git a/src/mame/drivers/hh_ucom4.cpp b/src/mame/drivers/hh_ucom4.cpp index c5242e40808..703453a2b63 100644 --- a/src/mame/drivers/hh_ucom4.cpp +++ b/src/mame/drivers/hh_ucom4.cpp @@ -65,11 +65,6 @@ (* means undumped unless noted, @ denotes it's in this driver) - -TODO: - - games that rely on the fact that faster/longer strobed elements appear brighter: - tactix(player 2) - ***************************************************************************/ #include "emu.h" @@ -97,16 +92,9 @@ TODO: void hh_ucom4_state::machine_start() { - // resolve handlers - m_out_x.resolve(); - m_out_a.resolve(); - m_out_digit.resolve(); + screenless_state::machine_start(); // zerofill - memset(m_display_state, 0, sizeof(m_display_state)); - memset(m_display_decay, 0, sizeof(m_display_decay)); - memset(m_display_segmask, 0, sizeof(m_display_segmask)); - memset(m_port, 0, sizeof(m_port)); m_int = 0; m_inp_mux = 0; @@ -114,14 +102,6 @@ void hh_ucom4_state::machine_start() m_plate = 0; // register for savestates - save_item(NAME(m_display_maxy)); - save_item(NAME(m_display_maxx)); - save_item(NAME(m_display_wait)); - - save_item(NAME(m_display_state)); - save_item(NAME(m_display_decay)); - save_item(NAME(m_display_segmask)); - save_item(NAME(m_port)); save_item(NAME(m_int)); save_item(NAME(m_inp_mux)); @@ -142,80 +122,6 @@ void hh_ucom4_state::machine_reset() ***************************************************************************/ -// The device may strobe the outputs very fast, it is unnoticeable to the user. -// To prevent flickering here, we need to simulate a decay. - -void hh_ucom4_state::display_update() -{ - for (int y = 0; y < m_display_maxy; y++) - { - u32 active_state = 0; - - for (int x = 0; x <= m_display_maxx; x++) - { - // turn on powered segments - if (m_display_state[y] >> x & 1) - m_display_decay[y][x] = m_display_wait; - - // determine active state - u32 ds = (m_display_decay[y][x] != 0) ? 1 : 0; - active_state |= (ds << x); - - // output to y.x, or y.a when always-on - if (x != m_display_maxx) - m_out_x[y][x] = ds; - else - m_out_a[y] = ds; - } - - // output to digity - if (m_display_segmask[y] != 0) - m_out_digit[y] = active_state & m_display_segmask[y]; - } -} - -TIMER_DEVICE_CALLBACK_MEMBER(hh_ucom4_state::display_decay_tick) -{ - // slowly turn off unpowered segments - for (int y = 0; y < m_display_maxy; y++) - for (int x = 0; x <= m_display_maxx; x++) - if (m_display_decay[y][x] != 0) - m_display_decay[y][x]--; - - display_update(); -} - -void hh_ucom4_state::set_display_size(int maxx, int maxy) -{ - m_display_maxx = maxx; - m_display_maxy = maxy; -} - -void hh_ucom4_state::set_display_segmask(u32 digits, u32 mask) -{ - // set a segment mask per selected digit, but leave unselected ones alone - for (int i = 0; i < 0x20; i++) - { - if (digits & 1) - m_display_segmask[i] = mask; - digits >>= 1; - } -} - -void hh_ucom4_state::display_matrix(int maxx, int maxy, u32 setx, u32 sety, bool update) -{ - set_display_size(maxx, maxy); - - // update current state - u32 mask = (1 << maxx) - 1; - for (int y = 0; y < maxy; y++) - m_display_state[y] = (sety >> y & 1) ? ((setx & mask) | (1 << maxx)) : 0; - - if (update) - display_update(); -} - - // generic input handlers u8 hh_ucom4_state::read_inputs(int columns) @@ -365,12 +271,10 @@ void ufombs_state::ufombs(machine_config &config) /* video hardware */ screen_device &screen(SCREEN(config, "screen", SCREEN_TYPE_SVG)); screen.set_svg_region("svg"); - screen.set_refresh_hz(50); + screen.set_refresh_hz(60); screen.set_size(243, 1080); screen.set_visarea_full(); - TIMER(config, "display_decay").configure_periodic(FUNC(hh_ucom4_state::display_decay_tick), attotime::from_msec(1)); - /* sound hardware */ SPEAKER(config, "mono").front_center(); SPEAKER_SOUND(config, m_speaker); @@ -523,12 +427,10 @@ void ssfball_state::ssfball(machine_config &config) /* video hardware */ screen_device &screen(SCREEN(config, "screen", SCREEN_TYPE_SVG)); screen.set_svg_region("svg"); - screen.set_refresh_hz(50); + screen.set_refresh_hz(60); screen.set_size(1920, 482); screen.set_visarea_full(); - TIMER(config, "display_decay").configure_periodic(FUNC(hh_ucom4_state::display_decay_tick), attotime::from_msec(1)); - /* sound hardware */ SPEAKER(config, "mono").front_center(); SPEAKER_SOUND(config, m_speaker); @@ -670,12 +572,10 @@ void bmsoccer_state::bmsoccer(machine_config &config) /* video hardware */ screen_device &screen(SCREEN(config, "screen", SCREEN_TYPE_SVG)); screen.set_svg_region("svg"); - screen.set_refresh_hz(50); + screen.set_refresh_hz(60); screen.set_size(271, 1080); screen.set_visarea_full(); - TIMER(config, "display_decay").configure_periodic(FUNC(hh_ucom4_state::display_decay_tick), attotime::from_msec(1)); - /* sound hardware */ SPEAKER(config, "mono").front_center(); SPEAKER_SOUND(config, m_speaker); @@ -788,12 +688,10 @@ void bmsafari_state::bmsafari(machine_config &config) /* video hardware */ screen_device &screen(SCREEN(config, "screen", SCREEN_TYPE_SVG)); screen.set_svg_region("svg"); - screen.set_refresh_hz(50); + screen.set_refresh_hz(60); screen.set_size(248, 1080); screen.set_visarea_full(); - TIMER(config, "display_decay").configure_periodic(FUNC(hh_ucom4_state::display_decay_tick), attotime::from_msec(1)); - /* sound hardware */ SPEAKER(config, "mono").front_center(); SPEAKER_SOUND(config, m_speaker); @@ -950,12 +848,10 @@ void splasfgt_state::splasfgt(machine_config &config) /* video hardware */ screen_device &screen(SCREEN(config, "screen", SCREEN_TYPE_SVG)); screen.set_svg_region("svg"); - screen.set_refresh_hz(50); + screen.set_refresh_hz(60); screen.set_size(1920, 476); screen.set_visarea_full(); - TIMER(config, "display_decay").configure_periodic(FUNC(hh_ucom4_state::display_decay_tick), attotime::from_msec(1)); - /* sound hardware */ SPEAKER(config, "mono").front_center(); SPEAKER_SOUND(config, m_speaker); @@ -1065,12 +961,10 @@ void bcclimbr_state::bcclimbr(machine_config &config) /* video hardware */ screen_device &screen(SCREEN(config, "screen", SCREEN_TYPE_SVG)); screen.set_svg_region("svg"); - screen.set_refresh_hz(50); + screen.set_refresh_hz(60); screen.set_size(310, 1080); screen.set_visarea_full(); - TIMER(config, "display_decay").configure_periodic(FUNC(hh_ucom4_state::display_decay_tick), attotime::from_msec(1)); - /* sound hardware */ SPEAKER(config, "mono").front_center(); SPEAKER_SOUND(config, m_speaker); @@ -1193,7 +1087,6 @@ void tactix_state::tactix(machine_config &config) m_maincpu->write_f().set(FUNC(tactix_state::leds_w)); m_maincpu->write_g().set(FUNC(tactix_state::speaker_w)); - TIMER(config, "display_decay").configure_periodic(FUNC(hh_ucom4_state::display_decay_tick), attotime::from_msec(1)); config.set_default_layout(layout_tactix); /* sound hardware */ @@ -1333,7 +1226,6 @@ void ctntune_state::ctntune(machine_config &config) m_maincpu->write_f().set(FUNC(ctntune_state::_7seg_w)); m_maincpu->write_g().set(FUNC(ctntune_state::speaker_w)); - TIMER(config, "display_decay").configure_periodic(FUNC(hh_ucom4_state::display_decay_tick), attotime::from_msec(1)); config.set_default_layout(layout_ctntune); /* sound hardware */ @@ -1440,12 +1332,10 @@ void invspace_state::invspace(machine_config &config) /* video hardware */ screen_device &screen(SCREEN(config, "screen", SCREEN_TYPE_SVG)); screen.set_svg_region("svg"); - screen.set_refresh_hz(50); + screen.set_refresh_hz(60); screen.set_size(289, 1080); screen.set_visarea_full(); - TIMER(config, "display_decay").configure_periodic(FUNC(hh_ucom4_state::display_decay_tick), attotime::from_msec(1)); - /* sound hardware */ SPEAKER(config, "mono").front_center(); SPEAKER_SOUND(config, m_speaker); @@ -1564,7 +1454,6 @@ void efball_state::efball(machine_config &config) m_maincpu->write_h().set(FUNC(efball_state::grid_w)); m_maincpu->write_i().set(FUNC(efball_state::plate_w)); - TIMER(config, "display_decay").configure_periodic(FUNC(hh_ucom4_state::display_decay_tick), attotime::from_msec(1)); config.set_default_layout(layout_efball); /* sound hardware */ @@ -1674,12 +1563,10 @@ void galaxy2_state::galaxy2(machine_config &config) /* video hardware */ screen_device &screen(SCREEN(config, "screen", SCREEN_TYPE_SVG)); screen.set_svg_region("svg"); - screen.set_refresh_hz(50); + screen.set_refresh_hz(60); screen.set_size(304, 1080); screen.set_visarea_full(); - TIMER(config, "display_decay").configure_periodic(FUNC(hh_ucom4_state::display_decay_tick), attotime::from_msec(1)); - /* sound hardware */ SPEAKER(config, "mono").front_center(); SPEAKER_SOUND(config, m_speaker); @@ -1813,12 +1700,10 @@ void astrocmd_state::astrocmd(machine_config &config) /* video hardware */ screen_device &screen(SCREEN(config, "screen", SCREEN_TYPE_SVG)); screen.set_svg_region("svg"); - screen.set_refresh_hz(50); + screen.set_refresh_hz(60); screen.set_size(1920, 525); screen.set_visarea_full(); - TIMER(config, "display_decay").configure_periodic(FUNC(hh_ucom4_state::display_decay_tick), attotime::from_msec(1)); - /* sound hardware */ SPEAKER(config, "mono").front_center(); SPEAKER_SOUND(config, m_speaker); @@ -1920,12 +1805,10 @@ void edracula_state::edracula(machine_config &config) /* video hardware */ screen_device &screen(SCREEN(config, "screen", SCREEN_TYPE_SVG)); screen.set_svg_region("svg"); - screen.set_refresh_hz(50); + screen.set_refresh_hz(60); screen.set_size(1920, 526); screen.set_visarea_full(); - TIMER(config, "display_decay").configure_periodic(FUNC(hh_ucom4_state::display_decay_tick), attotime::from_msec(1)); - /* sound hardware */ SPEAKER(config, "mono").front_center(); SPEAKER_SOUND(config, m_speaker); @@ -2013,7 +1896,7 @@ void mcompgin_state::mcompgin(machine_config &config) /* video hardware */ HLCD0530(config, m_lcd, 500); // C=0.01uF m_lcd->write_cols().set(FUNC(mcompgin_state::lcd_output_w)); - TIMER(config, "display_decay").configure_periodic(FUNC(hh_ucom4_state::display_decay_tick), attotime::from_msec(1)); + config.set_default_layout(layout_mcompgin); /* no sound! */ @@ -2120,7 +2003,6 @@ void mvbfree_state::mvbfree(machine_config &config) m_maincpu->write_h().set(FUNC(mvbfree_state::grid_w)); m_maincpu->write_i().set(FUNC(mvbfree_state::speaker_w)); - TIMER(config, "display_decay").configure_periodic(FUNC(hh_ucom4_state::display_decay_tick), attotime::from_msec(1)); config.set_default_layout(layout_mvbfree); /* sound hardware */ @@ -2242,7 +2124,6 @@ void grobot9_state::grobot9(machine_config &config) m_maincpu->write_e().set(FUNC(grobot9_state::lamps_w)); m_maincpu->write_f().set(FUNC(grobot9_state::lamps_w)); - TIMER(config, "display_decay").configure_periodic(FUNC(hh_ucom4_state::display_decay_tick), attotime::from_msec(1)); config.set_default_layout(layout_grobot9); /* sound hardware */ @@ -2345,12 +2226,10 @@ void tccombat_state::tccombat(machine_config &config) /* video hardware */ screen_device &screen(SCREEN(config, "screen", SCREEN_TYPE_SVG)); screen.set_svg_region("svg"); - screen.set_refresh_hz(50); + screen.set_refresh_hz(60); screen.set_size(300, 1080); screen.set_visarea_full(); - TIMER(config, "display_decay").configure_periodic(FUNC(hh_ucom4_state::display_decay_tick), attotime::from_msec(1)); - /* sound hardware */ SPEAKER(config, "mono").front_center(); SPEAKER_SOUND(config, m_speaker); @@ -2509,11 +2388,10 @@ void tmtennis_state::tmtennis(machine_config &config) /* video hardware */ screen_device &screen(SCREEN(config, "screen", SCREEN_TYPE_SVG)); screen.set_svg_region("svg"); - screen.set_refresh_hz(50); + screen.set_refresh_hz(60); screen.set_size(1920, 417); screen.set_visarea_full(); - TIMER(config, "display_decay").configure_periodic(FUNC(hh_ucom4_state::display_decay_tick), attotime::from_msec(1)); config.set_default_layout(layout_tmtennis); /* sound hardware */ @@ -2630,12 +2508,10 @@ void tmpacman_state::tmpacman(machine_config &config) /* video hardware */ screen_device &screen(SCREEN(config, "screen", SCREEN_TYPE_SVG)); screen.set_svg_region("svg"); - screen.set_refresh_hz(50); + screen.set_refresh_hz(60); screen.set_size(1920, 508); screen.set_visarea_full(); - TIMER(config, "display_decay").configure_periodic(FUNC(hh_ucom4_state::display_decay_tick), attotime::from_msec(1)); - /* sound hardware */ SPEAKER(config, "mono").front_center(); SPEAKER_SOUND(config, m_speaker); @@ -2744,12 +2620,10 @@ void tmscramb_state::tmscramb(machine_config &config) /* video hardware */ screen_device &screen(SCREEN(config, "screen", SCREEN_TYPE_SVG)); screen.set_svg_region("svg"); - screen.set_refresh_hz(50); + screen.set_refresh_hz(60); screen.set_size(1920, 556); screen.set_visarea_full(); - TIMER(config, "display_decay").configure_periodic(FUNC(hh_ucom4_state::display_decay_tick), attotime::from_msec(1)); - /* sound hardware */ SPEAKER(config, "mono").front_center(); SPEAKER_SOUND(config, m_speaker); @@ -2854,12 +2728,10 @@ void tcaveman_state::tcaveman(machine_config &config) /* video hardware */ screen_device &screen(SCREEN(config, "screen", SCREEN_TYPE_SVG)); screen.set_svg_region("svg"); - screen.set_refresh_hz(50); + screen.set_refresh_hz(60); screen.set_size(1920, 559); screen.set_visarea_full(); - TIMER(config, "display_decay").configure_periodic(FUNC(hh_ucom4_state::display_decay_tick), attotime::from_msec(1)); - /* sound hardware */ SPEAKER(config, "mono").front_center(); SPEAKER_SOUND(config, m_speaker); @@ -2998,12 +2870,10 @@ void alnchase_state::alnchase(machine_config &config) /* video hardware */ screen_device &screen(SCREEN(config, "screen", SCREEN_TYPE_SVG)); screen.set_svg_region("svg"); - screen.set_refresh_hz(50); + screen.set_refresh_hz(60); screen.set_size(365, 1080); screen.set_visarea_full(); - TIMER(config, "display_decay").configure_periodic(FUNC(hh_ucom4_state::display_decay_tick), attotime::from_msec(1)); - /* sound hardware */ SPEAKER(config, "mono").front_center(); SPEAKER_SOUND(config, m_speaker); diff --git a/src/mame/drivers/mattelchess.cpp b/src/mame/drivers/mattelchess.cpp index 855a7ec3967..04d51e6e1d3 100644 --- a/src/mame/drivers/mattelchess.cpp +++ b/src/mame/drivers/mattelchess.cpp @@ -208,7 +208,7 @@ void mchess_state::mchess(machine_config &config) screen_device &screen(SCREEN(config, "screen", SCREEN_TYPE_SVG)); screen.set_svg_region("svg"); - screen.set_refresh_hz(50); + screen.set_refresh_hz(60); screen.set_size(977, 1080); screen.set_visarea_full(); diff --git a/src/mame/drivers/tb303.cpp b/src/mame/drivers/tb303.cpp index 88eb81972ce..f5ced59fcff 100644 --- a/src/mame/drivers/tb303.cpp +++ b/src/mame/drivers/tb303.cpp @@ -269,8 +269,6 @@ void tb303_state::tb303(machine_config &config) tp3_clock.set_start_delay(TP3_PERIOD - TP3_LOW); TIMER(config, "tp3_clear").configure_periodic(FUNC(tb303_state::tp3_clear), TP3_PERIOD); - TIMER(config, "display_decay").configure_periodic(FUNC(hh_ucom4_state::display_decay_tick), attotime::from_msec(1)); - config.set_default_layout(layout_tb303); /* sound hardware */ diff --git a/src/mame/drivers/ticalc1x.cpp b/src/mame/drivers/ticalc1x.cpp index 899fc49ccd4..0eae6892078 100644 --- a/src/mame/drivers/ticalc1x.cpp +++ b/src/mame/drivers/ticalc1x.cpp @@ -197,7 +197,6 @@ void cmulti8_state::cmulti8(machine_config &config) m_maincpu->o().set(FUNC(cmulti8_state::write_o)); m_maincpu->r().set(FUNC(cmulti8_state::write_r)); - TIMER(config, "display_decay").configure_periodic(FUNC(hh_tms1k_state::display_decay_tick), attotime::from_msec(1)); config.set_default_layout(layout_cmulti8); /* no sound! */ @@ -425,7 +424,6 @@ void tisr16_state::tisr16(machine_config &config) m_maincpu->o().set(FUNC(tisr16_state::write_o)); m_maincpu->r().set(FUNC(tisr16_state::write_r)); - TIMER(config, "display_decay").configure_periodic(FUNC(hh_tms1k_state::display_decay_tick), attotime::from_msec(1)); config.set_default_layout(layout_tisr16); /* no sound! */ @@ -588,7 +586,6 @@ void ti1250_state::ti1250(machine_config &config) m_maincpu->o().set(FUNC(ti1250_state::write_o)); m_maincpu->r().set(FUNC(ti1250_state::write_r)); - TIMER(config, "display_decay").configure_periodic(FUNC(hh_tms1k_state::display_decay_tick), attotime::from_msec(1)); config.set_default_layout(layout_ti1250); /* no sound! */ @@ -760,7 +757,6 @@ void ti25503_state::ti25503(machine_config &config) m_maincpu->o().set(FUNC(ti25503_state::write_o)); m_maincpu->r().set(FUNC(ti25503_state::write_r)); - TIMER(config, "display_decay").configure_periodic(FUNC(hh_tms1k_state::display_decay_tick), attotime::from_msec(1)); config.set_default_layout(layout_ti25503); /* no sound! */ @@ -874,7 +870,6 @@ void ti1000_state::ti1000(machine_config &config) m_maincpu->o().set(FUNC(ti1000_state::write_o)); m_maincpu->r().set(FUNC(ti1000_state::write_r)); - TIMER(config, "display_decay").configure_periodic(FUNC(hh_tms1k_state::display_decay_tick), attotime::from_msec(1)); config.set_default_layout(layout_ti1270); /* no sound! */ @@ -991,7 +986,6 @@ void wizatron_state::wizatron(machine_config &config) m_maincpu->o().set(FUNC(wizatron_state::write_o)); m_maincpu->r().set(FUNC(wizatron_state::write_r)); - TIMER(config, "display_decay").configure_periodic(FUNC(hh_tms1k_state::display_decay_tick), attotime::from_msec(1)); config.set_default_layout(layout_wizatron); /* no sound! */ @@ -1083,7 +1077,6 @@ void lilprof_state::lilprof(machine_config &config) m_maincpu->o().set(FUNC(lilprof_state::write_o)); m_maincpu->r().set(FUNC(wizatron_state::write_r)); - TIMER(config, "display_decay").configure_periodic(FUNC(hh_tms1k_state::display_decay_tick), attotime::from_msec(1)); config.set_default_layout(layout_wizatron); /* no sound! */ @@ -1211,7 +1204,6 @@ void lilprof78_state::lilprof78(machine_config &config) m_maincpu->o().set(FUNC(lilprof78_state::write_o)); m_maincpu->r().set(FUNC(lilprof78_state::write_r)); - TIMER(config, "display_decay").configure_periodic(FUNC(hh_tms1k_state::display_decay_tick), attotime::from_msec(1)); config.set_default_layout(layout_wizatron); /* no sound! */ @@ -1341,7 +1333,6 @@ void dataman_state::dataman(machine_config &config) m_maincpu->r().set(FUNC(dataman_state::write_r)); m_maincpu->power_off().set(FUNC(hh_tms1k_state::auto_power_off)); - TIMER(config, "display_decay").configure_periodic(FUNC(hh_tms1k_state::display_decay_tick), attotime::from_msec(1)); config.set_default_layout(layout_dataman); /* no sound! */ @@ -1424,7 +1415,6 @@ void mathmarv_state::mathmarv(machine_config &config) m_maincpu->r().set(FUNC(mathmarv_state::write_r)); m_maincpu->power_off().set(FUNC(hh_tms1k_state::auto_power_off)); - TIMER(config, "display_decay").configure_periodic(FUNC(hh_tms1k_state::display_decay_tick), attotime::from_msec(1)); config.set_default_layout(layout_mathmarv); /* sound hardware */ @@ -1699,7 +1689,6 @@ void ti30_state::ti30(machine_config &config) m_maincpu->r().set(FUNC(ti30_state::write_r)); m_maincpu->power_off().set(FUNC(hh_tms1k_state::auto_power_off)); - TIMER(config, "display_decay").configure_periodic(FUNC(hh_tms1k_state::display_decay_tick), attotime::from_msec(1)); config.set_default_layout(layout_ti30); /* no sound! */ diff --git a/src/mame/drivers/tispeak.cpp b/src/mame/drivers/tispeak.cpp index af117ccfa7b..3dd9853efd2 100644 --- a/src/mame/drivers/tispeak.cpp +++ b/src/mame/drivers/tispeak.cpp @@ -466,7 +466,7 @@ public: private: virtual void power_off() override; void prepare_display(); - bool vfd_filament_on() { return m_display_decay[15][16] != 0; } + bool vfd_filament_on() { return display_element_on(16, 15); } DECLARE_READ8_MEMBER(snspell_read_k); DECLARE_WRITE16_MEMBER(snmath_write_o); @@ -1319,7 +1319,6 @@ void tispeak_state::snmath(machine_config &config) m_maincpu->write_ctl().set("tms5100", FUNC(tms5110_device::ctl_w)); m_maincpu->write_pdc().set("tms5100", FUNC(tms5110_device::pdc_w)); - TIMER(config, "display_decay").configure_periodic(FUNC(hh_tms1k_state::display_decay_tick), attotime::from_msec(1)); config.set_default_layout(layout_snmath); /* sound hardware */ @@ -1460,7 +1459,6 @@ void tispeak_state::vocaid(machine_config &config) m_maincpu->o().set(FUNC(tispeak_state::snspellc_write_o)); m_maincpu->r().set(FUNC(tispeak_state::snspellc_write_r)); - TIMER(config, "display_decay").configure_periodic(FUNC(hh_tms1k_state::display_decay_tick), attotime::from_msec(1)); TIMER(config, "ol_timer").configure_periodic(FUNC(tispeak_state::tntell_get_overlay), attotime::from_msec(50)); config.set_default_layout(layout_tntell); @@ -1492,7 +1490,6 @@ void tispeak_state::k28m2(machine_config &config) m_maincpu->o().set(FUNC(tispeak_state::k28_write_o)); m_maincpu->r().set(FUNC(tispeak_state::k28_write_r)); - TIMER(config, "display_decay").configure_periodic(FUNC(hh_tms1k_state::display_decay_tick), attotime::from_msec(1)); config.set_default_layout(layout_k28m2); /* sound hardware */ diff --git a/src/mame/drivers/tispellb.cpp b/src/mame/drivers/tispellb.cpp index 3b128fcd9c4..f8f23b55928 100644 --- a/src/mame/drivers/tispellb.cpp +++ b/src/mame/drivers/tispellb.cpp @@ -92,7 +92,7 @@ private: virtual void power_off() override; void prepare_display(); - bool vfd_filament_on() { return m_display_decay[15][16] != 0; } + bool vfd_filament_on() { return display_element_on(16, 15); } DECLARE_READ8_MEMBER(main_read_k); DECLARE_WRITE16_MEMBER(main_write_o); @@ -363,7 +363,6 @@ void tispellb_state::rev1(machine_config &config) config.m_perfect_cpu_quantum = subtag("maincpu"); - TIMER(config, "display_decay").configure_periodic(FUNC(hh_tms1k_state::display_decay_tick), attotime::from_msec(1)); config.set_default_layout(layout_spellb); /* no sound! */ @@ -383,7 +382,6 @@ void tispellb_state::rev2(machine_config &config) TMS6100(config, m_tms6100, 350000); m_tms6100->enable_4bit_mode(true); - TIMER(config, "display_decay").configure_periodic(FUNC(hh_tms1k_state::display_decay_tick), attotime::from_msec(1)); config.set_default_layout(layout_spellb); /* sound hardware */ diff --git a/src/mame/drivers/tr606.cpp b/src/mame/drivers/tr606.cpp index 970addc505b..001adda7094 100644 --- a/src/mame/drivers/tr606.cpp +++ b/src/mame/drivers/tr606.cpp @@ -90,7 +90,6 @@ void tr606_state::tr606(machine_config &config) tp3_clock.set_start_delay(TP3_PERIOD - TP3_LOW); TIMER(config, "tp3_clear").configure_periodic(FUNC(tr606_state::tp3_clear), TP3_PERIOD); - TIMER(config, "display_decay").configure_periodic(FUNC(hh_ucom4_state::display_decay_tick), attotime::from_msec(1)); config.set_default_layout(layout_tr606); /* sound hardware */ diff --git a/src/mame/includes/hh_tms1k.h b/src/mame/includes/hh_tms1k.h index c595772468b..c083c16a34f 100644 --- a/src/mame/includes/hh_tms1k.h +++ b/src/mame/includes/hh_tms1k.h @@ -11,6 +11,8 @@ #pragma once +#include "includes/screenless.h" + #include "cpu/tms1000/tms1000.h" #include "cpu/tms1000/tms1000c.h" #include "cpu/tms1000/tms1100.h" @@ -24,28 +26,19 @@ #include "sound/spkrdev.h" -class hh_tms1k_state : public driver_device +class hh_tms1k_state : public screenless_state { public: hh_tms1k_state(const machine_config &mconfig, device_type type, const char *tag) : - driver_device(mconfig, type, tag), + screenless_state(mconfig, type, tag), m_maincpu(*this, "maincpu"), m_inp_matrix(*this, "IN.%u", 0), - m_out_x(*this, "%u.%u", 0U, 0U), - m_out_a(*this, "%u.a", 0U), - m_out_digit(*this, "digit%u", 0U), - m_speaker(*this, "speaker"), - m_display_wait(33), - m_display_maxy(1), - m_display_maxx(0) + m_speaker(*this, "speaker") { } // devices required_device m_maincpu; optional_ioport_array<18> m_inp_matrix; // max 18 - output_finder<0x20, 0x20> m_out_x; - output_finder<0x20> m_out_a; - output_finder<0x20> m_out_digit; optional_device m_speaker; // misc common @@ -55,6 +48,9 @@ public: bool m_power_on; bool m_power_led; + u32 m_grid; // VFD/LED current row data + u32 m_plate; // VFD/LED current column data + u8 read_inputs(int columns); u8 read_rotated_inputs(int columns, u8 rowmask = 0xf); virtual DECLARE_INPUT_CHANGED_MEMBER(reset_button); @@ -66,27 +62,11 @@ public: template DECLARE_INPUT_CHANGED_MEMBER(switch_next) { if (newval) switch_change(Sel, (u32)(uintptr_t)param, true); } template DECLARE_INPUT_CHANGED_MEMBER(switch_prev) { if (newval) switch_change(Sel, (u32)(uintptr_t)param, false); } - // display common - int m_display_wait; // led/lamp off-delay in milliseconds (default 33ms) - int m_display_maxy; // display matrix number of rows - int m_display_maxx; // display matrix number of columns (max 31 for now) - - u32 m_grid; // VFD/LED current row data - u32 m_plate; // VFD/LED current column data - - u32 m_display_state[0x20]; // display matrix rows data (last bit is used for always-on) - u16 m_display_segmask[0x20]; // if not 0, display matrix row is a digit, mask indicates connected segments - u8 m_display_decay[0x20][0x20]; // (internal use) - - TIMER_DEVICE_CALLBACK_MEMBER(display_decay_tick); - void display_update(); - void set_display_size(int maxx, int maxy); - void set_display_segmask(u32 digits, u32 mask); - void display_matrix(int maxx, int maxy, u32 setx, u32 sety, bool update = true); - protected: virtual void machine_start() override; virtual void machine_reset() override; + + virtual void display_update() override; }; diff --git a/src/mame/includes/hh_ucom4.h b/src/mame/includes/hh_ucom4.h index daa9c89af59..8797041c2c7 100644 --- a/src/mame/includes/hh_ucom4.h +++ b/src/mame/includes/hh_ucom4.h @@ -9,33 +9,26 @@ #ifndef MAME_INCLUDES_HH_UCOM4_H #define MAME_INCLUDES_HH_UCOM4_H +#include "includes/screenless.h" + #include "cpu/ucom4/ucom4.h" #include "machine/timer.h" #include "sound/spkrdev.h" -class hh_ucom4_state : public driver_device +class hh_ucom4_state : public screenless_state { public: hh_ucom4_state(const machine_config &mconfig, device_type type, const char *tag) : - driver_device(mconfig, type, tag), + screenless_state(mconfig, type, tag), m_maincpu(*this, "maincpu"), m_inp_matrix(*this, "IN.%u", 0), - m_out_x(*this, "%u.%u", 0U, 0U), - m_out_a(*this, "%u.a", 0U), - m_out_digit(*this, "digit%u", 0U), - m_speaker(*this, "speaker"), - m_display_wait(33), - m_display_maxy(1), - m_display_maxx(0) + m_speaker(*this, "speaker") { } // devices required_device m_maincpu; optional_ioport_array<6> m_inp_matrix; // max 6 - output_finder<0x20, 0x20> m_out_x; - output_finder<0x20> m_out_a; - output_finder<0x20> m_out_digit; optional_device m_speaker; // misc common @@ -43,29 +36,14 @@ public: u8 m_int; // MCU INT pin state u16 m_inp_mux; // multiplexed inputs mask + u32 m_grid; // VFD current row data + u32 m_plate; // VFD current column data + u8 read_inputs(int columns); void refresh_interrupts(void); void set_interrupt(int state); DECLARE_INPUT_CHANGED_MEMBER(single_interrupt_line); - // display common - int m_display_wait; // led/lamp off-delay in milliseconds (default 33ms) - int m_display_maxy; // display matrix number of rows - int m_display_maxx; // display matrix number of columns (max 31 for now) - - u32 m_grid; // VFD current row data - u32 m_plate; // VFD current column data - - u32 m_display_state[0x20]; // display matrix rows data (last bit is used for always-on) - u16 m_display_segmask[0x20]; // if not 0, display matrix row is a digit, mask indicates connected segments - u8 m_display_decay[0x20][0x20]; // (internal use) - - TIMER_DEVICE_CALLBACK_MEMBER(display_decay_tick); - void display_update(); - void set_display_size(int maxx, int maxy); - void set_display_segmask(u32 digits, u32 mask); - void display_matrix(int maxx, int maxy, u32 setx, u32 sety, bool update = true); - protected: virtual void machine_start() override; virtual void machine_reset() override; diff --git a/src/mame/includes/screenless.h b/src/mame/includes/screenless.h new file mode 100644 index 00000000000..624005cb5bb --- /dev/null +++ b/src/mame/includes/screenless.h @@ -0,0 +1,75 @@ +// license:BSD-3-Clause +// copyright-holders:hap +/****************************************************************************** + + Generic screenless base class + + implementation is in machine/screenless.cpp + +******************************************************************************/ + +#ifndef MAME_INCLUDES_SCREENLESS_H +#define MAME_INCLUDES_SCREENLESS_H + +#pragma once + +class screenless_state : public driver_device +{ +public: + screenless_state(const machine_config &mconfig, device_type type, const char *tag) : + driver_device(mconfig, type, tag), + m_out_x(*this, "%u.%u", 0U, 0U), + m_out_a(*this, "%u.a", 0U), + m_out_digit(*this, "digit%u", 0U), + m_display_maxy(0), + m_display_maxx(-1) + { + // set defaults (60hz frames, 0.5 interpolation, 1 brightness level) + set_display_duration(attotime::from_hz(60)); + set_display_factor(0.5); + reset_display_levels(); + set_display_level(0.015); + } + +protected: + output_finder<0x20, 0x40> m_out_x; // max 32, 63 + output_finder<0x20> m_out_a; + output_finder<0x20> m_out_digit; + + int m_display_maxy; // display matrix number of rows + int m_display_maxx; // display matrix number of columns + u64 m_display_state[0x20]; // display matrix rows data (last bit is used for always-on) + u16 m_display_segmask[0x20]; // if not 0, display matrix row is a digit, mask indicates connected segments + + void set_display_duration(attotime duration); + void set_display_factor(double factor); + + void reset_display_levels(); + void set_display_level(double level, u8 i = 0); + void set_display_levels(u8 levels, ...); + + void set_display_size(int maxx, int maxy); + void set_display_segmask(u32 digits, u32 mask); + void display_matrix(int maxx, int maxy, u64 setx, u32 sety, bool update = true); + virtual void display_update(); + bool display_element_on(u32 x, u32 y); + + virtual void machine_start() override; + +private: + u64 m_ds_prev[0x20]; + double m_ds_bri[0x20][0x40]; + attotime m_ds_acc[0x20][0x40]; + attotime m_ds_update_time; + attotime m_ds_frame_time; + attotime m_ds_frame_time_set; + double m_ds_frame_factor; + double m_ds_level[0x100]; + + emu_timer *m_display_frame_timer; + TIMER_CALLBACK_MEMBER(display_frame); + void display_schedule_frame(); +}; + + +#endif // MAME_INCLUDES_SCREENLESS_H diff --git a/src/mame/layout/wildfire.lay b/src/mame/layout/wildfire.lay index c8782668f27..805b72b9d8f 100644 --- a/src/mame/layout/wildfire.lay +++ b/src/mame/layout/wildfire.lay @@ -9,7 +9,8 @@ - + + diff --git a/src/mame/machine/chessbase.cpp b/src/mame/machine/chessbase.cpp index 4515e632e28..cc38c8a5720 100644 --- a/src/mame/machine/chessbase.cpp +++ b/src/mame/machine/chessbase.cpp @@ -11,6 +11,9 @@ greatly affecting user playability of emulated electronic board games. As workaround for the chess games, use an external chess GUI on the side, such as Arena(in editmode). +TODO: +- use screenless class + ******************************************************************************/ #include "emu.h" diff --git a/src/mame/machine/screenless.cpp b/src/mame/machine/screenless.cpp new file mode 100644 index 00000000000..f69191c6799 --- /dev/null +++ b/src/mame/machine/screenless.cpp @@ -0,0 +1,205 @@ +// license:BSD-3-Clause +// copyright-holders:hap +/****************************************************************************** + +Generic screenless base class + +This file contains helpers for strobed display elements. + +TODO: +- multiple brightness levels doesn't work for SVGs + +******************************************************************************/ + +#include "emu.h" +#include "includes/screenless.h" + +#include + + +// machine start + +ALLOW_SAVE_TYPE(attotime); // m_ds_acc + +void screenless_state::machine_start() +{ + // resolve handlers + m_out_x.resolve(); + m_out_a.resolve(); + m_out_digit.resolve(); + + // initialize + std::fill_n(m_display_state, ARRAY_LENGTH(m_display_state), 0); + std::fill_n(m_ds_prev, ARRAY_LENGTH(m_ds_prev), 0); + std::fill_n(m_display_segmask, ARRAY_LENGTH(m_display_segmask), 0); + std::fill_n(*m_ds_bri, ARRAY_LENGTH(m_ds_bri) * ARRAY_LENGTH(m_ds_bri[0]), 0.0); + + m_display_frame_timer = machine().scheduler().timer_alloc(timer_expired_delegate(FUNC(screenless_state::display_frame),this)); + display_schedule_frame(); + m_ds_update_time = machine().time(); + + // register for savestates + save_item(NAME(m_display_maxy)); + save_item(NAME(m_display_maxx)); + save_item(NAME(m_display_state)); + save_item(NAME(m_display_segmask)); + + save_item(NAME(m_ds_prev)); + save_item(NAME(m_ds_bri)); + save_item(NAME(m_ds_acc)); + save_item(NAME(m_ds_update_time)); + save_item(NAME(m_ds_frame_time)); + save_item(NAME(m_ds_frame_time_set)); + save_item(NAME(m_ds_frame_factor)); + save_item(NAME(m_ds_level)); +} + + +// public interface + +void screenless_state::set_display_duration(attotime duration) +{ + // set frame duration + m_ds_frame_time_set = duration; +} + +void screenless_state::set_display_factor(double factor) +{ + // set frame interpolation (factor * curframe, 1.0-factor * prev frame) + // factor range is 0.0 to 1.0 + m_ds_frame_factor = factor; +} + +void screenless_state::reset_display_levels() +{ + std::fill_n(m_ds_level, ARRAY_LENGTH(m_ds_level), 1.0); +} + +void screenless_state::set_display_level(double level, u8 i) +{ + // set a brightness level, range is 0.0 to 1.0 + m_ds_level[i] = level; +} + +void screenless_state::set_display_levels(u8 levels, ...) +{ + // set multiple brightness levels + va_list v; + va_start(v, levels); + for (int i = 0; i < levels; i++) + m_ds_level[i] = va_arg(v, double); + + m_ds_level[levels] = 1.0; +} + +void screenless_state::set_display_size(int maxx, int maxy) +{ + m_display_maxx = maxx; + m_display_maxy = maxy; +} + +void screenless_state::set_display_segmask(u32 digits, u32 mask) +{ + // set a segment mask per selected digit, but leave unselected ones alone + for (int i = 0; i < 0x20; i++) + { + if (digits & 1) + m_display_segmask[i] = mask; + digits >>= 1; + } +} + +void screenless_state::display_matrix(int maxx, int maxy, u64 setx, u32 sety, bool update) +{ + set_display_size(maxx, maxy); + + // update current state + u64 mask = (u64(1) << maxx) - 1; + for (int y = 0; y < maxy; y++) + m_display_state[y] = (sety >> y & 1) ? ((setx & mask) | (u64(1) << maxx)) : 0; + + if (update) + display_update(); +} + +void screenless_state::display_update() +{ + // call this every time m_display_state is changed (automatic with display_matrix) + const attotime now = machine().time(); + const attotime diff = (m_ds_update_time >= now) ? attotime::zero : now - m_ds_update_time; + + // accumulate active time + for (int y = 0; y < m_display_maxy; y++) + { + u64 row = m_ds_prev[y]; + m_ds_prev[y] = m_display_state[y]; + + if (diff != attotime::zero) + { + for (int x = 0; x <= m_display_maxx; x++) + { + if (BIT(row, x)) + m_ds_acc[y][x] += diff; + } + } + } + + m_ds_update_time = now; +} + +bool screenless_state::display_element_on(u32 x, u32 y) +{ + // display element active state + return m_ds_bri[y][x] > m_ds_level[0]; +} + + +// internal handlers + +void screenless_state::display_schedule_frame() +{ + std::fill_n(*m_ds_acc, ARRAY_LENGTH(m_ds_acc) * ARRAY_LENGTH(m_ds_acc[0]), attotime::zero); + + m_ds_frame_time = m_ds_frame_time_set; + m_display_frame_timer->adjust(m_ds_frame_time); +} + +TIMER_CALLBACK_MEMBER(screenless_state::display_frame) +{ + display_update(); + + const double frame_time = m_ds_frame_time.as_double(); + const double factor0 = m_ds_frame_factor; + const double factor1 = 1.0 - factor0; + + for (int y = 0; y < m_display_maxy; y++) + { + u64 row = 0; + + for (int x = 0; x <= m_display_maxx; x++) + { + // determine brightness level + double bri = m_ds_bri[y][x] * factor1 + (m_ds_acc[y][x].as_double() / frame_time) * factor0; + if (bri > 1.0) bri = 1.0; // shouldn't happen + m_ds_bri[y][x] = bri; + + u8 level; + for (level = 0; bri > m_ds_level[level]; level++) { ; } + + if (level > 0) + row |= (u64(1) << x); + + // output to y.x, or y.a when always-on + if (x != m_display_maxx) + m_out_x[y][x] = level; + else + m_out_a[y] = level; + } + + // output to digity + if (m_display_segmask[y] != 0) + m_out_digit[y] = row & m_display_segmask[y]; + } + + display_schedule_frame(); +} -- cgit v1.2.3