redclash: add player shoot sample

This commit is contained in:
hap 2022-09-03 15:10:11 +02:00
parent 86d08c090d
commit 499fbd8358
3 changed files with 69 additions and 32 deletions

View file

@ -2,23 +2,21 @@
// copyright-holders:Aaron Giles // copyright-holders:Aaron Giles
/*************************************************************************** /***************************************************************************
samples.c
Sound device for sample playback. Sound device for sample playback.
**************************************************************************** ****************************************************************************
Playback of pre-recorded samples. Used for high-level simulation of Playback of pre-recorded samples. Used for high-level simulation of discrete
discrete sound circuits where proper low-level simulation isn't sound circuits where proper low-level simulation isn't available. Also used
available. Also used for tape loops and similar. for tape loops and similar.
Current limitations TODO:
- Only supports single channel samples! - Only supports single channel samples!
- When mame.ini samplerate is close to the loaded sample(s) samplerate,
Considerations (eg. 48000, with 44100Hz samples), things can sound quite bad. This is
- Maybe this should be part of the presentation layer more an issue in sound.cpp resampler, not this device.
(artwork etc.) with samples specified in .lay files instead of - Maybe this should be part of the presentation layer (artwork etc.)
in drivers? with samples specified in .lay files instead of in drivers?
***************************************************************************/ ***************************************************************************/

View file

@ -2,8 +2,6 @@
// copyright-holders:Aaron Giles // copyright-holders:Aaron Giles
/*************************************************************************** /***************************************************************************
samples.h
Sound device for sample playback. Sound device for sample playback.
***************************************************************************/ ***************************************************************************/
@ -169,7 +167,7 @@ public:
private: private:
// internal state // internal state
samples_device &m_samples; samples_device &m_samples;
int m_current; int m_current;
}; };
#endif // MAME_SOUND_SAMPLES_H #endif // MAME_SOUND_SAMPLES_H

View file

