mirror of
https://github.com/TomHarte/CLK.git
synced 2025-01-11 08:30:55 +00:00
Adds use of joystick input in the Apple II.
This commit is contained in:
parent
f1b430338e
commit
f26e4734b3
@ -138,16 +138,16 @@ class Joystick {
|
||||
class ConcreteJoystick: public Joystick {
|
||||
public:
|
||||
ConcreteJoystick(const std::vector<Input> &inputs) : inputs_(inputs) {
|
||||
// Size and populate axis_types_, which is used for digital <-> analogue conversion.
|
||||
// Size and populate stick_types_, which is used for digital <-> analogue conversion.
|
||||
for(const auto &input: inputs_) {
|
||||
const bool is_digital_axis = input.is_digital_axis();
|
||||
const bool is_analogue_axis = input.is_analogue_axis();
|
||||
if(is_digital_axis || is_analogue_axis) {
|
||||
const size_t required_size = static_cast<size_t>(input.info.control.index+1);
|
||||
if(axis_types_.size() < required_size) {
|
||||
axis_types_.resize(required_size);
|
||||
if(stick_types_.size() < required_size) {
|
||||
stick_types_.resize(required_size);
|
||||
}
|
||||
axis_types_[static_cast<size_t>(input.info.control.index)] = is_digital_axis ? AxisType::Digital : AxisType::Analogue;
|
||||
stick_types_[static_cast<size_t>(input.info.control.index)] = is_digital_axis ? StickType::Digital : StickType::Analogue;
|
||||
}
|
||||
}
|
||||
}
|
||||
@ -158,7 +158,7 @@ class ConcreteJoystick: public Joystick {
|
||||
|
||||
void set_input(const Input &input, bool is_active) override final {
|
||||
// If this is a digital setting to a digital property, just pass it along.
|
||||
if(input.is_button() || axis_types_[input.info.control.index] == AxisType::Digital) {
|
||||
if(input.is_button() || stick_types_[input.info.control.index] == StickType::Digital) {
|
||||
did_set_input(input, is_active);
|
||||
return;
|
||||
}
|
||||
@ -178,7 +178,7 @@ class ConcreteJoystick: public Joystick {
|
||||
|
||||
void set_input(const Input &input, float value) override final {
|
||||
// If this is an analogue setting to an analogue property, just pass it along.
|
||||
if(!input.is_button() && axis_types_[input.info.control.index] == AxisType::Analogue) {
|
||||
if(!input.is_button() && stick_types_[input.info.control.index] == StickType::Analogue) {
|
||||
did_set_input(input, value);
|
||||
return;
|
||||
}
|
||||
@ -209,11 +209,11 @@ class ConcreteJoystick: public Joystick {
|
||||
private:
|
||||
std::vector<Input> inputs_;
|
||||
|
||||
enum class AxisType {
|
||||
enum class StickType {
|
||||
Digital,
|
||||
Analogue
|
||||
};
|
||||
std::vector<AxisType> axis_types_;
|
||||
std::vector<StickType> stick_types_;
|
||||
};
|
||||
|
||||
}
|
||||
|
@ -176,7 +176,6 @@ class ConcreteMachine:
|
||||
bool should_load_quickly_ = false;
|
||||
|
||||
// MARK - joysticks
|
||||
std::vector<std::unique_ptr<Inputs::Joystick>> joysticks_;
|
||||
class Joystick: public Inputs::ConcreteJoystick {
|
||||
public:
|
||||
Joystick() :
|
||||
@ -191,7 +190,20 @@ class ConcreteMachine:
|
||||
Input(Input::Fire, 1),
|
||||
Input(Input::Fire, 2),
|
||||
}) {}
|
||||
|
||||
void did_set_input(const Input &input, float value) override {
|
||||
axes[(input.type == Input::Type::Horizontal) ? 1 : 0] = value;
|
||||
}
|
||||
|
||||
void did_set_input(const Input &input, bool value) override {
|
||||
buttons[input.info.control.index] = value;
|
||||
}
|
||||
|
||||
bool buttons[3] = {false, false, false};
|
||||
float axes[2] = {0.5f, 0.5f};
|
||||
};
|
||||
float analogue_charge_ = 0.0f;
|
||||
std::vector<std::unique_ptr<Inputs::Joystick>> joysticks_;
|
||||
|
||||
public:
|
||||
ConcreteMachine():
|
||||
@ -401,17 +413,28 @@ class ConcreteMachine:
|
||||
break;
|
||||
|
||||
case 0xc061: // Switch input 0.
|
||||
if(!static_cast<Joystick *>(joysticks_[0].get())->buttons[0] || !static_cast<Joystick *>(joysticks_[1].get())->buttons[2])
|
||||
*value &= 0x7f;
|
||||
break;
|
||||
case 0xc062: // Switch input 1.
|
||||
if(!static_cast<Joystick *>(joysticks_[0].get())->buttons[1] || !static_cast<Joystick *>(joysticks_[1].get())->buttons[1])
|
||||
*value &= 0x7f;
|
||||
break;
|
||||
case 0xc063: // Switch input 2.
|
||||
*value &= 0x7f;
|
||||
if(!static_cast<Joystick *>(joysticks_[0].get())->buttons[2] || !static_cast<Joystick *>(joysticks_[1].get())->buttons[0])
|
||||
*value &= 0x7f;
|
||||
break;
|
||||
|
||||
case 0xc064: // Analogue input 0.
|
||||
case 0xc065: // Analogue input 1.
|
||||
case 0xc066: // Analogue input 2.
|
||||
case 0xc067: // Analogue input 3.
|
||||
case 0xc067: { // Analogue input 3.
|
||||
const size_t input = address - 0xc064;
|
||||
*value &= 0x7f;
|
||||
break;
|
||||
if(static_cast<Joystick *>(joysticks_[input >> 1].get())->axes[input & 1] < analogue_charge_) {
|
||||
*value |= 0x80;
|
||||
}
|
||||
} break;
|
||||
}
|
||||
} else {
|
||||
// Write-only switches.
|
||||
@ -429,6 +452,7 @@ class ConcreteMachine:
|
||||
case 0xc057: update_video(); video_->set_high_resolution(); break;
|
||||
|
||||
case 0xc070: // Reset analogue inputs.
|
||||
analogue_charge_ = 0.0f;
|
||||
break;
|
||||
|
||||
case 0xc010:
|
||||
@ -528,6 +552,9 @@ class ConcreteMachine:
|
||||
}
|
||||
}
|
||||
|
||||
// Update analogue charge level.
|
||||
analogue_charge_ = std::min(analogue_charge_ + 1.0f / 2820.0f, 1.0f);
|
||||
|
||||
return Cycles(1);
|
||||
}
|
||||
|
||||
@ -669,3 +696,4 @@ Machine *Machine::AppleII() {
|
||||
}
|
||||
|
||||
Machine::~Machine() {}
|
||||
|
||||
|
Loading…
x
Reference in New Issue
Block a user