Home | History | Annotate | Download | only in gamepad
      1 // Copyright 2014 The Chromium Authors. All rights reserved.
      2 // Use of this source code is governed by a BSD-style license that can be
      3 // found in the LICENSE file.
      4 
      5 #ifndef CONTENT_BROWSER_GAMEPAD_RAW_INPUT_DATA_FETCHER_WIN_H_
      6 #define CONTENT_BROWSER_GAMEPAD_RAW_INPUT_DATA_FETCHER_WIN_H_
      7 
      8 #include "build/build_config.h"
      9 
     10 #include <stdlib.h>
     11 #include <Unknwn.h>
     12 #include <WinDef.h>
     13 #include <windows.h>
     14 
     15 #include <hidsdi.h>
     16 #include <map>
     17 #include <vector>
     18 
     19 #include "base/memory/scoped_ptr.h"
     20 #include "base/memory/weak_ptr.h"
     21 #include "base/message_loop/message_loop.h"
     22 #include "base/scoped_native_library.h"
     23 #include "base/win/message_window.h"
     24 #include "content/browser/gamepad/gamepad_data_fetcher.h"
     25 #include "content/browser/gamepad/gamepad_standard_mappings.h"
     26 #include "third_party/WebKit/public/platform/WebGamepads.h"
     27 
     28 namespace content {
     29 
     30 struct RawGamepadAxis {
     31   HIDP_VALUE_CAPS caps;
     32   float value;
     33   bool active;
     34 };
     35 
     36 struct RawGamepadInfo {
     37   HANDLE handle;
     38   scoped_ptr<uint8[]> ppd_buffer;
     39   PHIDP_PREPARSED_DATA preparsed_data;
     40 
     41   uint32_t report_id;
     42   uint32_t vendor_id;
     43   uint32_t product_id;
     44 
     45   wchar_t id[blink::WebGamepad::idLengthCap];
     46 
     47   uint32_t buttons_length;
     48   bool buttons[blink::WebGamepad::buttonsLengthCap];
     49 
     50   uint32_t axes_length;
     51   RawGamepadAxis axes[blink::WebGamepad::axesLengthCap];
     52 };
     53 
     54 class RawInputDataFetcher
     55     : public base::SupportsWeakPtr<RawInputDataFetcher>,
     56       public base::MessageLoop::DestructionObserver {
     57  public:
     58   explicit RawInputDataFetcher();
     59   ~RawInputDataFetcher();
     60 
     61   // DestructionObserver overrides.
     62   virtual void WillDestroyCurrentMessageLoop() OVERRIDE;
     63 
     64   bool Available() { return rawinput_available_; }
     65   void StartMonitor();
     66   void StopMonitor();
     67 
     68   std::vector<RawGamepadInfo*> EnumerateDevices();
     69   RawGamepadInfo* GetGamepadInfo(HANDLE handle);
     70 
     71  private:
     72   RawGamepadInfo* ParseGamepadInfo(HANDLE hDevice);
     73   void UpdateGamepad(RAWINPUT* input, RawGamepadInfo* gamepad_info);
     74   // Handles WM_INPUT messages.
     75   LRESULT OnInput(HRAWINPUT input_handle);
     76   // Handles messages received by |window_|.
     77   bool HandleMessage(UINT message,
     78                      WPARAM wparam,
     79                      LPARAM lparam,
     80                      LRESULT* result);
     81   RAWINPUTDEVICE* GetRawInputDevices(DWORD flags);
     82   void ClearControllers();
     83 
     84   // Function types we use from hid.dll.
     85   typedef NTSTATUS (__stdcall *HidPGetCapsFunc)(
     86       PHIDP_PREPARSED_DATA PreparsedData, PHIDP_CAPS Capabilities);
     87   typedef NTSTATUS (__stdcall *HidPGetButtonCapsFunc)(
     88       HIDP_REPORT_TYPE ReportType, PHIDP_BUTTON_CAPS ButtonCaps,
     89       PUSHORT ButtonCapsLength, PHIDP_PREPARSED_DATA PreparsedData);
     90   typedef NTSTATUS (__stdcall *HidPGetValueCapsFunc)(
     91       HIDP_REPORT_TYPE ReportType, PHIDP_VALUE_CAPS ValueCaps,
     92       PUSHORT ValueCapsLength, PHIDP_PREPARSED_DATA PreparsedData);
     93   typedef NTSTATUS(__stdcall* HidPGetUsagesExFunc)(
     94       HIDP_REPORT_TYPE ReportType,
     95       USHORT LinkCollection,
     96       PUSAGE_AND_PAGE ButtonList,
     97       ULONG* UsageLength,
     98       PHIDP_PREPARSED_DATA PreparsedData,
     99       PCHAR Report,
    100       ULONG ReportLength);
    101   typedef NTSTATUS (__stdcall *HidPGetUsageValueFunc)(
    102       HIDP_REPORT_TYPE ReportType, USAGE UsagePage, USHORT LinkCollection,
    103       USAGE Usage, PULONG UsageValue, PHIDP_PREPARSED_DATA PreparsedData,
    104       PCHAR Report, ULONG ReportLength);
    105   typedef NTSTATUS (__stdcall *HidPGetScaledUsageValueFunc)(
    106       HIDP_REPORT_TYPE ReportType, USAGE UsagePage, USHORT LinkCollection,
    107       USAGE Usage, PLONG UsageValue, PHIDP_PREPARSED_DATA PreparsedData,
    108       PCHAR Report, ULONG ReportLength);
    109   typedef BOOLEAN (__stdcall *HidDGetStringFunc)(
    110       HANDLE HidDeviceObject, PVOID Buffer, ULONG BufferLength);
    111 
    112   // Get functions from dynamically loaded hid.dll. Returns true if loading was
    113   // successful.
    114   bool GetHidDllFunctions();
    115 
    116   base::ScopedNativeLibrary hid_dll_;
    117   scoped_ptr<base::win::MessageWindow> window_;
    118   bool rawinput_available_;
    119   bool filter_xinput_;
    120   bool events_monitored_;
    121 
    122   std::map<HANDLE, RawGamepadInfo*> controllers_;
    123 
    124   // Function pointers to HID functionality, retrieved in
    125   // |GetHidDllFunctions|.
    126   HidPGetCapsFunc hidp_get_caps_;
    127   HidPGetButtonCapsFunc hidp_get_button_caps_;
    128   HidPGetValueCapsFunc hidp_get_value_caps_;
    129   HidPGetUsagesExFunc hidp_get_usages_ex_;
    130   HidPGetUsageValueFunc hidp_get_usage_value_;
    131   HidPGetScaledUsageValueFunc hidp_get_scaled_usage_value_;
    132   HidDGetStringFunc hidd_get_product_string_;
    133 
    134   DISALLOW_COPY_AND_ASSIGN(RawInputDataFetcher);
    135 };
    136 
    137 }  // namespace content
    138 
    139 #endif  // CONTENT_BROWSER_GAMEPAD_RAW_INPUT_DATA_FETCHER_WIN_H_
    140