A modern Music Player Daemon based on Rockbox open source high quality audio player
libadwaita audio rust zig deno mpris rockbox mpd
at master 227 lines 9.5 kB view raw
1/*************************************************************************** 2 * __________ __ ___. 3 * Open \______ \ ____ ____ | | _\_ |__ _______ ___ 4 * Source | _// _ \_/ ___\| |/ /| __ \ / _ \ \/ / 5 * Jukebox | | ( <_> ) \___| < | \_\ ( <_> > < < 6 * Firmware |____|_ /\____/ \___ >__|_ \|___ /\____/__/\_ \ 7 * \/ \/ \/ \/ \/ 8 * $Id$ 9 * 10 * Copyright (C) 2009 Tomer Shalev 11 * 12 * This program is free software; you can redistribute it and/or 13 * modify it under the terms of the GNU General Public License 14 * as published by the Free Software Foundation; either version 2 15 * of the License, or (at your option) any later version. 16 * 17 * This software is distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY 18 * KIND, either express or implied. 19 * 20 ****************************************************************************/ 21#include "config.h" 22 23#include "action.h" 24#include "lang.h" 25#include "misc.h" 26#include "usbstack/usb_hid.h" 27#include "usb_keymaps.h" 28/*#define LOGF_ENABLE*/ 29#include "logf.h" 30 31#define MODIFIER(modifier, key) ((key) | (modifier << 8)) 32 33#define ALT(key) MODIFIER(HID_KEYBOARD_LEFT_ALT, key) 34#define CTRL(key) MODIFIER(HID_KEYBOARD_LEFT_CONTROL, key) 35#define SHIFT(key) MODIFIER(HID_KEYBOARD_LEFT_SHIFT, key) 36 37typedef struct 38{ 39 int action; 40 int id; 41} mapping_t; 42 43typedef struct 44{ 45 int lang_name; 46 int context; 47 usage_page_t usage_page; 48 mapping_t mapping[]; 49} hid_key_mapping_t; 50 51static const hid_key_mapping_t hid_key_mapping_multimedia = { 52 LANG_MULTIMEDIA_MODE, 53 CONTEXT_USB_HID_MODE_MULTIMEDIA, 54 HID_USAGE_PAGE_CONSUMER, 55 { 56 { ACTION_USB_HID_MULTIMEDIA_VOLUME_UP, HID_CONSUMER_USAGE_VOLUME_INCREMENT }, 57 { ACTION_USB_HID_MULTIMEDIA_VOLUME_DOWN, HID_CONSUMER_USAGE_VOLUME_DECREMENT }, 58 { ACTION_USB_HID_MULTIMEDIA_VOLUME_MUTE, HID_CONSUMER_USAGE_MUTE }, 59 { ACTION_USB_HID_MULTIMEDIA_PLAYBACK_PLAY_PAUSE, HID_CONSUMER_USAGE_PLAY_PAUSE }, 60 { ACTION_USB_HID_MULTIMEDIA_PLAYBACK_STOP, HID_CONSUMER_USAGE_STOP }, 61 { ACTION_USB_HID_MULTIMEDIA_PLAYBACK_TRACK_PREV, HID_CONSUMER_USAGE_SCAN_PREVIOUS_TRACK }, 62 { ACTION_USB_HID_MULTIMEDIA_PLAYBACK_TRACK_NEXT, HID_CONSUMER_USAGE_SCAN_NEXT_TRACK }, 63 { 0, 0 }, 64 } 65}; 66 67static const hid_key_mapping_t hid_key_mapping_presentation = { 68 LANG_PRESENTATION_MODE, 69 CONTEXT_USB_HID_MODE_PRESENTATION, 70 HID_USAGE_PAGE_KEYBOARD_KEYPAD, 71 { 72 { ACTION_USB_HID_PRESENTATION_SLIDESHOW_START, HID_KEYBOARD_F5 }, 73 { ACTION_USB_HID_PRESENTATION_SLIDESHOW_LEAVE, HID_KEYBOARD_ESCAPE }, 74 { ACTION_USB_HID_PRESENTATION_SLIDE_PREV, HID_KEYBOARD_P }, 75 { ACTION_USB_HID_PRESENTATION_SLIDE_NEXT, HID_KEYBOARD_N }, 76 { ACTION_USB_HID_PRESENTATION_SLIDE_FIRST, HID_KEYBOARD_HOME }, 77 { ACTION_USB_HID_PRESENTATION_SLIDE_LAST, HID_KEYBOARD_END }, 78 { ACTION_USB_HID_PRESENTATION_SCREEN_BLACK, HID_KEYBOARD_DOT }, 79 { ACTION_USB_HID_PRESENTATION_SCREEN_WHITE, HID_KEYBOARD_COMMA }, 80 { ACTION_USB_HID_PRESENTATION_LINK_PREV, SHIFT(HID_KEYBOARD_TAB) }, 81 { ACTION_USB_HID_PRESENTATION_LINK_NEXT, HID_KEYBOARD_TAB }, 82 { ACTION_USB_HID_PRESENTATION_MOUSE_CLICK, HID_KEYBOARD_RETURN }, 83 { ACTION_USB_HID_PRESENTATION_MOUSE_OVER, SHIFT(HID_KEYBOARD_RETURN) }, 84 { 0, 0 }, 85 } 86}; 87 88static const hid_key_mapping_t hid_key_mapping_browser = { 89 LANG_BROWSER_MODE, 90 CONTEXT_USB_HID_MODE_BROWSER, 91 HID_USAGE_PAGE_KEYBOARD_KEYPAD, 92 { 93 { ACTION_USB_HID_BROWSER_SCROLL_UP, HID_KEYBOARD_UP_ARROW }, 94 { ACTION_USB_HID_BROWSER_SCROLL_DOWN, HID_KEYBOARD_DOWN_ARROW }, 95 { ACTION_USB_HID_BROWSER_SCROLL_UP, HID_KEYBOARD_PAGE_UP }, 96 { ACTION_USB_HID_BROWSER_SCROLL_DOWN, HID_KEYBOARD_PAGE_DOWN }, 97 { ACTION_USB_HID_BROWSER_ZOOM_IN, CTRL(HID_KEYPAD_PLUS) }, 98 { ACTION_USB_HID_BROWSER_ZOOM_OUT, CTRL(HID_KEYPAD_MINUS) }, 99 { ACTION_USB_HID_BROWSER_ZOOM_RESET, CTRL(HID_KEYPAD_0_AND_INSERT) }, 100 { ACTION_USB_HID_BROWSER_TAB_PREV, CTRL(HID_KEYBOARD_PAGE_UP) }, 101 { ACTION_USB_HID_BROWSER_TAB_NEXT, CTRL(HID_KEYBOARD_PAGE_DOWN) }, 102 { ACTION_USB_HID_BROWSER_TAB_CLOSE, CTRL(HID_KEYBOARD_W) }, 103 { ACTION_USB_HID_BROWSER_HISTORY_BACK, ALT(HID_KEYBOARD_LEFT_ARROW) }, 104 { ACTION_USB_HID_BROWSER_HISTORY_FORWARD, ALT(HID_KEYBOARD_RIGHT_ARROW) }, 105 { ACTION_USB_HID_BROWSER_VIEW_FULL_SCREEN, HID_KEYBOARD_F11 }, 106 { 0, 0 }, 107 } 108}; 109 110#ifdef HAVE_USB_HID_MOUSE 111static const hid_key_mapping_t hid_key_mapping_mouse = { 112 LANG_MOUSE_MODE, 113 CONTEXT_USB_HID_MODE_MOUSE, 114 HID_USAGE_PAGE_GENERIC_DESKTOP_CONTROLS, 115 { 116 /* Cursor move up */ 117 { ACTION_USB_HID_MOUSE_UP, HID_MOUSE_UP }, 118 { ACTION_USB_HID_MOUSE_UP_REP, HID_MOUSE_UP_REP }, 119 { ACTION_USB_HID_MOUSE_LDRAG_UP, HID_MOUSE_LDRAG_UP }, 120 { ACTION_USB_HID_MOUSE_LDRAG_UP_REP, HID_MOUSE_LDRAG_UP_REP }, 121 { ACTION_USB_HID_MOUSE_RDRAG_UP, HID_MOUSE_RDRAG_UP }, 122 { ACTION_USB_HID_MOUSE_RDRAG_UP_REP, HID_MOUSE_RDRAG_UP_REP }, 123 /* Cursor move down */ 124 { ACTION_USB_HID_MOUSE_DOWN, HID_MOUSE_DOWN }, 125 { ACTION_USB_HID_MOUSE_DOWN_REP, HID_MOUSE_DOWN_REP }, 126 { ACTION_USB_HID_MOUSE_LDRAG_DOWN, HID_MOUSE_LDRAG_DOWN }, 127 { ACTION_USB_HID_MOUSE_LDRAG_DOWN_REP, HID_MOUSE_LDRAG_DOWN_REP }, 128 { ACTION_USB_HID_MOUSE_RDRAG_DOWN, HID_MOUSE_RDRAG_DOWN }, 129 { ACTION_USB_HID_MOUSE_RDRAG_DOWN_REP, HID_MOUSE_RDRAG_DOWN_REP }, 130 /* Cursor move left */ 131 { ACTION_USB_HID_MOUSE_LEFT, HID_MOUSE_LEFT }, 132 { ACTION_USB_HID_MOUSE_LEFT_REP, HID_MOUSE_LEFT_REP }, 133 { ACTION_USB_HID_MOUSE_LDRAG_LEFT, HID_MOUSE_LDRAG_LEFT }, 134 { ACTION_USB_HID_MOUSE_LDRAG_LEFT_REP, HID_MOUSE_LDRAG_LEFT_REP }, 135 { ACTION_USB_HID_MOUSE_RDRAG_LEFT, HID_MOUSE_RDRAG_LEFT }, 136 { ACTION_USB_HID_MOUSE_RDRAG_LEFT_REP, HID_MOUSE_RDRAG_LEFT_REP }, 137 /* Cursor move right */ 138 { ACTION_USB_HID_MOUSE_RIGHT, HID_MOUSE_RIGHT }, 139 { ACTION_USB_HID_MOUSE_RIGHT_REP, HID_MOUSE_RIGHT_REP }, 140 { ACTION_USB_HID_MOUSE_LDRAG_RIGHT, HID_MOUSE_LDRAG_RIGHT }, 141 { ACTION_USB_HID_MOUSE_LDRAG_RIGHT_REP, HID_MOUSE_LDRAG_RIGHT_REP }, 142 { ACTION_USB_HID_MOUSE_RDRAG_RIGHT, HID_MOUSE_RDRAG_RIGHT }, 143 { ACTION_USB_HID_MOUSE_RDRAG_RIGHT_REP, HID_MOUSE_RDRAG_RIGHT_REP }, 144 /* Mouse button left-click */ 145 { ACTION_USB_HID_MOUSE_BUTTON_LEFT, HID_MOUSE_BUTTON_LEFT }, 146 { ACTION_USB_HID_MOUSE_BUTTON_LEFT_REL, HID_MOUSE_BUTTON_LEFT_REL }, 147 /* Mouse button right-click */ 148 { ACTION_USB_HID_MOUSE_BUTTON_RIGHT, HID_MOUSE_BUTTON_RIGHT }, 149 { ACTION_USB_HID_MOUSE_BUTTON_RIGHT_REL, HID_MOUSE_BUTTON_RIGHT_REL }, 150 /* Mouse wheel scroll up */ 151 { ACTION_USB_HID_MOUSE_WHEEL_SCROLL_UP, HID_MOUSE_SCROLL_UP }, 152 /* Mouse wheel scroll down */ 153 { ACTION_USB_HID_MOUSE_WHEEL_SCROLL_DOWN, HID_MOUSE_SCROLL_DOWN }, 154 { 0, 0 }, 155 } 156}; 157 158#define USB_KEYPAD_MODE_MOUSE 3 /* Value of the mouse setting (hard-coded) */ 159#endif /* HAVE_USB_HID_MOUSE */ 160 161static const hid_key_mapping_t *hid_key_mappings[] = 162{ 163 &hid_key_mapping_multimedia, 164 &hid_key_mapping_presentation, 165 &hid_key_mapping_browser, 166#ifdef HAVE_USB_HID_MOUSE 167 &hid_key_mapping_mouse, 168#endif 169}; 170 171extern int usb_keypad_mode; 172 173int get_hid_usb_action(void) 174{ 175 int action, step; 176 const hid_key_mapping_t *key_mapping = hid_key_mappings[usb_keypad_mode]; 177 178 step = -1; 179 action = get_action(key_mapping->context, HZ/4); 180 switch (action) 181 { 182 case ACTION_USB_HID_MODE_SWITCH_NEXT: 183 step = 1; 184 /* fallthrough */ 185 case ACTION_USB_HID_MODE_SWITCH_PREV: 186 /* Switch key mappings in a cyclic way */ 187 usb_keypad_mode = clamp_value_wrap(usb_keypad_mode + step, 188 ARRAYLEN(hid_key_mappings) - 1, 0); 189 break; 190 default: 191 { 192 const mapping_t *mapping; 193 const hid_key_mapping_t *key_mapping = 194 hid_key_mappings[usb_keypad_mode]; 195 196 if (action <= ACTION_USB_HID_FIRST || 197 action >= ACTION_USB_HID_LAST) 198 { 199 break; 200 } 201 202 for (mapping = key_mapping->mapping; mapping->action; mapping++) 203 { 204 if (action == mapping->action) 205 { 206 logf("Action %d", action); 207 usb_hid_send(key_mapping->usage_page, mapping->id); 208 break; 209 } 210 } 211#ifdef DEBUG 212 if (!mapping->action) 213 logf("Action %d not found", action); 214#endif 215 break; 216 } 217 } 218 219 return action; 220} 221 222int keypad_mode_name_get(unsigned int mode) 223{ 224 if (mode >= ARRAYLEN(hid_key_mappings)) 225 return -1; 226 return hid_key_mappings[mode]->lang_name; 227}