Enable PWM support for Planck EZ Indicator LEDs

pull/6512/head
Drashna Jael're 5 years ago committed by Florian Didron
parent 4a5b36ec4c
commit d2100ba45d

@ -14,9 +14,13 @@
* along with this program. If not, see <http://www.gnu.org/licenses/>.
*/
#include "ez.h"
#include "ch.h"
#include "hal.h"
keyboard_config_t keyboard_config;
#ifdef RGB_MATRIX_ENABLE
#ifdef RGB_MATRIX_ENABLE
void suspend_power_down_kb(void) {
rgb_matrix_set_suspend_state(true);
suspend_power_down_user();
@ -114,43 +118,150 @@ led_config_t g_led_config = { {
#endif
void matrix_init_kb(void) {
matrix_init_user();
// See http://jared.geek.nz/2013/feb/linear-led-pwm
static uint16_t cie_lightness(uint16_t v) {
if (v <= 5243) // if below 8% of max
return v / 9; // same as dividing by 900%
else {
uint32_t y = (((uint32_t) v + 10486) << 8) / (10486 + 0xFFFFUL); // add 16% of max and compare
// to get a useful result with integer division, we shift left in the expression above
// and revert what we've done again after squaring.
y = y * y * y >> 8;
if (y > 0xFFFFUL) // prevent overflow
return 0xFFFFU;
else
return (uint16_t) y;
}
}
palSetPadMode(GPIOB, 8, PAL_MODE_OUTPUT_PUSHPULL);
palSetPadMode(GPIOB, 9, PAL_MODE_OUTPUT_PUSHPULL);
static PWMConfig pwmCFG = {
0xFFFF,/* PWM clock frequency */
256,/* initial PWM period (in ticks) 1S (1/10kHz=0.1mS 0.1ms*10000 ticks=1S) */
NULL,
{
{PWM_OUTPUT_DISABLED, NULL}, /* channel 0 -> TIM1-CH1 = PA8 */
{PWM_OUTPUT_DISABLED, NULL}, /* channel 1 -> TIM1-CH2 = PA9 */
{PWM_OUTPUT_ACTIVE_HIGH, NULL},
{PWM_OUTPUT_ACTIVE_HIGH, NULL}
},
0, /* HW dependent part.*/
0
};
palClearPad(GPIOB, 8);
palClearPad(GPIOB, 9);
static uint32_t planck_ez_right_led_duty;
static uint32_t planck_ez_left_led_duty;
void planck_ez_right_led_level(uint8_t level) {
planck_ez_right_led_duty = (uint32_t)(cie_lightness(0xFFFF * (uint32_t) level / 255));
if (level == 0) {
// Turn backlight off
pwmDisableChannel(&PWMD4, 2);
} else {
// Turn backlight on
pwmEnableChannel(&PWMD4, 2, PWM_FRACTION_TO_WIDTH(&PWMD4,0xFFFF,planck_ez_right_led_duty));
}
}
void matrix_scan_kb(void) {
matrix_scan_user();
void planck_ez_right_led_on(void){
pwmEnableChannel(&PWMD4, 2, PWM_FRACTION_TO_WIDTH(&PWMD4,0xFFFF,planck_ez_right_led_duty));
}
layer_state_t layer_state_set_kb(layer_state_t state) {
palClearPad(GPIOB, 8);
palClearPad(GPIOB, 9);
state = layer_state_set_user(state);
uint8_t layer = biton32(state);
switch (layer) {
case 3:
palSetPad(GPIOB, 9);
break;
case 4:
palSetPad(GPIOB, 8);
break;
case 6:
palSetPad(GPIOB, 9);
palSetPad(GPIOB, 8);
break;
default:
break;
void planck_ez_right_led_off(void){
pwmDisableChannel(&PWMD4, 2);
}
void planck_ez_left_led_level(uint8_t level) {
planck_ez_left_led_duty = (uint32_t)(cie_lightness(0xFFFF * (uint32_t) level / 255));
if (level == 0) {
// Turn backlight off
pwmDisableChannel(&PWMD4, 3);
} else {
// Turn backlight on
pwmEnableChannel(&PWMD4, 3, PWM_FRACTION_TO_WIDTH(&PWMD4,0xFFFF,planck_ez_left_led_duty));
}
}
void planck_ez_left_led_on(void){
pwmEnableChannel(&PWMD4, 3, PWM_FRACTION_TO_WIDTH(&PWMD4,0xFFFF,planck_ez_left_led_duty));
}
void planck_ez_left_led_off(void){
pwmDisableChannel(&PWMD4, 3);
}
void led_initialize_hardware(void) {
pwmStart(&PWMD4, &pwmCFG);
// set up defaults
planck_ez_right_led_level((uint8_t)keyboard_config.led_level * 255 / 4 );
palSetPadMode(GPIOB, 8, PAL_MODE_ALTERNATE(2));
planck_ez_left_led_level((uint8_t)keyboard_config.led_level * 255 / 4 );
palSetPadMode(GPIOB, 9, PAL_MODE_ALTERNATE(2));
// turn LEDs off by default
planck_ez_left_led_off();
planck_ez_right_led_off();
}
void keyboard_pre_init_kb(void) {
// read kb settings from eeprom
keyboard_config.raw = eeconfig_read_kb();
// initialize settings for front LEDs
led_initialize_hardware();
}
void eeconfig_init_kb(void) { // EEPROM is getting reset!
keyboard_config.raw = 0;
keyboard_config.led_level = 4;
eeconfig_update_kb(keyboard_config.raw);
eeconfig_init_user();
}
uint32_t layer_state_set_kb(uint32_t state) {
planck_ez_left_led_off();
planck_ez_right_led_off();
state = layer_state_set_user(state);
uint8_t layer = biton32(state);
switch (layer) {
case 3:
planck_ez_left_led_on();
break;
case 4:
planck_ez_right_led_on();
break;
case 6:
planck_ez_right_led_on();
planck_ez_left_led_on();
break;
default:
break;
}
return state;
}
bool process_record_kb(uint16_t keycode, keyrecord_t *record) {
switch (keycode) {
case LED_LEVEL:
if (record->event.pressed) {
keyboard_config.led_level++;
if (keyboard_config.led_level > 4) {
keyboard_config.led_level = 0;
}
planck_ez_right_led_level((uint8_t)keyboard_config.led_level * 255 / 4 );
planck_ez_left_led_level((uint8_t)keyboard_config.led_level * 255 / 4 );
eeconfig_update_kb(keyboard_config.raw);
layer_state_set_kb(layer_state);
}
break;
}
return process_record_user(keycode, record);
}
#ifdef AUDIO_ENABLE
bool music_mask_kb(uint16_t keycode) {
switch (keycode) {

@ -50,3 +50,24 @@ LAYOUT_planck_1x2uC( \
#define KEYMAP LAYOUT_ortho_4x12
#define LAYOUT_planck_mit LAYOUT_planck_1x2uC
#define LAYOUT_planck_grid LAYOUT_ortho_4x12
void planck_ez_right_led_on(void);
void planck_ez_right_led_off(void);
void planck_ez_right_led_level(uint8_t level);
void planck_ez_left_led_on(void);
void planck_ez_left_led_off(void);
void planck_ez_left_led_level(uint8_t level);
enum planck_ez_keycodes {
LED_LEVEL = SAFE_RANGE,
EZ_SAFE_RANGE,
};
typedef union {
uint32_t raw;
struct {
uint8_t led_level :3;
};
} keyboard_config_t;
extern keyboard_config_t keyboard_config;

@ -48,7 +48,7 @@
* @details Frequency of the system timer that drives the system ticks. This
* setting also defines the system tick time unit.
*/
#define CH_CFG_ST_FREQUENCY 100000
#define CH_CFG_ST_FREQUENCY 1000
/**
* @brief Time delta constant for the tick-less mode.
@ -58,7 +58,7 @@
* The value one is not valid, timeouts are rounded up to
* this value.
*/
#define CH_CFG_ST_TIMEDELTA 2
#define CH_CFG_ST_TIMEDELTA 0
/** @} */

@ -111,7 +111,7 @@
* @brief Enables the PWM subsystem.
*/
#if !defined(HAL_USE_PWM) || defined(__DOXYGEN__)
#define HAL_USE_PWM FALSE
#define HAL_USE_PWM TRUE
#endif
/**

@ -185,7 +185,7 @@
#define STM32_PWM_USE_TIM1 FALSE
#define STM32_PWM_USE_TIM2 TRUE
#define STM32_PWM_USE_TIM3 TRUE
#define STM32_PWM_USE_TIM4 FALSE
#define STM32_PWM_USE_TIM4 TRUE
#define STM32_PWM_USE_TIM8 FALSE
#define STM32_PWM_TIM1_IRQ_PRIORITY 7
#define STM32_PWM_TIM2_IRQ_PRIORITY 7

Loading…
Cancel
Save