mirror of
https://github.com/holub/mame
synced 2025-07-04 09:28:51 +03:00
XaviX - fix opcode access in upper banks (needed for rad_fb) + basic input mapping to push things along (#4237)
* some cleanups, opcode access fix (nw) * start looking at the football * rad_fb inputs (nw) * slight video refactor (nw) * (nw)
This commit is contained in:
parent
c8572d9508
commit
84e9644c4f
@ -3447,6 +3447,8 @@ files {
|
||||
MAME_DIR .. "src/mame/includes/xavix.h",
|
||||
MAME_DIR .. "src/mame/machine/xavix_mtrk_wheel.cpp",
|
||||
MAME_DIR .. "src/mame/machine/xavix_mtrk_wheel.h",
|
||||
MAME_DIR .. "src/mame/machine/xavix_madfb_ball.cpp",
|
||||
MAME_DIR .. "src/mame/machine/xavix_madfb_ball.h",
|
||||
}
|
||||
|
||||
createMESSProjects(_target, _subtarget, "ultimachine")
|
||||
|
@ -209,30 +209,6 @@
|
||||
// NTSC clock for regular XaviX?
|
||||
#define MAIN_CLOCK XTAL(21'477'272)
|
||||
|
||||
READ8_MEMBER(xavix_state::main_r)
|
||||
{
|
||||
if (offset & 0x8000)
|
||||
{
|
||||
return m_rgn[(offset) & (m_rgnlen - 1)];
|
||||
}
|
||||
else
|
||||
{
|
||||
return m_lowbus->read8(space, offset & 0x7fff);
|
||||
}
|
||||
}
|
||||
|
||||
WRITE8_MEMBER(xavix_state::main_w)
|
||||
{
|
||||
if (offset & 0x8000)
|
||||
{
|
||||
logerror("write to ROM area?\n");
|
||||
}
|
||||
else
|
||||
{
|
||||
m_lowbus->write8(space, offset & 0x7fff, data);
|
||||
}
|
||||
}
|
||||
|
||||
/* rad_madf has callf #$8f3f21 in various places, and expects to jump to code in ROM, it is unclear how things map in this case, as presumably
|
||||
the CPU 0 page memory and stack are still at 0 but ROM must be in the 3xxx range (game hasn't got far enough to call this yet to help either)
|
||||
|
||||
@ -259,7 +235,8 @@ WRITE8_MEMBER(xavix_state::main_w)
|
||||
|
||||
|
||||
*/
|
||||
READ8_MEMBER(xavix_state::main2_r)
|
||||
|
||||
READ8_MEMBER(xavix_state::opcodes_000000_r)
|
||||
{
|
||||
if (offset & 0x8000)
|
||||
{
|
||||
@ -267,35 +244,21 @@ READ8_MEMBER(xavix_state::main2_r)
|
||||
}
|
||||
else
|
||||
{
|
||||
if ((offset & 0xffff) >= 0x200)
|
||||
{
|
||||
return m_rgn[(offset) & (m_rgnlen - 1)];
|
||||
}
|
||||
else
|
||||
return m_lowbus->read8(space, offset & 0x7fff);
|
||||
return m_lowbus->read8(space, offset & 0x7fff);
|
||||
}
|
||||
}
|
||||
|
||||
WRITE8_MEMBER(xavix_state::main2_w)
|
||||
READ8_MEMBER(xavix_state::opcodes_800000_r)
|
||||
{
|
||||
if (offset & 0x8000)
|
||||
{
|
||||
logerror("write to ROM area?\n");
|
||||
}
|
||||
else
|
||||
{
|
||||
if ((offset & 0xffff) >= 0x200)
|
||||
logerror("write to ROM area?\n");
|
||||
else
|
||||
m_lowbus->write8(space, offset & 0x7fff, data);
|
||||
}
|
||||
// rad_fb, rad_madf confirm that for >0x800000 the CPU only sees ROM when executing opcodes
|
||||
return m_rgn[(offset) & (m_rgnlen - 1)];
|
||||
}
|
||||
|
||||
// this is only used for opcode / oprand reads, data memory addressing is handled in core, doing the opcode / oprand addressing in core causes disassembly issues when running from lowbus space (ram, interrupts on most games)
|
||||
void xavix_state::xavix_map(address_map &map)
|
||||
{
|
||||
map(0x000000, 0x7fffff).rw(FUNC(xavix_state::main_r), FUNC(xavix_state::main_w));
|
||||
map(0x800000, 0xffffff).rw(FUNC(xavix_state::main2_r), FUNC(xavix_state::main2_w));
|
||||
map(0x000000, 0x7fffff).r(FUNC(xavix_state::opcodes_000000_r));
|
||||
map(0x800000, 0xffffff).r(FUNC(xavix_state::opcodes_800000_r));
|
||||
}
|
||||
|
||||
// this is used by data reads / writes after some processing in the core to decide if data reads can see lowbus, zeropage, stack, bank registers etc. and only falls through to here on a true external bus access
|
||||
@ -316,8 +279,8 @@ void xavix_state::xavix_lowbus_map(address_map &map)
|
||||
map(0x6000, 0x67ff).ram().share("fragment_sprite");
|
||||
|
||||
// Palette RAM
|
||||
map(0x6800, 0x68ff).ram().share("palram_sh");
|
||||
map(0x6900, 0x69ff).ram().share("palram_l");
|
||||
map(0x6800, 0x68ff).ram().w(FUNC(xavix_state::palram_sh_w)).share("palram_sh");
|
||||
map(0x6900, 0x69ff).ram().w(FUNC(xavix_state::palram_l_w)).share("palram_l");
|
||||
|
||||
// Segment RAM
|
||||
map(0x6a00, 0x6a1f).ram().share("segment_regs"); // test mode, pass flag 0x20
|
||||
@ -342,8 +305,8 @@ void xavix_state::xavix_lowbus_map(address_map &map)
|
||||
map(0x6fea, 0x6fea).rw(FUNC(xavix_state::arena_control_r), FUNC(xavix_state::arena_control_w));
|
||||
|
||||
// Colour Mixing / Enabling Registers
|
||||
map(0x6ff0, 0x6ff0).ram().share("colmix_sh"); // a single colour (for effects?) not bgpen
|
||||
map(0x6ff1, 0x6ff1).ram().share("colmix_l");
|
||||
map(0x6ff0, 0x6ff0).ram().w(FUNC(xavix_state::colmix_sh_w)).share("colmix_sh"); // effect colour?
|
||||
map(0x6ff1, 0x6ff1).ram().w(FUNC(xavix_state::colmix_l_w)).share("colmix_l");
|
||||
map(0x6ff2, 0x6ff2).ram().w(FUNC(xavix_state::colmix_6ff2_w)).share("colmix_ctrl"); // set to 07 after clearing above things in interrupt 0
|
||||
|
||||
// Display Control Register / Status Flags
|
||||
@ -421,6 +384,7 @@ void xavix_state::xavix_lowbus_map(address_map &map)
|
||||
map(0x7c00, 0x7c00).rw(FUNC(xavix_state::timer_status_r), FUNC(xavix_state::timer_control_w));
|
||||
map(0x7c01, 0x7c01).rw(FUNC(xavix_state::timer_baseval_r), FUNC(xavix_state::timer_baseval_w)); // r/w tested
|
||||
map(0x7c02, 0x7c02).rw(FUNC(xavix_state::timer_freq_r), FUNC(xavix_state::timer_freq_w));
|
||||
map(0x7c03, 0x7c03).r(FUNC(xavix_state::timer_curval_r));
|
||||
|
||||
// Barrel Shifter registers
|
||||
// map(0x7ff0, 0x7ff1)
|
||||
@ -444,8 +408,8 @@ void xavix_state::superxavix_lowbus_map(address_map &map)
|
||||
xavix_lowbus_map(map);
|
||||
|
||||
// bitmap layer palette
|
||||
map(0x6c00, 0x6cff).ram().share("bmp_palram_sh");
|
||||
map(0x6d00, 0x6dff).ram().share("bmp_palram_l");
|
||||
map(0x6c00, 0x6cff).ram().w(FUNC(xavix_state::bmp_palram_sh_w)).share("bmp_palram_sh");
|
||||
map(0x6d00, 0x6dff).ram().w(FUNC(xavix_state::bmp_palram_l_w)).share("bmp_palram_l");
|
||||
|
||||
map(0x6fb0, 0x6fc7).ram().share("bmp_base");
|
||||
}
|
||||
@ -720,6 +684,21 @@ static INPUT_PORTS_START( ttv_mx )
|
||||
INPUT_PORTS_END
|
||||
|
||||
|
||||
static INPUT_PORTS_START( rad_fb )
|
||||
PORT_INCLUDE(xavix)
|
||||
|
||||
PORT_MODIFY("IN0")
|
||||
PORT_BIT( 0x01, IP_ACTIVE_HIGH, IPT_JOYSTICK_LEFT ) PORT_PLAYER(1)
|
||||
PORT_BIT( 0x02, IP_ACTIVE_HIGH, IPT_BUTTON1 ) PORT_PLAYER(1)
|
||||
PORT_BIT( 0x04, IP_ACTIVE_HIGH, IPT_JOYSTICK_RIGHT ) PORT_PLAYER(1)
|
||||
PORT_BIT( 0x08, IP_ACTIVE_HIGH, IPT_JOYSTICK_LEFT ) PORT_PLAYER(2)
|
||||
PORT_BIT( 0x10, IP_ACTIVE_HIGH, IPT_BUTTON1 ) PORT_PLAYER(2)
|
||||
PORT_BIT( 0x20, IP_ACTIVE_HIGH, IPT_JOYSTICK_RIGHT ) PORT_PLAYER(2)
|
||||
|
||||
PORT_MODIFY("IN1")
|
||||
PORT_BIT( 0x40, IP_ACTIVE_HIGH, IPT_POWER_OFF ) PORT_NAME("Power Switch") // pressing this will turn the game off.
|
||||
INPUT_PORTS_END
|
||||
|
||||
CUSTOM_INPUT_MEMBER( xavix_state::rad_rh_in1_08_r )
|
||||
{
|
||||
// it's unclear what rad_rh wants here
|
||||
@ -819,7 +798,7 @@ MACHINE_CONFIG_START(xavix_state::xavix)
|
||||
|
||||
MCFG_DEVICE_ADD("gfxdecode", GFXDECODE, "palette", gfx_xavix)
|
||||
|
||||
MCFG_PALETTE_ADD("palette", 256 + 1)
|
||||
MCFG_PALETTE_ADD("palette", 256)
|
||||
|
||||
/* sound hardware */
|
||||
SPEAKER(config, "mono").front_center();
|
||||
@ -861,7 +840,7 @@ MACHINE_CONFIG_START(xavix_state::xavix2000)
|
||||
MCFG_XAVIX_VECTOR_CALLBACK(xavix_state, get_vectors)
|
||||
|
||||
MCFG_DEVICE_REMOVE("palette")
|
||||
MCFG_PALETTE_ADD("palette", 512+1)
|
||||
MCFG_PALETTE_ADD("palette", 512)
|
||||
|
||||
MACHINE_CONFIG_END
|
||||
|
||||
@ -893,6 +872,13 @@ MACHINE_CONFIG_START(xavix_mtrk_state::xavix_mtrkp)
|
||||
MCFG_SCREEN_REFRESH_RATE(50)
|
||||
MACHINE_CONFIG_END
|
||||
|
||||
MACHINE_CONFIG_START(xavix_madfb_state::xavix_madfb)
|
||||
xavix(config);
|
||||
|
||||
XAVIX_MADFB_BALL(config, m_ball, 0);
|
||||
m_ball->event_out_cb().set(FUNC(xavix_state::ioevent_trg01));
|
||||
|
||||
MACHINE_CONFIG_END
|
||||
|
||||
DEVICE_IMAGE_LOAD_MEMBER( xavix_ekara_state, ekara_cart )
|
||||
{
|
||||
@ -907,7 +893,6 @@ DEVICE_IMAGE_LOAD_MEMBER( xavix_ekara_state, ekara_cart )
|
||||
return image_init_result::PASS;
|
||||
}
|
||||
|
||||
|
||||
MACHINE_CONFIG_START(xavix_ekara_state::xavix_ekara)
|
||||
xavix(config);
|
||||
|
||||
@ -921,10 +906,6 @@ MACHINE_CONFIG_START(xavix_ekara_state::xavix_ekara)
|
||||
|
||||
MACHINE_CONFIG_END
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
void xavix_state::init_xavix()
|
||||
{
|
||||
m_rgnlen = memregion("bios")->bytes();
|
||||
@ -1055,7 +1036,7 @@ ROM_START( has_wamg )
|
||||
ROM_LOAD( "minigolf.bin", 0x000000, 0x400000, CRC(35cee2ad) SHA1(c7344e8ba336bc329638485ea571cd731ebf7649) )
|
||||
ROM_END
|
||||
|
||||
/* Standalone TV Games */
|
||||
/* XaviX hardware titles */
|
||||
|
||||
CONS( 2006, taitons1, 0, 0, xavix_i2c_24lc04, namcons2, xavix_state, init_xavix, "Bandai / SSD Company LTD / Taito", "Let's! TV Play Classic - Taito Nostalgia 1", MACHINE_NOT_WORKING | MACHINE_IMPERFECT_GRAPHICS | MACHINE_NO_SOUND )
|
||||
|
||||
@ -1085,9 +1066,9 @@ CONS( 2001, rad_bassp, rad_bass, 0, xavixp, rad_bassp,xavix_state, init_xavix
|
||||
CONS( 2001, rad_snow, 0, 0, xavix, rad_snow, xavix_state, init_xavix, "Radica / SSD Company LTD", "Play TV Snowboarder (Blue) (NTSC)", MACHINE_NOT_WORKING | MACHINE_IMPERFECT_GRAPHICS | MACHINE_NO_SOUND)
|
||||
CONS( 2001, rad_snowp, rad_snow, 0, xavixp, rad_snowp,xavix_state, init_xavix, "Radica / SSD Company LTD", "ConnecTV Snowboarder (Blue) (PAL)", MACHINE_NOT_WORKING | MACHINE_IMPERFECT_GRAPHICS | MACHINE_NO_SOUND)
|
||||
|
||||
CONS( 2003, rad_madf, 0, 0, xavix, xavix, xavix_state, init_xavix, "Radica / SSD Company LTD", "EA Sports Madden Football (NTSC)", MACHINE_NOT_WORKING | MACHINE_IMPERFECT_GRAPHICS | MACHINE_NO_SOUND) // no Play TV branding, USA only release?
|
||||
CONS( 2003, rad_madf, 0, 0, xavix_madfb, rad_fb, xavix_madfb_state, init_xavix, "Radica / SSD Company LTD", "EA Sports Madden Football (NTSC)", MACHINE_NOT_WORKING | MACHINE_IMPERFECT_GRAPHICS | MACHINE_NO_SOUND) // no Play TV branding, USA only release?
|
||||
|
||||
CONS( 200?, rad_fb, 0, 0, xavix, xavix, xavix_state, init_xavix, "Radica / SSD Company LTD", "Play TV Football (NTSC)", MACHINE_NOT_WORKING | MACHINE_IMPERFECT_GRAPHICS | MACHINE_NO_SOUND) // USA only release? doesn't change logo for PAL
|
||||
CONS( 200?, rad_fb, 0, 0, xavix_madfb, rad_fb, xavix_madfb_state, init_xavix, "Radica / SSD Company LTD", "Play TV Football (NTSC)", MACHINE_NOT_WORKING | MACHINE_IMPERFECT_GRAPHICS | MACHINE_NO_SOUND) // USA only release? doesn't change logo for PAL.
|
||||
|
||||
CONS( 200?, rad_rh, 0, 0, xavix, rad_rh, xavix_state, init_xavix, "Radioa / Fisher-Price / SSD Company LTD", "Play TV Rescue Heroes", MACHINE_NOT_WORKING | MACHINE_IMPERFECT_GRAPHICS | MACHINE_NO_SOUND)
|
||||
|
||||
@ -1097,6 +1078,8 @@ CONS( 200?, has_wamg, 0, 0, xavix, xavix, xavix_state, init_xavix
|
||||
|
||||
CONS( 200?, ekara, 0, 0, xavix_ekara, ekara, xavix_ekara_state, init_xavix, "Takara / Hasbro / SSD Company LTD", "e-kara (US?)", MACHINE_NOT_WORKING | MACHINE_IMPERFECT_GRAPHICS | MACHINE_NO_SOUND|MACHINE_IS_BIOS_ROOT)
|
||||
|
||||
/* SuperXaviX hardware titles */
|
||||
|
||||
/* The 'XaviXPORT' isn't a real console, more of a TV adapter, all the actual hardware (CPU including video hw, sound hw) is in the cartridges and controllers
|
||||
and can vary between games, see notes at top of driver.
|
||||
*/
|
||||
@ -1106,9 +1089,6 @@ ROM_START( xavtenni )
|
||||
ROM_LOAD( "xavixtennis.bin", 0x000000, 0x800000, CRC(23a1d918) SHA1(2241c59e8ea8328013e55952ebf9060ea0a4675b) )
|
||||
ROM_END
|
||||
|
||||
/* Tiger games have extended opcodes too */
|
||||
|
||||
|
||||
ROM_START( ttv_sw )
|
||||
ROM_REGION( 0x800000, "bios", ROMREGION_ERASE00 )
|
||||
ROM_LOAD( "jedi.bin", 0x000000, 0x800000, CRC(51cae5fd) SHA1(1ed8d556f31b4182259ca8c766d60c824d8d9744) )
|
||||
|
@ -15,6 +15,7 @@
|
||||
#include "bus/generic/carts.h"
|
||||
|
||||
#include "machine/xavix_mtrk_wheel.h"
|
||||
#include "machine/xavix_madfb_ball.h"
|
||||
|
||||
class xavix_state : public driver_device
|
||||
{
|
||||
@ -86,12 +87,8 @@ void superxavix_lowbus_map(address_map &map);
|
||||
|
||||
virtual void video_start() override;
|
||||
|
||||
DECLARE_READ8_MEMBER(main_r);
|
||||
DECLARE_WRITE8_MEMBER(main_w);
|
||||
DECLARE_READ8_MEMBER(main2_r);
|
||||
DECLARE_WRITE8_MEMBER(main2_w);
|
||||
DECLARE_READ8_MEMBER(main3_r);
|
||||
DECLARE_WRITE8_MEMBER(main3_w);
|
||||
DECLARE_READ8_MEMBER(opcodes_000000_r);
|
||||
DECLARE_READ8_MEMBER(opcodes_800000_r);
|
||||
|
||||
DECLARE_READ8_MEMBER(extbus_r) { return m_rgn[(offset) & (m_rgnlen - 1)]; }
|
||||
DECLARE_WRITE8_MEMBER(extbus_w) { logerror("write to external bus %06x %02x\n", offset, data); }
|
||||
@ -201,11 +198,19 @@ void superxavix_lowbus_map(address_map &map);
|
||||
DECLARE_WRITE8_MEMBER(timer_baseval_w);
|
||||
DECLARE_READ8_MEMBER(timer_freq_r);
|
||||
DECLARE_WRITE8_MEMBER(timer_freq_w);
|
||||
DECLARE_READ8_MEMBER(timer_curval_r);
|
||||
uint8_t m_timer_control;
|
||||
uint8_t m_timer_freq;
|
||||
TIMER_CALLBACK_MEMBER(freq_timer_done);
|
||||
emu_timer *m_freq_timer;
|
||||
|
||||
DECLARE_WRITE8_MEMBER(palram_sh_w);
|
||||
DECLARE_WRITE8_MEMBER(palram_l_w);
|
||||
DECLARE_WRITE8_MEMBER(colmix_sh_w);
|
||||
DECLARE_WRITE8_MEMBER(colmix_l_w);
|
||||
DECLARE_WRITE8_MEMBER(bmp_palram_sh_w);
|
||||
DECLARE_WRITE8_MEMBER(bmp_palram_l_w);
|
||||
|
||||
|
||||
DECLARE_WRITE8_MEMBER(tmap1_regs_w);
|
||||
DECLARE_WRITE8_MEMBER(tmap2_regs_w);
|
||||
@ -300,7 +305,7 @@ void superxavix_lowbus_map(address_map &map);
|
||||
|
||||
required_device<gfxdecode_device> m_gfxdecode;
|
||||
|
||||
void handle_palette(screen_device &screen, bitmap_ind16 &bitmap, const rectangle &cliprect, uint8_t* ramsh, uint8_t* raml, int size, int basecol);
|
||||
void update_pen(int pen, uint8_t shval, uint8_t lval);
|
||||
double hue2rgb(double p, double q, double t);
|
||||
void draw_tile_line(screen_device &screen, bitmap_ind16 &bitmap, const rectangle &cliprect, int tile, int bpp, int xpos, int ypos, int drawheight, int drawwidth, int flipx, int flipy, int pal, int zval, int line);
|
||||
void draw_tilemap(screen_device &screen, bitmap_ind16 &bitmap, const rectangle &cliprect, int which);
|
||||
@ -346,6 +351,21 @@ protected:
|
||||
required_device<xavix_mtrk_wheel_device> m_wheel;
|
||||
};
|
||||
|
||||
class xavix_madfb_state : public xavix_state
|
||||
{
|
||||
public:
|
||||
xavix_madfb_state(const machine_config &mconfig, device_type type, const char *tag)
|
||||
: xavix_state(mconfig, type, tag),
|
||||
m_ball(*this, "ball")
|
||||
{ }
|
||||
|
||||
void xavix_madfb(machine_config &config);
|
||||
|
||||
protected:
|
||||
required_device<xavix_madfb_ball_device> m_ball;
|
||||
};
|
||||
|
||||
|
||||
class xavix_ekara_state : public xavix_state
|
||||
{
|
||||
public:
|
||||
|
@ -268,7 +268,15 @@ INTERRUPT_GEN_MEMBER(xavix_state::interrupt)
|
||||
}
|
||||
|
||||
|
||||
WRITE8_MEMBER(xavix_state::colmix_sh_w)
|
||||
{
|
||||
m_colmix_sh[offset] = data;
|
||||
}
|
||||
|
||||
WRITE8_MEMBER(xavix_state::colmix_l_w)
|
||||
{
|
||||
m_colmix_l[offset] = data;
|
||||
}
|
||||
|
||||
WRITE8_MEMBER(xavix_state::colmix_6ff2_w)
|
||||
{
|
||||
@ -532,6 +540,14 @@ READ8_MEMBER(xavix_state::timer_freq_r)
|
||||
return m_timer_freq;
|
||||
}
|
||||
|
||||
READ8_MEMBER(xavix_state::timer_curval_r)
|
||||
{
|
||||
// TODO implement properly with timers etc. as rad_fb / rad_madfb rely on these values to calculate throw strength!
|
||||
LOG("%s: timer_curval_r\n", machine().describe_context());
|
||||
return machine().rand();
|
||||
}
|
||||
|
||||
|
||||
WRITE8_MEMBER(xavix_state::timer_freq_w)
|
||||
{
|
||||
// 4-bit prescale
|
||||
|
87
src/mame/machine/xavix_madfb_ball.cpp
Normal file
87
src/mame/machine/xavix_madfb_ball.cpp
Normal file
@ -0,0 +1,87 @@
|
||||
// license:BSD-3-Clause
|
||||
// copyright-holders:David Haywood
|
||||
|
||||
/*
|
||||
Motion Football simulation for XaviX based games
|
||||
EA Sports Madden Football
|
||||
Play TV Football
|
||||
|
||||
seems to register a pulse when you move it, and another when it stops moving
|
||||
game uses current timer register (without interrupt) to measure time between pulses
|
||||
to get 'throw' value
|
||||
|
||||
need to verify with code and work out how best to handle this
|
||||
*/
|
||||
|
||||
#include "emu.h"
|
||||
#include "machine/xavix_madfb_ball.h"
|
||||
|
||||
DEFINE_DEVICE_TYPE(XAVIX_MADFB_BALL, xavix_madfb_ball_device, "xavix_madfb_ball", "XaviX / Radica Football Ball")
|
||||
|
||||
xavix_madfb_ball_device::xavix_madfb_ball_device(const machine_config &mconfig, const char *tag, device_t *owner, uint32_t clock)
|
||||
: device_t(mconfig, XAVIX_MADFB_BALL, tag, owner, clock),
|
||||
m_event_out_cb(*this),
|
||||
m_in(*this, "BALL")
|
||||
{
|
||||
}
|
||||
|
||||
TIMER_CALLBACK_MEMBER(xavix_madfb_ball_device::event_timer)
|
||||
{
|
||||
m_event_out_cb(1);
|
||||
m_is_running = 0;
|
||||
check_ball();
|
||||
}
|
||||
|
||||
void xavix_madfb_ball_device::check_ball()
|
||||
{
|
||||
uint8_t ballval = m_in->read();
|
||||
|
||||
if (ballval == 0x00)
|
||||
{
|
||||
m_event_timer->adjust(attotime::never, 0);
|
||||
m_is_running = 0;
|
||||
}
|
||||
else
|
||||
{
|
||||
// TODO: set frequency based on value
|
||||
m_event_timer->adjust(attotime::from_hz(800), 0);
|
||||
m_is_running = 1;
|
||||
}
|
||||
}
|
||||
|
||||
INPUT_CHANGED_MEMBER( xavix_madfb_ball_device::changed )
|
||||
{
|
||||
// this could happen while the timer is still active, which could end up cancelling it in flight
|
||||
// should probably calculate adjustment based on current expiry?
|
||||
// instead I'm just making sure the timer isn't running right now
|
||||
//printf("ball changed to %02x\n", m_in->read());
|
||||
if (!m_is_running)
|
||||
{
|
||||
check_ball();
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
static INPUT_PORTS_START( ball )
|
||||
PORT_START("BALL")
|
||||
PORT_BIT( 0xff, 0x00, IPT_PEDAL ) PORT_SENSITIVITY(100) PORT_KEYDELTA(20) PORT_CHANGED_MEMBER(DEVICE_SELF, xavix_madfb_ball_device, changed, nullptr)
|
||||
INPUT_PORTS_END
|
||||
|
||||
|
||||
ioport_constructor xavix_madfb_ball_device::device_input_ports() const
|
||||
{
|
||||
return INPUT_PORTS_NAME(ball);
|
||||
}
|
||||
|
||||
|
||||
void xavix_madfb_ball_device::device_start()
|
||||
{
|
||||
m_event_out_cb.resolve_safe();
|
||||
m_event_timer = machine().scheduler().timer_alloc(timer_expired_delegate(FUNC(xavix_madfb_ball_device::event_timer), this));
|
||||
}
|
||||
|
||||
void xavix_madfb_ball_device::device_reset()
|
||||
{
|
||||
m_event_timer->adjust(attotime::never, 0);
|
||||
m_is_running = 0;
|
||||
}
|
39
src/mame/machine/xavix_madfb_ball.h
Normal file
39
src/mame/machine/xavix_madfb_ball.h
Normal file
@ -0,0 +1,39 @@
|
||||
// license:BSD-3-Clause
|
||||
// copyright-holders:David Haywood
|
||||
|
||||
#ifndef MAME_MACHINE_XAVIX_MADFB_BALL_H
|
||||
#define MAME_MACHINE_XAVIX_MADFB_BALL_H
|
||||
|
||||
#pragma once
|
||||
|
||||
#include "machine/timer.h"
|
||||
|
||||
DECLARE_DEVICE_TYPE(XAVIX_MADFB_BALL, xavix_madfb_ball_device)
|
||||
|
||||
|
||||
class xavix_madfb_ball_device : public device_t
|
||||
{
|
||||
public:
|
||||
// construction/destruction
|
||||
xavix_madfb_ball_device(const machine_config &mconfig, const char *tag, device_t *owner, uint32_t clock);
|
||||
|
||||
auto event_out_cb() { return m_event_out_cb.bind(); }
|
||||
|
||||
int read_direction();
|
||||
DECLARE_INPUT_CHANGED_MEMBER( changed );
|
||||
|
||||
protected:
|
||||
virtual void device_start() override;
|
||||
virtual void device_reset() override;
|
||||
virtual ioport_constructor device_input_ports() const override;
|
||||
|
||||
private:
|
||||
devcb_write_line m_event_out_cb;
|
||||
required_ioport m_in;
|
||||
TIMER_CALLBACK_MEMBER(event_timer);
|
||||
emu_timer *m_event_timer;
|
||||
void check_ball();
|
||||
int m_is_running;
|
||||
};
|
||||
|
||||
#endif // MAME_MACHINE_XAVIX_MADFB_BALL_H
|
@ -57,6 +57,31 @@ void xavix_state::video_start()
|
||||
}
|
||||
|
||||
|
||||
WRITE8_MEMBER(xavix_state::palram_sh_w)
|
||||
{
|
||||
m_palram_sh[offset] = data;
|
||||
update_pen(offset, m_palram_sh[offset], m_palram_l[offset]);
|
||||
}
|
||||
|
||||
WRITE8_MEMBER(xavix_state::palram_l_w)
|
||||
{
|
||||
m_palram_l[offset] = data;
|
||||
update_pen(offset, m_palram_sh[offset], m_palram_l[offset]);
|
||||
}
|
||||
|
||||
WRITE8_MEMBER(xavix_state::bmp_palram_sh_w)
|
||||
{
|
||||
m_bmp_palram_sh[offset] = data;
|
||||
update_pen(offset+256, m_bmp_palram_sh[offset], m_bmp_palram_l[offset]);
|
||||
}
|
||||
|
||||
WRITE8_MEMBER(xavix_state::bmp_palram_l_w)
|
||||
{
|
||||
m_bmp_palram_l[offset] = data;
|
||||
update_pen(offset+256, m_bmp_palram_sh[offset], m_bmp_palram_l[offset]);
|
||||
}
|
||||
|
||||
|
||||
double xavix_state::hue2rgb(double p, double q, double t)
|
||||
{
|
||||
if (t < 0) t += 1;
|
||||
@ -67,63 +92,57 @@ double xavix_state::hue2rgb(double p, double q, double t)
|
||||
return p;
|
||||
}
|
||||
|
||||
void xavix_state::handle_palette(screen_device &screen, bitmap_ind16 &bitmap, const rectangle &cliprect, uint8_t* ramsh, uint8_t* raml, int size, int basecol)
|
||||
void xavix_state::update_pen(int pen, uint8_t shval, uint8_t lval)
|
||||
{
|
||||
// not verified
|
||||
int offs = 0;
|
||||
for (int index = 0; index < size; index++)
|
||||
{
|
||||
uint16_t dat;
|
||||
dat = ramsh[offs];
|
||||
dat |= raml[offs] << 8;
|
||||
uint16_t dat;
|
||||
dat = shval;
|
||||
dat |= lval << 8;
|
||||
|
||||
offs++;
|
||||
int l_raw = (dat & 0x1f00) >> 8;
|
||||
int s_raw = (dat & 0x00e0) >> 5;
|
||||
int h_raw = (dat & 0x001f) >> 0;
|
||||
|
||||
int l_raw = (dat & 0x1f00) >> 8;
|
||||
int s_raw = (dat & 0x00e0) >> 5;
|
||||
int h_raw = (dat & 0x001f) >> 0;
|
||||
//if (h_raw > 24)
|
||||
// LOG("hraw >24 (%02x)\n", h_raw);
|
||||
|
||||
//if (h_raw > 24)
|
||||
// LOG("hraw >24 (%02x)\n", h_raw);
|
||||
//if (l_raw > 24)
|
||||
// LOG("lraw >24 (%02x)\n", l_raw);
|
||||
|
||||
//if (l_raw > 24)
|
||||
// LOG("lraw >24 (%02x)\n", l_raw);
|
||||
//if (s_raw > 7)
|
||||
// LOG("s_raw >5 (%02x)\n", s_raw);
|
||||
|
||||
//if (s_raw > 7)
|
||||
// LOG("s_raw >5 (%02x)\n", s_raw);
|
||||
double l = (double)l_raw / 24.0f; // ekara and drgqst go up to 23 during fades, expect that to be brightest
|
||||
l = l * (std::atan(1)*2); // does not appear to be a linear curve
|
||||
l = std::sin(l);
|
||||
|
||||
double l = (double)l_raw / 24.0f; // ekara and drgqst go up to 23 during fades, expect that to be brightest
|
||||
l = l * (std::atan(1)*2); // does not appear to be a linear curve
|
||||
l = std::sin(l);
|
||||
double s = (double)s_raw / 7.0f;
|
||||
s = s * (std::atan(1)*2); // does not appear to be a linear curve
|
||||
s = std::sin(s);
|
||||
|
||||
double s = (double)s_raw / 7.0f;
|
||||
s = s * (std::atan(1)*2); // does not appear to be a linear curve
|
||||
s = std::sin(s);
|
||||
double h = (double)h_raw / 24.0f; // hue values 24-31 render as transparent
|
||||
|
||||
double h = (double)h_raw / 24.0f; // hue values 24-31 render as transparent
|
||||
|
||||
double r, g, b;
|
||||
|
||||
if (s == 0) {
|
||||
r = g = b = l; // greyscale
|
||||
}
|
||||
else {
|
||||
double q = l < 0.5f ? l * (1 + s) : l + s - l * s;
|
||||
double p = 2 * l - q;
|
||||
r = hue2rgb(p, q, h + 1 / 3.0f);
|
||||
g = hue2rgb(p, q, h);
|
||||
b = hue2rgb(p, q, h - 1 / 3.0f);
|
||||
}
|
||||
|
||||
int r_real = r * 255.0f;
|
||||
int g_real = g * 255.0f;
|
||||
int b_real = b * 255.0f;
|
||||
|
||||
m_palette->set_pen_color(basecol+index, r_real, g_real, b_real);
|
||||
double r, g, b;
|
||||
|
||||
if (s == 0) {
|
||||
r = g = b = l; // greyscale
|
||||
}
|
||||
else {
|
||||
double q = l < 0.5f ? l * (1 + s) : l + s - l * s;
|
||||
double p = 2 * l - q;
|
||||
r = hue2rgb(p, q, h + 1 / 3.0f);
|
||||
g = hue2rgb(p, q, h);
|
||||
b = hue2rgb(p, q, h - 1 / 3.0f);
|
||||
}
|
||||
|
||||
int r_real = r * 255.0f;
|
||||
int g_real = g * 255.0f;
|
||||
int b_real = b * 255.0f;
|
||||
|
||||
m_palette->set_pen_color(pen, r_real, g_real, b_real);
|
||||
}
|
||||
|
||||
|
||||
|
||||
void xavix_state::draw_tilemap(screen_device &screen, bitmap_ind16 &bitmap, const rectangle &cliprect, int which)
|
||||
{
|
||||
for (int y = cliprect.min_y; y <= cliprect.max_y; y++)
|
||||
@ -671,18 +690,6 @@ void xavix_state::draw_tile_line(screen_device &screen, bitmap_ind16 &bitmap, co
|
||||
|
||||
uint32_t xavix_state::screen_update(screen_device &screen, bitmap_ind16 &bitmap, const rectangle &cliprect)
|
||||
{
|
||||
handle_palette(screen, bitmap, cliprect, m_palram_sh, m_palram_l, 256, 0);
|
||||
|
||||
if (m_bmp_palram_sh)
|
||||
{
|
||||
handle_palette(screen, bitmap, cliprect, m_bmp_palram_sh, m_bmp_palram_l, 256, 256);
|
||||
handle_palette(screen, bitmap, cliprect, m_colmix_sh, m_colmix_l, 1, 512);
|
||||
}
|
||||
else
|
||||
{
|
||||
handle_palette(screen, bitmap, cliprect, m_colmix_sh, m_colmix_l, 1, 256);
|
||||
}
|
||||
|
||||
// not sure what you end up with if you fall through all layers as transparent, so far no issues noticed
|
||||
bitmap.fill(m_palette->black_pen(), cliprect);
|
||||
m_zbuffer.fill(0, cliprect);
|
||||
|
Loading…
Reference in New Issue
Block a user