HID-Deskriptor zur Verwendung für einen Playstation 2-Controller

Ich mache gerade einen Playstaion 2-Controller zum USB-Konverter mit einem Arduino Uno, und es läuft sehr gut, aber ich stecke bei einem bestimmten Problem fest.

Ich versuche, die druckempfindlichen Tasten zu unterstützen, weiß aber nicht, welchen HID-Deskriptor ich für den USB verwenden soll. Ich habe derzeit Folgendes, aber mein Computer scheint die Schaltflächenzustände nicht richtig zu registrieren, wobei jstest zeigt, dass die Schaltflächen in einem eingeschalteten Zustand zu "kleben" scheinen. Außerdem bin ich mir nicht sicher, ob die Verwendung von Rx und Ry für den zweiten Analogstick richtig ist.

Welche Bereiche des Deskriptors sollte ich ändern, damit alles richtig funktioniert?

Hier ist meine aktuelle Beschreibung:

const PROGMEM USB_Descriptor_HIDReport_Datatype_t hidDescriptor[] =
{
    0x05, 0x01,                    // USAGE_PAGE (Generic Desktop)
    0x09, 0x05,                    // USAGE (Game Pad)
    0xa1, 0x01,                    // COLLECTION (Application)
    0x09, 0x01,                    //   USAGE (Pointer)
    0xa1, 0x00,                    //   COLLECTION (Physical)
                                   //     ; Right stick
    0x09, 0x33,                    //     USAGE (Rx)
    0x09, 0x34,                    //     USAGE (Ry)
    0x15, 0x00,                    //     LOGICAL_MINIMUM (0)
    0x26, 0xff, 0x00,              //     LOGICAL_MAXIMUM (255)
    0x75, 0x08,                    //     REPORT_SIZE (8)
    0x95, 0x02,                    //     REPORT_COUNT (2)
    0x81, 0x02,                    //     INPUT (Data,Var,Abs)

                                   //     ; Left stick
    0x09, 0x30,                    //     USAGE (X)
    0x09, 0x31,                    //     USAGE (Y)
    0x15, 0x00,                    //     LOGICAL_MINIMUM (0)
    0x26, 0xff, 0x00,              //     LOGICAL_MAXIMUM (255)
    0x75, 0x08,                    //     REPORT_SIZE (8)
    0x95, 0x02,                    //     REPORT_COUNT (2)
    0x81, 0x02,                    //     INPUT (Data,Var,Abs)
    0xc0,                          //   END_COLLECTION

    0x05, 0x09,                    //   USAGE_PAGE (Button)
                                   //   ; Pressure sensitive buttons
    0x19, 0x01,                    //   USAGE_MINIMUM (Button 1)
    0x29, 0x0c,                    //   USAGE_MAXIMUM (Button 12)
    0x15, 0x00,                    //   LOGICAL_MINIMUM (0)
    0x26, 0xff, 0x00,              //   LOGICAL_MAXIMUM (255)
    0x75, 0x08,                    //   REPORT_SIZE (8)
    0x95, 0x0c,                    //   REPORT_COUNT (12)
    0x81, 0x02,                    //   INPUT (Data,Var,Abs)

                                   //   ; Other buttons (L3, R3, Select, Start)
    0x19, 0x0d,                    //   USAGE_MINIMUM (Button 13)
    0x29, 0x10,                    //   USAGE_MAXIMUM (Button 16)
    0x15, 0x00,                    //   LOGICAL_MINIMUM (0)
    0x25, 0x01,                    //   LOGICAL_MAXIMUM (1)
    0x75, 0x01,                    //   REPORT_SIZE (1)
    0x95, 0x04,                    //   REPORT_COUNT (4)
    0x81, 0x02,                    //   INPUT (Data,Var,Abs)
    0xc0                           // END_COLLECTION
};

PS. Ich verwende LUFA und flashe die Firmware des USB-Controllers des Uno

Antworten (2)

