From 4881a087523343b5241be15da5e87ff9a3d01d31 Mon Sep 17 00:00:00 2001 From: hap Date: Mon, 23 Dec 2024 20:03:40 +0100 Subject: tama: add svg screen, svg shapes taken from BrickEmuPy [hap, azya] --- src/devices/cpu/e0c6200/e0c6s46.cpp | 42 ++++++++++++---------- src/devices/cpu/e0c6200/e0c6s46.h | 28 +++++++++------ src/mame/bandai/tamag1.cpp | 69 +++++++------------------------------ src/mame/layout/tama.lay | 68 ------------------------------------ 4 files changed, 52 insertions(+), 155 deletions(-) delete mode 100644 src/mame/layout/tama.lay diff --git a/src/devices/cpu/e0c6200/e0c6s46.cpp b/src/devices/cpu/e0c6200/e0c6s46.cpp index fcc9ac6c5cf..f2dc35103dd 100644 --- a/src/devices/cpu/e0c6200/e0c6s46.cpp +++ b/src/devices/cpu/e0c6200/e0c6s46.cpp @@ -41,8 +41,8 @@ void e0c6s46_device::e0c6s46_program(address_map &map) void e0c6s46_device::e0c6s46_data(address_map &map) { map(0x0000, 0x027f).ram(); - map(0x0e00, 0x0e4f).ram().share("vram1"); - map(0x0e80, 0x0ecf).ram().share("vram2"); + map(0x0e00, 0x0e4f).ram().share(m_vram[0]); + map(0x0e80, 0x0ecf).ram().share(m_vram[1]); map(0x0f00, 0x0f7f).rw(FUNC(e0c6s46_device::io_r), FUNC(e0c6s46_device::io_w)); } @@ -50,9 +50,9 @@ void e0c6s46_device::e0c6s46_data(address_map &map) // device definitions e0c6s46_device::e0c6s46_device(const machine_config &mconfig, const char *tag, device_t *owner, u32 clock) : e0c6200_cpu_device(mconfig, E0C6S46, tag, owner, clock, address_map_constructor(FUNC(e0c6s46_device::e0c6s46_program), this), address_map_constructor(FUNC(e0c6s46_device::e0c6s46_data), this)), - m_vram1(*this, "vram1"), - m_vram2(*this, "vram2"), - m_pixel_update_cb(*this), + m_vram(*this, "vram%u", 1U), + m_write_segs(*this), + m_write_contrast(*this), m_write_r(*this), m_read_p(*this, 0), m_write_p(*this) @@ -68,15 +68,19 @@ void e0c6s46_device::device_start() { e0c6200_cpu_device::device_start(); - m_pixel_update_cb.resolve(); - - // create timers + // misc init m_core_256_handle = timer_alloc(FUNC(e0c6s46_device::core_256_cb), this); m_core_256_handle->adjust(attotime::from_ticks(64, unscaled_clock())); m_prgtimer_handle = timer_alloc(FUNC(e0c6s46_device::prgtimer_cb), this); m_prgtimer_handle->adjust(attotime::never); m_buzzer_handle = timer_alloc(FUNC(e0c6s46_device::buzzer_cb), this); m_buzzer_handle->adjust(attotime::never); + m_lcd_driver = timer_alloc(FUNC(e0c6s46_device::lcd_driver_cb), this); + m_lcd_driver->adjust(attotime::from_ticks(1024, unscaled_clock())); + + const u32 render_buf_size = m_vram[0].bytes() * 2 * 4; + m_render_buf = make_unique_clear(render_buf_size); + save_pointer(NAME(m_render_buf), render_buf_size); // zerofill memset(m_port_r, 0x0, sizeof(m_port_r)); @@ -195,6 +199,8 @@ void e0c6s46_device::device_reset() m_data->write_byte(0xf7d, 0x0); m_data->write_byte(0xf7e, 0x0); + m_write_contrast(m_lcd_contrast); + // reset ports for (int i = 0; i < 5; i++) write_r(i, m_port_r[i]); @@ -545,13 +551,11 @@ void e0c6s46_device::clock_bz_1shot() // LCD Driver //------------------------------------------------- -u32 e0c6s46_device::screen_update(screen_device &screen, bitmap_ind16 &bitmap, const rectangle &cliprect) +TIMER_CALLBACK_MEMBER(e0c6s46_device::lcd_driver_cb) { - // call this 32 times per second (osc1/1024: 32hz at default clock of 32768hz) + // this gets called 32 times per second (osc1/1024: 32hz at default clock of 32768hz) for (int bank = 0; bank < 2; bank++) { - const u8* vram = bank ? m_vram2 : m_vram1; - // determine operating mode bool lcd_on = false; int pixel = 0; @@ -563,26 +567,25 @@ u32 e0c6s46_device::screen_update(screen_device &screen, bitmap_ind16 &bitmap, c lcd_on = true; // draw pixels - for (int offset = 0; offset < 0x50; offset++) + for (int offset = 0; offset < m_vram[0].bytes(); offset++) { for (int c = 0; c < 4; c++) { if (lcd_on) - pixel = vram[offset] >> c & 1; + pixel = m_vram[bank][offset] >> c & 1; // 16 COM(common) pins, 40 SEG(segment) pins int seg = offset / 2; int com = bank * 8 + (offset & 1) * 4 + c; - if (!m_pixel_update_cb.isnull()) - m_pixel_update_cb(bitmap, cliprect, m_lcd_contrast, seg, com, pixel); - else if (cliprect.contains(seg, com)) - bitmap.pix(com, seg) = pixel; + const u8 width = m_vram[0].bytes() * 4 / 8; + m_render_buf[com * width + seg] = pixel; + m_write_segs(seg << 4 | com, pixel); } } } - return 0; + m_lcd_driver->adjust(attotime::from_ticks(1024, unscaled_clock())); } @@ -760,6 +763,7 @@ void e0c6s46_device::io_w(offs_t offset, u8 data) case 0x72: // contrast adjustment (0=light, 15=dark) m_lcd_contrast = data; + m_write_contrast(data); break; // SVD circuit (supply voltage detection) diff --git a/src/devices/cpu/e0c6200/e0c6s46.h b/src/devices/cpu/e0c6200/e0c6s46.h index 3f1e09e6c9e..ad96db9e6ca 100644 --- a/src/devices/cpu/e0c6200/e0c6s46.h +++ b/src/devices/cpu/e0c6200/e0c6s46.h @@ -42,10 +42,6 @@ enum }; -// lcd driver -#define E0C6S46_PIXEL_UPDATE(name) void name(bitmap_ind16 &bitmap, const rectangle &cliprect, int contrast, int seg, int com, int state) - - class e0c6s46_device : public e0c6200_cpu_device { public: @@ -60,12 +56,14 @@ public: template auto read_p() { return m_read_p[Port].bind(); } template auto write_p() { return m_write_p[Port].bind(); } - template void set_pixel_update_cb(T &&... args) { m_pixel_update_cb.set(std::forward(args)...); } + // LCD segment outputs: COM0-COM15 as a0-a3, SEG0-SEGx as a4-a10 + auto write_segs() { return m_write_segs.bind(); } - u8 io_r(offs_t offset); - void io_w(offs_t offset, u8 data); + // LCD contrast (adjusts VL pins overall voltage level) + auto write_contrast() { return m_write_contrast.bind(); } - u32 screen_update(screen_device &screen, bitmap_ind16 &bitmap, const rectangle &cliprect); + const u8 *lcd_buffer() { return &m_render_buf[0]; } // get intermediate LCD pixel buffer + //u32 screen_update(screen_device &screen, bitmap_rgb32 &bitmap, const rectangle &cliprect); // optional protected: // device-level overrides @@ -81,17 +79,25 @@ protected: void e0c6s46_program(address_map &map) ATTR_COLD; private: - required_shared_ptr m_vram1; - required_shared_ptr m_vram2; + u8 io_r(offs_t offset); + void io_w(offs_t offset, u8 data); + + required_shared_ptr_array m_vram; u8 m_irqflag[6]; u8 m_irqmask[6]; u8 m_osc; u8 m_svd; + // lcd driver u8 m_lcd_control; u8 m_lcd_contrast; - pixel_update_delegate m_pixel_update_cb; + std::unique_ptr m_render_buf; + devcb_write8 m_write_segs; + devcb_write8 m_write_contrast; + + emu_timer *m_lcd_driver; + TIMER_CALLBACK_MEMBER(lcd_driver_cb); // i/o ports devcb_write8::array<5> m_write_r; diff --git a/src/mame/bandai/tamag1.cpp b/src/mame/bandai/tamag1.cpp index 36e9f7c47a1..9dc17e52831 100644 --- a/src/mame/bandai/tamag1.cpp +++ b/src/mame/bandai/tamag1.cpp @@ -1,6 +1,6 @@ // license:BSD-3-Clause // copyright-holders:hap -// thanks-to:digshadow, Segher +// thanks-to:digshadow, Segher, azya /******************************************************************************* Bandai Tamagotchi generation 1 hardware @@ -12,7 +12,6 @@ Hardware notes: - 1-bit sound TODO: -- change to SVG screen - add the Mothra version that was recently dumped (has a E0C6S48) *******************************************************************************/ @@ -22,12 +21,9 @@ TODO: #include "cpu/e0c6200/e0c6s46.h" #include "sound/spkrdev.h" -#include "emupal.h" #include "screen.h" #include "speaker.h" -#include "tama.lh" - namespace { @@ -48,8 +44,7 @@ protected: virtual void machine_start() override ATTR_COLD; private: - void tama_palette(palette_device &palette) const; - E0C6S46_PIXEL_UPDATE(pixel_update); + void lcd_segment_w(offs_t offset, u8 data) { m_out_x[offset & 0xf][offset >> 4] = data; } required_device m_maincpu; output_finder<16, 40> m_out_x; @@ -62,43 +57,6 @@ void tamag1_state::machine_start() -/******************************************************************************* - Video -*******************************************************************************/ - -E0C6S46_PIXEL_UPDATE(tamag1_state::pixel_update) -{ - // 16 COM(common) pins, 40 SEG(segment) pins from MCU, 32x16 LCD screen: - static const int seg2x[0x28] = - { - 0, 1, 2, 3, 4, 5, 6, 7, - 35,8, 9, 10,11,12,13,14, - 15,34,33,32,31,30,29,28, - 27,26,25,24,36,23,22,21, - 20,19,18,17,16,37,38,39 - }; - - int y = com, x = seg2x[seg]; - if (cliprect.contains(x, y)) - bitmap.pix(y, x) = state; - - // 2 rows of indicators: - // above screen: 0:meal, 1:lamp, 2:play, 3:medicine - // under screen: 4:bath, 5:scales, 6:shout, 7:attention - // they are on pin SEG8(x=35) + COM0-3, pin SEG28(x=36) + COM12-15 - - // output to y.x - m_out_x[y][x] = state; -} - -void tamag1_state::tama_palette(palette_device &palette) const -{ - palette.set_pen_color(0, rgb_t(0xf1, 0xf0, 0xf9)); // background - palette.set_pen_color(1, rgb_t(0x3c, 0x38, 0x38)); // lcd pixel -} - - - /******************************************************************************* Input Ports *******************************************************************************/ @@ -127,20 +85,14 @@ void tamag1_state::tama(machine_config &config) { // basic machine hardware E0C6S46(config, m_maincpu, 32.768_kHz_XTAL); - m_maincpu->set_pixel_update_cb(FUNC(tamag1_state::pixel_update)); + m_maincpu->write_segs().set(FUNC(tamag1_state::lcd_segment_w)); m_maincpu->write_r<4>().set("speaker", FUNC(speaker_sound_device::level_w)).bit(3); // video hardware - screen_device &screen(SCREEN(config, "screen", SCREEN_TYPE_LCD)); - screen.set_refresh_hz(32.768_kHz_XTAL/1024); - screen.set_vblank_time(ATTOSECONDS_IN_USEC(0)); - screen.set_size(40, 16); - screen.set_visarea(0, 32-1, 0, 16-1); - screen.set_screen_update("maincpu", FUNC(e0c6s46_device::screen_update)); - screen.set_palette("palette"); - config.set_default_layout(layout_tama); - - PALETTE(config, "palette", FUNC(tamag1_state::tama_palette), 2); + screen_device &screen(SCREEN(config, "screen", SCREEN_TYPE_SVG)); + screen.set_refresh_hz(32); + screen.set_size(1119, 1080); + screen.set_visarea_full(); // sound hardware SPEAKER(config, "mono").front_center(); @@ -159,6 +111,9 @@ ROM_START( tama ) ROM_REGION( 0x3000, "maincpu:test", 0 ) ROM_LOAD( "test.bin", 0x0000, 0x3000, CRC(4372220e) SHA1(6e13d015113e16198c0059b9d0c38d7027ae7324) ) // this rom is on the die too, test pin enables it? + + ROM_REGION( 139072, "screen", 0) + ROM_LOAD( "tama.svg", 0, 139072, CRC(9468b964) SHA1(ab49471db21a00a3b3a68da39c40da69da5d7e1b) ) ROM_END } // anonymous namespace @@ -169,5 +124,5 @@ ROM_END Drivers *******************************************************************************/ -// YEAR NAME PARENT COMPAT MACHINE INPUT CLASS INIT COMPANY FULLNAME FLAGS -SYST( 1997, tama, 0, 0, tama, tama, tamag1_state, empty_init, "Bandai", "Tamagotchi (USA)", MACHINE_SUPPORTS_SAVE ) +// YEAR NAME PARENT COMPAT MACHINE INPUT CLASS INIT COMPANY FULLNAME FLAGS +SYST( 1997, tama, 0, 0, tama, tama, tamag1_state, empty_init, "Bandai", "Tamagotchi (World)", MACHINE_SUPPORTS_SAVE | MACHINE_REQUIRES_ARTWORK ) diff --git a/src/mame/layout/tama.lay b/src/mame/layout/tama.lay deleted file mode 100644 index 403676fee81..00000000000 --- a/src/mame/layout/tama.lay +++ /dev/null @@ -1,68 +0,0 @@ - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -- cgit v1.2.3