ckb-next  v0.2.8 at branch master
ckb-next driver for corsair devices
 All Data Structures Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Macros Pages
rebindwidget.cpp
Go to the documentation of this file.
1 #include <QStandardPaths>
2 #include "rebindwidget.h"
3 #include "ui_rebindwidget.h"
4 #include <qdebug.h> // lae.
5 
6 static const int DPI_OFFSET = -KeyAction::DPI_CYCLE_UP + 1;
8 
10  QWidget(parent),
11  ui(new Ui::RebindWidget),
12  bind(0), profile(0), macReader(0)
13 {
14  ui->setupUi(this);
15  ui->lightWrapBox->hide();
16  ui->modeWrapBox->hide();
17  ui->programKpExtra->hide();
18  ui->programKrExtra->hide();
19 
20  // Populate key lists
21  modKeys << "caps" << "lshift" << "rshift" << "lctrl" << "rctrl" << "lwin" << "rwin" << "lalt" << "ralt" << "rmenu" << "fn";
22  fnKeys << "esc" << "f1" << "f2" << "f3" << "f4" << "f5" << "f6" << "f7" << "f8" << "f9" << "f10" << "f11" << "f12" << "prtscn" << "scroll" << "pause" << "f13" << "f14" << "f15" << "f16" << "f17" << "f18" << "f19" << "f20" << "ins" << "del" << "home" << "end" << "pgup" << "pgdn" << "power" << "lightup" << "lightdn" << "up" << "down" << "left" << "right";
23  numKeys << "numlock" << "num0" << "num1" << "num2" << "num3" << "num4" << "num5" << "num6" << "num7" << "num8" << "num9" << "numslash" << "numstar" << "numminus" << "numplus" << "numdot" << "numenter";
24  mediaKeys << "stop" << "prev" << "play" << "next" << "volup" << "voldn" << "mute" << "eject";
25  mouseKeys << "mouse1" << "mouse2" << "mouse3";
26  mouseExtKeys << "mouse4" << "mouse5" << "mouse6" << "mouse7" << "mouse8";
27  wheelKeys << "wheelup" << "wheeldn";
28  // Populate boxes
29  foreach(const QString& key, modKeys)
30  ui->modBox->addItem(KeyMap::friendlyName(key));
31  foreach(const QString& key, fnKeys)
32  ui->fnBox->addItem(KeyMap::friendlyName(key).replace("\n", " / "));
33  foreach(const QString& key, numKeys)
34  ui->numBox->addItem(KeyMap::friendlyName(key).remove("NumPad "));
35  foreach(const QString& key, mediaKeys)
36  ui->mediaBox->addItem(KeyMap::friendlyName(key));
37 #ifdef Q_OS_MACX
38  // Replace some OSX keys with their actual meanings
39  ui->modBox->setItemText(modKeys.indexOf("lwin") + 1, "Left Cmd");
40  ui->modBox->setItemText(modKeys.indexOf("rwin") + 1, "Right Cmd");
41  ui->modBox->setItemText(modKeys.indexOf("lalt") + 1, "Left Option");
42  ui->modBox->setItemText(modKeys.indexOf("ralt") + 1, "Right Option");
43  ui->fnBox->setItemText(fnKeys.indexOf("prtscn") + 1, "F13");
44  ui->fnBox->setItemText(fnKeys.indexOf("scroll") + 1, "F14");
45  ui->fnBox->setItemText(fnKeys.indexOf("pause") + 1, "F15");
46  ui->fnBox->setItemText(fnKeys.indexOf("f13") + 1, "F13 (Windows/Linux)");
47  ui->fnBox->setItemText(fnKeys.indexOf("f14") + 1, "F14 (Windows/Linux)");
48  ui->fnBox->setItemText(fnKeys.indexOf("f15") + 1, "F15 (Windows/Linux)");
49  ui->fnBox->setItemText(fnKeys.indexOf("ins") + 1, "Help");
50  ui->numBox->setItemText(numKeys.indexOf("numlock") + 1, "Clear");
51 
52  // Add tip label
53  ui->progTipLabel->setText("<p style=\"line-height:150%\">Tip: use the <font face=\"monospace\">open</font> command to launch a file, directory, or app. For instance, to start Safari:<br /><font face=\"monospace\">&nbsp;&nbsp;open /Applications/Safari.app</font></p>");
54 #else
55  ui->progTipLabel->setText("<p style=\"line-height:150%\">Tip: use <font face=\"monospace\">xdg-open</font> to launch a file or directory. For instance, to open your home folder:<br /><font face=\"monospace\">&nbsp;&nbsp;xdg-open " + QStandardPaths::writableLocation(QStandardPaths::HomeLocation) + "</font></p>");
56 #endif
57 }
58 
60  delete ui;
61 }
62 
63 void RebindWidget::setBind(KbBind* newBind, KbProfile* newProfile){
64  bind = newBind;
65  profile = newProfile;
66  setSelection(QStringList());
67 
68  // Populate typing keys by position
69  ui->typingBox->clear();
70  ui->typingBox->addItem(" ");
71  typingKeys.clear();
72  // Use the K95 map as it has all keys
73  const KeyMap& map = KeyMap(KeyMap::K95, bind->map().layout());
74  foreach(const QString& name, map.byPosition()){
75  KeyAction action(bind->defaultAction(name));
76  if(action.isNormal() && !modKeys.contains(name) && !fnKeys.contains(name) && !numKeys.contains(name) && !mediaKeys.contains(name) && name != "enter" && name != "tab" && name != "bspace"){
77  const Key& pos = map[name];
78  QString friendly = pos.friendlyName();
79  ui->typingBox->addItem(friendly);
80  typingKeys.append(name);
81  }
82  }
83  typingKeys << "enter" << "tab" << "bspace";
84  ui->typingBox->addItem("Enter");
85  ui->typingBox->addItem("Tab");
86  ui->typingBox->addItem("Backspace");
87  if(!map.isISO()){
88  // Add ISO backslash (aka KEY_102ND) to ANSI options
89  typingKeys << "bslash_iso";
90  ui->typingBox->addItem("Backslash (ISO layout)");
91  }
92 
93  // Populate mode list
94  ui->modeBox->clear();
95  ui->modeBox->addItem(" ");
96  ui->modeBox->addItem("(Previous)");
97  ui->modeBox->addItem("(Next)");
98  int idx = 1;
99  foreach(KbMode* mode, newProfile->modes())
100  ui->modeBox->addItem(QString("%1: %2").arg(idx++).arg(mode->name()));
101 
102  // Enable/disable DPI based on device
103  if(bind->isMouse()){
104  ui->dpiButton->setEnabled(true);
105  ui->dpiBox->setEnabled(true);
106  ui->dpiWarning->hide();
107  // Fill DPI slots
108  const KbPerf* perf = bind->perf();
109  for(int i = 0; i < KbPerf::DPI_COUNT; i++){
110  bool sniper = (i == 0);
111  int boxIdx = i + DPI_OFFSET;
112  QPoint dpi = perf->dpi(i);
113  QString text = tr(sniper ? "Sniper:\t%1 x %2" : "%3:\t%1 x %2").arg(dpi.x()).arg(dpi.y());
114  if(!sniper) text = text.arg(i);
115  ui->dpiBox->setItemText(boxIdx, text);
116  }
117  } else {
118  ui->dpiButton->setEnabled(false);
119  ui->dpiBox->setEnabled(false);
120  ui->dpiWarning->show();
121  }
122  // Always disable custom DPI boxes until selected
123  ui->dpiCustXBox->setEnabled(false);
124  ui->dpiCustYBox->setEnabled(false);
125  ui->dpiCustLabel->setEnabled(false);
126 }
127 
128 void RebindWidget::setSelection(const QStringList& newSelection, bool applyPrevious){
129  if(bind){
130  // Populate animation list
131  // FIXME: There should be a trigger to update this whenever an animation is added/removed, even if the key selection hasn't changed
132  ui->animBox->clear();
133  ui->animBox->addItem(" ");
134  foreach(KbAnim* anim, bind->light()->animList())
135  ui->animBox->addItem(anim->name());
136  }
137 
138  // Apply changes to previous selection (if any)
139  if(!selection.isEmpty() && applyPrevious){
140  QStringList previous = selection;
141  selection = QStringList();
142  applyChanges(previous, false);
143  }
144 
145  selection = newSelection;
146  if(newSelection.isEmpty()){
147  hide();
148  return;
149  } else
150  show();
151 
152  bool hasAction = false;
153  QString action;
154  if(selection.count() == 1){
155  // Select action from the UI
156  action = bind->action(selection.first());
157  if(!action.isEmpty())
158  hasAction = true;
159  } else {
160  // Select an action from the UI if all keys are the same.
161  // Select nothing if any are unbound or different
162  foreach(const QString& key, selection){
163  QString keyAction = bind->action(key);
164  if(keyAction.isEmpty() || (hasAction && keyAction != action)){
165  hasAction = false;
166  break;
167  } else if(action.isEmpty()){
168  action = keyAction;
169  hasAction = true;
170  }
171  }
172  }
173 
174  if(!hasAction)
175  action = "";
176  KeyAction act(action);
177  // Clear everything
178  setBox(0);
179  ui->dpiCustXBox->setValue(400);
180  ui->dpiCustYBox->setValue(400);
181  ui->animOnceBox->setChecked(false);
182  ui->animKrBox->setChecked(false);
183  ui->programKpBox->setText("");
184  ui->programKrBox->setText("");
185  ui->programKpSIBox->setChecked(false);
186  ui->programKrSIBox->setChecked(false);
187  ui->programKpModeBox->setCurrentIndex(0);
188  ui->programKrModeBox->setCurrentIndex(0);
189  ui->programKpModeBox->setEnabled(false);
190  ui->programKrModeBox->setEnabled(false);
191  // Clear neu UI elements in MacroTab
192  ui->pteMacroBox->setPlainText("");
193  ui->pteMacroText->setPlainText("");
194  ui->pteMacroComment->setPlainText("");
195  ui->txtBuffer->setText("");
196  // Fill in field and select tab according to action type
197  bool mouse = act.isMouse();
198  if(mouse){
199  // Mouse buttons
200  ui->tabWidget->setCurrentIndex(TAB_MOUSE);
201  // Set mouse buttons (indexOf returns -1 if not found, index zero is blank)
202  ui->mbBox->setCurrentIndex(mouseKeys.indexOf(action) + 1);
203  ui->mb2Box->setCurrentIndex(mouseExtKeys.indexOf(action) + 1);
204  ui->wheelBox->setCurrentIndex(wheelKeys.indexOf(action) + 1);
205  if(act.isDPI()){
206  QPoint custom;
207  int value = act.dpiInfo(custom);
208  if(value <= -DPI_OFFSET || value > KeyAction::DPI_CUSTOM)
209  return;
210  ui->dpiBox->setCurrentIndex(value + DPI_OFFSET);
211  if(value == KeyAction::DPI_CUSTOM){
212  ui->dpiCustXBox->setValue(custom.x());
213  ui->dpiCustYBox->setValue(custom.y());
214  }
215  }
216  } else if(act.isNormal()){
217  // Standard key
218  ui->tabWidget->setCurrentIndex(TAB_KB);
219  ui->typingBox->setCurrentIndex(typingKeys.indexOf(action) + 1);
220  ui->modBox->setCurrentIndex(modKeys.indexOf(action) + 1);
221  ui->fnBox->setCurrentIndex(fnKeys.indexOf(action) + 1);
222  ui->numBox->setCurrentIndex(numKeys.indexOf(action) + 1);
223  ui->mediaBox->setCurrentIndex(mediaKeys.indexOf(action) + 1);
224  } else if(act.isProgram()){
225  // Program key
226  ui->tabWidget->setCurrentIndex(TAB_PROGRAM);
227  QString onPress, onRelease;
228  int stop = act.programInfo(onPress, onRelease);
229  ui->programKpBox->setText(onPress);
230  ui->programKrBox->setText(onRelease);
231  switch(stop & 0x0F){
233  ui->programKpSIBox->setChecked(false);
234  ui->programKpModeBox->setCurrentIndex(0);
235  ui->programKpModeBox->setEnabled(false);
236  break;
237  default:
238  ui->programKpSIBox->setChecked(true);
239  ui->programKpModeBox->setCurrentIndex(stop & 0x0F);
240  ui->programKpModeBox->setEnabled(true);
241  break;
242  }
243  switch(stop & 0xF0){
245  ui->programKrSIBox->setChecked(false);
246  ui->programKrModeBox->setCurrentIndex(0);
247  ui->programKrModeBox->setEnabled(false);
248  break;
250  ui->programKrSIBox->setChecked(true);
251  ui->programKrModeBox->setCurrentIndex(0);
252  ui->programKrModeBox->setEnabled(true);
253  break;
255  ui->programKrSIBox->setChecked(true);
256  ui->programKrModeBox->setCurrentIndex(1);
257  ui->programKrModeBox->setEnabled(true);
258  break;
259  }
260  } else if(act.isAnim()){
261  // Animation key
262  ui->tabWidget->setCurrentIndex(TAB_ANIM);
263  bool onlyOnce = false, stopOnRelease = false;
264  QUuid id = act.animInfo(onlyOnce, stopOnRelease);
265  // Find this animation in the list. If not found, -1 will be returned, resulting in the blank space being selected
266  int index = bind->light()->findAnimIdx(id);
267  ui->animBox->setCurrentIndex(index + 1);
268  ui->animOnceBox->setChecked(!onlyOnce);
269  ui->animKrBox->setChecked(stopOnRelease);
270  } else if(act.isSpecial()){
271  // Other special keys
272  ui->tabWidget->setCurrentIndex(TAB_SPECIAL);
273  int param;
274  QString sAction = act.specialInfo(param);
275  // Mode selection. Check wrap-around flag
276  ui->modeWrapBox->setChecked(true);
277  if(sAction == "mode"){
278  ui->modeWrapBox->setChecked(true);
279  if(param == KeyAction::MODE_PREV_WRAP)
280  param = KeyAction::MODE_PREV;
281  else if(param == KeyAction::MODE_NEXT_WRAP)
282  param = KeyAction::MODE_NEXT;
283  else if(param < 0)
284  ui->modeWrapBox->setChecked(false);
285  // Set mode box to current selection, or to mode 1 if invalid
286  param += 3;
287  if(param >= 0 && param < ui->modeBox->count())
288  ui->modeBox->setCurrentIndex(param);
289  else
290  // 0 -> "", 1 -> Prev, 2 -> Next, 3 -> Mode 1
291  ui->modeBox->setCurrentIndex(3);
292  } else if (sAction == "macro") {
293  ui->tabWidget->setCurrentIndex(TAB_MACRO);
294  if (act.isValidMacro()) {
295  ui->pteMacroBox->setPlainText(act.macroContent());
296  ui->pteMacroText->setPlainText(act.macroLine()[1].replace("&das_IST_31N_col0n;", ":"));
297  ui->pteMacroComment->setPlainText(act.macroLine()[2].replace("&das_IST_31N_col0n;", ":"));
298  // Set the invisible Buffer to the original timing information.
299  // For convenience / Migration from older versions:
300  // If the timing information is only "x", then ignore it by setting it to an empty QString.
301  ui->txtBuffer->setText("");
302  if (act.macroTiming() != "x") ui->txtBuffer->setText(act.macroTiming());
304  } else {
305  qDebug("RebindWidget::setSelection found invalid macro definition.");
306  act.macroDisplay();
307  }
308  } else
309  ui->modeBox->setCurrentIndex(0);
310  // Brightness control. Also check wrap
311  if(sAction == "light"){
312  ui->lightWrapBox->setChecked(true);
313  if(param == KeyAction::LIGHT_DOWN_WRAP)
314  param = KeyAction::LIGHT_DOWN;
315  else if(param == KeyAction::LIGHT_UP_WRAP)
316  param = KeyAction::LIGHT_UP;
317  else
318  ui->lightWrapBox->setChecked(false);
319  if(param < 0 || param > 1)
320  param = -1;
321  ui->lightBox->setCurrentIndex(param + 1);
322  } else
323  ui->lightBox->setCurrentIndex(0);
324  // Win lock
325  if(sAction == "lock"){
326  if(param < 0 || param > 2)
327  param = -1;
328  ui->lockBox->setCurrentIndex(param + 1);
329  } else
330  ui->lockBox->setCurrentIndex(0);
331  }
332 }
333 
334 void RebindWidget::applyChanges(const QStringList& keys, bool doUnbind){
335  if(ui->typingBox->currentIndex() > 0)
336  bind->setAction(keys, typingKeys[ui->typingBox->currentIndex() - 1]);
337  else if(ui->modBox->currentIndex() > 0)
338  bind->setAction(keys, modKeys[ui->modBox->currentIndex() - 1]);
339  else if(ui->fnBox->currentIndex() > 0)
340  bind->setAction(keys, fnKeys[ui->fnBox->currentIndex() - 1]);
341  else if(ui->numBox->currentIndex() > 0)
342  bind->setAction(keys, numKeys[ui->numBox->currentIndex() - 1]);
343  else if(ui->mediaBox->currentIndex() > 0)
344  bind->setAction(keys, mediaKeys[ui->mediaBox->currentIndex() - 1]);
345  else if(ui->mbBox->currentIndex() > 0)
346  bind->setAction(keys, mouseKeys[ui->mbBox->currentIndex() - 1]);
347  else if(ui->mb2Box->currentIndex() > 0)
348  bind->setAction(keys, mouseExtKeys[ui->mb2Box->currentIndex() - 1]);
349  else if(ui->wheelBox->currentIndex() > 0)
350  bind->setAction(keys, wheelKeys[ui->wheelBox->currentIndex() - 1]);
351  else if(ui->dpiBox->currentIndex() > 0)
352  bind->setAction(keys, KeyAction::dpiAction(ui->dpiBox->currentIndex() - DPI_OFFSET, ui->dpiCustXBox->value(), ui->dpiCustYBox->value()));
353  else if(ui->modeBox->currentIndex() > 0)
354  bind->setAction(keys, KeyAction::modeAction(ui->modeBox->currentIndex() - 3 - (ui->modeWrapBox->isChecked() && ui->modeBox->currentIndex() < 3 ? 2 : 0)));
355  else if(ui->lightBox->currentIndex() > 0)
356  bind->setAction(keys, KeyAction::lightAction(ui->lightBox->currentIndex() - 1 + (ui->lightWrapBox->isChecked() ? 2 : 0)));
357  else if(ui->lockBox->currentIndex() > 0)
358  bind->setAction(keys, KeyAction::lockAction(ui->lockBox->currentIndex() - 1));
359  else if(ui->animBox->currentIndex() > 0){
360  KbAnim* anim = bind->light()->animList().at(ui->animBox->currentIndex() - 1);
361  bind->setAction(keys, KeyAction::animAction(anim->guid(), !ui->animOnceBox->isChecked(), ui->animKrBox->isChecked()));
362  } else if(!ui->programKpBox->text().isEmpty() || !ui->programKrBox->text().isEmpty()){
363  int kpStop = 0, krStop = 0;
364  if(!ui->programKpBox->text().isEmpty()){
365  if(!ui->programKpSIBox->isChecked())
367  else
368  kpStop = ui->programKpModeBox->currentIndex();
369  }
370  if(!ui->programKrBox->text().isEmpty()){
371  if(!ui->programKrSIBox->isChecked())
373  else if(ui->programKrModeBox->currentIndex() == 0)
375  else
377  }
378  bind->setAction(keys, KeyAction::programAction(ui->programKpBox->text(), ui->programKrBox->text(), kpStop | krStop));
379  } else if (ui->pteMacroBox->toPlainText().length() > 0) {
384 
389  if (ui->rb_delay_asTyped->isChecked()) ui->txtBuffer->setText(ui->pteMacroBox->toPlainText());
390 
396  QString mac;
397  mac = ui->txtBuffer->text();
398  mac = ui->pteMacroComment->toPlainText().replace(":", "&das_IST_31N_col0n;") + ":" + mac;
399  mac = ui->pteMacroText->toPlainText().replace(":", "&das_IST_31N_col0n;") + ":" + mac;
400  mac = ui->pteMacroBox->toPlainText() + ":" + mac;
402  } else if(doUnbind)
403  bind->noAction(keys);
404 }
405 
407  // Normally, this should be done via signalling.
408  // Because there is no serarate thread, we have to call it directly
409  // (otherwise we could do Key char conversion step by step,
410  // but so it is more easy to change the key definition):
412  applyChanges(selection, true);
413 }
414 
416  // Re-load selection
418 }
419 
422 }
423 
426 }
427 
429  // Un-select every item except for the current one.
430  // on_*_currentIndexChanged will take care of deselecting the checkbox.
431  // Key
432  if(box != ui->typingBox) ui->typingBox->setCurrentIndex(0);
433  if(box != ui->modBox) ui->modBox->setCurrentIndex(0);
434  if(box != ui->fnBox) ui->fnBox->setCurrentIndex(0);
435  if(box != ui->numBox) ui->numBox->setCurrentIndex(0);
436  if(box != ui->mediaBox) ui->mediaBox->setCurrentIndex(0);
437  // Mouse
438  if(box != ui->mbBox) ui->mbBox->setCurrentIndex(0);
439  if(box != ui->mb2Box) ui->mb2Box->setCurrentIndex(0);
440  if(box != ui->wheelBox) ui->wheelBox->setCurrentIndex(0);
441  if(box != ui->dpiBox) ui->dpiBox->setCurrentIndex(0);
442  // Anim
443  if(box != ui->animBox) ui->animBox->setCurrentIndex(0);
444  // Special
445  if(box != ui->modeBox) ui->modeBox->setCurrentIndex(0);
446  if(box != ui->lightBox) ui->lightBox->setCurrentIndex(0);
447  if(box != ui->lockBox) ui->lockBox->setCurrentIndex(0);
448  // Program
449  if(box != ui->programKpBox && box != ui->programKrBox){
450  ui->programKpButton->setChecked(false);
451  ui->programKrButton->setChecked(false);
452  }
453  // Clear macro panel
454  if (box != ui->pteMacroBox) {
455  ui->pteMacroBox->setPlainText("");
456  ui->txtBuffer->setText("");
457  helpStatus(1);
458  }
459 }
460 
462  if(index == 0)
463  ui->typingButton->setChecked(false);
464  else {
465  ui->typingButton->setChecked(true);
466  setBox(ui->typingBox);
467  }
468 }
469 
471  if (ui->pteMacroBox->toPlainText().length() > 0) {
473  }
474 }
475 
477  if(index == 0)
478  ui->modButton->setChecked(false);
479  else {
480  ui->modButton->setChecked(true);
481  setBox(ui->modBox);
482  }
483 }
484 
486  if(index == 0)
487  ui->fnButton->setChecked(false);
488  else {
489  ui->fnButton->setChecked(true);
490  setBox(ui->fnBox);
491  }
492 }
493 
495  if(index == 0)
496  ui->numButton->setChecked(false);
497  else {
498  ui->numButton->setChecked(true);
499  setBox(ui->numBox);
500  }
501 }
502 
504  if(index == 0)
505  ui->mediaButton->setChecked(false);
506  else {
507  ui->mediaButton->setChecked(true);
508  setBox(ui->mediaBox);
509  }
510 }
511 
513  if(index == 0)
514  ui->mbButton->setChecked(false);
515  else {
516  ui->mbButton->setChecked(true);
517  setBox(ui->mbBox);
518  }
519 }
520 
522  if(index == 0)
523  ui->mb2Button->setChecked(false);
524  else {
525  ui->mb2Button->setChecked(true);
526  setBox(ui->mb2Box);
527  }
528 }
529 
531  if(index == 0)
532  ui->wheelButton->setChecked(false);
533  else {
534  ui->wheelButton->setChecked(true);
535  setBox(ui->wheelBox);
536  }
537 }
538 
540  if(index != DPI_CUST_IDX){
541  // Clear custom DPI
542  ui->dpiCustXBox->setEnabled(false);
543  ui->dpiCustYBox->setEnabled(false);
544  ui->dpiCustLabel->setEnabled(false);
545  } else {
546  ui->dpiCustXBox->setEnabled(true);
547  ui->dpiCustYBox->setEnabled(true);
548  ui->dpiCustLabel->setEnabled(true);
549  }
550  if(index == 0)
551  ui->dpiButton->setChecked(false);
552  else {
553  ui->dpiButton->setChecked(true);
554  setBox(ui->dpiBox);
555  }
556 }
557 
559  if(index == 1 || index == 2)
560  ui->modeWrapBox->show();
561  else
562  ui->modeWrapBox->hide();
563  if(index == 0)
564  ui->modeButton->setChecked(false);
565  else {
566  ui->modeButton->setChecked(true);
567  setBox(ui->modeBox);
568  }
569 }
570 
572  if(index == 0){
573  ui->lightButton->setChecked(false);
574  ui->lightWrapBox->hide();
575  } else {
576  ui->lightWrapBox->show();
577  ui->lightButton->setChecked(true);
578  setBox(ui->lightBox);
579  }
580 }
581 
583  if(index == 0)
584  ui->lockButton->setChecked(false);
585  else {
586  ui->lockButton->setChecked(true);
587  setBox(ui->lockBox);
588  }
589 }
590 
592  if(arg1.isEmpty()){
593  ui->programKpButton->setChecked(false);
594  ui->programKpExtra->hide();
595  } else {
596  ui->programKpButton->setChecked(true);
598  ui->programKpExtra->show();
599  }
600 }
601 
603  if(arg1.isEmpty()){
604  ui->programKrButton->setChecked(false);
605  ui->programKrExtra->hide();
606  } else {
607  ui->programKrButton->setChecked(true);
609  ui->programKrExtra->show();
610  }
611 }
612 
614  if(index == 0)
615  ui->animButton->setChecked(false);
616  else {
617  ui->animButton->setChecked(true);
618  setBox(ui->animBox);
619  }
620 }
621 
623  if(checked && ui->typingBox->currentIndex() == 0)
624  ui->typingBox->setCurrentIndex(1);
625 }
626 
628  if(checked && ui->modBox->currentIndex() == 0)
629  ui->modBox->setCurrentIndex(1);
630 }
631 
633  if(checked && ui->fnBox->currentIndex() == 0)
634  ui->fnBox->setCurrentIndex(1);
635 }
636 
638  if(checked && ui->numBox->currentIndex() == 0)
639  ui->numBox->setCurrentIndex(1);
640 }
641 
643  if(checked && ui->mediaBox->currentIndex() == 0)
644  ui->mediaBox->setCurrentIndex(1);
645 }
646 
648  if(checked && ui->modeBox->currentIndex() == 0)
649  ui->modeBox->setCurrentIndex(1);
650 }
651 
653  if(checked && ui->lightBox->currentIndex() == 0)
654  ui->lightBox->setCurrentIndex(1);
655 }
656 
658  if(checked && ui->lockBox->currentIndex() == 0)
659  ui->lockBox->setCurrentIndex(1);
660 }
661 
663  if(!checked){
664  ui->programKpBox->setText("");
665  } else if(ui->programKpBox->text().isEmpty()){
666  ui->programKpBox->setFocus();
668  }
669 }
670 
672  if(!checked){
673  ui->programKrBox->setText("");
674  } else if(ui->programKrBox->text().isEmpty()){
675  ui->programKrBox->setFocus();
677  }
678 }
679 
681  if(checked && ui->mbBox->currentIndex() == 0)
682  ui->mbBox->setCurrentIndex(1);
683 }
684 
686  if(checked && ui->mb2Box->currentIndex() == 0)
687  ui->mb2Box->setCurrentIndex(1);
688 }
689 
691  if(checked && ui->wheelBox->currentIndex() == 0)
692  ui->wheelBox->setCurrentIndex(1);
693 }
694 
696  if(checked && ui->dpiBox->currentIndex() == 0)
697  ui->dpiBox->setCurrentIndex(1);
698 }
699 
701  ui->programKpModeBox->setCurrentIndex(0);
702  ui->programKpModeBox->setEnabled(checked);
703 }
704 
706  ui->programKrModeBox->setCurrentIndex(0);
707  ui->programKrModeBox->setEnabled(checked);
708 }
709 
711  if(checked && ui->animBox->currentIndex() == 0)
712  ui->animBox->setCurrentIndex(1);
713 }
714 
725  if (!macReader) {
728  // because of the second thread we need to disable three of the four bottom buttons.
729  // Clicking "Stop" will enable them again.
730  ui->applyButton->setEnabled(false);
731  ui->resetButton->setEnabled(false);
732  ui->unbindButton->setEnabled(false);
733  ui->btnStartMacro->setEnabled(false);
734  ui->btnStopMacro->setEnabled(true);
735  ui->rb_delay_asTyped->setEnabled(false);
736  ui->rb_delay_no->setEnabled(false);
737  ui->rb_delay_default->setEnabled(false);
738  helpStatus(2);
739  }
740 }
741 
750  if (macReader) {
752  delete macReader;
753  macReader = 0;
754  convertMacroBox();
755  ui->applyButton->setEnabled(true);
756  ui->resetButton->setEnabled(true);
757  ui->unbindButton->setEnabled(true);
758  ui->btnStartMacro->setEnabled(true);
759  ui->btnStopMacro->setEnabled(false);
760  ui->rb_delay_asTyped->setEnabled(true);
761  ui->rb_delay_no->setEnabled(true);
762  ui->rb_delay_default->setEnabled(true);
763  helpStatus(3);
764  }
765 }
766 
775  helpStatus(1);
776 }
777 
782 void RebindWidget::helpStatus(int status) {
783  switch (status) {
784  case 1:
785  ui->lbl_macro->setText("Type in a macro name in the comment box and click start.");
786  break;
787  case 2:
788  ui->lbl_macro->setText("Type your macro and click stop when finished.");
789  break;
790  case 3:
791  ui->lbl_macro->setText("Click Apply or change values in Macro Key Actions in advance.");
792  break;
793  default:
794  ui->lbl_macro->setText(QString("Oops: Some magic in RebindWidget::helpStatus (%1)").arg(status));
795  }
796 }
797 
809  QString in;
810 
811  // Remember the original input stream before it is converted.
812  // In case of new choice of delay mode we have to restore it.
813  if (ui->txtBuffer->text() == "") {
814  ui->txtBuffer->setText(ui->pteMacroBox->toPlainText());
815  in = ui->pteMacroBox->toPlainText();
816  } else in = ui->txtBuffer->text();
817 
818  in.replace (QRegExp("\n"), ","); // first join all in one line
819  in.replace (QRegExp("key "), ""); // then delete keyword "key" followed by space
820  in.replace (QRegExp(",="), "="); // at last join each keystroke with its delay parameter
821 
822  // How to deal with the delay params?
823  // Because the three radio buttons are mututally exclusive,
824  // we can run through the if-chain w/o conflicts.
825  // If rb_delay_asTyped is checked, do nothing, because that's the standard.
826 
827  if (ui->rb_delay_default->isChecked()) {
828  in.replace(QRegExp("=\\d+,"), ","); // Delete the timing infos, use default value
829  in.replace(QRegExp("=\\d+$"), ""); // The last entry is without comma
830  }
831  if (ui->rb_delay_no->isChecked()) {
832  in.replace(QRegExp("=\\d+,"), "=0,"); // Set timing infos to zero for no delay
833  in.replace(QRegExp("=\\d+$"), "=0"); // Again the last entry w/o comma
834  in.replace(QRegExp("([\\+\\-]\\w+),"), "\\1=0,"); // If no delay is given, force it to zero
835  in.replace(QRegExp("([\\+\\-]\\w+)$"), "\\1=0");
836  }
837 
838  // Show the new format by replacing the older one.
839  ui->pteMacroBox->setPlainText(in);
840 }
841 
851 {
852  convertMacroBox();
853 }
854 
863 {
864  convertMacroBox();
865 }
866 
874 {
875  convertMacroBox();
876 }
877 
887 void RebindWidget::setCorrectRadioButton (QString macdef) {
888  if (!macdef.contains(QRegExp("=\\d+,"))) {
889  ui->rb_delay_default->setChecked(true);
890  return;
891  }
892  if (macdef.contains(QRegExp("=\\d\\d+,"))) {
893  ui->rb_delay_asTyped->setChecked(true);
894  return;
895  }
896  ui->rb_delay_no->setChecked(true);
897 }
void on_applyButton_clicked()
const ModeList & modes() const
Definition: kbprofile.h:42
void on_wheelBox_currentIndexChanged(int index)
RebindWidget(QWidget *parent)
Definition: rebindwidget.cpp:9
void on_mediaButton_clicked(bool checked)
bool isMouse() const
Definition: kbbind.h:45
bool isProgram() const
Definition: keyaction.h:158
void on_wheelButton_clicked(bool checked)
void on_modBox_currentIndexChanged(int index)
QRadioButton * mb2Button
void on_lockButton_clicked(bool checked)
QRadioButton * wheelButton
static const int DPI_OFFSET
Definition: rebindwidget.cpp:6
QPushButton * resetButton
void on_btnClearMacro_clicked()
RebindWidget::on_btnClearMacro_clicked changes the help info an the panel. The job of clearing the in...
QCheckBox * programKrButton
QRadioButton * fnButton
static QString animAction(const QUuid &guid, bool onlyOnce, bool stopOnRelease)
Definition: keyaction.cpp:184
QStringList wheelKeys
Definition: rebindwidget.h:105
KbBind * bind
Definition: rebindwidget.h:94
bool isMouse() const
Definition: keyaction.h:163
QStringList byPosition() const
Definition: keymap.cpp:902
static QString macroAction(QString macroDef)
well documented in cpp file
Definition: keyaction.cpp:523
static QString friendlyName(const QString &key, Layout layout=US)
Definition: keymap.cpp:925
QCheckBox * programKpSIBox
static const int DPI_CUSTOM
Definition: keyaction.h:128
static const int PROGRAM_PR_MULTI
Definition: keyaction.h:138
QStringList mouseExtKeys
Definition: rebindwidget.h:104
const AnimList & animList()
Definition: kblight.h:49
The MacroReader class creates a worker thread object. It does a connect do delayed deletion of thread...
Definition: macroreader.h:87
QPlainTextEdit * pteMacroText
void on_fnBox_currentIndexChanged(int index)
QComboBox * typingBox
void on_numButton_clicked(bool checked)
void on_modeButton_clicked(bool checked)
QPlainTextEdit * pteMacroBox
void on_btnStopMacro_clicked()
RebindWidget::on_btnStopMacro_clicked ends the macro recording. Notify channel ist closed...
void on_cancelButton_clicked()
QRadioButton * lockButton
KbPerf * perf()
Definition: kbbind.cpp:50
void on_lightButton_clicked(bool checked)
void setBox(QWidget *box)
static const int PROGRAM_RE_MULTI
Definition: keyaction.h:139
static QString dpiAction(int level, int customX=0, int customY=0)
Definition: keyaction.cpp:162
QString friendlyName(bool os=true) const
Definition: keymap.h:23
void on_pteMacroBox_textChanged()
QString specialInfo(int &parameter) const
Definition: keyaction.cpp:189
void on_resetButton_clicked()
const KeyMap & map()
Definition: kbbind.h:41
bool isValidMacro() const
isValidMacro checks whether a keyAction contains a valid macro. This is done easily: If the macro act...
Definition: keyaction.h:55
QCheckBox * modeWrapBox
const QString & name() const
Definition: kbanim.h:73
static const int TAB_SPECIAL
Definition: rebindwidget.h:83
static const int MODE_PREV
Definition: keyaction.h:122
static QString programAction(const QString &onPress, const QString &onRelease, int stop)
Definition: keyaction.cpp:177
void on_typingBox_currentIndexChanged(int index)
QPushButton * unbindButton
bool isDPI() const
Definition: keyaction.h:162
void on_unbindButton_clicked()
void on_modeBox_currentIndexChanged(int index)
QUuid animInfo(bool &onlyOnce, bool &stopOnRelease) const
Definition: keyaction.cpp:225
void on_fnButton_clicked(bool checked)
QStringList macroLine() const
macroLine returns all interresting content for a macro definition.
Definition: keyaction.h:73
Definition: keymap.h:49
static const int TAB_MOUSE
Definition: rebindwidget.h:83
QRadioButton * mbButton
static const int TAB_PROGRAM
Definition: rebindwidget.h:83
QCheckBox * lightWrapBox
QComboBox * animBox
QComboBox * modBox
QComboBox * dpiBox
static const int PROGRAM_RE_INDEF
Definition: keyaction.h:139
QStringList mediaKeys
Definition: rebindwidget.h:102
void setupUi(QWidget *RebindWidget)
QRadioButton * mediaButton
void on_programKpSIBox_clicked(bool checked)
QCheckBox * animOnceBox
QLineEdit * programKpBox
QStringList mouseKeys
Definition: rebindwidget.h:103
QPushButton * btnStartMacro
QStringList typingKeys
Definition: rebindwidget.h:98
void on_btnStartMacro_clicked()
RebindWidget::on_btnStartMacro_clicked starts macro recording. A new notification channel and MacroRe...
QRadioButton * lightButton
void on_mediaBox_currentIndexChanged(int index)
QComboBox * numBox
QComboBox * lockBox
static const int PROGRAM_RE_KPSTOP
Definition: keyaction.h:139
void on_programKrSIBox_clicked(bool checked)
static QString lockAction(int type=LOCK_TOGGLE)
Definition: keyaction.cpp:173
void resetAction(const QString &key)
Definition: kbbind.cpp:171
static const int MODE_PREV_WRAP
Definition: keyaction.h:123
void on_rb_delay_asTyped_toggled(bool checked)
RebindWidget::on_rb_delay_asTyped_toggled.
QPushButton * applyButton
QLineEdit * programKrBox
KbProfile * profile
Definition: rebindwidget.h:95
void on_programKpButton_clicked(bool checked)
KbLight * light()
Definition: kbbind.cpp:54
void on_mb2Button_clicked(bool checked)
void setCorrectRadioButton(QString macdef)
RebindWidget::setCorrectRadioButton.
QComboBox * mb2Box
static const int TAB_MACRO
Definition: rebindwidget.h:83
void on_dpiBox_currentIndexChanged(int index)
QPoint dpi(int index) const
Definition: kbperf.h:50
Definition: kbmode.h:36
QString action(const QString &key)
Definition: kbbind.cpp:145
void on_programKrButton_clicked(bool checked)
Definition: kbperf.h:15
QCheckBox * animKrBox
static bool isISO(Layout layout)
Definition: keymap.h:94
QCheckBox * programKpButton
void on_modButton_clicked(bool checked)
QString defaultAction(const QString &key)
Definition: kbbind.cpp:155
QRadioButton * dpiButton
void on_typingButton_clicked(bool checked)
bool isNormal() const
Definition: keyaction.h:153
static const int DPI_COUNT
Definition: kbperf.h:46
Definition: kbanim.h:11
Layout layout() const
Definition: keymap.h:130
static QString modeAction(int mode)
Definition: keyaction.cpp:158
Definition: kbbind.h:20
QRadioButton * rb_delay_asTyped
const QUuid & guid() const
Definition: kbanim.h:71
void convertMacroBox()
RebindWidget::convertMacroBox converts the macroBox content. The KB sends each keypress as "key [+|-]...
QLabel * dpiCustLabel
static const int TAB_ANIM
Definition: rebindwidget.h:83
void on_mbBox_currentIndexChanged(int index)
QComboBox * programKpModeBox
static const int LIGHT_DOWN
Definition: keyaction.h:131
QStringList selection
Definition: rebindwidget.h:96
QPushButton * btnStopMacro
void on_programKrBox_textChanged(const QString &arg1)
static const int DPI_CYCLE_UP
Definition: keyaction.h:126
QRadioButton * modeButton
Ui::RebindWidget * ui
Definition: rebindwidget.h:80
QTabWidget * tabWidget
QSpinBox * dpiCustYBox
QRadioButton * animButton
QStringList modKeys
Definition: rebindwidget.h:99
void helpStatus(int status)
RebindWidget::helpStatus shows a help line in the ui.
int dpiInfo(QPoint &custom) const
Definition: keyaction.cpp:211
QWidget * programKpExtra
QString getMacroPath()
KbBind::getMacroPath.
Definition: kbbind.cpp:274
MacroReader * macReader
macReader holds the MacroReader when macro recording starts.
Definition: rebindwidget.h:106
static QString lightAction(int type=LIGHT_UP_WRAP)
Definition: keyaction.cpp:169
QRadioButton * modButton
void handleNotificationChannel(bool start)
handleNotificationChannel sends commands to ckb-daemon for (de-) activating the notify channel...
Definition: kbbind.cpp:284
static const int MODE_NEXT_WRAP
Definition: keyaction.h:123
const QString & name() const
Definition: kbmode.h:50
QStringList fnKeys
Definition: rebindwidget.h:100
void on_numBox_currentIndexChanged(int index)
void noAction(const QString &key)
Definition: kbbind.cpp:181
Definition: keymap.h:8
void on_rb_delay_no_toggled(bool checked)
RebindWidget::on_rb_delay_no_toggled.
bool isAnim() const
Definition: keyaction.h:159
Definition: keymap.h:49
void on_mb2Box_currentIndexChanged(int index)
QRadioButton * typingButton
void setSelection(const QStringList &newSelection, bool applyPrevious=false)
void macroDisplay()
Debug output for invalid macro Definitions.
Definition: keyaction.cpp:456
QRadioButton * rb_delay_default
QString macroTiming() const
macroTiming returns the macro key definition with original timing infos (the fifth and up to now last...
Definition: keyaction.h:98
QComboBox * mediaBox
int programInfo(QString &onPress, QString &onRelease) const
Definition: keyaction.cpp:199
static const int MODE_NEXT
Definition: keyaction.h:122
QSpinBox * dpiCustXBox
void setAction(const QString &key, const QString &action)
Definition: kbbind.cpp:189
QStringList numKeys
Definition: rebindwidget.h:101
void on_lightBox_currentIndexChanged(int index)
static const int TAB_KB
Definition: rebindwidget.h:83
void applyChanges(const QStringList &keys, bool doUnbind)
QComboBox * lightBox
int getMacroNumber()
KbBind::getMacroNumber.
Definition: kbbind.cpp:266
QRadioButton * numButton
static const int LIGHT_DOWN_WRAP
Definition: keyaction.h:132
void on_programKpBox_textChanged(const QString &arg1)
QWidget * programKrExtra
void on_lockBox_currentIndexChanged(int index)
QString macroContent() const
macroContent returns the macro key definition only (the second part of the macro action).
Definition: keyaction.h:86
static const int LIGHT_UP_WRAP
Definition: keyaction.h:132
static const int DPI_CUST_IDX
Definition: rebindwidget.cpp:7
QCheckBox * programKrSIBox
void on_dpiButton_clicked(bool checked)
void setBind(KbBind *newBind, KbProfile *newProfile)
QComboBox * modeBox
QComboBox * mbBox
QRadioButton * rb_delay_no
bool isSpecial() const
Definition: keyaction.h:154
QComboBox * fnBox
static const int LIGHT_UP
Definition: keyaction.h:131
QComboBox * wheelBox
QComboBox * programKrModeBox
void on_rb_delay_default_toggled(bool checked)
RebindWidget::on_rb_delay_default_toggled.
void on_animBox_currentIndexChanged(int index)
struct keyAnim * anim
Definition: main.c:55
int findAnimIdx(const QUuid &guid) const
Definition: kblight.h:52
QPlainTextEdit * pteMacroComment
void on_mbButton_clicked(bool checked)
void on_animButton_clicked(bool checked)