@ -17,9 +17,11 @@ TODO:
scrolling at the same speed as the stars, it's used in canyon parts and during the scrolling at the same speed as the stars, it's used in canyon parts and during the
big ufo explosion big ufo explosion
- redclash canyon level, a gap sometimes appears on the right side, maybe BTANB - redclash canyon level, a gap sometimes appears on the right side, maybe BTANB
- replace zerohour samples with netlist audio (schematics available) - replace samples with netlist audio (schematics available for zerohour)
- zerohour should play a beep when an orange asteroid is shot, missing sample? - zerohour should play a beep when an orange asteroid is shot (not sure if it's
- add redclash samples or netlist audio (eg. player shot sound, explosions) worth simulating this, netlist would auto solve this problem)
- does redclash have more triggered sounds? according to a pcb video, it only
has the player shot sound, no explosions (not counting the beeper)
- redclash beeper frequency range should be higher, but it can't be solved with a - redclash beeper frequency range should be higher, but it can't be solved with a
simple multiply calculation. Besides, anything more than right now and ears will simple multiply calculation. Besides, anything more than right now and ears will
be destroyed, so maybe the sound is softer(filtered) be destroyed, so maybe the sound is softer(filtered)
@ -101,10 +103,11 @@ protected:
required_device<palette_device> m_palette; required_device<palette_device> m_palette;
required_device<gfxdecode_device> m_gfxdecode; required_device<gfxdecode_device> m_gfxdecode;
required_device<zerohour_stars_device> m_stars; required_device<zerohour_stars_device> m_stars;
optional_device<samples_device> m_samples; required_device<samples_device> m_samples;
tilemap_t *m_fg_tilemap = nullptr; tilemap_t *m_fg_tilemap = nullptr;
int m_sound_on = 0; int m_sound_on = 0;
int m_sample_asteroid = 0;
int m_gfxbank = 0; // redclash only int m_gfxbank = 0; // redclash only
}; };
@ -129,6 +132,7 @@ private:
DECLARE_WRITE_LINE_MEMBER(gfxbank_w); DECLARE_WRITE_LINE_MEMBER(gfxbank_w);
void background_w(u8 data); void background_w(u8 data);
void beeper_w(u8 data); void beeper_w(u8 data);
DECLARE_WRITE_LINE_MEMBER(redclash_sample_w);
void redclash_map(address_map &map); void redclash_map(address_map &map);
@ -155,6 +159,7 @@ void zerohour_state::init_zerohour()
void zerohour_state::machine_start() void zerohour_state::machine_start()
{ {
save_item(NAME(m_sound_on)); save_item(NAME(m_sound_on));
save_item(NAME(m_sample_asteroid));
} }
void redclash_state::machine_start() void redclash_state::machine_start()
@ -438,16 +443,23 @@ u32 redclash_state::screen_update(screen_device &screen, bitmap_ind16 &bitmap, c
static const char *const zerohour_sample_names[] = static const char *const zerohour_sample_names[] =
{ {
"*zerohour", "*zerohour",
"zh0", "shoot",
"zh1", "asteroid_hit_1",
"zh2", "asteroid_hit_2",
"zh3", "enemy_descend",
"zh4", "shield_hit",
"zh5", "player_dies",
"zh6", "enemy_fire",
"zh7", "bonus_warn",
"zh8", "thrust",
"zh9", "coin",
nullptr
};
static const char *const redclash_sample_names[] =
{
"*redclash",
"shoot",
nullptr nullptr
}; };
@ -467,14 +479,37 @@ WRITE_LINE_MEMBER(redclash_state::sound_enable_w)
template <unsigned N> WRITE_LINE_MEMBER(zerohour_state::sample_w) template <unsigned N> WRITE_LINE_MEMBER(zerohour_state::sample_w)
{ {
int sample = N;
// asteroid hit sample alternates on each trigger
if (state && N == 1)
{
sample += m_sample_asteroid & 1;
m_sample_asteroid ^= 1;
}
// trigger 2 appears to be a modifier for asteroid hit, white noise is masked with pulse wave
if (N == 2)
{
// TODO
return;
}
if (m_sound_on && state) if (m_sound_on && state)
m_samples->start(N, N); m_samples->start(N, sample);
// thrust sound is level-triggered // thrust sound is level-triggered
else if (N == 8) else if (N == 8)
m_samples->stop(N); m_samples->stop(N);
} }
WRITE_LINE_MEMBER(redclash_state::redclash_sample_w)
{
// only one sample
if (m_sound_on && state)
m_samples->start(0, 0);
}
void redclash_state::beeper_w(u8 data) void redclash_state::beeper_w(u8 data)
{ {
// beeper frequency (0xff is off), preliminary // beeper frequency (0xff is off), preliminary
@ -820,14 +855,20 @@ void redclash_state::redclash(machine_config &config)
m_stars->has_va_bit(false); m_stars->has_va_bit(false);
// sound hardware // sound hardware
m_outlatch[0]->q_out_cb<0>().set(FUNC(redclash_state::redclash_sample_w));
m_outlatch[1]->q_out_cb<2>().set(FUNC(redclash_state::sound_enable_w)); m_outlatch[1]->q_out_cb<2>().set(FUNC(redclash_state::sound_enable_w));
SPEAKER(config, "mono").front_center(); SPEAKER(config, "mono").front_center();
SPEAKER_SOUND(config, m_beep).add_route(ALL_OUTPUTS, "mono", 0.25); SPEAKER_SOUND(config, m_beep).add_route(ALL_OUTPUTS, "mono", 0.2);
CLOCK(config, m_beep_clock, 0); CLOCK(config, m_beep_clock, 0);
m_beep_clock->signal_handler().set(m_beep, FUNC(speaker_sound_device::level_w)); m_beep_clock->signal_handler().set(m_beep, FUNC(speaker_sound_device::level_w));
m_beep_clock->set_duty_cycle(0.25); m_beep_clock->set_duty_cycle(0.2);
SAMPLES(config, m_samples);
m_samples->set_channels(1);
m_samples->set_samples_names(redclash_sample_names);
m_samples->add_route(ALL_OUTPUTS, "mono", 0.5);
} }