summaryrefslogtreecommitdiffstatshomepage
path: root/src/emu/ioport.cpp
diff options
context:
space:
mode:
Diffstat (limited to 'src/emu/ioport.cpp')
-rw-r--r--src/emu/ioport.cpp418
1 files changed, 228 insertions, 190 deletions
diff --git a/src/emu/ioport.cpp b/src/emu/ioport.cpp
index 77e42c100c1..712df85db29 100644
--- a/src/emu/ioport.cpp
+++ b/src/emu/ioport.cpp
@@ -32,6 +32,7 @@
#include <algorithm>
#include <cctype>
#include <ctime>
+#include <sstream>
namespace {
@@ -237,6 +238,19 @@ const struct
{ INPUT_STRING_None, "None" },
};
+const char *const input_gm_notes_names[128] = {
+ "C-1", "C-1#", "D-1", "D-1#", "E-1", "F-1", "F-1#", "G-1", "G-1#", "A-1", "A-1#", "B-1",
+ "C0", "C0#", "D0", "D0#", "E0", "F0", "F0#", "G0", "G0#", "A0", "A0#", "B0",
+ "C1", "C1#", "D1", "D1#", "E1", "F1", "F1#", "G1", "G1#", "A1", "A1#", "B1",
+ "C2", "C2#", "D2", "D2#", "E2", "F2", "F2#", "G2", "G2#", "A2", "A2#", "B2",
+ "C3", "C3#", "D3", "D3#", "E3", "F3", "F3#", "G3", "G3#", "A3", "A3#", "B3",
+ "C4", "C4#", "D4", "D4#", "E4", "F4", "F4#", "G4", "G4#", "A4", "A4#", "B4",
+ "C5", "C5#", "D5", "D5#", "E5", "F5", "F5#", "G5", "G5#", "A5", "A5#", "B5",
+ "C6", "C6#", "D6", "D6#", "E6", "F6", "F6#", "G6", "G6#", "A6", "A6#", "B6",
+ "C7", "C7#", "D7", "D7#", "E7", "F7", "F7#", "G7", "G7#", "A7", "A7#", "B7",
+ "C8", "C8#", "D8", "D8#", "E8", "F8", "F8#", "G8", "G8#", "A8", "A8#", "B8",
+ "C9", "C9#", "D9", "D9#", "E9", "F9", "F9#", "G9"
+};
inline bool input_seq_good(running_machine &machine, input_seq const &seq)
{
@@ -407,16 +421,13 @@ u8 const inp_header::MAGIC[inp_header::OFFS_BASETIME - inp_header::OFFS_MAGIC] =
// to the current list
//-------------------------------------------------
-void ioport_list::append(device_t &device, std::string &errorbuf)
+void ioport_list::append(device_t &device, std::ostream &errorbuf)
{
// no constructor, no list
ioport_constructor constructor = device.input_ports();
- if (constructor == nullptr)
+ if (!constructor)
return;
- // reset error buffer
- errorbuf.clear();
-
// detokenize into the list
(*constructor)(device, *this, errorbuf);
@@ -435,22 +446,22 @@ void ioport_list::append(device_t &device, std::string &errorbuf)
// input_type_entry - constructors
//-------------------------------------------------
-input_type_entry::input_type_entry(ioport_type type, ioport_group group, int player, const char *token, const char *name, input_seq standard) noexcept
- : m_type(type),
- m_group(group),
- m_player(player),
- m_token(token),
- m_name(name)
+input_type_entry::input_type_entry(ioport_type type, ioport_group group, int player, const char *token, const char *name, input_seq standard) noexcept :
+ m_type(type),
+ m_group(group),
+ m_player(player),
+ m_token(token),
+ m_name(name)
{
m_defseq[SEQ_TYPE_STANDARD] = m_seq[SEQ_TYPE_STANDARD] = standard;
}
-input_type_entry::input_type_entry(ioport_type type, ioport_group group, int player, const char *token, const char *name, input_seq standard, input_seq decrement, input_seq increment) noexcept
- : m_type(type),
- m_group(group),
- m_player(player),
- m_token(token),
- m_name(name)
+input_type_entry::input_type_entry(ioport_type type, ioport_group group, int player, const char *token, const char *name, input_seq standard, input_seq decrement, input_seq increment) noexcept :
+ m_type(type),
+ m_group(group),
+ m_player(player),
+ m_token(token),
+ m_name(name)
{
m_defseq[SEQ_TYPE_STANDARD] = m_seq[SEQ_TYPE_STANDARD] = standard;
m_defseq[SEQ_TYPE_INCREMENT] = m_seq[SEQ_TYPE_INCREMENT] = increment;
@@ -520,12 +531,12 @@ void input_type_entry::restore_default_seq() noexcept
// digital_joystick - constructor
//-------------------------------------------------
-digital_joystick::digital_joystick(int player, int number)
- : m_player(player),
- m_number(number),
- m_current(0),
- m_current4way(0),
- m_previous(0)
+digital_joystick::digital_joystick(int player, int number) :
+ m_player(player),
+ m_number(number),
+ m_current(0),
+ m_current4way(0),
+ m_previous(0)
{
}
@@ -608,6 +619,8 @@ void digital_joystick::frame_update()
m_current4way &= ~(UP_BIT | DOWN_BIT);
}
}
+ else
+ m_current4way &= m_current;
}
@@ -662,10 +675,10 @@ void ioport_condition::initialize(device_t &device)
// ioport_setting - constructor
//-------------------------------------------------
-ioport_setting::ioport_setting(ioport_field &field, ioport_value _value, const char *_name)
- : m_field(field),
- m_value(_value),
- m_name(_name)
+ioport_setting::ioport_setting(ioport_field &field, ioport_value _value, const char *_name) :
+ m_field(field),
+ m_value(_value),
+ m_name(_name)
{
}
@@ -679,10 +692,10 @@ ioport_setting::ioport_setting(ioport_field &field, ioport_value _value, const c
// ioport_diplocation - constructor
//-------------------------------------------------
-ioport_diplocation::ioport_diplocation(const char *name, u8 swnum, bool invert)
- : m_name(name),
- m_number(swnum),
- m_invert(invert)
+ioport_diplocation::ioport_diplocation(std::string_view name, u8 swnum, bool invert) :
+ m_name(name),
+ m_number(swnum),
+ m_invert(invert)
{
}
@@ -696,41 +709,41 @@ ioport_diplocation::ioport_diplocation(const char *name, u8 swnum, bool invert)
// ioport_field - constructor
//-------------------------------------------------
-ioport_field::ioport_field(ioport_port &port, ioport_type type, ioport_value defvalue, ioport_value maskbits, const char *name)
- : m_next(nullptr),
- m_port(port),
- m_modcount(port.modcount()),
- m_mask(maskbits),
- m_defvalue(defvalue & maskbits),
- m_type(type),
- m_player(0),
- m_flags(0),
- m_impulse(0),
- m_name(name),
- m_read(port.device()),
- m_write(port.device()),
- m_write_param(0),
- m_digital_value(false),
- m_min(0),
- m_max(maskbits),
- m_sensitivity(0),
- m_delta(0),
- m_centerdelta(0),
- m_crosshair_axis(CROSSHAIR_AXIS_NONE),
- m_crosshair_scale(1.0),
- m_crosshair_offset(0),
- m_crosshair_altaxis(0),
- m_crosshair_mapper(port.device()),
- m_full_turn_count(0),
- m_remap_table(nullptr),
- m_way(0)
+ioport_field::ioport_field(ioport_port &port, ioport_type type, ioport_value defvalue, ioport_value maskbits, const char *name) :
+ m_next(nullptr),
+ m_port(port),
+ m_modcount(port.modcount()),
+ m_mask(maskbits),
+ m_defvalue(defvalue & maskbits),
+ m_type(type),
+ m_player(0),
+ m_flags(0),
+ m_impulse(0),
+ m_name(name),
+ m_read(port.device()),
+ m_write(port.device()),
+ m_write_param(0),
+ m_digital_value(false),
+ m_min(0),
+ m_max(maskbits),
+ m_sensitivity(0),
+ m_delta(0),
+ m_centerdelta(0),
+ m_crosshair_axis(CROSSHAIR_AXIS_NONE),
+ m_crosshair_scale(1.0),
+ m_crosshair_offset(0),
+ m_crosshair_altaxis(0),
+ m_crosshair_mapper(port.device()),
+ m_full_turn_count(0),
+ m_remap_table(nullptr),
+ m_way(0)
{
// reset sequences and chars
for (input_seq_type seqtype = SEQ_TYPE_STANDARD; seqtype < SEQ_TYPE_TOTAL; ++seqtype)
m_seq[seqtype].set_default();
- for (int i = 0; i < std::size(m_chars); i++)
- std::fill(std::begin(m_chars[i]), std::end(m_chars[i]), char32_t(0));
+ for (auto &chars : m_chars)
+ std::fill(std::begin(chars), std::end(chars), UCHAR_INVALID);
// for DIP switches and configs, look for a default value from the owner
if (type == IPT_DIPSWITCH || type == IPT_CONFIG)
@@ -898,11 +911,8 @@ std::vector<char32_t> ioport_field::keyboard_codes(int which) const
if (which >= std::size(m_chars))
throw emu_fatalerror("Tried to access keyboard_code with out-of-range index %d\n", which);
- std::vector<char32_t> result;
- for (int i = 0; i < std::size(m_chars[which]) && m_chars[which][i] != 0; i++)
- result.push_back(m_chars[which][i]);
-
- return result;
+ auto &chars = m_chars[which];
+ return std::vector<char32_t>(std::begin(chars), std::find(std::begin(chars), std::end(chars), UCHAR_INVALID));
}
@@ -1346,7 +1356,7 @@ float ioport_field::crosshair_read() const
// descriptions
//-------------------------------------------------
-void ioport_field::expand_diplocation(const char *location, std::string &errorbuf)
+void ioport_field::expand_diplocation(const char *location, std::ostream &errorbuf)
{
// if nothing present, bail
if (!location)
@@ -1355,71 +1365,76 @@ void ioport_field::expand_diplocation(const char *location, std::string &errorbu
m_diploclist.clear();
// parse the string
- std::string name; // Don't move this variable inside the loop, lastname's lifetime depends on it being outside
- const char *lastname = nullptr;
+ std::string_view lastname;
const char *curentry = location;
int entries = 0;
- while (*curentry != 0)
+ while (*curentry)
{
// find the end of this entry
const char *comma = strchr(curentry, ',');
- if (comma == nullptr)
+ if (!comma)
comma = curentry + strlen(curentry);
// extract it to tempbuf
- std::string tempstr(curentry, comma - curentry);
+ std::string_view tempstr(curentry, comma - curentry);
// first extract the switch name if present
- const char *number = tempstr.c_str();
- const char *colon = strchr(tempstr.c_str(), ':');
+ std::string_view::size_type number = 0;
+ std::string_view::size_type const colon = tempstr.find(':');
- if (colon != nullptr)
+ std::string_view name;
+ if (colon != std::string_view::npos)
{
// allocate and copy the name if it is present
- lastname = name.assign(number, colon - number).c_str();
+ lastname = tempstr.substr(0, colon);
number = colon + 1;
+ if (lastname.empty())
+ {
+ util::stream_format(errorbuf, "Switch location '%s' has empty switch name!\n", location);
+ lastname = "UNK";
+ }
+ name = lastname;
}
else
{
// otherwise, just copy the last name
- if (lastname == nullptr)
+ if (lastname.empty())
{
- errorbuf.append(string_format("Switch location '%s' missing switch name!\n", location));
- lastname = (char *)"UNK";
+ util::stream_format(errorbuf, "Switch location '%s' missing switch name!\n", location);
+ lastname = "UNK";
}
- name.assign(lastname);
+ name = lastname;
}
// if the number is preceded by a '!' it's active high
- bool invert = false;
- if (*number == '!')
- {
- invert = true;
- number++;
- }
+ bool const invert = tempstr[number] == '!';
+ if (invert)
+ ++number;
// now scan the switch number
int swnum = -1;
- if (sscanf(number, "%d", &swnum) != 1)
- errorbuf.append(string_format("Switch location '%s' has invalid format!\n", location));
+ if (sscanf(&tempstr[number], "%d", &swnum) != 1)
+ util::stream_format(errorbuf, "Switch location '%s' has invalid format!\n", location);
+ else if (0 >= swnum)
+ util::stream_format(errorbuf, "Switch location '%s' has switch number that is not positive!\n", location);
// allocate a new entry
- m_diploclist.emplace_back(name.c_str(), swnum, invert);
+ if (0 < swnum)
+ m_diploclist.emplace_back(name, swnum, invert);
entries++;
// advance to the next item
curentry = comma;
- if (*curentry != 0)
+ if (*curentry)
curentry++;
}
// then verify the number of bits in the mask matches
- ioport_value temp;
- int bits;
- for (bits = 0, temp = m_mask; temp != 0 && bits < 32; bits++)
- temp &= temp - 1;
- if (bits != entries)
- errorbuf.append(string_format("Switch location '%s' does not describe enough bits for mask %X\n", location, m_mask));
+ int const bits = population_count_32(m_mask);
+ if (bits > entries)
+ util::stream_format(errorbuf, "Switch location '%s' does not describe enough bits for mask %X\n", location, m_mask);
+ else if (bits < entries)
+ util::stream_format(errorbuf, "Switch location '%s' describes too many bits for mask %X\n", location, m_mask);
}
@@ -1453,15 +1468,15 @@ void ioport_field::init_live_state(analog_field *analog)
// ioport_field_live - constructor
//-------------------------------------------------
-ioport_field_live::ioport_field_live(ioport_field &field, analog_field *analog)
- : analog(analog),
- joystick(nullptr),
- value(field.defvalue()),
- impulse(0),
- last(0),
- toggle(field.toggle()),
- joydir(digital_joystick::JOYDIR_COUNT),
- lockout(false)
+ioport_field_live::ioport_field_live(ioport_field &field, analog_field *analog) :
+ analog(analog),
+ joystick(nullptr),
+ value(field.defvalue()),
+ impulse(0),
+ last(0),
+ toggle(field.toggle()),
+ joydir(digital_joystick::JOYDIR_COUNT),
+ lockout(false)
{
// fill in the basic values
for (input_seq_type seqtype = SEQ_TYPE_STANDARD; seqtype < SEQ_TYPE_TOTAL; ++seqtype)
@@ -1509,12 +1524,12 @@ ioport_field_live::ioport_field_live(ioport_field &field, analog_field *analog)
// ioport_port - constructor
//-------------------------------------------------
-ioport_port::ioport_port(device_t &owner, const char *tag)
- : m_next(nullptr),
- m_device(owner),
- m_tag(tag),
- m_modcount(0),
- m_active(0)
+ioport_port::ioport_port(device_t &owner, const char *tag) :
+ m_next(nullptr),
+ m_device(owner),
+ m_tag(tag),
+ m_modcount(0),
+ m_active(0)
{
}
@@ -1626,7 +1641,7 @@ void ioport_port::frame_update()
// wholly overlapped by other fields
//-------------------------------------------------
-void ioport_port::collapse_fields(std::string &errorbuf)
+void ioport_port::collapse_fields(std::ostream &errorbuf)
{
ioport_value maskbits = 0;
int lastmodcount = -1;
@@ -1655,13 +1670,13 @@ void ioport_port::collapse_fields(std::string &errorbuf)
// for errors
//-------------------------------------------------
-void ioport_port::insert_field(ioport_field &newfield, ioport_value &disallowedbits, std::string &errorbuf)
+void ioport_port::insert_field(ioport_field &newfield, ioport_value &disallowedbits, std::ostream &errorbuf)
{
// verify against the disallowed bits, but only if we are condition-free
if (newfield.condition().none())
{
if ((newfield.mask() & disallowedbits) != 0)
- errorbuf.append(string_format("INPUT_TOKEN_FIELD specifies duplicate port bits (port=%s mask=%X)\n", tag(), newfield.mask()));
+ util::stream_format(errorbuf, "INPUT_TOKEN_FIELD specifies duplicate port bits (port=%s mask=%X)\n", tag(), newfield.mask());
disallowedbits |= newfield.mask();
}
@@ -1733,10 +1748,10 @@ void ioport_port::update_defvalue(bool flush_defaults)
// ioport_port_live - constructor
//-------------------------------------------------
-ioport_port_live::ioport_port_live(ioport_port &port)
- : defvalue(0),
- digital(0),
- outputvalue(0)
+ioport_port_live::ioport_port_live(ioport_port &port) :
+ defvalue(0),
+ digital(0),
+ outputvalue(0)
{
// iterate over fields
for (ioport_field &field : port.fields())
@@ -1769,15 +1784,15 @@ ioport_port_live::ioport_port_live(ioport_port &port)
// ioport_manager - constructor
//-------------------------------------------------
-ioport_manager::ioport_manager(running_machine &machine)
- : m_machine(machine)
- , m_safe_to_read(false)
- , m_last_frame_time(attotime::zero)
- , m_last_delta_nsec(0)
- , m_playback_accumulated_speed(0)
- , m_playback_accumulated_frames(0)
- , m_deselected_card_config()
- , m_applied_device_defaults(false)
+ioport_manager::ioport_manager(running_machine &machine) :
+ m_machine(machine),
+ m_safe_to_read(false),
+ m_last_frame_time(attotime::zero),
+ m_last_delta_nsec(0),
+ m_playback_accumulated_speed(0),
+ m_playback_accumulated_frames(0),
+ m_deselected_card_config(),
+ m_applied_device_defaults(false)
{
for (auto &entries : m_type_to_entry)
std::fill(std::begin(entries), std::end(entries), nullptr);
@@ -1800,12 +1815,17 @@ time_t ioport_manager::initialize()
// if we have a token list, proceed
device_enumerator iter(machine().root_device());
- for (device_t &device : iter)
{
- std::string errors;
- m_portlist.append(device, errors);
- if (!errors.empty())
- osd_printf_error("Input port errors:\n%s", errors);
+ std::ostringstream errors;
+ for (device_t &device : iter)
+ {
+ m_portlist.append(device, errors);
+ if (errors.tellp())
+ {
+ osd_printf_error("Input port errors:\n%s", std::move(errors).str());
+ errors.str("");
+ }
+ }
}
// renumber player numbers for controller ports
@@ -2946,9 +2966,13 @@ Type ioport_manager::playback_read(Type &result)
return result = Type(0);
// read the value; if we fail, end playback
- size_t read;
- m_playback_stream->read(&result, sizeof(result), read);
- if (sizeof(result) != read)
+ auto const [err, actual] = read(*m_playback_stream, &result, sizeof(result));
+ if (err)
+ {
+ playback_end("Read error");
+ return result = Type(0);
+ }
+ else if (sizeof(result) != actual)
{
playback_end("End of file");
return result = Type(0);
@@ -3132,9 +3156,8 @@ void ioport_manager::record_write(Type value)
value = little_endianize_int16(value);
// write the value; if we fail, end recording
- size_t written;
- if (m_record_stream->write(&value, sizeof(value), written) || (sizeof(value) != written))
- record_end("Out of space");
+ if (write(*m_record_stream, &value, sizeof(value)).first)
+ record_end("Write error");
}
template<>
@@ -3259,16 +3282,28 @@ void ioport_manager::record_port(ioport_port &port)
// ioport_configurer - constructor
//-------------------------------------------------
-ioport_configurer::ioport_configurer(device_t &owner, ioport_list &portlist, std::string &errorbuf)
- : m_owner(owner),
- m_portlist(portlist),
- m_errorbuf(errorbuf),
- m_curport(nullptr),
- m_curfield(nullptr),
- m_cursetting(nullptr)
+ioport_configurer::ioport_configurer(device_t &owner, ioport_list &portlist, std::ostream &errorbuf) :
+ m_owner(owner),
+ m_portlist(portlist),
+ m_errorbuf(errorbuf),
+ m_curport(nullptr),
+ m_curfield(nullptr),
+ m_cursetting(nullptr),
+ m_curshift(0)
{
}
+//-------------------------------------------------
+// field_set_gm_note - set a ioport as a general
+// midi-encoded note number. Only sets the name
+// for now
+//-------------------------------------------------
+
+ioport_configurer& ioport_configurer::field_set_gm_note(u8 note)
+{
+ field_set_name(input_gm_notes_names[note]);
+ return *this;
+}
//-------------------------------------------------
// string_from_token - convert an
@@ -3359,6 +3394,7 @@ ioport_configurer& ioport_configurer::field_alloc(ioport_type type, ioport_value
// reset the current setting
m_cursetting = nullptr;
+ m_curshift = 0;
return *this;
}
@@ -3369,16 +3405,17 @@ ioport_configurer& ioport_configurer::field_alloc(ioport_type type, ioport_value
ioport_configurer& ioport_configurer::field_add_char(std::initializer_list<char32_t> charlist)
{
- for (int index = 0; index < std::size(m_curfield->m_chars); index++)
- if (m_curfield->m_chars[index][0] == 0)
- {
- const size_t char_count = std::size(m_curfield->m_chars[index]);
- assert(charlist.size() > 0 && charlist.size() <= char_count);
+ if (m_curshift < std::size(m_curfield->m_chars))
+ {
+ auto &chars = m_curfield->m_chars[m_curshift++];
+ assert(chars[0] == UCHAR_INVALID);
+ assert(charlist.size() <= std::size(chars));
- for (size_t i = 0; i < char_count; i++)
- m_curfield->m_chars[index][i] = i < charlist.size() ? *(charlist.begin() + i) : 0;
- return *this;
- }
+ std::copy(charlist.begin(), charlist.end(), std::begin(chars));
+ std::fill(std::begin(chars) + charlist.size(), std::end(chars), UCHAR_INVALID);
+
+ return *this;
+ }
std::ostringstream s;
bool is_first = true;
@@ -3462,10 +3499,10 @@ ioport_configurer& ioport_configurer::onoff_alloc(const char *name, ioport_value
// dynamic_field - constructor
//-------------------------------------------------
-dynamic_field::dynamic_field(ioport_field &field)
- : m_field(field)
- , m_shift(0)
- , m_oldval(field.defvalue())
+dynamic_field::dynamic_field(ioport_field &field) :
+ m_field(field),
+ m_shift(0),
+ m_oldval(field.defvalue())
{
// fill in the data
for (ioport_value mask = field.mask(); !(mask & 1); mask >>= 1)
@@ -3519,36 +3556,36 @@ void dynamic_field::write(ioport_value newval)
// analog_field - constructor
//-------------------------------------------------
-analog_field::analog_field(ioport_field &field)
- : m_field(field)
- , m_shift(compute_shift(field.mask()))
- , m_adjdefvalue((field.defvalue() & field.mask()) >> m_shift)
- , m_adjmin((field.minval() & field.mask()) >> m_shift)
- , m_adjmax((field.maxval() & field.mask()) >> m_shift)
- , m_adjoverride((field.defvalue() & field.mask()) >> m_shift)
- , m_sensitivity(field.sensitivity())
- , m_reverse(field.analog_reverse())
- , m_delta(field.delta())
- , m_centerdelta(field.centerdelta())
- , m_accum(0)
- , m_previous(0)
- , m_previousanalog(0)
- , m_minimum(osd::input_device::ABSOLUTE_MIN)
- , m_maximum(osd::input_device::ABSOLUTE_MAX)
- , m_center(0)
- , m_reverse_val(0)
- , m_scalepos(0)
- , m_scaleneg(0)
- , m_keyscalepos(0)
- , m_keyscaleneg(0)
- , m_positionalscale(0)
- , m_absolute(false)
- , m_wraps(false)
- , m_autocenter(false)
- , m_single_scale(false)
- , m_interpolate(false)
- , m_lastdigital(false)
- , m_use_adjoverride(false)
+analog_field::analog_field(ioport_field &field) :
+ m_field(field),
+ m_shift(compute_shift(field.mask())),
+ m_adjdefvalue((field.defvalue() & field.mask()) >> m_shift),
+ m_adjmin((field.minval() & field.mask()) >> m_shift),
+ m_adjmax((field.maxval() & field.mask()) >> m_shift),
+ m_adjoverride((field.defvalue() & field.mask()) >> m_shift),
+ m_sensitivity(field.sensitivity()),
+ m_reverse(field.analog_reverse()),
+ m_delta(field.delta()),
+ m_centerdelta(field.centerdelta()),
+ m_accum(0),
+ m_previous(0),
+ m_previousanalog(0),
+ m_minimum(osd::input_device::ABSOLUTE_MIN),
+ m_maximum(osd::input_device::ABSOLUTE_MAX),
+ m_center(0),
+ m_reverse_val(0),
+ m_scalepos(0),
+ m_scaleneg(0),
+ m_keyscalepos(0),
+ m_keyscaleneg(0),
+ m_positionalscale(0),
+ m_absolute(false),
+ m_wraps(false),
+ m_autocenter(false),
+ m_single_scale(false),
+ m_interpolate(false),
+ m_lastdigital(false),
+ m_use_adjoverride(false)
{
// set basic parameters based on the configured type
switch (field.type())
@@ -3760,10 +3797,11 @@ s32 analog_field::apply_settings(s32 value) const
value -= osd::input_device::ABSOLUTE_MIN;
// map differently for positive and negative values
+ const s32 adjust = m_field.analog_reset() ? 0 : (1 << 23);
if (value >= 0)
- value = apply_scale(value, m_scalepos);
+ value = ((s64(value) * m_scalepos) + adjust) / (1 << 24);
else
- value = apply_scale(value, m_scaleneg);
+ value = ((s64(value) * m_scaleneg) - adjust) / (1 << 24);
value += m_adjdefvalue;
// for relative devices, wrap around when we go past the edge