duckstation

duckstation, but archived from the revision just before upstream changed it to a proprietary software project, this version is the libre one
git clone https://git.neptards.moe/u3shit/duckstation.git
Log | Files | Refs | README | LICENSE

controller.h (4517B)


      1 // SPDX-FileCopyrightText: 2019-2024 Connor McLaughlin <stenzek@gmail.com>
      2 // SPDX-License-Identifier: (GPL-3.0 OR CC-BY-NC-ND-4.0)
      3 
      4 #pragma once
      5 
      6 #include "input_types.h"
      7 #include "settings.h"
      8 #include "types.h"
      9 
     10 #include <memory>
     11 #include <optional>
     12 #include <span>
     13 #include <string>
     14 #include <string_view>
     15 #include <tuple>
     16 #include <vector>
     17 
     18 class SettingsInterface;
     19 class StateWrapper;
     20 class HostInterface;
     21 
     22 class Controller
     23 {
     24 public:
     25   enum class VibrationCapabilities : u8
     26   {
     27     NoVibration,
     28     LargeSmallMotors,
     29     SingleMotor,
     30     Count
     31   };
     32 
     33   struct ControllerBindingInfo
     34   {
     35     const char* name;
     36     const char* display_name;
     37     const char* icon_name;
     38     u32 bind_index;
     39     InputBindingInfo::Type type;
     40     GenericInputBinding generic_mapping;
     41   };
     42 
     43   struct ControllerInfo
     44   {
     45     ControllerType type;
     46     const char* name;
     47     const char* display_name;
     48     const char* icon_name;
     49     std::span<const ControllerBindingInfo> bindings;
     50     std::span<const SettingInfo> settings;
     51     VibrationCapabilities vibration_caps;
     52 
     53     /// Returns localized controller type name.
     54     const char* GetDisplayName() const;
     55   };
     56 
     57   /// Default stick deadzone/sensitivity.
     58   static constexpr float DEFAULT_STICK_DEADZONE = 0.0f;
     59   static constexpr float DEFAULT_STICK_SENSITIVITY = 1.33f;
     60   static constexpr float DEFAULT_BUTTON_DEADZONE = 0.25f;
     61 
     62   Controller(u32 index);
     63   virtual ~Controller();
     64 
     65   /// Returns the type of controller.
     66   virtual ControllerType GetType() const = 0;
     67 
     68   virtual void Reset();
     69   virtual bool DoState(StateWrapper& sw, bool apply_input_state);
     70 
     71   // Resets all state for the transferring to/from the device.
     72   virtual void ResetTransferState();
     73 
     74   // Returns the value of ACK, as well as filling out_data.
     75   virtual bool Transfer(const u8 data_in, u8* data_out);
     76 
     77   /// Changes the specified axis state. Values are normalized from -1..1.
     78   virtual float GetBindState(u32 index) const;
     79 
     80   /// Changes the specified bind state. Values are normalized from -1..1.
     81   virtual void SetBindState(u32 index, float value);
     82 
     83   /// Returns a bitmask of the current button states, 1 = on.
     84   virtual u32 GetButtonStateBits() const;
     85 
     86   /// Returns true if the controller supports analog mode, and it is active.
     87   virtual bool InAnalogMode() const;
     88 
     89   /// Returns analog input bytes packed as a u32. Values are specific to controller type.
     90   virtual std::optional<u32> GetAnalogInputBytes() const;
     91 
     92   /// Returns the colour to use in the input overlay.
     93   virtual u32 GetInputOverlayIconColor() const;
     94 
     95   /// Loads/refreshes any per-controller settings.
     96   virtual void LoadSettings(SettingsInterface& si, const char* section, bool initial);
     97 
     98   /// Creates a new controller of the specified type.
     99   static std::unique_ptr<Controller> Create(ControllerType type, u32 index);
    100 
    101   /// Returns the default type for the specified port.
    102   static const char* GetDefaultPadType(u32 pad);
    103 
    104   /// Returns a list of controller type names. Pair of [name, display name].
    105   static std::vector<std::pair<std::string, std::string>> GetControllerTypeNames();
    106 
    107   /// Gets the integer code for an axis in the specified controller type.
    108   static std::optional<u32> GetBindIndex(ControllerType type, std::string_view bind_name);
    109 
    110   /// Returns general information for the specified controller type.
    111   static const ControllerInfo* GetControllerInfo(ControllerType type);
    112   static const ControllerInfo* GetControllerInfo(std::string_view name);
    113 
    114   /// Converts a global pad index to a multitap port and slot.
    115   static std::tuple<u32, u32> ConvertPadToPortAndSlot(u32 index);
    116 
    117   /// Converts a multitap port and slot to a global pad index.
    118   static u32 ConvertPortAndSlotToPad(u32 port, u32 slot);
    119 
    120   /// Returns true if the given pad index is a multitap slot.
    121   static bool PadIsMultitapSlot(u32 index);
    122   static bool PortAndSlotIsMultitap(u32 port, u32 slot);
    123 
    124   /// Returns the configuration section for the specified gamepad.
    125   static std::string GetSettingsSection(u32 pad);
    126 
    127   /// Applies an analog deadzone/sensitivity.
    128   static float ApplyAnalogDeadzoneSensitivity(float deadzone, float sensitivity, float value)
    129   {
    130     return (value < deadzone) ? 0.0f : ((value - deadzone) / (1.0f - deadzone) * sensitivity);
    131   }
    132 
    133   /// Returns true if the specified coordinates are inside a circular deadzone.
    134   static bool InCircularDeadzone(float deadzone, float pos_x, float pos_y);
    135 
    136 protected:
    137   /// Returns true if automatic analog mode can be used.
    138   static bool CanStartInAnalogMode(ControllerType ctype);
    139 
    140   u32 m_index;
    141 };