Sie können keine druckempfindlichen Tasten haben. Sie müssen sie als zusätzliche Achsen angeben.

Außerdem hat der Controller wirklich 12 druckempfindliche Tasten? In diesem Fall haben Sie Pech, da ich noch keine Software gefunden habe, die mit mehr als 8 Achsen funktioniert (einschließlich Windows!).

Darüber hinaus können Sie einige Ihrer Achsensteuerungen konsolidieren:

const PROGMEM USB_Descriptor_HIDReport_Datatype_t hidDescriptor[] =
{
    0x05, 0x01,                    // USAGE_PAGE (Generic Desktop)
    0x09, 0x05,                    // USAGE (Game Pad)
    0xa1, 0x01,                    // COLLECTION (Application)
    0x09, 0x01,                    //   USAGE (Pointer)
    0xa1, 0x00,                    //   COLLECTION (Physical)

 // ----- Consolidated
                                   //     ; Right stick
    0x09, 0x33,                    //     USAGE (Rx)
    0x09, 0x34,                    //     USAGE (Ry)
                                   //     ; Left stick
    0x09, 0x30,                    //     USAGE (X)
    0x09, 0x31,                    //     USAGE (Y)
    0x15, 0x00,                    //     LOGICAL_MINIMUM (0)
    0x26, 0xff, 0x00,              //     LOGICAL_MAXIMUM (255)
    0x75, 0x08,                    //     REPORT_SIZE (8)
    0x95, 0x02,                    //     REPORT_COUNT (4)    //changed
    0x81, 0x02,                    //     INPUT (Data,Var,Abs)

    0xc0,                          //   END_COLLECTION


    0x05, 0x09,                    //   USAGE_PAGE (Button)
// this section isn't going to work...
                                   //   ; Pressure sensitive buttons
    0x19, 0x01,                    //   USAGE_MINIMUM (Button 1)
    0x29, 0x0c,                    //   USAGE_MAXIMUM (Button 12)
    0x15, 0x00,                    //   LOGICAL_MINIMUM (0)
    0x26, 0xff, 0x00,              //   LOGICAL_MAXIMUM (255)
    0x75, 0x08,                    //   REPORT_SIZE (8)
    0x95, 0x0c,                    //   REPORT_COUNT (12)
    0x81, 0x02,                    //   INPUT (Data,Var,Abs)
// this section will, though the previous section will likely break something, and the whole descriptor will likely be rejected.
                                   //   ; Other buttons (L3, R3, Select, Start)
    0x19, 0x0d,                    //   USAGE_MINIMUM (Button 13)
    0x29, 0x10,                    //   USAGE_MAXIMUM (Button 16)
    0x15, 0x00,                    //   LOGICAL_MINIMUM (0)
    0x25, 0x01,                    //   LOGICAL_MAXIMUM (1)
    0x75, 0x01,                    //   REPORT_SIZE (1)
    0x95, 0x04,                    //   REPORT_COUNT (4)
    0x81, 0x02,                    //   INPUT (Data,Var,Abs)
    0xc0                           // END_COLLECTION
};

Was ich vermute, ist, dass der Computer a für den Wert auf den Tasten als "nicht gedrückt" und alles andere als "gedrückt" interpretiert 0. Solange die Taste nicht vollständig in den nicht gedrückten Zustand zurückkehrt, scheint die Taste zu "kleben".

Wie auch immer, die generic desktopNutzungsseite der HID-Nutzungstabelle definiert tatsächlich nur insgesamt 9 analoge Achsen in ihrer Gesamtheit, also haben Sie irgendwie Pech. Selbst die Windows-Controller-Diagnose unterstützt nur maximal 8 Achsen, und die meisten Bibliotheken, die auf Gamepads zugreifen, unterstützen sogar noch weniger.

DirectX erlaubt beispielsweise nur den Zugriff auf 6 analoge Achsen.

Wie auch immer, werfen Sie einen Blick auf die USB-HID-Nutzungstabellen hier .

