SHARE
TWEET

XInput

Holy87 Dec 20th, 2016 (edited) 209 Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
  1. #===============================================================================
  2. # Interfaccia XInput di Holy87
  3. # Difficoltà utente: ★
  4. # Versione 1.03
  5. # Licenza: CC. Chiunque può scaricare, modificare, distribuire e utilizzare
  6. # lo script nei propri progetti, sia amatoriali che commerciali. Vietata
  7. # l'attribuzione impropria.
  8. #
  9. # changelog
  10. # v1.03 => Fix per l'input controller tramite condizione evento
  11. # v1.02 => Inserita compatibilità con sistemi che non supportano DX11
  12. # v1.01 => Bugfix
  13. #===============================================================================
  14. # Questo script vi permette di utilizzare i controller per PC più moderni, come
  15. # il controller dell'XBox 360/One, PS4 e Logitech. Lo script è subito utilizzabile
  16. # per miglirare i controlli del gioco automaticamente (ad esempio, muovervi con
  17. # le frecce direzionali anziché gli analogici e selezionare con il tasto A),
  18. # inoltre offre le seguenti funzionalità:
  19. # ● Supporto agli analogici: potete ottenere il valore preciso degli stick
  20. #   analogici destro e sinistro e dei grilletti dorsali
  21. # ● Supporto fino a 4 controller, per giochi multigiocatore
  22. # ● Vibrazione: possibiltà di gestire la vibrazione sui 2 diversi motori
  23. # ● Livello batteria: potrete riconoscere se il controller è wireless e lo stato
  24. #   della batteria
  25. # ● Rimappamento tasti: è possibile personalizzare i controlli e sovrascrivere
  26. #   quelli di default di RPG Maker
  27. # ● Utilizzo dello script a 3 strati: alto (semplice), medio e basso (raw)
  28. # Questo script scavalca le impostazioni del game pad del gioco (quella
  29. # finestra che compare quando si preme F1)
  30. #===============================================================================
  31. # Istruzioni: inserire lo script sotto Materials, prima del Main.
  32. # RICHIEDE IL MODULO DI SUPPORTO UNIVERSLE.
  33. # Lo script è plug & play, ma ci sono 3 livelli di interazione (opzionali)
  34. #
  35. # ■ LIVELLO ALTO
  36. # Questo livello è adatto a tutti: comprende semplici metodi per gestire solo la
  37. # vibrazione del controller via eventi in modo semplificato.
  38. # Inoltre puoi ottenere le informazioni sugli analogici, grilletti e batteria
  39. # direttamente da delle variabili di gioco che vengono automaticamente
  40. # aggiornate (leggi la parte della configurazione dello script)
  41. # Puoi assegnare invece gli stati in questo modo: dalla finestra
  42. # degli eventi, selezionate il comando chiama script scrivendo queste righe:
  43. # ● start_vibration(forza) per far vibrare il controller (forza è un valore
  44. #   da 0 a 100). Esempio: start_vibration(50) farà vibrare a metà potenza.
  45. # ● start_vibration(forza_sinistra, forza_destra) per far vibrare il controller
  46. #   con forze diverse destra e sinistra
  47. # ● stop_vibration per fermare la vibrazione
  48. # ● controller_vibration(forza_sinistra, forza_destra, tempo) per far vibrare
  49. #   il controller per x frame determinati dal valore tempo.
  50. # ● controller_plugged_in? se messo in una condizione controlla se un pad
  51. #   è presente.
  52. #
  53. # ■ LIVELLO MEDIO
  54. # Questo livello è adatto a chi se ne intende un po' di script (ma non troppo).
  55. # Si basa sul controllo del modulo Input e richiamabile da qualsiasi posizione
  56. # È possibile utilizzare nuovi simboli per i tasti specifici del controller,
  57. # come DPAD_UP, PAD_Y, :PAD_START, PAD_A ecc... (trovi la lista più in basso)
  58. # nei metodi press? trigger? repeat?
  59. # inoltre questi metodi sono stati arricchiti da un nuovo parametro che consente
  60. # di scegliere quale controller verificare. Ad esempio:
  61. # Input.trigger?(:C, 1) verificherà se il tasto C è premuto sul secondo
  62. # controller.
  63. #                                * ATTENZIONE *
  64. # È possibile usare TUTTI i metodi sottostanti aggiungendo un ulteriore parametro
  65. # che specifica quale dei 4 controller scegliere (con valori da 0 a 3, dove 0
  66. # è il giocaore 1 e 3 il giocatore 4). Se non viene specificato, viene
  67. # automaticamente scelto il controller 1.
  68. # Esempio:
  69. # Input.press?(:LEFT) < controllerà se il tasto sinistra è premuto dal gioc. 1
  70. # Input.press?(:LEFT, 1) < controllerà se sinistra è premuto dal giocatore 2
  71. # Input.press?(:DPAD_LEFT) < controllerà se è stato premuto specificamente il
  72. #       pulsante sinistro del pad direzionale del controller del giocatore 1.
  73. #
  74. # ● Input.battery_level: restituisce il livello di batteria del controller.
  75. #   -1: senza batteria; 0: scarico, 1: basso, 2: medio, 3: carico
  76. #
  77. # ● Input.left_analog / Input.right_analog: restituiscono rispettivamente le
  78. #   coordinate X e Y degli analogici sinistro e destro come hash {:x => 0, :y => 0}
  79. #   Esempio:
  80. #   print Input.left_analog[:x] => se l'analogico è inclinato all'estrema destra,
  81. #   restituirà 32767
  82. #   I valori degli analogici variano da -32767 a 32767 sia per coordinata X che
  83. #   Y, questo significa che se l'analogico è dritto segnerà 0.
  84. #
  85. # ● Input.left_trigger / Input.right_trigger: restituiscono i valori dei
  86. #   grilletti sinistro e destro con un valore che varia da 0 (riposo) a 255
  87. #
  88. # ● Input.vibrate(sinistro, destro, frames)
  89. #   Fa vibrare il controller. Bisogna impostare la potenza dei motori sinistro
  90. #   e destro (valore da 0 a 100) e la durata in frames.
  91. # ● Input.start_vibration(forza): fa vibrare il controller in tempo indefinito
  92. # ● Input.stop_vibration: Interrompe la vibrazione del controller
  93. #
  94. # ● Input.user_control: restituisce l'ultimo tipo di controllo usato come:
  95. #   :controller, significa che è stato usato un controller
  96. #   :legacy, significa che il giocatore sta usando la tastira o un vecchio pad
  97. #   compatibile Direct 2D (i vecchi controller senza analogico).
  98. #
  99. # ■ LIVELLO BASSO
  100. # Si tratta della comunicazione al livello più basso del controller, dove ricevi
  101. # i dati RAW del gamepad. Se sai gestire questo livello, probabilmente non hai
  102. # neanche bisogno di questa documentazione in quanto ti basterà guardare le
  103. # descrizioni dei metodi contenute negli script.
  104. # ● XInput.get_state restituisce una classe rappresentante l'istanziazione della
  105. #   struttura dello stato del controller, ossia XInput_State con i seguenti
  106. #   attributi (o nil se non è collegato alcun controller):
  107. #   packet_number restituisce il numero del pacchetto. Il numero differisce
  108. #   dallo stato del controller, se non è cambiato allora lo stato  del
  109. #   controller non è cambiato.
  110. #   game_pad restituisce lo stato dei pulsanti come classe Game_Pad ed ha i
  111. #   seguenti metodi e attributi:
  112. #   buttons restituisce un intero indicante i pulsanti premuti. Si tratta di un
  113. #   intero a 16 bit dove ogni bit rappresenta lo stato di un pulsante. Ad
  114. #   esempio, 2 in binario corrisponde a 0000000000000010, il secondo bit a
  115. #   1 indica che è premuto il tasto giù del D-PAD.
  116. #   Altro esempio: 6 in binario corrisponde a 0000000000000110, il secondo bit
  117. #   è sempre il tasto giù mentre il terzo è il tasto sinistra: il giocatore sta
  118. #   premendo giù e sinistra contemporaneamente. Per evitare di impazzire, puoi
  119. #   utilizzare il metodo 'keymap_state' per ottenere un hash con tutti i pulsanti
  120. #   premuti (le chiavi dell'hash sono i pulsanti, il valore è true se sono
  121. #   normali pulsanti e intero se sono analogici o grilletti rappresentanti il
  122. #       loro valore)
  123. #   Puoi anche usare il metodo button_pressed?(costante) per controllare se
  124. #   un determinato pulsante, rappresentato da una costante definita in basso,
  125. #   è premuto. Alcune costanti: GAMEPAD_LEFT_SHOULDER, GAMEPAD_A, GAMEPAD_BACK
  126. #   Esempio d'uso:
  127. #       XInput.get_state.game_pad.button_pressed?(XInput::PAD_X)
  128. #           restituisce true se il tasto X del controller è premuto
  129. #       XInput.get_state.keymap_state.keys
  130. #           restituisce l'array dei pulsanti premuti, es. [:DPAD_UP, :LEFT_SHOULDER]
  131. #
  132. # ● XInput.get_battery_info: restituisce le informazioni sulla batteria come
  133. #           oggetto XInput_BatteryInformation che ha 2 attributi:
  134. #           battery_type restituisce il tipo di batteria, che può essere
  135. #           BATTERY_TYPE_WIRED se il controller è a cavo (no wireless)
  136. #         BATTERY_TYPE_ALKALINE se alimentato con pile alcaline (le classiche stilo)
  137. #         BATTERY_TYPE_NIMH se alimentato con batteria ricaricabile al litio
  138. #         BATTERY_TYPE_UNKNOWN se la batteria è sconosciuta.
  139. #           Queste costanti rappresentano rispettivamente i valori 1, 2, 3 e 4.
  140. #           battery_level restituisce il livello di carica, che può essere
  141. #           BATTERY_LEVEL_EMPTY se il controller è scarico
  142. #       BATTERY_LEVEL_LOW se la batteria è quasi scarica
  143. #       BATTERY_LEVEL_MEDIUM se la batteria è sul livello medio
  144. #       BATTERY_LEVEL_FULL se la batteria è carica.
  145. #           Queste costanti rappresentano rispettivamente i valori 0, 1, 2 e 3.
  146. #
  147. # ● XInput.set_vibration(forza_sinistra, forza_destra) fa vibrare il controller.
  148. #           Imposta la forza a 0 per farlo smettere. Il valore forza va da 0 a 65535
  149. #
  150. #       Deadzone: Per evitare che imprecisioni sul pad facciano risultare analogici e
  151. #       grilletti come premuti/mossi, è stata predisposta una "zona morta"
  152. #       che impone una quantità minima di spostamento per specificare quando un
  153. #       analogico è spostato rispetto al centro o quando il grilletto è premuto,
  154. #       secondo le linee guida delle DirectX. Puoi modificare queste deadzone a
  155. #   piacimento modificando le costanti LEFT_THUMB_DEADZONE, RIGHT_THUMB_DEADZONE
  156. #   e TRIGGER_THRESHOLD.
  157. #
  158. # ■ IMPOSTAZIONI GIOCATORE
  159. # È possibile definire le impostazioni del controller del giocatore che sono
  160. # memorizzate in $game_system.
  161. # ● xinput_key_set: restituisce l'hash contenenti le impostazioni della mappatura
  162. #   dei pulsanti (inizialmente è come definito in DEFAULT_KEY_SET). Puoi anche
  163. #   personalizzare i pulsanti, ad esempio
  164. #   $game_system.ximput_key_set[:L] = :LEFT_THUMB imposterà la funzione L al tasto
  165. #   L3 del controller.
  166. # ● vibration_enabled? restituisce se la vibrazione è attiva
  167. # ● set_vibration_enabled(valore) imposta la funzione di vibrazione
  168. # ● set_vibration_rate(valore) imposta la potenza della vibrazione con un valore
  169. #   da 0 a 100
  170. # Nota: queste impostazioni non valgono se si usa direttamente XInput, bisogna
  171. #   usare i comandi evento o il modulo Input.
  172. #===============================================================================
  173.  
  174.  
  175. #===============================================================================
  176. # ** XInput_Settings
  177. #-------------------------------------------------------------------------------
  178. # Settings section
  179. #===============================================================================
  180. module XInput_Settings
  181.   DEFAULT_KEY_SET = {
  182.       :UP     => :DPAD_UP,
  183.       :DOWN   => :DPAD_DOWN,
  184.       :LEFT   => :DPAD_LEFT,
  185.       :RIGHT  => :DPAD_RIGHT,
  186.       :START  => :PAD_START,    #not really used by RPG Maker
  187.       :SELECT => :PAD_BACK,     #not used too
  188.       :L      => :LEFT_SHOULDER,
  189.       :R      => :RIGHT_SHOULDER,
  190.       :A      => :PAD_Y,
  191.       :B      => :PAD_B,
  192.       :C      => :PAD_A,
  193.       :X      => :PAD_X,
  194.       :Y      => :LEFT_THUMB,
  195.       :Z      => :RIGHT_THUMB
  196.   }
  197.  
  198.   VOCABS = {
  199.       :DPAD_UP        => 'D Su',
  200.       :DPAD_DOWN      => 'D Giù',
  201.       :DPAD_LEFT      => 'D Sinistra',
  202.       :DPAD_RIGHT     => 'D Destra',
  203.       :PAD_START      => 'Start',
  204.       :PAD_BACK       => 'Indietro/Select',
  205.       :LEFT_SHOULDER  => 'Dorsale sinistro',
  206.       :RIGHT_SHOULDER => 'Dorsale destro',
  207.       :PAD_A          => 'A',
  208.       :PAD_B          => 'B',
  209.       :LEFT_THUMB     => 'Levetta sinistra',
  210.       :PAD_X          => 'X',
  211.       :PAD_Y          => 'Y',
  212.       :RIGHT_THUMB    => 'Levetta destra',
  213.       :R_TRIG         => 'Grilletto destro',
  214.       :L_TRIG         => 'Grilletto sinistro',
  215.       :L_AXIS_X       => 'Analogico sinistro (asse X)',
  216.       :L_AXIS_Y       => 'Analogico sinistro (asse Y)',
  217.       :R_AXIS_X       => 'Analogico destro (asse X)',
  218.       :R_AXIS_Y       => 'Analogico destro (asse Y)',
  219.       :L_AXIS_LEFT      => 'Analogico a sinistra',
  220.       :L_AXIS_RIGHT     => 'Analogico a destra',
  221.       :L_AXIS_UP            => 'Analogico su',
  222.       :L_AXIS_DOWN      => 'Analogico giù',
  223.       :R_AXIS_LEFT      => 'Analogico destro a sinistra',
  224.       :R_AXIS_RIGHT     => 'Analogico destro a destra',
  225.       :R_AXIS_UP            => 'Analogico destro su',
  226.       :R_AXIS_DOWN      => 'Analogico destro giù',
  227.   }
  228.  
  229.   # Sistema di memorizzazione in variabili e switch. Imposta
  230.   # la costante sotto come true per fare in modo che lo stato
  231.   # degli analogici, grilletti e batteria vengano memorizzati
  232.   # in variabili, lascia false se non vuoi usarli.
  233.   VARIABLE_SYSTEM = false
  234.   # Variabili e switch dove leggere lo stato del controller.
  235.   LEFT_TRIGGER_VAR  = 110 # variabile valore grilletto sinistro
  236.   RIGHT_TRIGGER_VAR = 111 # variabile valore grilletto destro
  237.   LEFT_AXIS_X_VAR   = 112 # variabile valore analog. sinistro X
  238.   LEFT_AXIS_Y_VAR   = 113 # variabile valore analog. sinistro Y
  239.   RIGHT_AXIS_X_VAR  = 114 # variabile valore analog. destro X
  240.   RIGHT_AXIS_Y_VAR  = 115 # variabile valore analog. destro Y
  241.   # Livello batteria: -1 se non c'è (perché con filo), 0 scarica
  242.   # 1 bassa, 2 media e 3 piena.
  243.   BATTERY_LEVEL     = 116 # variabile livello della batteria
  244.   # Connessione PAD: questo switch sarà ON se un pad è conesso
  245.   PLUGGED_SW        = 110 # switch di stato di connessione del pad
  246.  
  247.     # Quanto bisogna inclinare l'analogico per fargli riconoscere una direzione
  248.   # in genere questo parametro viene definito zona morta
  249.     ANALOG_DIRECTION_MIN = 16300 # max 32767
  250. end
  251.  
  252. # ---------ATTENZIONE: MODIFICARE SOTTO QUESTO PARAGRAFO COMPORTA SERI RISCHI
  253. #           PER IL CORRETTO FUNZIONAMENTO DELLO SCRIPT! -------------
  254.  
  255.  
  256.  
  257. $imported = {} if $imported == nil
  258. $imported['H87-XInput'] = 1.0
  259. unless $imported['H87_UniversalModule']
  260.   raise('Questo script richiede il modulo universale di Holy87.')
  261. end
  262. #===============================================================================
  263. # ** XInput
  264. #-------------------------------------------------------------------------------
  265. # Core module for controller connection
  266. #===============================================================================
  267. module XInput
  268.   XINPUT_FLAG_GAMEPAD     = 0x01
  269.   #--------------------------------------------------------------------------
  270.   # * Battery constants
  271.   #--------------------------------------------------------------------------
  272.   BATTERY_DEVTYPE_GAMEPAD = 0x00
  273.   BATTERY_TYPE_WIRED      = 0x01
  274.   BATTERY_TYPE_ALKALINE   = 0x02
  275.   BATTERY_TYPE_NIMH       = 0x03
  276.   BATTERY_TYPE_UNKNOWN    = 0xFF
  277.   BATTERY_LEVEL_EMPTY     = 0x00
  278.   BATTERY_LEVEL_LOW       = 0x01
  279.   BATTERY_LEVEL_MEDIUM    = 0x02
  280.   BATTERY_LEVEL_FULL      = 0x03
  281.   #--------------------------------------------------------------------------
  282.   # * Button constants
  283.   #--------------------------------------------------------------------------
  284.   GAMEPAD_DPAD_UP         = 0x0001
  285.   GAMEPAD_DPAD_DOWN       = 0x0002
  286.   GAMEPAD_DPAD_LEFT       = 0x0004
  287.   GAMEPAD_DPAD_RIGHT      = 0x0008
  288.   GAMEPAD_START           = 0x0010
  289.   GAMEPAD_BACK            = 0x0020
  290.   GAMEPAD_LEFT_THUMB      = 0x0040
  291.   GAMEPAD_RIGHT_THUMB     = 0x0080
  292.   GAMEPAD_LEFT_SHOULDER   = 0x0100
  293.   GAMEPAD_RIGHT_SHOULDER  = 0x0200
  294.   GAMEPAD_A               = 0x1000
  295.   GAMEPAD_B               = 0x2000
  296.   GAMEPAD_X               = 0x4000
  297.   GAMEPAD_Y               = 0x8000
  298.   #--------------------------------------------------------------------------
  299.   # * Deadzones
  300.   #--------------------------------------------------------------------------
  301.   LEFT_THUMB_DEADZONE     = 7849
  302.   RIGHT_THUMB_DEADZONE    = 8689
  303.   TRIGGER_THRESHOLD       = 30
  304.   #--------------------------------------------------------------------------
  305.   # * Error states
  306.   #--------------------------------------------------------------------------
  307.   ERROR_SUCCESS           = 0
  308.   ERROR_DEVICE_NOT_CONNECTED = 1167
  309.   DEVICE_NOT_GAMEPAD      = 538976288
  310.   #--------------------------------------------------------------------------
  311.   # * Supported keys
  312.   #--------------------------------------------------------------------------
  313.   GAMEPAD_KEYS = {
  314.       :DPAD_UP            => GAMEPAD_DPAD_UP,
  315.       :DPAD_DOWN          => GAMEPAD_DPAD_DOWN,
  316.       :DPAD_LEFT          => GAMEPAD_DPAD_LEFT,
  317.       :DPAD_RIGHT         => GAMEPAD_DPAD_RIGHT,
  318.       :PAD_START          => GAMEPAD_START,
  319.       :PAD_BACK           => GAMEPAD_BACK,
  320.       :LEFT_THUMB         => GAMEPAD_LEFT_THUMB,
  321.       :RIGHT_THUMB        => GAMEPAD_RIGHT_THUMB,
  322.       :RIGHT_SHOULDER     => GAMEPAD_RIGHT_SHOULDER,
  323.       :LEFT_SHOULDER      => GAMEPAD_LEFT_SHOULDER,
  324.       :PAD_A              => GAMEPAD_A,
  325.       :PAD_B              => GAMEPAD_B,
  326.       :PAD_X              => GAMEPAD_X,
  327.       :PAD_Y              => GAMEPAD_Y}
  328.   #--------------------------------------------------------------------------
  329.   # * Tries to load DirectX11 (Windows 7 or above)
  330.   #--------------------------------------------------------------------------
  331.   def self.try_load_dx11
  332.     begin
  333.       @x_get = Win32API.new('Xinput1_4', 'XInputGetState', 'IP', 'V')
  334.       @x_set = Win32API.new('Xinput1_4', 'XInputSetState', 'IP', 'L')
  335.       @x_cap = Win32API.new('Xinput1_4', 'XInputGetCapabilities','IIP', 'I')
  336.       @x_gbi = Win32API.new('Xinput1_4', 'XInputGetBatteryInformation', 'ILP', 'I')
  337.       @directx = 11
  338.       true
  339.     rescue
  340.       puts('DirectX 11 not installed, can\'t get battery info')
  341.       false
  342.     end
  343.   end
  344.   #--------------------------------------------------------------------------
  345.   # * Tries to load DirectX10 (Windows Vista or above)
  346.   #--------------------------------------------------------------------------
  347.   def self.try_load_dx10
  348.     begin
  349.       @x_get = Win32API.new('XINPUT9_1_0', 'XInputGetState', 'IP', 'V')
  350.       @x_set = Win32API.new('XINPUT9_1_0', 'XInputSetState', 'IP', 'L')
  351.       @x_cap = Win32API.new('XINPUT9_1_0', 'XInputGetCapabilities','IIP', 'I')
  352.       @directx = 10
  353.       true
  354.     rescue
  355.       puts('DirectX10 not installed, can\'t use XInput module.')
  356.       false
  357.     end
  358.   end
  359.   #--------------------------------------------------------------------------
  360.   # * Simply does nothing
  361.   #--------------------------------------------------------------------------
  362.   def self.try_load_dx09; @directx = 9; end
  363.   #--------------------------------------------------------------------------
  364.   # * Loads the proper library
  365.   #--------------------------------------------------------------------------
  366.   def self.load_libraries
  367.     return if try_load_dx11
  368.     return if try_load_dx10
  369.     try_load_dx09
  370.   end
  371.   #--------------------------------------------------------------------------
  372.   # * Gets the controller keys state
  373.   # @param [Index] index
  374.   # @return [XInput_State]
  375.   #--------------------------------------------------------------------------
  376.   def self.get_state(index = 0)
  377.     return nil if @x_get.nil?
  378.     buffer = ' ' * 16
  379.     error = @x_get.call(index, buffer)
  380.     error == ERROR_SUCCESS ? XInput_State.new(buffer) : nil
  381.   end
  382.   #--------------------------------------------------------------------------
  383.   # * Gets the hash containing all the pressed keys
  384.   # @param [Integer] index
  385.   # @return [Hash]
  386.   #--------------------------------------------------------------------------
  387.   def self.get_key_state(index = 0)
  388.     state = get_state(index)
  389.     state != nil ? state.game_pad.keymap_state : {}
  390.   end
  391.   #--------------------------------------------------------------------------
  392.   # * Sets the controller vibration
  393.   # @param [Integer] l_strenght     value between 0 and 65535
  394.   # @param [Integer] r_strenght     value between 0 and 65535
  395.   # @param [Integer] index          controller index
  396.   # @return [Integer]               ERROR_SUCCESS/ERROR_DEVICE_NOT_CONNECTED
  397.   #--------------------------------------------------------------------------
  398.   def self.set_vibration(l_strenght, r_strenght, index = 0)
  399.     return ERROR_DEVICE_NOT_CONNECTED if @x_set.nil?
  400.     l_strenght = [l_strenght, 65535].min
  401.     r_strenght = [r_strenght, 65535].min
  402.     @x_set.call(index, [l_strenght, r_strenght].pack('SS'))
  403.   end
  404.   #--------------------------------------------------------------------------
  405.   # * Returns if the controller is plugged in
  406.   # @param [Integer] controller_index
  407.   #--------------------------------------------------------------------------
  408.   def self.controller_plugged_in?(controller_index = 0)
  409.     get_state(controller_index) != nil
  410.   end
  411.   #--------------------------------------------------------------------------
  412.   # * Gets the battery information
  413.   # @param [Integer] index
  414.   # @return [XInput_BatteryInformation]
  415.   #--------------------------------------------------------------------------
  416.   def self.get_battery_info(index = 0)
  417.     return if @x_gbi.nil?
  418.     buffer = ' ' * 8
  419.     result = @x_gbi.call(index, BATTERY_DEVTYPE_GAMEPAD, buffer)
  420.     result == ERROR_SUCCESS ? XInput_BatteryInformation.new(buffer) : nil
  421.   end
  422.     #--------------------------------------------------------------------------
  423.   # * Returns the default key set
  424.   #--------------------------------------------------------------------------
  425.     def self.default_key_set; XInput_Settings::DEFAULT_KEY_SET.clone; end
  426.   #--------------------------------------------------------------------------
  427.   # * Returns the controller capabilities
  428.   # @param [XInput_Capability] index
  429.   #--------------------------------------------------------------------------
  430.   def self.controller_capabilities(index = 0)
  431.     return if @x_cap.nil?
  432.     buffer = ' ' * 18
  433.     @x_cap.call(index, XINPUT_FLAG_GAMEPAD, buffer)
  434.     XInput_Capability.new(buffer)
  435.   end
  436.   #--------------------------------------------------------------------------
  437.   # * Checks if in your PC is installed DX10 or above
  438.   #--------------------------------------------------------------------------
  439.   def self.directx_capable?; @directx >= 10; end
  440. end # xinput
  441.  
  442. #===============================================================================
  443. # ** Vocab
  444. #-------------------------------------------------------------------------------
  445. # Gamepad keys vocabs
  446. #===============================================================================
  447. module Vocab
  448.   #--------------------------------------------------------------------------
  449.   # * Gamepad key vocab
  450.   # @param [Symbol] key
  451.   #--------------------------------------------------------------------------
  452.   def self.gamepad_key(key)
  453.     XInput_Settings::VOCABS[key]
  454.   end
  455. end # vocab
  456.  
  457. #===============================================================================
  458. # ** XInput_State
  459. #-------------------------------------------------------------------------------
  460. # Controller state
  461. #===============================================================================
  462. class XInput_State
  463.   attr_reader :packet_number
  464.   #--------------------------------------------------------------------------
  465.   # * Object initializazion
  466.   # @param [String] input_data
  467.   #--------------------------------------------------------------------------
  468.   def initialize(input_data)
  469.     inp = input_data.unpack('LSCCssss')
  470.     @packet_number = inp[0]
  471.         keys = inp[1]
  472.         tl = inp[2]; tr = inp[3]
  473.     lx = inp[4]; ly = inp[5]
  474.     rx = inp[6]; ry = inp[7]
  475.     @game_pad = Game_Pad.new(keys, tl, tr, lx.to_i, ly.to_i, rx.to_i, ry.to_i)
  476.   end
  477.   #--------------------------------------------------------------------------
  478.   # * Returns the game pad status
  479.   # @return [Game_Pad]
  480.   #--------------------------------------------------------------------------
  481.   def game_pad; @game_pad; end
  482. end
  483.  
  484. #===============================================================================
  485. # ** XInput_BatteryInformation
  486. #-------------------------------------------------------------------------------
  487. # Battery information container
  488. #===============================================================================
  489. class XInput_BatteryInformation
  490.   attr_reader :battery_type   # 1: Wired, 2: Alkhaline, 3: Nimh, 4: Unknown
  491.   attr_reader :battery_level  # 0: Empy,  1: Low, 2: Medium, 3: High
  492.   #--------------------------------------------------------------------------
  493.   # * Object initialization
  494.   # @param [String] buffer
  495.   #--------------------------------------------------------------------------
  496.   def initialize(buffer)
  497.     result = buffer.unpack('CC')
  498.     @battery_type = result[0]
  499.     @battery_level = result[1]
  500.   end
  501.   #--------------------------------------------------------------------------
  502.   # * Gets if battery level is low
  503.   #--------------------------------------------------------------------------
  504.   def battery_low?
  505.     wireless? && @battery_level <= XInput::BATTERY_LEVEL_LOW
  506.   end
  507.   #--------------------------------------------------------------------------
  508.   # * Gets if the controller is wireless
  509.   #--------------------------------------------------------------------------
  510.   def wireless?
  511.     @battery_type == XInput::BATTERY_TYPE_ALKALINE ||
  512.       @battery_type == XInput::BATTERY_TYPE_NIMH
  513.   end
  514.   #--------------------------------------------------------------------------
  515.   # * Gets if the controller is wired
  516.   #--------------------------------------------------------------------------
  517.   def wired?
  518.     @battery_type == XInput::BATTERY_TYPE_WIRED
  519.   end
  520.   #--------------------------------------------------------------------------
  521.   # * To String (for screen printable)
  522.   #--------------------------------------------------------------------------
  523.   def to_s
  524.     case @battery_type
  525.       when XInput::BATTERY_TYPE_ALKALINE
  526.         type = 'Alkaline'
  527.       when XInput::BATTERY_TYPE_WIRED
  528.         type = 'Wired'
  529.       when XInput::BATTERY_TYPE_NIMH
  530.         type = 'Nimh'
  531.       else
  532.         type = 'Unknown'
  533.     end
  534.     case @battery_level
  535.       when XInput::BATTERY_LEVEL_EMPTY
  536.         level = 'Empty'
  537.       when XInput::BATTERY_LEVEL_LOW
  538.         level = 'Low'
  539.       when XInput::BATTERY_LEVEL_MEDIUM
  540.         level = 'Medium'
  541.       when XInput::BATTERY_LEVEL_FULL
  542.         level = 'Full'
  543.       else
  544.         level = 'Unknown'
  545.     end
  546.     sprintf('Type: %s, Level: %s', type, level)
  547.   end
  548. end
  549.  
  550. #===============================================================================
  551. # ** XInput_Capability
  552. #-------------------------------------------------------------------------------
  553. # Contains informations about the connected controller.
  554. #===============================================================================
  555. class XInput_Capability
  556.   # @attr[Integer] type
  557.   # @attr[Integer] sub_yupe
  558.   # @attr[Integer] flags
  559.   attr_reader :type # XINPUT_DEVTYPE_GAMEPAD
  560.   attr_reader :sub_type
  561.   attr_reader :flags
  562.   #--------------------------------------------------------------------------
  563.   # * Object initializazion
  564.   # @param [String] buffer
  565.   #--------------------------------------------------------------------------
  566.   def initialize(buffer)
  567.     data = buffer.unpack('CCSSCCssssCC')
  568.     @type = data[0]
  569.     @sub_type = data[1]
  570.     @flags = data[2]
  571.     @game_pad = Game_Pad.new(data[3], data[4], data[5], data[6], data[7], data[8], data[9])
  572.     @vibration = XInput_Vibration.new(data[10], data[11])
  573.   end
  574.   #--------------------------------------------------------------------------
  575.   # * Returns the game pad status
  576.   # @return [Game_Pad]
  577.   #--------------------------------------------------------------------------
  578.   def game_pad; @game_pad; end
  579.   #--------------------------------------------------------------------------
  580.   # * Returns the game pad status
  581.   # @return [XInput_Vibration]
  582.   #--------------------------------------------------------------------------
  583.   def vibration; @vibration; end
  584. end #xinput_capability
  585.  
  586. #===============================================================================
  587. # ** Game_Pad
  588. #-------------------------------------------------------------------------------
  589. # Gamepad keys structure
  590. #===============================================================================
  591. class Game_Pad
  592.   # @attr[Integer] buttons
  593.   # @attr[Integer] left_trigger
  594.   # @attr[Integer] right_trigger
  595.   # @attr[Integer] thumb_lx
  596.   # @attr[Integer] thumb_ly
  597.   # @attr[Integer] thumb_rx
  598.   # @attr[Integer] thumb_ry
  599.   attr_reader :buttons        # buttons pressed in integer value
  600.   attr_reader :left_trigger   # LT key, value from 0 to 255
  601.   attr_reader :right_trigger  # RT key, value from 0 to 255
  602.   attr_reader :thumb_lx       # left analog X, value between -32768 and 32767
  603.   attr_reader :thumb_ly       # left analog Y, value between -32768 and 32767
  604.   attr_reader :thumb_rx       # right analog X, value between -32768 and 32767
  605.   attr_reader :thumb_ry       # right analog Y, value between -32768 and 32767
  606.   #--------------------------------------------------------------------------
  607.   # * Object initialization
  608.   # @param [String] buttons     integer with buttons pressed
  609.   # @param [Integer] lt         left trigger value (0 to 255)
  610.   # @param [Integer] rt         right trigger value (0 to 255)
  611.   # @param [Integer] lx         left stick x axis (-32768 to 32767)
  612.   # @param [Integer] ly         left stick y axis (-32768 to 32767)
  613.   # @param [Integer] rx         right stick x axis (-32768 to 32767)
  614.   # @param [Integer] ry         right stick y axis (-32768 to 32767)
  615.   #--------------------------------------------------------------------------
  616.   def initialize(buttons, lt, rt, lx, ly, rx, ry)
  617.     @buttons = buttons
  618.     @left_trigger = adjust_trigger(lt, XInput::TRIGGER_THRESHOLD)
  619.     @right_trigger = adjust_trigger(rt, XInput::TRIGGER_THRESHOLD)
  620.     left = normalize(lx, ly, XInput::LEFT_THUMB_DEADZONE)
  621.     right = normalize(rx, ry, XInput::RIGHT_THUMB_DEADZONE)
  622.     @thumb_lx = (lx * left).to_i
  623.     @thumb_ly = (ly * -left).to_i
  624.     @thumb_rx = (rx * right).to_i
  625.     @thumb_ry = (ry * -right).to_i
  626.   end
  627.   #--------------------------------------------------------------------------
  628.   # * Returns true if the pad button is pressed
  629.   # @param [Integer] button_const (integer value)
  630.   # @return [Boolean]
  631.   #--------------------------------------------------------------------------
  632.   def button_pressed?(button_const)
  633.     @buttons | button_const == @buttons # or for bit comparator
  634.   end
  635.   #--------------------------------------------------------------------------
  636.   # * Gets a keymap state with (true/false) if buttons, values if analog.
  637.   # @return [Hash]
  638.   #--------------------------------------------------------------------------
  639.   def keymap_state
  640.     if @keymap_state.nil?
  641.       @keymap_state = {}
  642.       XInput::GAMEPAD_KEYS.each_pair {|key, value|
  643.         @keymap_state[key] = true if button_pressed?(value)
  644.       }
  645.       @keymap_state[:L_AXIS_X] = @thumb_lx if @thumb_lx != 0
  646.       @keymap_state[:L_AXIS_Y] = @thumb_ly if @thumb_ly != 0
  647.       @keymap_state[:R_AXIS_X] = @thumb_rx if @thumb_rx != 0
  648.       @keymap_state[:R_AXIS_Y] = @thumb_ry if @thumb_ry != 0
  649.       @keymap_state[:R_TRIG]   = @right_trigger if @right_trigger > 0
  650.       @keymap_state[:L_TRIG]   = @left_trigger if @left_trigger > 0
  651.             min = XInput_Settings::ANALOG_DIRECTION_MIN
  652.             if @keymap_state[:L_AXIS_X]
  653.                 @keymap_state[:L_AXIS_RIGHT] = true if @keymap_state[:L_AXIS_X] > min
  654.                 @keymap_state[:L_AXIS_LEFT] = true if @keymap_state[:L_AXIS_X] < -min
  655.             end
  656.             if @keymap_state[:L_AXIS_Y]
  657.                 @keymap_state[:L_AXIS_DOWN] = true if @keymap_state[:L_AXIS_Y] > min
  658.                 @keymap_state[:L_AXIS_UP] = true if @keymap_state[:L_AXIS_Y] < -min
  659.             end
  660.             if @keymap_state[:R_AXIS_X]
  661.                 @keymap_state[:R_AXIS_RIGHT] = true if @keymap_state[:R_AXIS_X] > min
  662.                 @keymap_state[:R_AXIS_LEFT] = true if @keymap_state[:R_AXIS_X] < -min
  663.             end
  664.             if @keymap_state[:R_AXIS_Y]
  665.                 @keymap_state[:R_AXIS_DOWN] = true if @keymap_state[:R_AXIS_Y] > min
  666.                 @keymap_state[:R_AXIS_UP] = true if @keymap_state[:R_AXIS_Y] < -min
  667.             end
  668.     end
  669.     @keymap_state
  670.   end
  671.   #--------------------------------------------------------------------------
  672.   # * Checks if the analog stick is over the dead zone
  673.   # @param [Integer] x
  674.   # @param [Integer] y
  675.   # @param [Integer] deadzone
  676.   #--------------------------------------------------------------------------
  677.   def normalize(x, y, deadzone)
  678.     magnitude = Math.sqrt(x*x + y*y)
  679.     if magnitude > deadzone
  680.       magnitude = [magnitude, 32767].min
  681.       magnitude -= deadzone
  682.       normalized_magnitude = magnitude / (32767 - deadzone)
  683.     else
  684.       normalized_magnitude = 0
  685.     end
  686.     normalized_magnitude
  687.   end
  688.   #--------------------------------------------------------------------------
  689.   # * Checks if the trigger is over the dead zone
  690.   # @param [Integer] value
  691.   # @param [Integer] threshold
  692.   #--------------------------------------------------------------------------
  693.   def adjust_trigger(value, threshold)
  694.     return 0 if value <= threshold
  695.     magnitude = 255 / (255 - threshold)
  696.     ((value - threshold) * magnitude).to_i
  697.   end
  698.   #--------------------------------------------------------------------------
  699.   # * To string
  700.   # @return [String]
  701.   #--------------------------------------------------------------------------
  702.   def to_s; keymap_state.to_s; end
  703. end
  704.  
  705. #===============================================================================
  706. # ** XInput_Vibration
  707. #-------------------------------------------------------------------------------
  708. # Contains informations about the controller motors. If left and right values
  709. # are 0, the controller doesn not support vibration.
  710. #===============================================================================
  711. class XInput_Vibration
  712.   attr_reader :left_motor_speed   # left motor speed. 0 to 65535
  713.   attr_reader :right_motor_speed  # right motor speed. 0 to 65535
  714.   #--------------------------------------------------------------------------
  715.   # * Object initialization
  716.   # @param [Integer] left_m
  717.   # @param [Integer] right_m
  718.   #--------------------------------------------------------------------------
  719.   def initialize(left_m, right_m)
  720.     @left_motor_speed = left_m
  721.     @right_motor_speed = right_m
  722.   end
  723. end
  724.  
  725. #===============================================================================
  726. # ** Game_System
  727. #-------------------------------------------------------------------------------
  728. # Controller settings container
  729. #===============================================================================
  730. class Game_System
  731.   #--------------------------------------------------------------------------
  732.   # * Custom key set
  733.   # @param [Integer] controller_index
  734.   # @return [Hash]
  735.   #--------------------------------------------------------------------------
  736.   def xinput_key_set(controller_index = 0)
  737.     @xinput_key_set ||= create_default_key_set
  738.     @xinput_key_set[controller_index]
  739.   end
  740.   #--------------------------------------------------------------------------
  741.   # * Checks if the vibration is enabled
  742.   # @param [Integer] controller_index
  743.   #--------------------------------------------------------------------------
  744.   def vibration_enabled?(controller_index = 0)
  745.     @xinput_vibration ||= {}
  746.     @xinput_vibration[controller_index] ||= true
  747.   end
  748.   #--------------------------------------------------------------------------
  749.   # * Sets the vibration enable option
  750.   # @param [Boolean] value
  751.   # @param [Integer] controller_index
  752.   #--------------------------------------------------------------------------
  753.   def set_vibration_enabled(value, controller_index = 0)
  754.     @xinput_vibration ||= {}
  755.     @xinput_vibration[controller_index] = value
  756.   end
  757.   #--------------------------------------------------------------------------
  758.   # * Keys conversion (for user key settings)
  759.   # @param [Symbol] original_key
  760.   # @param [Integer] controller_index
  761.   #--------------------------------------------------------------------------
  762.   def adjust_buttons(original_key, controller_index = 0)
  763.     if xinput_key_set(controller_index).include?(original_key)
  764.       xinput_key_set(controller_index)[original_key]
  765.     else
  766.       original_key
  767.     end
  768.   end
  769.   #--------------------------------------------------------------------------
  770.   # * Default key set initialization (from script settings)
  771.   #--------------------------------------------------------------------------
  772.   def create_default_key_set
  773.     @xinput_key_set = {}
  774.     (0..3).each {|pad_index|
  775.       @xinput_key_set[pad_index] = XInput.default_key_set
  776.     }
  777.     @xinput_key_set
  778.   end
  779.   #--------------------------------------------------------------------------
  780.   # * gets the vibration power settings
  781.   #--------------------------------------------------------------------------
  782.   def vibration_rate(pad_index = 0)
  783.     @vibration_rate ||= [100] * 4
  784.     @vibration_rate[pad_index]
  785.   end
  786.   #--------------------------------------------------------------------------
  787.   # * Sets the vibration power setting
  788.   # @param [Integer] rate
  789.   # @param [Integer] pad_index
  790.   #--------------------------------------------------------------------------
  791.   def set_vibration_rate(rate, pad_index = 0)
  792.     @vibration_rate ||= [100] * 4
  793.     @vibration_rate[pad_index] = [[0, rate].max, 100].min
  794.   end
  795.     #--------------------------------------------------------------------------
  796.   # * Gets the vibration power
  797.   # @param [Integer] pad_index
  798.   # @return [Integer]
  799.   #--------------------------------------------------------------------------
  800.   def calc_vibration_power(pad_index = 0)
  801.     65535 * vibration_rate(pad_index) / 100
  802.     end
  803. end # game_system
  804.  
  805. #===============================================================================
  806. # ** Input
  807. #-------------------------------------------------------------------------------
  808. # Input redefinition
  809. #===============================================================================
  810. module Input
  811.   # input normalization from conditional branch fix
  812.   NORMALIZER = {2 => :DOWN, 4 => :LEFT, 6 => :RIGHT, 8 => :UP, 11 => :A,
  813.   12 => :B, 13 => :C, 14 => :X, 15 => :Y, 16 => :Z, 17 => :L, 18 => :R}
  814.   #--------------------------------------------------------------------------
  815.   # * Variable initialization
  816.   #--------------------------------------------------------------------------
  817.   @key_timing = {0 => {}, 1 => {}, 2 => {}, 3 => {}}
  818.   @key_state = {0 => {}, 1 => {}, 2 => {}, 3 => {}}
  819.   @controller_plugged = [false] * 4
  820.   @vibration_state = [0] * 4
  821.   #---------------- ----------------------------------------------------------
  822.   # * Method aliases
  823.   #--------------------------------------------------------------------------
  824.   # noinspection ALL
  825.   class << self
  826.     alias h87controller_update update
  827.     alias legacy_trigger? trigger?
  828.     alias legacy_press? press?
  829.     alias legacy_repeat? repeat?
  830.   end
  831.   #--------------------------------------------------------------------------
  832.   # * Update process
  833.   #--------------------------------------------------------------------------
  834.   def self.update
  835.     h87controller_update
  836.     update_xinput
  837.   end
  838.   #--------------------------------------------------------------------------
  839.   # * Game pad updating process
  840.   #--------------------------------------------------------------------------
  841.   def self.update_xinput
  842.     update_keystate
  843.     update_controller_used
  844.     update_vibration
  845.   end
  846.   #--------------------------------------------------------------------------
  847.   # * Returns the controller connection state
  848.   # @param [Integer] pad_index
  849.   # @return [Boolean]
  850.   #--------------------------------------------------------------------------
  851.   def self.controller_connected?(pad_index = 0)
  852.     @controller_plugged[pad_index]
  853.   end
  854.   #--------------------------------------------------------------------------
  855.   # * Keydown
  856.   #--------------------------------------------------------------------------
  857.   def self.trigger?(key, controller_index = 0)
  858.     if controller_used?(controller_index)
  859.       @last_input_used = :controller
  860.       real_key = adjust_button(key, controller_index)
  861.       timing = @key_timing[controller_index][real_key]
  862.       timing == 0
  863.     else
  864.       result = legacy_trigger?(key)
  865.       @last_input_used = :legacy if result
  866.       result
  867.     end
  868.   end
  869.   #--------------------------------------------------------------------------
  870.   # * Key pressed
  871.   #--------------------------------------------------------------------------
  872.   def self.press?(key, pad_index = 0)
  873.     if controller_used?(pad_index)
  874.       key = normalize_input(key) if key.is_a?(Integer)
  875.       @last_input_used = :controller
  876.       @key_state[pad_index].include?(adjust_button(key, pad_index))
  877.     else
  878.       result = legacy_press?(key)
  879.       @last_input_used = :legacy if result
  880.       result
  881.     end
  882.   end
  883.   #--------------------------------------------------------------------------
  884.   # * Cursor moving
  885.   #--------------------------------------------------------------------------
  886.   def self.repeat?(key, controller_index = 0)
  887.     if controller_used?(controller_index)
  888.       @last_input_used = :controller
  889.       real_key = adjust_button(key, controller_index)
  890.       timing = @key_timing[controller_index][real_key]
  891.       timing != nil and (timing == 0 or timing == 30 or timing > 30 and timing % 5 == 0)
  892.     else
  893.       result = legacy_repeat?(key)
  894.       @last_input_used = :legacy if result
  895.       result
  896.     end
  897.   end
  898.   #--------------------------------------------------------------------------
  899.   # * Normalizes input from a conditional branch code
  900.   #--------------------------------------------------------------------------
  901.   def self.normalize_input(key)
  902.     NORMALIZER[key]
  903.   end
  904.   #--------------------------------------------------------------------------
  905.   # * Gets the proper controller key
  906.   #--------------------------------------------------------------------------
  907.   def self.adjust_button(key, pad_index = 0)
  908.     if $game_system
  909.       $game_system.adjust_buttons(key, pad_index)
  910.     elsif XInput_Settings::DEFAULT_KEY_SET[key]
  911.       XInput_Settings::DEFAULT_KEY_SET[key]
  912.     else
  913.       key
  914.     end
  915.   end
  916.   #--------------------------------------------------------------------------
  917.   # * Direction pressed
  918.   #--------------------------------------------------------------------------
  919.   def self.dir4(controller_index = 0)
  920.     return 2 if press?(:DOWN, controller_index)
  921.     return 4 if press?(:LEFT, controller_index)
  922.     return 6 if press?(:RIGHT, controller_index)
  923.     return 8 if press?(:UP, controller_index)
  924.     0
  925.   end
  926.   #--------------------------------------------------------------------------
  927.   # * Eight directions pressed
  928.   #--------------------------------------------------------------------------
  929.   def self.dir8(controller_index = 0)
  930.     return 1 if press?(:DOWN, controller_index) and press?(:LEFT, controller_index)
  931.     return 3 if press?(:DOWN, controller_index) and press?(:RIGHT, controller_index)
  932.     return 7 if press?(:UP, controller_index)   and press?(:LEFT, controller_index)
  933.     return 9 if press?(:UP, controller_index)   and press?(:RIGHT, controller_index)
  934.     dir4(controller_index)
  935.   end
  936.   #--------------------------------------------------------------------------
  937.   # * Checks if the controller is being used
  938.   #--------------------------------------------------------------------------
  939.   def self.controller_used?(controller_index = 0)
  940.     @controller_plugged[controller_index] && @controller_used[controller_index]
  941.   end
  942.   #--------------------------------------------------------------------------
  943.   # * Vibration update process
  944.   #--------------------------------------------------------------------------
  945.   def self.update_vibration
  946.     (0..3).each {|pad_index|
  947.       if @vibration_state[pad_index] > 0
  948.         @vibration_state[pad_index] -= 1
  949.         XInput.set_vibration(0, 0, pad_index) if @vibration_state[pad_index] == 0
  950.       end
  951.     }
  952.   end
  953.   #--------------------------------------------------------------------------
  954.   # * Manually stops the vibration
  955.   #--------------------------------------------------------------------------
  956.   def self.stop_vibration(controller_index = 0)
  957.     @vibration_state[controller_index] = 0
  958.   end
  959.   #--------------------------------------------------------------------------
  960.   # * Starts the vibration with no time limit
  961.   #--------------------------------------------------------------------------
  962.   def self.start_vibration(l_strenght, r_strenght = l_strenght, controller_index = 0)
  963.     l_strenght = [[0, l_strenght].max, 100].min * adjust_vibration(controller_index) / 100
  964.     r_strenght = [[0, r_strenght].max, 100].min * adjust_vibration(controller_index) / 100
  965.     @vibration_state[controller_index] = -1
  966.     XInput.set_vibration(l_strenght, r_strenght, controller_index)
  967.   end
  968.   #--------------------------------------------------------------------------
  969.   # * Pad keys update process
  970.   #--------------------------------------------------------------------------
  971.   def self.update_keystate
  972.     @old_key_state = @key_state
  973.     (0..3).each {|pad_index|
  974.       update_keys(pad_index)
  975.       update_key_variables if pad_index == 0
  976.     }
  977.   end
  978.   #--------------------------------------------------------------------------
  979.   # * Single pad update process
  980.   #--------------------------------------------------------------------------
  981.   def self.update_keys(controller_index = 0)
  982.     state = XInput.get_state(controller_index)
  983.     if state && state.packet_number != XInput::DEVICE_NOT_GAMEPAD
  984.       @controller_plugged[controller_index] = true
  985.       @key_state[controller_index] = state.game_pad.keymap_state
  986.       @key_timing[controller_index].each_key { |key|
  987.         @key_timing[controller_index][key] = nil unless @key_state[controller_index].keys.include?(key)
  988.       }
  989.       @key_state[controller_index].each_key {|key|
  990.         if @old_key_state[controller_index].keys.include?(key)
  991.           @key_timing[controller_index][key] ||= -1
  992.           @key_timing[controller_index][key] += 1
  993.         else
  994.           @key_timing[controller_index][key] = 0
  995.         end
  996.       }
  997.     else
  998.       @controller_plugged[controller_index] = false
  999.     end
  1000.   end
  1001.   #--------------------------------------------------------------------------
  1002.   # * Updates the game variables
  1003.   #--------------------------------------------------------------------------
  1004.   def self.update_key_variables
  1005.     return unless XInput_Settings::VARIABLE_SYSTEM
  1006.     return unless $game_variables
  1007.     $game_switches[XInput_Settings::PLUGGED_SW] = controller_connected?
  1008.     return unless controller_connected?
  1009.     $game_variables[XInput_Settings::LEFT_TRIGGER_VAR] = left_trigger
  1010.     $game_variables[XInput_Settings::RIGHT_TRIGGER_VAR] = right_trigger
  1011.     $game_variables[XInput_Settings::LEFT_AXIS_X_VAR] = left_analog[:x]
  1012.     $game_variables[XInput_Settings::LEFT_AXIS_Y_VAR] = left_analog[:y]
  1013.     $game_variables[XInput_Settings::RIGHT_AXIS_X_VAR] = right_analog[:x]
  1014.     $game_variables[XInput_Settings::RIGHT_AXIS_Y_VAR] = right_analog[:y]
  1015.     $game_variables[XInput_Settings::BATTERY_LEVEL] = battery_level
  1016.   end
  1017.   #--------------------------------------------------------------------------
  1018.   # * Controller check update process
  1019.   #--------------------------------------------------------------------------
  1020.   def self.update_controller_used
  1021.     @controller_used = {}
  1022.     (0..3).each {|i|
  1023.       @controller_used[i] = @key_state[i].size > 0
  1024.     }
  1025.   end
  1026.   #--------------------------------------------------------------------------
  1027.   # * Returns the last used controls (:controller or :legacy)
  1028.   #--------------------------------------------------------------------------
  1029.   def self.used_control; @last_input_used; end
  1030.   #--------------------------------------------------------------------------
  1031.   # * Vibration activation
  1032.   # @param [Float] l_strenght       value from 0 to 100
  1033.   # @param [Float] r_strenght       value from 0 to 100
  1034.   # @param [Integer] timing         frames (1/60 second)
  1035.   # @param [Integer] pad_index      pad index
  1036.   #--------------------------------------------------------------------------
  1037.   def self.vibrate(l_strenght, r_strenght, timing, pad_index = 0)
  1038.     l_strenght = [[0, l_strenght].max, 100].min * adjust_vibration(pad_index) / 100
  1039.     r_strenght = [[0, r_strenght].max, 100].min * adjust_vibration(pad_index) / 100
  1040.     XInput.set_vibration(l_strenght, r_strenght, pad_index)
  1041.     @vibration_state[pad_index] = timing
  1042.   end
  1043.   #--------------------------------------------------------------------------
  1044.   # * Adjusts the vibration power due to user settings
  1045.   # @return [Integer]
  1046.   #--------------------------------------------------------------------------
  1047.   def self.adjust_vibration(pad_index = 0)
  1048.     $game_system ? $game_system.calc_vibration_power(pad_index) : 0
  1049.   end
  1050.   #--------------------------------------------------------------------------
  1051.   # * Gets the left analog stick coordinates
  1052.   # @param [Integer] controller_index
  1053.   # @return [Array]
  1054.   #--------------------------------------------------------------------------
  1055.   def self.left_analog(controller_index = 0)
  1056.     result = {:x => 0, :y => 0}
  1057.     if @key_state[controller_index][:L_AXIS_X]
  1058.       result[:x] = @key_state[controller_index][:L_AXIS_X]
  1059.     end
  1060.     if @key_state[controller_index][:L_AXIS_Y]
  1061.       result[:y] = @key_state[controller_index][:L_AXIS_Y]
  1062.     end
  1063.     result
  1064.   end
  1065.   #--------------------------------------------------------------------------
  1066.   # * Gets the right analog stick coordinates
  1067.   # @param [Integer] controller_index
  1068.   # @return [Array]
  1069.   #--------------------------------------------------------------------------
  1070.   def self.right_analog(controller_index = 0)
  1071.     result = {:x => 0, :y => 0}
  1072.     if @key_state[controller_index][:R_AXIS_X]
  1073.       result[:x] = @key_state[controller_index][:R_AXIS_X]
  1074.     end
  1075.     if @key_state[controller_index][:R_AXIS_Y]
  1076.       result[:y] = @key_state[controller_index][:R_AXIS_Y]
  1077.     end
  1078.     result
  1079.   end
  1080.   #--------------------------------------------------------------------------
  1081.   # * Returns the left trigger value (value between 0 and 255)
  1082.   # @return [Integer]
  1083.   #--------------------------------------------------------------------------
  1084.   def self.left_trigger(controller_index = 0)
  1085.     if @key_state[controller_index][:L_TRIG]
  1086.       @key_state[controller_index][:L_TRIG]
  1087.     else
  1088.       0
  1089.     end
  1090.   end
  1091.   #--------------------------------------------------------------------------
  1092.   # * Returns the right trigger value (value between 0 and 255)
  1093.   # @return [Integer]
  1094.   #--------------------------------------------------------------------------
  1095.   def self.right_trigger(controller_index = 0)
  1096.     if @key_state[controller_index][:R_TRIG]
  1097.       @key_state[controller_index][:R_TRIG]
  1098.     else
  1099.       0
  1100.     end
  1101.   end
  1102.   #--------------------------------------------------------------------------
  1103.   # * Gets the battery level of a selected controller
  1104.   # return values: -1: wired controller; 0: empty, 1: low, 2: medium, 3: high
  1105.   # @return [Integer]
  1106.   #--------------------------------------------------------------------------
  1107.   def self.battery_level(controller_index = 0)
  1108.     battery_info = XInput.get_battery_info(controller_index)
  1109.     return -2 if battery_info.nil?
  1110.     battery_info.battery_type == 0 ? -1 : battery_info.battery_level
  1111.   end
  1112. end # input
  1113.  
  1114. #===============================================================================
  1115. # ** Game_Interpreter
  1116. #-------------------------------------------------------------------------------
  1117. # easy method calls
  1118. #===============================================================================
  1119. class Game_Interpreter
  1120.   #--------------------------------------------------------------------------
  1121.   # * Call vibration process
  1122.   # @param [Integer] l_strenght
  1123.   # @param [Integer] r_strenght
  1124.   # @param [Integer] timing
  1125.   # @param [Integer] pad_index
  1126.   #--------------------------------------------------------------------------
  1127.   def controller_vibration(l_strenght, r_strenght, timing, pad_index = 0)
  1128.     Input.vibrate(l_strenght, r_strenght, timing, pad_index)
  1129.   end
  1130.   #--------------------------------------------------------------------------
  1131.   # * Starts the vibration with no time limit
  1132.   # @param [Integer] l_strenght
  1133.   # @param [Integer] r_strenght
  1134.   # @param [Integer] pad_index
  1135.   #--------------------------------------------------------------------------
  1136.   def start_vibration(l_strenght, r_strenght = l_strenght, pad_index = 0)
  1137.     Input.start_vibration(l_strenght, r_strenght, pad_index)
  1138.   end
  1139.   #--------------------------------------------------------------------------
  1140.   # * Stops the vibration
  1141.   #--------------------------------------------------------------------------
  1142.   def stop_vibration(pad_index = 0)
  1143.     Input.stop_vibration(pad_index)
  1144.   end
  1145.   #--------------------------------------------------------------------------
  1146.   # * Returns the controller plugged state
  1147.   #--------------------------------------------------------------------------
  1148.   def controller_plugged_in?(pad_index = 0)
  1149.     Input.controller_connected?(pad_index)
  1150.   end
  1151. end # game_interpreter
  1152.  
  1153. # Starting load libraries
  1154. XInput.load_libraries
RAW Paste Data
We use cookies for various purposes including analytics. By continuing to use Pastebin, you agree to our use of cookies as described in the Cookies Policy. OK, I Understand
Top