How to build your very own keyboard firmware

ROFLmonster

29 Jan 2015, 13:28

So I've tinkered a bit, and I only need to iron some things out.

I have a function called 'showColor()' which accepts red, green and blue values and outputs it to a certain pin.
I can't seem to work out the 'ACTION_BACKLIGHT_LEVEL(BACKLIGHT_FN1)' part.
I have FN1 through FN7 set as the following in backlight.h:

Code: Select all

enum backlight_level {
BACKLIGHT_FN1    = 0b0000001,
BACKLIGHT_FN2    = 0b0000010,
BACKLIGHT_FN3    = 0b0000100,
BACKLIGHT_FN4    = 0b0001000,
BACKLIGHT_FN5    = 0b0010000,
BACKLIGHT_FN6    = 0b0100000,
BACKLIGHT_FN7    = 0b1000000,
};
And I have the 'if' statements like this:

Code: Select all

if (level & BACKLIGHT_FN1)
    {
        showColor(253,102,0);
    }
    else
    {
        showColor(0,0,0);
    }
    if (level & BACKLIGHT_FN2)
    {
        showColor(0,120,255);
    }
    else
    {
        showColor(0,0,0);
    }
//and so on...
And so on and so on, but when I press FN2 it works (cycles on/off), and FN1 does nothing.
If I add FN3, same thing. Only FN3 works and the rest don't.

I managed to make 'ACTION_BACKLIGHT_STEP()' work, and having the following conditions:

Code: Select all

