|
|
@@ -1,6 +1,7 @@
|
|
|
#include <furi.h>
|
|
|
#include <furi_hal.h>
|
|
|
#include <furi_hal_usb.h>
|
|
|
+#include <applications/services/power/power_service/power.h>
|
|
|
#include <usb.h>
|
|
|
#include <usb_hid.h>
|
|
|
#include <stdlib.h>
|
|
|
@@ -8,7 +9,7 @@
|
|
|
#include <input/input.h>
|
|
|
|
|
|
/* generated by fbt from .png files in images folder */
|
|
|
-#include <template_icons.h>
|
|
|
+#include <xinput_controller_icons.h>
|
|
|
|
|
|
#define XBOX_SURFACE_EP_IN 0x81 // IN Endpoint 1
|
|
|
#define HID_EP_SZ 0x10
|
|
|
@@ -16,8 +17,6 @@
|
|
|
typedef struct {
|
|
|
uint8_t x, y;
|
|
|
} Position;
|
|
|
-static Position text_pos = {.x = 0, .y = 0};
|
|
|
-
|
|
|
enum {
|
|
|
UP = 1 << 0,
|
|
|
DOWN = 1 << 1,
|
|
|
@@ -511,25 +510,60 @@ static void app_draw_callback(Canvas* canvas, void* ctx) {
|
|
|
canvas_clear(canvas);
|
|
|
canvas_set_color(canvas, ColorBlack);
|
|
|
canvas_set_font(canvas, FontSecondary);
|
|
|
- if (hid_connected) {
|
|
|
- canvas_draw_str_aligned(
|
|
|
- canvas, // Callback variable
|
|
|
- text_pos.x, // x coordinate
|
|
|
- text_pos.y, // y coordinate
|
|
|
- AlignLeft, // Horizontal alignement
|
|
|
- AlignTop, // Vertical alignement
|
|
|
- "Connected! :D" // Text to display
|
|
|
- );
|
|
|
- }
|
|
|
- canvas_draw_str_aligned(
|
|
|
- canvas, // Callback variable
|
|
|
- text_pos.x, // x coordinate
|
|
|
- text_pos.y + 20, // y coordinate
|
|
|
- AlignLeft, // Horizontal alignement
|
|
|
- AlignTop, // Vertical alignement
|
|
|
- message // Text to display
|
|
|
- );
|
|
|
- // canvas_draw_icon(canvas, image_position.x % 128, image_position.y % 64, &I_airplane);
|
|
|
+ if (!hid_connected) {
|
|
|
+ canvas_set_font(canvas, FontPrimary);
|
|
|
+ canvas_draw_str(canvas, 60, 35, "Connecting...");
|
|
|
+ canvas_draw_icon(canvas, 5, 20, &I_usb);
|
|
|
+ } else {
|
|
|
+ canvas_set_font(canvas, FontPrimary);
|
|
|
+ canvas_draw_str(canvas, 74, 12, "Controller");
|
|
|
+ canvas_set_font(canvas, FontSecondary);
|
|
|
+ canvas_draw_str(canvas, 64, 24, "Hold");
|
|
|
+ canvas_draw_icon(canvas, 84, 16, &I_back);
|
|
|
+ canvas_draw_str(canvas, 97, 24, "to exit");
|
|
|
+
|
|
|
+ // Joystick up
|
|
|
+ if (current_surface.left_y > 200) {
|
|
|
+ canvas_draw_icon(canvas, 26, 13, &I_up_held);
|
|
|
+ } else {
|
|
|
+ canvas_draw_icon(canvas, 26, 13, &I_up);
|
|
|
+ }
|
|
|
+
|
|
|
+ // Joystick down
|
|
|
+ if (current_surface.left_y < -200) {
|
|
|
+ canvas_draw_icon(canvas, 26, 36, &I_down_held);
|
|
|
+ } else {
|
|
|
+ canvas_draw_icon(canvas, 26, 36, &I_down);
|
|
|
+ }
|
|
|
+
|
|
|
+ // Joystick left
|
|
|
+ if (current_surface.left_x < -200) {
|
|
|
+ canvas_draw_icon(canvas, 3, 33, &I_left_held);
|
|
|
+ } else {
|
|
|
+ canvas_draw_icon(canvas, 3, 33, &I_left);
|
|
|
+ }
|
|
|
+
|
|
|
+ // Joystick right
|
|
|
+ if (current_surface.left_x > 200) {
|
|
|
+ canvas_draw_icon(canvas, 52, 33, &I_right_held);
|
|
|
+ } else {
|
|
|
+ canvas_draw_icon(canvas, 52, 33, &I_right);
|
|
|
+ }
|
|
|
+
|
|
|
+ // A
|
|
|
+ if (current_surface.buttons & A) {
|
|
|
+ canvas_draw_icon(canvas, 79, 40, &I_a_held);
|
|
|
+ } else {
|
|
|
+ canvas_draw_icon(canvas, 79, 40, &I_a);
|
|
|
+ }
|
|
|
+
|
|
|
+ // B
|
|
|
+ if (current_surface.buttons & B) {
|
|
|
+ canvas_draw_icon(canvas, 100, 40, &I_b_held);
|
|
|
+ } else {
|
|
|
+ canvas_draw_icon(canvas, 100, 40, &I_b);
|
|
|
+ }
|
|
|
+ }
|
|
|
}
|
|
|
|
|
|
static void app_input_callback(InputEvent* input_event, void* ctx) {
|
|
|
@@ -539,10 +573,8 @@ static void app_input_callback(InputEvent* input_event, void* ctx) {
|
|
|
furi_message_queue_put(event_queue, input_event, FuriWaitForever);
|
|
|
}
|
|
|
|
|
|
-int32_t template_app(void* p) {
|
|
|
+int32_t xinput_app(void* p) {
|
|
|
UNUSED(p);
|
|
|
- FURI_LOG_I("TEST", "Hello world");
|
|
|
- FURI_LOG_I("TEST", "I'm template!");
|
|
|
|
|
|
FuriMessageQueue* event_queue = furi_message_queue_alloc(8, sizeof(InputEvent));
|
|
|
ViewPort* view_port = view_port_alloc();
|
|
|
@@ -558,34 +590,39 @@ int32_t template_app(void* p) {
|
|
|
|
|
|
furi_check(furi_hal_usb_set_config(&usb_xbox, NULL));
|
|
|
while (true) {
|
|
|
+ while (!hid_connected) {
|
|
|
+ view_port_update(view_port);
|
|
|
+ }
|
|
|
furi_check(furi_message_queue_get(event_queue, &input_event, FuriWaitForever) == FuriStatusOk);
|
|
|
if (!running) {
|
|
|
break;
|
|
|
}
|
|
|
message = strdup(input_get_type_name(input_event.type));
|
|
|
- hid_send_report();
|
|
|
+ if (input_event.type == InputTypeLong && input_event.key == InputKeyBack && current_surface.buttons == B) {
|
|
|
+ running = false;
|
|
|
+ }
|
|
|
+
|
|
|
if (input_event.type == InputTypeRepeat) {
|
|
|
// No
|
|
|
} else if (input_event.type == InputTypePress) {
|
|
|
switch (input_event.key) {
|
|
|
case InputKeyLeft:
|
|
|
- current_surface.buttons = current_surface.buttons | LEFT;
|
|
|
+ current_surface.left_x = -32767;
|
|
|
break;
|
|
|
case InputKeyRight:
|
|
|
- current_surface.buttons = current_surface.buttons | RIGHT;
|
|
|
+ current_surface.left_x = 32767;
|
|
|
break;
|
|
|
case InputKeyOk:
|
|
|
current_surface.buttons = current_surface.buttons | A;
|
|
|
break;
|
|
|
case InputKeyUp:
|
|
|
- current_surface.buttons = current_surface.buttons | UP;
|
|
|
+ current_surface.left_y = 32767;
|
|
|
break;
|
|
|
case InputKeyDown:
|
|
|
- current_surface.buttons = current_surface.buttons | DOWN;
|
|
|
- break;
|
|
|
- case InputKeyBack:
|
|
|
- running = false;
|
|
|
+ current_surface.left_y = -32767;
|
|
|
break;
|
|
|
+ case InputKeyBack:
|
|
|
+ current_surface.buttons = current_surface.buttons | B;
|
|
|
default:
|
|
|
break;
|
|
|
}
|
|
|
@@ -593,29 +630,26 @@ int32_t template_app(void* p) {
|
|
|
if (input_event.type == InputTypeRelease) {
|
|
|
switch (input_event.key) {
|
|
|
case InputKeyLeft:
|
|
|
- current_surface.buttons = current_surface.buttons & ~ LEFT;
|
|
|
- break;
|
|
|
case InputKeyRight:
|
|
|
- current_surface.buttons = current_surface.buttons & ~ RIGHT;
|
|
|
+ current_surface.left_x = 0;
|
|
|
break;
|
|
|
case InputKeyOk:
|
|
|
// current_surface.buttons = current_surface.buttons | THE_VOID_ONE;
|
|
|
current_surface.buttons = current_surface.buttons & ~ A;
|
|
|
break;
|
|
|
+ case InputKeyBack:
|
|
|
+ current_surface.buttons = current_surface.buttons & ~ B;
|
|
|
+ break;
|
|
|
case InputKeyUp:
|
|
|
- current_surface.buttons = current_surface.buttons & ~ UP;
|
|
|
- break;
|
|
|
case InputKeyDown:
|
|
|
- current_surface.buttons = current_surface.buttons & ~ DOWN;
|
|
|
- break;
|
|
|
- case InputKeyBack:
|
|
|
- running = false;
|
|
|
+ current_surface.left_y = 0;
|
|
|
break;
|
|
|
default:
|
|
|
break;
|
|
|
}
|
|
|
}
|
|
|
view_port_update(view_port);
|
|
|
+ hid_send_report();
|
|
|
}
|
|
|
view_port_enabled_set(view_port, false);
|
|
|
gui_remove_view_port(gui, view_port);
|
|
|
@@ -626,6 +660,7 @@ int32_t template_app(void* p) {
|
|
|
furi_check(furi_hal_usb_set_config(NULL, NULL));
|
|
|
|
|
|
// reboot the system to get usb working again
|
|
|
+ furi_hal_power_reset();
|
|
|
|
|
|
return 0;
|
|
|
}
|