mirror of
https://github.com/holub/mame
synced 2025-04-24 01:11:11 +03:00
Added support for autofire under cheat menu and available only if cheats
activated.
This commit is contained in:
parent
e49253b0e0
commit
00aec89192
@ -730,6 +730,7 @@ void construct_core_types_UI(simple_list<input_type_entry> &typelist)
|
||||
INPUT_PORT_DIGITAL_TYPE( 0, UI, UI_TIMECODE, "Write current timecode", input_seq(KEYCODE_F12, input_seq::not_code, KEYCODE_LSHIFT) )
|
||||
INPUT_PORT_DIGITAL_TYPE( 0, UI, UI_RECORD_MOVIE, "Record Movie", input_seq(KEYCODE_F12, KEYCODE_LSHIFT) )
|
||||
INPUT_PORT_DIGITAL_TYPE( 0, UI, UI_TOGGLE_CHEAT, "Toggle Cheat", input_seq(KEYCODE_F6) )
|
||||
INPUT_PORT_DIGITAL_TYPE( 0, UI, UI_TOGGLE_AUTOFIRE, "Toggle Autofire", input_seq() )
|
||||
INPUT_PORT_DIGITAL_TYPE( 0, UI, UI_UP, "UI Up", input_seq(KEYCODE_UP, input_seq::or_code, JOYCODE_Y_UP_SWITCH_INDEXED(0)) )
|
||||
INPUT_PORT_DIGITAL_TYPE( 0, UI, UI_DOWN, "UI Down", input_seq(KEYCODE_DOWN, input_seq::or_code, JOYCODE_Y_DOWN_SWITCH_INDEXED(0)) )
|
||||
INPUT_PORT_DIGITAL_TYPE( 0, UI, UI_LEFT, "UI Left", input_seq(KEYCODE_LEFT, input_seq::or_code, JOYCODE_X_LEFT_SWITCH_INDEXED(0)) )
|
||||
|
@ -1699,6 +1699,7 @@ void ioport_field::get_user_settings(user_settings &settings)
|
||||
else
|
||||
{
|
||||
settings.toggle = m_live->toggle;
|
||||
settings.autofire = m_live->autofire;
|
||||
}
|
||||
}
|
||||
|
||||
@ -1737,6 +1738,7 @@ void ioport_field::set_user_settings(const user_settings &settings)
|
||||
else
|
||||
{
|
||||
m_live->toggle = settings.toggle;
|
||||
m_live->autofire = settings.autofire;
|
||||
}
|
||||
}
|
||||
|
||||
@ -1904,6 +1906,19 @@ void ioport_field::frame_update(ioport_value &result, bool mouse_down)
|
||||
|
||||
// if the state changed, look for switch down/switch up
|
||||
bool curstate = mouse_down || machine().input().seq_pressed(seq()) || m_digital_value;
|
||||
if (m_live->autofire && !machine().ioport().get_autofire_toggle())
|
||||
{
|
||||
if (curstate)
|
||||
{
|
||||
if (m_live->autopressed > machine().ioport().get_autofire_delay())
|
||||
m_live->autopressed = 0;
|
||||
else if (m_live->autopressed > machine().ioport().get_autofire_delay() / 2)
|
||||
curstate = false;
|
||||
m_live->autopressed++;
|
||||
}
|
||||
else
|
||||
m_live->autopressed = 0;
|
||||
}
|
||||
bool changed = false;
|
||||
if (curstate != m_live->last)
|
||||
{
|
||||
@ -2156,7 +2171,9 @@ ioport_field_live::ioport_field_live(ioport_field &field, analog_field *analog)
|
||||
impulse(0),
|
||||
last(0),
|
||||
toggle(field.toggle()),
|
||||
joydir(digital_joystick::JOYDIR_COUNT)
|
||||
joydir(digital_joystick::JOYDIR_COUNT),
|
||||
autofire(false),
|
||||
autopressed(0)
|
||||
{
|
||||
// fill in the basic values
|
||||
for (input_seq_type seqtype = SEQ_TYPE_STANDARD; seqtype < SEQ_TYPE_TOTAL; ++seqtype)
|
||||
@ -2460,7 +2477,9 @@ ioport_manager::ioport_manager(running_machine &machine)
|
||||
m_has_configs(false),
|
||||
m_has_analog(false),
|
||||
m_has_dips(false),
|
||||
m_has_bioses(false)
|
||||
m_has_bioses(false),
|
||||
m_autofire_toggle(false),
|
||||
m_autofire_delay(3) // 1 seems too fast for a bunch of games
|
||||
{
|
||||
memset(m_type_to_entry, 0, sizeof(m_type_to_entry));
|
||||
}
|
||||
|
@ -382,6 +382,7 @@ enum ioport_type
|
||||
IPT_UI_EXPORT,
|
||||
IPT_UI_AUDIT_FAST,
|
||||
IPT_UI_AUDIT_ALL,
|
||||
IPT_UI_TOGGLE_AUTOFIRE,
|
||||
|
||||
// additional OSD-specified UI port types (up to 16)
|
||||
IPT_OSD_1,
|
||||
@ -1095,6 +1096,7 @@ public:
|
||||
struct user_settings
|
||||
{
|
||||
ioport_value value; // for DIP switches
|
||||
bool autofire; // for autofire settings
|
||||
input_seq seq[SEQ_TYPE_TOTAL]; // sequences of all types
|
||||
INT32 sensitivity; // for analog controls
|
||||
INT32 delta; // for analog controls
|
||||
@ -1171,6 +1173,8 @@ struct ioport_field_live
|
||||
bool last; // were we pressed last time?
|
||||
bool toggle; // current toggle setting
|
||||
digital_joystick::direction_t joydir; // digital joystick direction index
|
||||
bool autofire; // autofire
|
||||
int autopressed; // autofire status
|
||||
std::string name; // overridden name
|
||||
};
|
||||
|
||||
@ -1413,6 +1417,12 @@ public:
|
||||
ioport_type token_to_input_type(const char *string, int &player) const;
|
||||
std::string input_type_to_token(ioport_type type, int player);
|
||||
|
||||
// autofire
|
||||
bool get_autofire_toggle() { return m_autofire_toggle; }
|
||||
void set_autofire_toggle(bool toggle) { m_autofire_toggle = toggle; }
|
||||
int get_autofire_delay() { return m_autofire_delay; }
|
||||
void set_autofire_delay(int delay) { m_autofire_delay = delay; }
|
||||
|
||||
private:
|
||||
// internal helpers
|
||||
void init_port_types();
|
||||
@ -1484,6 +1494,10 @@ private:
|
||||
bool m_has_analog;
|
||||
bool m_has_dips;
|
||||
bool m_has_bioses;
|
||||
|
||||
// autofire
|
||||
bool m_autofire_toggle; // autofire toggle
|
||||
int m_autofire_delay; // autofire delay
|
||||
};
|
||||
|
||||
|
||||
|
@ -24,6 +24,7 @@ void ui_menu_cheat::handle()
|
||||
/* process the menu */
|
||||
const ui_menu_event *menu_event = process(UI_MENU_PROCESS_LR_REPEAT);
|
||||
|
||||
|
||||
/* handle events */
|
||||
if (menu_event != nullptr && menu_event->itemref != nullptr)
|
||||
{
|
||||
@ -33,7 +34,7 @@ void ui_menu_cheat::handle()
|
||||
machine().popmessage(nullptr);
|
||||
|
||||
/* handle reset all + reset all cheats for reload all option */
|
||||
if ((FPTR)menu_event->itemref < 3 && menu_event->iptkey == IPT_UI_SELECT)
|
||||
if (menu_event->itemref < ITEMREF_CHEATS_FIRST_ITEM && menu_event->iptkey == IPT_UI_SELECT)
|
||||
{
|
||||
for (cheat_entry *curcheat = machine().cheat().first(); curcheat != nullptr; curcheat = curcheat->next())
|
||||
if (curcheat->select_default_state())
|
||||
@ -42,7 +43,7 @@ void ui_menu_cheat::handle()
|
||||
|
||||
|
||||
/* handle individual cheats */
|
||||
else if ((FPTR)menu_event->itemref > 2)
|
||||
else if (menu_event->itemref > ITEMREF_CHEATS_FIRST_ITEM)
|
||||
{
|
||||
cheat_entry *curcheat = reinterpret_cast<cheat_entry *>(menu_event->itemref);
|
||||
const char *string;
|
||||
@ -80,7 +81,7 @@ void ui_menu_cheat::handle()
|
||||
}
|
||||
|
||||
/* handle reload all */
|
||||
if ((FPTR)menu_event->itemref == 2 && menu_event->iptkey == IPT_UI_SELECT)
|
||||
if (menu_event->itemref == ITEMREF_CHEATS_RELOAD_ALL && menu_event->iptkey == IPT_UI_SELECT)
|
||||
{
|
||||
/* re-init cheat engine and thus reload cheats/cheats have already been turned off by here */
|
||||
machine().cheat().reload();
|
||||
@ -90,6 +91,12 @@ void ui_menu_cheat::handle()
|
||||
machine().popmessage("All cheats reloaded");
|
||||
}
|
||||
|
||||
/* handle autofire menu */
|
||||
if (menu_event->itemref == ITEMREF_CHEATS_AUTOFIRE_SETTINGS && menu_event->iptkey == IPT_UI_SELECT)
|
||||
{
|
||||
ui_menu::stack_push(global_alloc_clear<ui_menu_autofire>(machine(), container));
|
||||
}
|
||||
|
||||
/* if things changed, update */
|
||||
if (changed)
|
||||
reset(UI_MENU_RESET_REMEMBER_REF);
|
||||
@ -110,23 +117,210 @@ void ui_menu_cheat::populate()
|
||||
/* iterate over cheats */
|
||||
std::string text;
|
||||
std::string subtext;
|
||||
for (cheat_entry *curcheat = machine().cheat().first(); curcheat != nullptr; curcheat = curcheat->next())
|
||||
{
|
||||
UINT32 flags;
|
||||
curcheat->menu_text(text, subtext, flags);
|
||||
item_append(text.c_str(), subtext.c_str(), flags, curcheat);
|
||||
}
|
||||
|
||||
// add the autofire menu
|
||||
item_append("Autofire Settings", nullptr, 0, (void *)ITEMREF_CHEATS_AUTOFIRE_SETTINGS);
|
||||
|
||||
/* add a separator */
|
||||
item_append(MENU_SEPARATOR_ITEM, nullptr, 0, nullptr);
|
||||
|
||||
/* add a reset all option */
|
||||
item_append("Reset All", nullptr, 0, (void *)1);
|
||||
// add other cheats
|
||||
if (machine().cheat().first() != nullptr) {
|
||||
for (cheat_entry *curcheat = machine().cheat().first(); curcheat != nullptr; curcheat = curcheat->next())
|
||||
{
|
||||
UINT32 flags;
|
||||
curcheat->menu_text(text, subtext, flags);
|
||||
item_append(text.c_str(), subtext.c_str(), flags, curcheat);
|
||||
}
|
||||
|
||||
/* add a reload all cheats option */
|
||||
item_append("Reload All", nullptr, 0, (void *)2);
|
||||
/* add a separator */
|
||||
item_append(MENU_SEPARATOR_ITEM, nullptr, 0, nullptr);
|
||||
|
||||
/* add a reset all option */
|
||||
item_append("Reset All", nullptr, 0, (void *)ITEMREF_CHEATS_RESET_ALL);
|
||||
|
||||
/* add a reload all cheats option */
|
||||
item_append("Reload All", nullptr, 0, (void *)ITEMREF_CHEATS_RELOAD_ALL);
|
||||
}
|
||||
}
|
||||
|
||||
ui_menu_cheat::~ui_menu_cheat()
|
||||
{
|
||||
}
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
/*-------------------------------------------------
|
||||
menu_autofire - handle the autofire settings
|
||||
menu
|
||||
-------------------------------------------------*/
|
||||
|
||||
ui_menu_autofire::ui_menu_autofire(running_machine &machine, render_container *container) : ui_menu(machine, container)
|
||||
{
|
||||
screen_device_iterator iter(machine.root_device());
|
||||
const screen_device *screen = iter.first();
|
||||
|
||||
if (screen == nullptr)
|
||||
{
|
||||
refresh = 60.0;
|
||||
}
|
||||
else
|
||||
{
|
||||
refresh = ATTOSECONDS_TO_HZ(screen->refresh_attoseconds());
|
||||
}
|
||||
}
|
||||
|
||||
ui_menu_autofire::~ui_menu_autofire()
|
||||
{
|
||||
}
|
||||
|
||||
void ui_menu_autofire::handle()
|
||||
{
|
||||
ioport_field *field;
|
||||
bool changed = false;
|
||||
|
||||
/* process the menu */
|
||||
const ui_menu_event *menu_event = process(0);
|
||||
|
||||
/* handle events */
|
||||
if (menu_event != nullptr && menu_event->itemref != nullptr)
|
||||
{
|
||||
// menu item is changed using left/right keys only
|
||||
if (menu_event->iptkey == IPT_UI_LEFT || menu_event->iptkey == IPT_UI_RIGHT)
|
||||
{
|
||||
if (menu_event->itemref == ITEMREF_AUTOFIRE_STATUS)
|
||||
{
|
||||
// toggle autofire status
|
||||
bool autofire_toggle = machine().ioport().get_autofire_toggle(); // (menu_event->iptkey == IPT_UI_LEFT);
|
||||
machine().ioport().set_autofire_toggle(!autofire_toggle);
|
||||
changed = true;
|
||||
}
|
||||
else if (menu_event->itemref == ITEMREF_AUTOFIRE_DELAY)
|
||||
{
|
||||
// change autofire frequency
|
||||
int autofire_delay = machine().ioport().get_autofire_delay();
|
||||
if (menu_event->iptkey == IPT_UI_LEFT)
|
||||
{
|
||||
autofire_delay--;
|
||||
if (autofire_delay < 1)
|
||||
autofire_delay = 1;
|
||||
}
|
||||
else
|
||||
{
|
||||
autofire_delay++;
|
||||
if (autofire_delay > 30)
|
||||
autofire_delay = 30;
|
||||
}
|
||||
machine().ioport().set_autofire_delay(autofire_delay);
|
||||
changed = true;
|
||||
}
|
||||
else
|
||||
{
|
||||
// enable autofire on specific button
|
||||
field = (ioport_field *)menu_event->itemref;
|
||||
ioport_field::user_settings settings;
|
||||
field->get_user_settings(settings);
|
||||
settings.autofire = (menu_event->iptkey == IPT_UI_RIGHT);
|
||||
field->set_user_settings(settings);
|
||||
changed = true;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// if toggle settings changed, redraw menu to reflect new options
|
||||
if (!changed)
|
||||
{
|
||||
changed = (last_toggle != machine().ioport().get_autofire_toggle());
|
||||
}
|
||||
|
||||
/* if something changed, rebuild the menu */
|
||||
if (changed)
|
||||
{
|
||||
reset(UI_MENU_RESET_REMEMBER_REF);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
/*-------------------------------------------------
|
||||
menu_autofire_populate - populate the autofire
|
||||
menu
|
||||
-------------------------------------------------*/
|
||||
|
||||
void ui_menu_autofire::populate()
|
||||
{
|
||||
ioport_field *field;
|
||||
ioport_port *port;
|
||||
char temp_text[64];
|
||||
|
||||
/* add autofire toggle item */
|
||||
bool autofire_toggle = machine().ioport().get_autofire_toggle();
|
||||
item_append("Autofire Status", (autofire_toggle ? "Disabled" : "Enabled"),
|
||||
(autofire_toggle ? MENU_FLAG_RIGHT_ARROW : MENU_FLAG_LEFT_ARROW), (void *)ITEMREF_AUTOFIRE_STATUS);
|
||||
|
||||
/* iterate over the input ports and add autofire toggle items */
|
||||
int menu_items = 0;
|
||||
for (port = machine().ioport().first_port(); port != nullptr; port = port->next())
|
||||
{
|
||||
bool is_first_button = true;
|
||||
for (field = port->first_field(); field != nullptr; field = field->next())
|
||||
{
|
||||
if ((field->name()) && ((field->type() >= IPT_BUTTON1 && field->type() <= IPT_BUTTON16))) // IPT_BUTTON1 + 15)))
|
||||
{
|
||||
menu_items++;
|
||||
ioport_field::user_settings settings;
|
||||
field->get_user_settings(settings);
|
||||
|
||||
if (is_first_button)
|
||||
{
|
||||
/* add a separator for each player */
|
||||
item_append(MENU_SEPARATOR_ITEM, nullptr, 0, nullptr);
|
||||
is_first_button = false;
|
||||
}
|
||||
/* add an autofire item */
|
||||
if (!autofire_toggle)
|
||||
{
|
||||
// item is enabled and can be switched to values on/off
|
||||
item_append(field->name(), (settings.autofire ? "On" : "Off"),
|
||||
(settings.autofire ? MENU_FLAG_LEFT_ARROW : MENU_FLAG_RIGHT_ARROW), (void *)field);
|
||||
}
|
||||
else
|
||||
{
|
||||
// item is disabled
|
||||
item_append(field->name(), (settings.autofire ? "On" : "Off"),
|
||||
MENU_FLAG_DISABLE | MENU_FLAG_INVERT, nullptr);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/* add text item if no buttons found */
|
||||
if (menu_items==0)
|
||||
{
|
||||
item_append(MENU_SEPARATOR_ITEM, nullptr, 0, nullptr);
|
||||
item_append("No buttons found on this machine!", nullptr, MENU_FLAG_DISABLE, nullptr);
|
||||
}
|
||||
|
||||
/* add a separator */
|
||||
item_append(MENU_SEPARATOR_ITEM, nullptr, 0, nullptr);
|
||||
|
||||
/* add autofire delay item */
|
||||
int value = machine().ioport().get_autofire_delay();
|
||||
snprintf(temp_text, ARRAY_LENGTH(temp_text), "%d = %.2f Hz", value, (float)refresh/value);
|
||||
if (!autofire_toggle)
|
||||
{
|
||||
item_append("Autofire Delay", temp_text, MENU_FLAG_LEFT_ARROW | MENU_FLAG_RIGHT_ARROW, (void *)ITEMREF_AUTOFIRE_DELAY);
|
||||
}
|
||||
else
|
||||
{
|
||||
item_append("Autofire Delay", temp_text, MENU_FLAG_DISABLE | MENU_FLAG_INVERT, nullptr);
|
||||
}
|
||||
|
||||
/* add a separator */
|
||||
item_append(MENU_SEPARATOR_ITEM, nullptr, 0, nullptr);
|
||||
|
||||
last_toggle = autofire_toggle;
|
||||
}
|
||||
|
||||
|
||||
|
@ -13,6 +13,12 @@
|
||||
#ifndef __UI_CHEATOPT_H__
|
||||
#define __UI_CHEATOPT_H__
|
||||
|
||||
// itemrefs for key menu items
|
||||
#define ITEMREF_CHEATS_RESET_ALL ((void *) 0x0001)
|
||||
#define ITEMREF_CHEATS_RELOAD_ALL ((void *) 0x0002)
|
||||
#define ITEMREF_CHEATS_AUTOFIRE_SETTINGS ((void *) 0x0003)
|
||||
#define ITEMREF_CHEATS_FIRST_ITEM ((void *) 0x0004)
|
||||
|
||||
class ui_menu_cheat : public ui_menu {
|
||||
public:
|
||||
ui_menu_cheat(running_machine &machine, render_container *container);
|
||||
@ -21,4 +27,23 @@ public:
|
||||
virtual void handle() override;
|
||||
};
|
||||
|
||||
|
||||
// itemrefs for key menu items
|
||||
#define ITEMREF_AUTOFIRE_STATUS ((void *) 0x0001)
|
||||
#define ITEMREF_AUTOFIRE_DELAY ((void *) 0x0002)
|
||||
#define ITEMREF_AUTOFIRE_FIRST_BUTTON ((void *) 0x0003)
|
||||
|
||||
class ui_menu_autofire : public ui_menu {
|
||||
public:
|
||||
ui_menu_autofire(running_machine &machine, render_container *container);
|
||||
virtual ~ui_menu_autofire();
|
||||
virtual void populate() override;
|
||||
virtual void handle() override;
|
||||
|
||||
private:
|
||||
float refresh;
|
||||
bool last_toggle;
|
||||
};
|
||||
|
||||
|
||||
#endif /* __UI_CHEATOPT_H__ */
|
||||
|
@ -133,7 +133,7 @@ void ui_menu_main::populate()
|
||||
item_append("Crosshair Options", nullptr, 0, (void *)CROSSHAIR);
|
||||
|
||||
/* add cheat menu */
|
||||
if (machine().options().cheat() && machine().cheat().first() != nullptr)
|
||||
if (machine().options().cheat())
|
||||
item_append("Cheat", nullptr, 0, (void *)CHEAT);
|
||||
|
||||
// add dats menu
|
||||
|
@ -1769,6 +1769,21 @@ UINT32 ui_manager::handler_ingame(running_machine &machine, render_container *co
|
||||
if (machine.ui_input().pressed(IPT_UI_THROTTLE))
|
||||
machine.video().toggle_throttle();
|
||||
|
||||
// toggle autofire
|
||||
if (machine.ui_input().pressed(IPT_UI_TOGGLE_AUTOFIRE))
|
||||
{
|
||||
if (!machine.options().cheat())
|
||||
{
|
||||
machine.popmessage("Autofire can't be enabled");
|
||||
}
|
||||
else
|
||||
{
|
||||
bool autofire_toggle = machine.ioport().get_autofire_toggle();
|
||||
machine.ioport().set_autofire_toggle(!autofire_toggle);
|
||||
machine.popmessage("Autofire %s", autofire_toggle ? "Disabled" : "Enabled");
|
||||
}
|
||||
}
|
||||
|
||||
// check for fast forward
|
||||
if (machine.ioport().type_pressed(IPT_UI_FAST_FORWARD))
|
||||
{
|
||||
|
Loading…
Reference in New Issue
Block a user