ckb-next  beta-v0.2.8 at branch testing
ckb-next driver for corsair devices
 All Data Structures Files Functions Variables Typedefs Enumerations Enumerator Macros Pages
led.c
Go to the documentation of this file.
1 #include "command.h"
2 #include "led.h"
3 #include "profile.h"
4 #include "usb.h"
5 
6 void cmd_rgb(usbdevice* kb, usbmode* mode, int dummy, int keyindex, const char* code){
7  int index = keymap[keyindex].led;
8  if(index < 0) {
9  if (index == -2){ // Process strafe sidelights
10  uchar sideshine;
11  if (sscanf(code, "%2hhx",&sideshine)) // monochromatic
12  mode->light.sidelight = sideshine;
13  }
14  return;
15  }
16  uchar r, g, b;
17  if(sscanf(code, "%2hhx%2hhx%2hhx", &r, &g, &b) == 3){
18  mode->light.r[index] = r;
19  mode->light.g[index] = g;
20  mode->light.b[index] = b;
21  }
22 }
23 
24 // Indicator bitfield from string
25 static uchar iselect(const char* led){
26  int result = 0;
27  if(!strncmp(led, "num", 3) || strstr(led, ",num"))
28  result |= I_NUM;
29  if(!strncmp(led, "caps", 4) || strstr(led, ",caps"))
30  result |= I_CAPS;
31  if(!strncmp(led, "scroll", 6) || strstr(led, ",scroll"))
32  result |= I_SCROLL;
33  if(!strncmp(led, "all", 3) || strstr(led, ",all"))
34  result |= I_NUM | I_CAPS | I_SCROLL;
35  return result;
36 }
37 
38 void cmd_ioff(usbdevice* kb, usbmode* mode, int dummy1, int dummy2, const char* led){
39  uchar bits = iselect(led);
40  // Add the bits to ioff, remove them from ion
41  mode->ioff |= bits;
42  mode->ion &= ~bits;
43  kb->vtable->updateindicators(kb, 0);
44 }
45 
46 void cmd_ion(usbdevice* kb, usbmode* mode, int dummy1, int dummy2, const char* led){
47  uchar bits = iselect(led);
48  // Remove the bits from ioff, add them to ion
49  mode->ioff &= ~bits;
50  mode->ion |= bits;
51  kb->vtable->updateindicators(kb, 0);
52 }
53 
54 void cmd_iauto(usbdevice* kb, usbmode* mode, int dummy1, int dummy2, const char* led){
55  uchar bits = iselect(led);
56  // Remove the bits from both ioff and ion
57  mode->ioff &= ~bits;
58  mode->ion &= ~bits;
59  kb->vtable->updateindicators(kb, 0);
60 }
61 
62 void cmd_inotify(usbdevice* kb, usbmode* mode, int nnumber, int dummy, const char* led){
63  uchar bits = iselect(led);
64  if(strstr(led, ":off"))
65  // Turn notifications for these bits off
66  mode->inotify[nnumber] &= ~bits;
67  else
68  // Turn notifications for these bits on
69  mode->inotify[nnumber] |= bits;
70 }
71 
72 // Does a key exist in the current LED layout?
73 static int has_key(const char* name, const usbdevice* kb){
74  if(!name)
75  return 0;
76  if(IS_MOUSE(kb->vendor, kb->product)){
77  // Mice only have the RGB zones
78  if((IS_SABRE(kb) || IS_SCIMITAR(kb)) && !strcmp(name, "wheel"))
79  return 1;
80  if(IS_SCIMITAR(kb) && !strcmp(name, "thumb"))
81  return 1;
82  if(strstr(name, "dpi") == name || !strcmp(name, "front") || !strcmp(name, "back"))
83  return 1;
84  return 0;
85  } else {
86  // But keyboards don't have them at all
87  if(strstr(name, "dpi") == name || !strcmp(name, "front") || !strcmp(name, "back") || !strcmp(name, "wheel") || !strcmp(name, "thumb"))
88  return 0;
89  // Only K95 has G keys and M keys (G1 - G18, MR, M1 - M3)
90  if(!IS_K95(kb) && ((name[0] == 'g' && name[1] >= '1' && name[1] <= '9') || (name[0] == 'm' && (name[1] == 'r' || name[1] == '1' || name[1] == '2' || name[1] == '3'))))
91  return 0;
92  // Only K65 has lights on VolUp/VolDn
93  if(!IS_K65(kb) && (!strcmp(name, "volup") || !strcmp(name, "voldn")))
94  return 0;
95  // K65 lacks numpad and media buttons
96  if(IS_K65(kb) && (strstr(name, "num") == name || !strcmp(name, "stop") || !strcmp(name, "prev") || !strcmp(name, "play") || !strcmp(name, "next")))
97  return 0;
98  }
99  return 1;
100 }
101 
102 char* printrgb(const lighting* light, const usbdevice* kb){
104  const uchar* mr = light->r;
105  const uchar* mg = light->g;
106  const uchar* mb = light->b;
107  for(int i = 0; i < N_KEYS_EXTENDED; i++){
108  // Translate the key index to an RGB index using the key map
109  int k = keymap[i].led;
110  if(k < 0)
111  continue;
112  r[i] = mr[k];
113  g[i] = mg[k];
114  b[i] = mb[k];
115  }
116  // Make a buffer to track key names and to filter out duplicates
117  char names[N_KEYS_EXTENDED][11];
118  for(int i = 0; i < N_KEYS_EXTENDED; i++){
119  const char* name = keymap[i].name;
120  if(keymap[i].led < 0 || !has_key(name, kb))
121  names[i][0] = 0;
122  else
123  strncpy(names[i], name, 11);
124  }
125  // Check to make sure these aren't all the same color
126  int same = 1;
127  for(int i = 1; i < N_KEYS_EXTENDED; i++){
128  if(!names[i][0])
129  continue;
130  if(r[i] != r[0] || g[i] != g[0] || b[i] != b[0]){
131  same = 0;
132  break;
133  }
134  }
135  // If they are, just output that color
136  if(same){
137  char* buffer = malloc(7);
138  snprintf(buffer, 7, "%02x%02x%02x", r[0], g[0], b[0]);
139  return buffer;
140  }
141  const int BUFFER_LEN = 4096; // Should be more than enough to fit all keys
142  char* buffer = malloc(BUFFER_LEN);
143  int length = 0;
144  for(int i = 0; i < N_KEYS_EXTENDED; i++){
145  if(!names[i][0])
146  continue;
147  // Print the key name
148  int newlen = 0;
149  snprintf(buffer + length, BUFFER_LEN - length, length == 0 ? "%s%n" : " %s%n", names[i], &newlen);
150  length += newlen;
151  // Look ahead to see if any other keys have this color. If so, print them here as well.
152  uchar kr = r[i], kg = g[i], kb = b[i];
153  for(int j = i + 1; j < N_KEYS_EXTENDED; j++){
154  if(!names[j][0])
155  continue;
156  if(r[j] != kr || g[j] != kg || b[j] != kb)
157  continue;
158  snprintf(buffer + length, BUFFER_LEN - length, ",%s%n", names[j], &newlen);
159  length += newlen;
160  // Erase the key's name so it won't get printed later
161  names[j][0] = 0;
162  }
163  // Print the color
164  snprintf(buffer + length, BUFFER_LEN - length, ":%02x%02x%02x%n", kr, kg, kb, &newlen);
165  length += newlen;
166  }
167  return buffer;
168 }
void cmd_ioff(usbdevice *kb, usbmode *mode, int dummy1, int dummy2, const char *led)
Definition: led.c:38
static int has_key(const char *name, const usbdevice *kb)
Definition: led.c:73
uchar sidelight
Definition: structures.h:78
uchar b[152+11]
Definition: structures.h:76
uchar ion
Definition: structures.h:93
#define N_KEYS_EXTENDED
Definition: keymap.h:45
#define IS_SCIMITAR(kb)
Definition: usb.h:99
const char * name
Definition: keymap.h:50
void cmd_rgb(usbdevice *kb, usbmode *mode, int dummy, int keyindex, const char *code)
Definition: led.c:6
#define IS_SABRE(kb)
Definition: usb.h:93
lighting light
Definition: structures.h:84
void cmd_inotify(usbdevice *kb, usbmode *mode, int nnumber, int dummy, const char *led)
Definition: led.c:62
#define IS_K65(kb)
Definition: usb.h:49
#define IS_MOUSE(vendor, product)
Mouse vs keyboard test.
Definition: usb.h:141
uchar ioff
Definition: structures.h:93
unsigned char uchar
Definition: includes.h:24
short led
Definition: keymap.h:51
short product
Definition: structures.h:237
const union devcmd * vtable
Definition: structures.h:180
#define I_NUM
Definition: structures.h:19
char * printrgb(const lighting *light, const usbdevice *kb)
Definition: led.c:102
uchar g[152+11]
Definition: structures.h:75
uchar inotify[10]
Definition: structures.h:95
Definitions for using USB interface.
uchar r[152+11]
Definition: structures.h:74
const key keymap[(((152+3+12)+25)+11)]
Definition: keymap.c:5
#define IS_K95(kb)
Definition: usb.h:71
#define I_CAPS
Definition: structures.h:20
static uchar iselect(const char *led)
Definition: led.c:25
void cmd_iauto(usbdevice *kb, usbmode *mode, int dummy1, int dummy2, const char *led)
Definition: led.c:54
#define I_SCROLL
Definition: structures.h:21
short vendor
Definition: structures.h:237
void cmd_ion(usbdevice *kb, usbmode *mode, int dummy1, int dummy2, const char *led)
Definition: led.c:46