Ich verbrachte auch eine Weile damit, mit HID-Tischen zu spielen, um einen Arduino-Leonardo in einen Joystick umzuwandeln. Schau dir das hier an .

Übrigens, wenn Sie können, empfehle ich einen Arduino Leonardo für diese Art von Bastelei. Es ist viel einfacher, damit umzugehen, als zu versuchen, den ATmega8U2 in einem Arduino Uno neu zu flashen.

Der Playstation-Controller hat sicherlich 12 druckempfindliche Tasten! ( en.wikipedia.org/wiki/DualShock#DualShock_2 ) Glücklicherweise ist das Betriebssystem, das ich verwende, Linux, und mit jstest scheint es, dass alle Achsen in Ordnung sind. Die Zielsoftware, für die ich den Controller verwenden wollte, ist PCSX2, und sie scheint auch alle Achsen zu unterstützen
Im Ernst. Das ist irgendwie lächerlich. Wie auch immer, wenn das Betriebssystem, auf dem Sie sich befinden, viele Achsen verarbeiten kann , melden Sie einfach alle Schaltflächen als separate analoge Achsen, und Sie sollten gut sein.

Nachdem Fake Name gesagt hatte, dass ich Achse für die Schaltflächen verwenden musste, entschied ich mich, stattdessen diesen Deskriptor zu verwenden, und es funktioniert! (Ich habe allerdings nur unter Linux getestet)
Ich musste das Usage (Z)12 Mal wiederholen, aber das schien keine Probleme zu bereiten.

const PROGMEM USB_Descriptor_HIDReport_Datatype_t hidDescriptor[] =
{
    0x05, 0x01,                    // USAGE_PAGE (Generic Desktop)
    0x09, 0x05,                    // USAGE (Game Pad)
    0xa1, 0x01,                    // COLLECTION (Application)

                                   //   ; Right stick
    0x09, 0x33,                    //   USAGE (Rx)
    0x09, 0x34,                    //   USAGE (Ry)
                                   //   ; Left stick
    0x09, 0x30,                    //   USAGE (X)
    0x09, 0x31,                    //   USAGE (Y)
                                   //   ; Pressure sensitive buttons
    0x09, 0x32,                    //   USAGE (Z)
    0x09, 0x32,                    //   USAGE (Z)
    0x09, 0x32,                    //   USAGE (Z)
    0x09, 0x32,                    //   USAGE (Z)
    0x09, 0x32,                    //   USAGE (Z)
    0x09, 0x32,                    //   USAGE (Z)
    0x09, 0x32,                    //   USAGE (Z)
    0x09, 0x32,                    //   USAGE (Z)
    0x09, 0x32,                    //   USAGE (Z)
    0x09, 0x32,                    //   USAGE (Z)
    0x09, 0x32,                    //   USAGE (Z)
    0x09, 0x32,                    //   USAGE (Z)
    0x15, 0x00,                    //   LOGICAL_MINIMUM (0)
    0x26, 0xff, 0x00,              //   LOGICAL_MAXIMUM (255)
    0x75, 0x08,                    //   REPORT_SIZE (8)
    0x95, 0x10,                    //   REPORT_COUNT (16)
    0x81, 0x02,                    //   INPUT (Data,Var,Abs)

    0x05, 0x09,                    //   USAGE_PAGE (Button)
                                   //   ; Other buttons (L3, R3, Select, Start)
    0x19, 0x01,                    //   USAGE_MINIMUM (Button 1)
    0x29, 0x04,                    //   USAGE_MAXIMUM (Button 4)
    0x15, 0x00,                    //   LOGICAL_MINIMUM (0)
    0x25, 0x01,                    //   LOGICAL_MAXIMUM (1)
    0x75, 0x01,                    //   REPORT_SIZE (1)
    0x95, 0x04,                    //   REPORT_COUNT (4)
    0x81, 0x02,                    //   INPUT (Data,Var,Abs)
    0xc0                           // END_COLLECTION
};