diff --git a/src/emucore/Lightgun.cxx b/src/emucore/Lightgun.cxx new file mode 100644 index 000000000..43c582998 --- /dev/null +++ b/src/emucore/Lightgun.cxx @@ -0,0 +1,72 @@ +//============================================================================ +// +// SSSS tt lll lll +// SS SS tt ll ll +// SS tttttt eeee ll ll aaaa +// SSSS tt ee ee ll ll aa +// SS tt eeeeee ll ll aaaaa -- "An Atari 2600 VCS Emulator" +// SS SS tt ee ll ll aa aa +// SSSS ttt eeeee llll llll aaaaa +// +// Copyright (c) 1995-2019 by Bradford W. Mott, Stephen Anthony +// and the Stella Team +// +// See the file "License.txt" for information on usage and redistribution of +// this file, and for a DISCLAIMER OF ALL WARRANTIES. +//============================================================================ + +#include "Lightgun.hxx" + +// - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - +Lightgun::Lightgun(Jack jack, const Event& event, const System& system) + : Controller(jack, event, system, Controller::Type::Lightgun) +{ + if (myJack == Jack::Left) + { + myFireEvent = Event::JoystickZeroFire; + //myFireEvent = Event::LightgunZeroFire; + myPosValue = Event::LightgunZeroPos; + } + else + { + myFireEvent = Event::JoystickOneFire; + //myFireEvent = Event::LightgunOneFire; + myPosValue = Event::LightgunOnePos; + } + + // Digital pins 1, 2 and 6 are not connected (TOOD: check) + //setPin(DigitalPin::One, true); + //setPin(DigitalPin::Two, true); + //setPin(DigitalPin::Six, true); +} + +// - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - +void Lightgun::update() +{ + // | | Left port | Right port | + // | Fire button | SWCHA bit 4 | SWCHA bit 0 | DP:1 + // | Detect light | INPT4 bit 7 | INPT5 bit 7 | DP:6 + + myCharge = BSPF::clamp(myEvent.get(Event::MouseAxisXValue) * MOUSE_SENSITIVITY, TRIGMIN, TRIGMAX); + + if (myCharge != myLastCharge) + { + setPin(DigitalPin::Six, Int32(MAX_RESISTANCE * (myCharge / double(TRIGMAX)))); + myLastCharge = myCharge; + } + + setPin(DigitalPin::One, myEvent.get(Event::MouseButtonLeftValue) ? false : true); +} + +// - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - +void Lightgun::setMouseSensitivity(int sensitivity) +{ + MOUSE_SENSITIVITY = BSPF::clamp(sensitivity, 1, MAX_MOUSE_SENSE); +} + +// - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - +int Lightgun::MOUSE_SENSITIVITY = -1; + +// - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - +//const Controller::DigitalPin Lightgun::ourButtonPin = DigitalPin::One; // TODO + diff --git a/src/emucore/Lightgun.hxx b/src/emucore/Lightgun.hxx new file mode 100644 index 000000000..850c3deba --- /dev/null +++ b/src/emucore/Lightgun.hxx @@ -0,0 +1,96 @@ +//============================================================================ +// +// SSSS tt lll lll +// SS SS tt ll ll +// SS tttttt eeee ll ll aaaa +// SSSS tt ee ee ll ll aa +// SS tt eeeeee ll ll aaaaa -- "An Atari 2600 VCS Emulator" +// SS SS tt ee ll ll aa aa +// SSSS ttt eeeee llll llll aaaaa +// +// Copyright (c) 1995-2019 by Bradford W. Mott, Stephen Anthony +// and the Stella Team +// +// See the file "License.txt" for information on usage and redistribution of +// this file, and for a DISCLAIMER OF ALL WARRANTIES. +//============================================================================ + +#ifndef LIGHTGUN_HXX +#define LIGHTGUN_HXX + +#include "bspf.hxx" +#include "Control.hxx" +#include "Event.hxx" + +/** + This class handles the lighgun controller + + @author Thomas Jentzsch +*/ + +class Lightgun : public Controller +{ +public: + /** + Create a new pair of paddle controllers plugged into the specified jack + + @param jack The jack the controller is plugged into + @param event The event object to use for events + @param system The system using this controller + */ + Lightgun(Jack jack, const Event& event, const System& system); + virtual ~Lightgun() = default; + +public: + static constexpr int MAX_MOUSE_SENSE = 20; + + /** + Update the entire digital and analog pin state according to the + events currently set. + */ + void update() override; + + /** + Returns the name of this controller. + */ + string name() const override { return "Lightgun"; } + + /** + Answers whether the controller is intrinsically an analog controller. + */ + bool isAnalog() const override { return true; } + + /** + Sets the sensitivity for analog emulation of lightgun movement + using a mouse. + + @param sensitivity Value from 1 to MAX_MOUSE_SENSE, with larger + values causing more movement + */ + static void setMouseSensitivity(int sensitivity); + +private: + // Pre-compute the events we care about based on given port + // This will eliminate test for left or right port in update() + Event::Type myPosValue, myFireEvent; + + int myCharge, myLastCharge; + + static constexpr int TRIGMIN = 1; + static constexpr int TRIGMAX = 4096; + + static int MOUSE_SENSITIVITY; + + // Lookup table for associating paddle buttons with controller pins + static const Controller::DigitalPin ourButtonPin; + +private: + // Following constructors and assignment operators not supported + Lightgun() = delete; + Lightgun(const Lightgun&) = delete; + Lightgun(Lightgun&&) = delete; + Lightgun& operator=(const Lightgun&) = delete; + Lightgun& operator=(Lightgun&&) = delete; +}; + +#endif