void backlight_set(uint8_t level) 
{
	switch(level)
	{
		case 0: //off
		showColor(0,0,0);
		break;
		case 1: //Portal orange
		showColor(253,102,0);
		break;
		case 2: //Portal blue
		showColor(0,120,255);
		break;
//and so on..
And everything works as expected. FN1 cycles through all backlight levels.

Did I miss anything?

jip

29 Jan 2015, 14:17

If I understand your problem correctly, the issue is caused by the if ... else statements. It's only the last if ... else statement that is going to have any effect. You should instead write something like:

Code: Select all

	if (level & BACKLIGHT_FN1)
		showColor(253, 102, 0);
	else if (level & BACKLIGHT_FN2)
		showColor(0, 120, 255);
	else if (level & BACKLIGHT_FN3)
		// ... and so on...
	else
		showColor(0, 0, 0);
	/* with only ONE 'else' statement at the very end
	since this will be executed if neither of the
	previous 'if' or 'else if' statements are true */
Aside from your post, I am yet to read any of the source code mentioned in this thread; so what I am about to say may not work at all. But based on your code, I can't see any reason for you to use a bit-field (which are only useful when you need multiple flags); you might as well use the same approach as with backlight_set():

Code: Select all

	/* the values can (supposedly) be left out */
	enum backlight_level {
		BACKLIGHT_FN1,
		BACKLIGHT_FN2,
		BACKLIGHT_FN3,
		BACKLIGHT_FN4,
		BACKLIGHT_FN5,
		BACKLIGHT_FN6,
		BACKLIGHT_FN7,
	};

	/* ... and ... */

	switch (level) {
	case BACKLIGHT_FN1:
		showColor(253, 102, 0);
		break;
	case BACKLIGHT_FN2:
		showColor(0, 120, 255);
		break;
	case BACKLIGHT_FN3:
		/* ... */
		break;
	/* ...and so on... */
	default:
		showColor(0, 0, 0);
		break;
	}

ROFLmonster

29 Jan 2015, 19:14

Oh, I see.
Well I changed the follwing:
In backlight.h:

Code: Select all

enum backlight_level {
    BACKLIGHT_FN1 = 0,
    BACKLIGHT_FN2 = 2,
    BACKLIGHT_FN3 = 3,
    BACKLIGHT_FN4 = 4,
	BACKLIGHT_FN5 = 5,
	BACKLIGHT_FN6 = 6,
	BACKLIGHT_FN7 = 7,
In backlight.c:

Code: Select all

void backlight_set(uint8_t level)
{
	switch(level)
	{
		case BACKLIGHT_FN2:
			showColor(253,102,0); //Portal orange
			break;
		case BACKLIGHT_FN3:
			showColor(0,120,255); //Portal blue
			break;
		case BACKLIGHT_FN4:
			showColor(255,255,255);
			break;
		case BACKLIGHT_FN5:
			showColor(rand()%255,rand()%255,rand()%255);
			break;
		case BACKLIGHT_FN6:
			increase();
			break;
		case BACKLIGHT_FN7:
			decrease();
			break;
		default:
			showColor(0,0,0);
			break;
	}
}
And in the keymap file:

Code: Select all

const uint16_t PROGMEM fn_actions[] = {
    [0] = ACTION_LAYER_MOMENTARY(1),
	[1] = ACTION_BACKLIGHT_LEVEL(BACKLIGHT_FN1),
	[2] = ACTION_BACKLIGHT_LEVEL(BACKLIGHT_FN2),
	[3] = ACTION_BACKLIGHT_LEVEL(BACKLIGHT_FN3),
	[4] = ACTION_BACKLIGHT_LEVEL(BACKLIGHT_FN4),
	[5] = ACTION_BACKLIGHT_LEVEL(BACKLIGHT_FN5),
	[6] = ACTION_BACKLIGHT_LEVEL(BACKLIGHT_FN6),
	[7] = ACTION_BACKLIGHT_LEVEL(BACKLIGHT_FN7)
};

/* FN1 = Off
 * FN2 = Portal Orange
 * FN3 = Portal Blue
 * FN4 = White
 * FN5 = Random
 * FN6 = Increase brightness
 * FN7 = Decrease brightness
 */
And now it just randomly changes. I thought that 'ACTION_BACKLIGHT_LEVEL' sets (VARIABLE) as the 'level' value, but now I'm lost.
I'll try your first suggestion, though.
Thanks.

EDIT: Nope, your first (else if) suggestion didn't work either. I think I'm messing up the BACKLIGHT_FN values somehow...
EDIT2: So I tried with and without assigning the BACKLIGHT_FN values, using binary and decimal, using 'if's and switches.. I can't get it work, I just get seemingly random reaction.

xauser

30 Jan 2015, 21:05

If you use

Code: Select all

void backlight_set(uint8_t level)
with level beeing used as decimal increment you should use the macros

ACTION_BACKLIGHT_INCREASE()
ACTION_BACKLIGHT_DECREASE()
ACTION_BACKLIGHT_STEP()

If you use it as a bitfield then you should use the macro

ACTION_BACKLIGHT_LEVEL

mixing both will result in undefined behaviour as the macros aren't meant to be mixed. Another thing, if you use the bitmask you have only 7 bits available, not 8. 8th bit is reserved for on/off.

You only need the bitmask if you have different led channels and want to combine them in every possible way.

ROFLmonster

31 Jan 2015, 17:37

Ah, got it.

And what kind of conditions should I put in backlight.c? I'm guessing I'm gonna need an 'if' for every FN I have. (talking about having a bitmask).
Also what do you mean different channels? The backlight is only controlled from one pin, but I want to have every FN as a different "mode", and INCREASE and DECREASE is like cycling between the modes, right?

Thanks for the help!

EDIT: Another question. What is the keycode for the Menu button? The one that acts like a right-click? I typed in MENU, but it doesn't do anything. :\

xauser

31 Jan 2015, 18:12

ROFLmonster wrote: The backlight is only controlled from one pin, but I want to have every FN as a different "mode", and INCREASE and DECREASE is like cycling between the modes, right?
Yes that's what increase/decrease does. Current led api is not great and won't exactly do what you want. So you can either use increase and decrease macros or you can write your own ACTION_FUNCTION(id, opt) and pass the parameters the way you want them to be.

xauser

31 Jan 2015, 18:18

ROFLmonster wrote: Another question. What is the keycode for the Menu button? The one that acts like a right-click? I typed in MENU, but it doesn't do anything. :\
I know of LGUI, RGUI and APP but I've never used APP before.

ROFLmonster

31 Jan 2015, 18:27

xauser wrote:
ROFLmonster wrote: The backlight is only controlled from one pin, but I want to have every FN as a different "mode", and INCREASE and DECREASE is like cycling between the modes, right?
Yes that's what increase/decrease does. Current led api is not great and won't exactly do what you want. So you can either use increase and decrease macros or you can write your own ACTION_FUNCTION(id, opt) and pass the parameters the way you want them to be.

How would I do that? I tried reading the documentation (keymap.md) but it's not very clear about what I put in 'id' and 'opt'.

Also 'APP' is the one I was looking for! Thanks!

EDIT: Found this issue:
https://github.com/tmk/tmk_keyboard/issues/111

Seems simple enough, I'll try to get it working.

EDIT2: Hmm, now I get "unknown type name 'keyrecord_t' when trying the following:
http://pastebin.com/QJ5cqXng

A definition I've missed, perhaps?

xauser

31 Jan 2015, 21:50

Code: Select all

void action_function(keyrecord_t* record, uint8_t id, uint8_t opt)
should be placed in keymap.c not in backlight.c

Ah and the parameter "id" you pass to ACTION_FUNCTION(id) macro will be the one you get in action_function.

ROFLmonster

01 Feb 2015, 08:54

So should I move everything in backlight.c to my keymap (keymap_poker.c)? Because now I have all sorts of "undefined reference to 'backlight_set'" from '.../common/backlight.c'.

full error:

Code: Select all

obj_gh60_lufa/common/backlight.o: In function `backlight_init':
D:\Documents\projects\CherryMX\firmware\portalboard\keyboard\gh60/../../common/backlight.c:31: undefined reference to `backlight_set'
obj_gh60_lufa/common/backlight.o: In function `backlight_increase':
D:\Documents\projects\CherryMX\firmware\portalboard\keyboard\gh60/../../common/backlight.c:43: undefined reference to `backlight_set'
obj_gh60_lufa/common/backlight.o: In function `backlight_decrease':
D:\Documents\projects\CherryMX\firmware\portalboard\keyboard\gh60/../../common/backlight.c:55: undefined reference to `backlight_set'
obj_gh60_lufa/common/backlight.o: In function `backlight_toggle':
D:\Documents\projects\CherryMX\firmware\portalboard\keyboard\gh60/../../common/backlight.c:63: undefined reference to `backlight_set'
obj_gh60_lufa/common/backlight.o: In function `backlight_step':
D:\Documents\projects\CherryMX\firmware\portalboard\keyboard\gh60/../../common/backlight.c:76: undefined reference to `backlight_set'
obj_gh60_lufa/common/backlight.o:D:\Documents\projects\CherryMX\firmware\portalboard\keyboard\gh60/../../common/backlight.c:84: more undefined references to `backlight_set' follow
collect2.exe: error: ld returned 1 exit status
../../rules.mk:534: recipe for target 'gh60_lufa.elf' failed
make: *** [gh60_lufa.elf] Error 1

Kaibz

05 Feb 2015, 00:21

Wow Xauser and RolfMontser your converstation is really very inspiring, please keep sharing.
I'm sorry i'm too much of a noob to help you Rolf, but i would if i could.

seankeyboard

05 Feb 2015, 09:09

Where can I go to change the default RESET command?
I closed my keyboard and I don't have access to the hardware reset button
Assuming your keyboard is correctly working, software reset is it accomplished with LSHIFT + RSHIFT + PAUSE.

ROFLmonster

05 Feb 2015, 12:34

@Kaibz : Sorry but I'm still stuck there. In the meantime I'm using BACKLIGHT_STEP to cycle through all (7) modes, which is not ideal, but I check this thread from time to time and also try different solutions. So far nothing.

@seankeyboard I believe it's in the config file.
For example in ./keyboard/gh60/config.h you see:

Code: Select all

/* key combination for command */
#define IS_COMMAND() ( \
    keyboard_report->mods == (MOD_BIT(KC_LSHIFT) | MOD_BIT(KC_RSHIFT)) \
So LSHIFT + RSHIFT trigger "command", and PAUSE which is defined elsewhere calls for RESET.
What you put there instead, I'm not sure. Experiment!

User avatar
Halvar

05 Feb 2015, 15:01

ROFLmonster wrote: So should I move everything in backlight.c to my keymap (keymap_poker.c)? Because now I have all sorts of "undefined reference to 'backlight_set'" from '.../common/backlight.c'.
Not sure if I can help here ... isn't your function backlight_set() defined in backlight.c? If the compiler/linker still can't find it from other functions in backlight.c then it seems like something is wrong with the function definition.

Do you have mor than one file called backlight.c? Did you change the parameters that the function take? Or is the function definition maybe commented out or something like that? Maybe we can find it if you post your backlight.c file.

ROFLmonster

05 Feb 2015, 15:18

Halvar wrote:
ROFLmonster wrote: So should I move everything in backlight.c to my keymap (keymap_poker.c)? Because now I have all sorts of "undefined reference to 'backlight_set'" from '.../common/backlight.c'.
Not sure if I can help here ... isn't your function backlight_set() defined in backlight.c? If the compiler/linker still can't find it from other functions in backlight.c then it seems like something is wrong with the function definition.

Do you have mor than one file called backlight.c? Did you change the parameters that the function take? Or is the function definition maybe commented out or something like that? Maybe we can find it if you post your backlight.c file.
You just gave me an idea which solved my problem.
I don't actually need the backlight files when using ACTION_FUNCTION since it has nothing to do with the backlight file. The backlight file only handles the 'level' part.
It's fixed. I press FN1 = orange. FN2 = blue, etc, etc.

Thanks everyone for your help! Once I finish it I'll make sure to post a few pictures!

Edit: Forgot to actually say the solution: 'disable' backlight (BACKLIGHT_ENABLE = yes) and remove backlight.c dependency from the Makefile, and viola.

Edit 2: Now I have another (minor) problem. The function runs twice. Once when I press, second time on release. I can see that when I use FN4 it selects a random color as intended, but then switches to another random color. I can't see that on the other ones I assume because it's the same color, but they're written the same way....

Edit 3: Fixed that, too. Used "ACTION_FUNCTION_TAP" instead of just "ACTION_FUNCTION".

Kaibz

05 Feb 2015, 17:11

ROFLmonster wrote: Thanks everyone for your help! Once I finish it I'll make sure to post a few pictures!
And will you also post......your code? :oops:

ROFLmonster

05 Feb 2015, 17:46

Kaibz wrote:
ROFLmonster wrote: Thanks everyone for your help! Once I finish it I'll make sure to post a few pictures!
And will you also post......your code? :oops:
No problem, but it fits my specific layout and pinout (which is also included as a .PNG), not sure how that'll help you.

The .rar contains only the modified GH60 library since I didn't change anything else, including the WS2812B RGB LED strip libraries I used which can be found in full here: https://github.com/cpldcpu/light_ws2812 ... apa102_AVR

It's a bit messy, towards the end I just wanted to finish everything, but if something's not clear I'd be glad to help.

Mediafire link just in case:
http://www.mediafire.com/download/r958zpn0tw2g65p
Attachments
portalboard_gh60.rar
(1.08 MiB) Downloaded 280 times

GF357

05 Feb 2015, 18:17

Not sure if this the correct area... but, I've run into a small problem using this guide to build an Atomic semi grid from Jack Humbert's Ortholinear. Specifically, the caps lock LED doesn't light up. I've tested the wiring of the LED (red T1) by using the simple blink program, and it blinks happily, so the resistor (220 ohm) and wiring seem to be correct. I've changed the values in led.c to represent the pin being used - C7 on a Teensy 2. Pressing caps will cause a second keyboard to light up, and everything typed is in caps, but measuring voltage at the pin shows no change.

Any ideas?

User avatar
Halvar

05 Feb 2015, 18:28

Do you use the other LED ports (Scrollock, numlock)? Do they work?

EDIT: sorry, I just saw that led.c seems to handle only Caps Lock:

Code: Select all

void led_set(uint8_t usb_led)
{
if (usb_led & (1<<USB_LED_CAPS_LOCK)) {
// output low
DDRB |= (1<<2);
PORTB &= ~(1<<2);
} else {
// Hi-Z
DDRB &= ~(1<<2);
PORTB &= ~(1<<2);
}
}
This looks like it's setting the LED pin to low when active, so the LED would have to be soldered in between +5v and the pin, not the pin and GND. Did you do that? I'm not sure if that's also the way the blink program works.
Last edited by Halvar on 05 Feb 2015, 18:47, edited 2 times in total.

GF357

05 Feb 2015, 18:41

No, only the caps lock. And with two USB keyboards plugged in, the other keyboard lights up correctly. With only the Atomic plugged in, no lights, but the key behaves like it should.

User avatar
Halvar

05 Feb 2015, 18:45

Edited my last post.

GF357

05 Feb 2015, 18:52

Nope, the electrician in me took it to ground. Let me fire up the Hakko and move it to the +5V pin and see what happens.

GF357

05 Feb 2015, 19:05

Success! Thank you, gentlemen. Time now to add a few more lights.

seankeyboard

05 Feb 2015, 20:36

ROFLmonster wrote: @Kaibz : Sorry but I'm still stuck there. In the meantime I'm using BACKLIGHT_STEP to cycle through all (7) modes, which is not ideal, but I check this thread from time to time and also try different solutions. So far nothing.

@seankeyboard I believe it's in the config file.
For example in ./keyboard/gh60/config.h you see:

Code: Select all

/* key combination for command */
#define IS_COMMAND() ( \
    keyboard_report->mods == (MOD_BIT(KC_LSHIFT) | MOD_BIT(KC_RSHIFT)) \
So LSHIFT + RSHIFT trigger "command", and PAUSE which is defined elsewhere calls for RESET.
What you put there instead, I'm not sure. Experiment!
Does anyone know where the pause is and if I can reassign it

Kaibz

05 Feb 2015, 23:00

Thanks for sharing your code RolfMonster and to anyone else sharing/helping in this awesome thread!

ROFLmonster

06 Feb 2015, 12:43

seankeyboard wrote:
ROFLmonster wrote: @Kaibz : Sorry but I'm still stuck there. In the meantime I'm using BACKLIGHT_STEP to cycle through all (7) modes, which is not ideal, but I check this thread from time to time and also try different solutions. So far nothing.

@seankeyboard I believe it's in the config file.
For example in ./keyboard/gh60/config.h you see:

Code: Select all

/* key combination for command */
#define IS_COMMAND() ( \
    keyboard_report->mods == (MOD_BIT(KC_LSHIFT) | MOD_BIT(KC_RSHIFT)) \
So LSHIFT + RSHIFT trigger "command", and PAUSE which is defined elsewhere calls for RESET.
What you put there instead, I'm not sure. Experiment!
Does anyone know where the pause is and if I can reassign it
You can try looking into the 'common' folder in the 'command.c' file. On line 219 you have this:

Code: Select all

case KC_PAUSE:
            clear_keyboard();
            print("\n\nJump to bootloader... ");
            _delay_ms(1000);
            bootloader_jump(); // not return
            print("not supported.\n");
            break;
Change 'KC_PAUSE' to something else and give it a shot.

seankeyboard

06 Feb 2015, 19:54

ROFLmonster wrote:
seankeyboard wrote:
ROFLmonster wrote: @Kaibz : Sorry but I'm still stuck there. In the meantime I'm using BACKLIGHT_STEP to cycle through all (7) modes, which is not ideal, but I check this thread from time to time and also try different solutions. So far nothing.

@seankeyboard I believe it's in the config file.
For example in ./keyboard/gh60/config.h you see:

Code: Select all

/* key combination for command */
#define IS_COMMAND() ( \
    keyboard_report->mods == (MOD_BIT(KC_LSHIFT) | MOD_BIT(KC_RSHIFT)) \
So LSHIFT + RSHIFT trigger "command", and PAUSE which is defined elsewhere calls for RESET.
What you put there instead, I'm not sure. Experiment!
Does anyone know where the pause is and if I can reassign it
You can try looking into the 'common' folder in the 'command.c' file. On line 219 you have this:

Code: Select all

case KC_PAUSE:
            clear_keyboard();
            print("\n\nJump to bootloader... ");
            _delay_ms(1000);
            bootloader_jump(); // not return
            print("not supported.\n");
            break;
Change 'KC_PAUSE' to something else and give it a shot.

thanks! once i get my teensy in ill trsy this!

Kaibz

07 Feb 2015, 14:28

Hey RolfMonster,

I've been studying your code, and thanks again for sharing it, i must admit that i'm not as good with C as you are. The thing is, i want to use a RGB LCD to output layer number as a color (and may be custom layer names later) so of course i'm really really trying to understand how you've managed to incorporate your code inside Tmk firmware. Fist may i ask you for how long you've been studying C or general programming?

From the beginning of page 4 to the end you seem to have completely changed your method, you said you remove backlight.c dependency, and it fixed the problem, and that using ACTION_FUNCTION was the way to go...but could you please elaborate on your general method for people like me who are beginners at programming ?

I know i should ask you once i have a much better understanding of C but the problem is that may be you won't be looking at this thread in a few months or years so that's why i'm asking now if that's ok?

ROFLmonster

07 Feb 2015, 19:17

Kaibz wrote: Hey RolfMonster,

I've been studying your code, and thanks again for sharing it, i must admit that i'm not as good with C as you are. The thing is, i want to use a RGB LCD to output layer number as a color (and may be custom layer names later) so of course i'm really really trying to understand how you've managed to incorporate your code inside Tmk firmware. Fist may i ask you for how long you've been studying C or general programming?

From the beginning of page 4 to the end you seem to have completely changed your method, you said you remove backlight.c dependency, and it fixed the problem, and that using ACTION_FUNCTION was the way to go...but could you please elaborate on your general method for people like me who are beginners at programming ?

I know i should ask you once i have a much better understanding of C but the problem is that may be you won't be looking at this thread in a few months or years so that's why i'm asking now if that's ok?
I'm by no means an expert in C, I just study it as part of my engineering class for the past couple of years, and a bit earlier in school.
I just use existing libraries such as the ones I linked for the WS2812B strip and the tmk keyboard firmware collection.

Take a look here in the keymap framework:
https://github.com/tmk/tmk_keyboard/blo ... /keymap.md
It shows you how layers work and how they're programmed, it also has a bunch of examples.

In my case, I have a single pin connected to the 'DATA' pin on the LED strip, which outputs a certain data according to the light_ws2812 library (you can take a look in the datasheet of the strip itself if that interests you). I made a simple function called 'showColor' which writes RGB to the whole strip which is basically a loop that goes for <number of LEDs> times and writes the same values for LED #1, LED #2, and so on and so on.

But back on topic. The tmk firmware has a certain API to handle backlight, and it's having 'levels' of backlighting, as I understand it (Keep in mind that I can be wrong, I'm not an expert or anything). For example in my first post in the page I had 7 (FN1 through 7) levels, each has a different value. If you look in backlight.c in the common folder you'll see all the function that you saw earlier in keymap.md that I linked above which are increase (level=level+1), decrease (level=level-1), step (level=level+1 until level==number of levels, then go back to 0), toggle, and simply level (level= input), all of which work only with values with a single bit in them. (Hence the 0b0001,0b0010,etc.)
I'm not sure what went wrong when I assigned different values to each backlight level, or why it worked fine when I used 'step' (i.e. cycle through all levels), but I needed a different approach, and tmk came up with a way to run custom functions (like my 'showColor') when a button is pressed.

So when you use 'ACTION_FUNCTION(id)', it send to the function 'void action_function()' the value that is 'id', which after that can be used however you like. You also have the option of sending another value, 'opt', to whatever purpose.

In my case when you press FN4, i.e. [4]=ACTION_FUNCTION(BACKLIGHT_MODE4), it will send whichever value 'BACKLIGHT_MODE4' is (in my case, well, 4.) to the function that I mentioned above.
The 'switch(id)' is checking which of the following conditions is met, and acts accordingly. If 'id' is 1, then run this, if it's 2, run that, and so on. You get to 'case BACKLIGHT_MODE4:', and it runs the 'showColor' function and exits.

Now you want to have an LCD. Basically what you will need to do is find (or make) a library that writes to the LCD. I don't know which LCD you have, but if you mean the Arduino one (http://arduino.cc/en/Tutorial/LiquidCrystal) or the RGB one from Adafruit (http://www.adafruit.com/product/714) then you have lots of resources all over the web. Here's an example for the RGB one:
https://github.com/adafruit/Adafruit-RG ... ld-Library

In the 'hello world' example you see it uses the 'lcd.print()' function to print and 'lcd.setBacklight()' function to set the backlight color, so your firmware will look something like this:

Code: Select all

void action_function(keyrecord_t *record, uint8_t id, uint8_t opt)
{
 switch (id)
  {
   case FN1:
   lcd.print("FN1 pressed");
   break;
   case FN2:
   lcd.setbacklight(RED);
   break;
......
Luckily the Teensy has I2C pins, so if you can spare a couple of pins besides your matrix, you're golden.
Add the library header ('Adafruit_RGBLCDShield.h' for example) to your code, and you're good to go.

If you want some specific advice, me and the rest of the people here in the thread will be glad to help you.

Bonus pic: http://imgur.com/xM5uzx1

Kaibz

08 Feb 2015, 18:11

First thing i'd like to say RolfMonster is how good this RGB led implementation of your looks! Honestly i was expecting more like a "capslock" kind of RGB led at the top of the keyboard but this, is even better than a LCD as you almost have the entire area of the keyboard that can give you visual feedback, and it also looks gorgeous i must say.

I'm very tempted to buy a RBG led strip and use your code, but as a learning process i have to go through with my LCD.

You were right it's the RGB Adafruit LCD that you linked that i plan on using, but i have a couple more questions is that's all right.

1.You said that i could use the Adafruit RGB library for instance, but this library is written in C++ if i'm not mistaken? Does that mean i can still use it? Still on this topic you said that i (only?) needed the header file and add it to my code and that i would be good to go, so if i don't "need" this C++ file, then why does it exists? i m sorry if that sounds stupid to you, i'm trying to learn C as fast as i can.

2.If i understand correctly your are using FN keys to change RBG values for your strip, but in your implementation, do you also use FN keys to change layers (like a media key layer, cursor layer, mouse layer...) or only stricly for RBG values?
I'm asking because for me each layer (FN) also has a different layout for specific application, game...

3.ACTION_FUNCTION can take 2 parameters, but for the id parameter, what are the different "values" that id can take? In your case you're passing for example BACKLIGHT_MODE4 as an argument and you did that because you've "assign" BACKLIGHT_MODE4 to FN4 in const uint16_t PROGMEM fn_actions[] ? do you think it would have worked if you had simply use FNx directly as an argument and then in void action_function() and use cases for FNx instead of Backlight?
Sorry once again if that sounds stupid to you.

4.Finally for the code you generously wrote, do you think i could do 2 "actions" for each case like this:

Code: Select all

   void action_function(keyrecord_t *record, uint8_t id, uint8_t opt)
    {
     switch (id)
      {
       case FN1:
       lcd.print("FN1 activated");
       lcd.setbacklight(RED);   
    break;
       case FN2:
       lcd.print("FN2 activated");
       lcd.setbacklight(GREEN);
       break;
    ......
Even if you don't have time to answer, i just wanted to say that i really appreciate that you took the time to answer me before, i have learnt a lot.

Thank you!

Post Reply

Return to “Workshop”