Fix formatting

This commit is contained in:
Kuba Birecki 2021-12-04 19:49:56 +01:00
parent 8e5574ab49
commit 2dfec75038
5 changed files with 135 additions and 182 deletions

View file

@ -37,7 +37,8 @@ typedef void (*animation_api_prep_next_frame)(const struct device *dev);
*
* @see animation_prep_next_frame() for argument descriptions.
*/
typedef void (*animation_api_get_pixel)(const struct device *dev, const struct animation_pixel_position *pixel_position,
typedef void (*animation_api_get_pixel)(const struct device *dev,
const struct animation_pixel_position *pixel_position,
struct zmk_color_rgb *value);
struct animation_api {
@ -50,7 +51,7 @@ struct animation_api {
* @param dev [description]
*/
static inline void animation_prep_next_frame(const struct device *dev) {
const struct animation_api *api = (const struct animation_api *) dev->api;
const struct animation_api *api = (const struct animation_api *)dev->api;
return api->prep_next_frame(dev);
}
@ -60,9 +61,10 @@ static inline void animation_prep_next_frame(const struct device *dev) {
* @param dev [description]
* @param pixel [description]
*/
static inline void animation_get_pixel(const struct device *dev, const struct animation_pixel_position *pixel_position,
static inline void animation_get_pixel(const struct device *dev,
const struct animation_pixel_position *pixel_position,
struct zmk_color_rgb *value) {
const struct animation_api *api = (const struct animation_api *) dev->api;
const struct animation_api *api = (const struct animation_api *)dev->api;
return api->get_pixel(dev, pixel_position, value);
}

View file

@ -34,8 +34,8 @@ struct zmk_color_hsl {
/**
* Converts color from HSL to RGB.
*
* @param hsl [description]
* @param rgb [description]
* @param hsl Color to convert
* @param rgb Converted color
*/
void zmk_hsl_to_rgb(const struct zmk_color_hsl *hsl, struct zmk_color_rgb *rgb);
@ -43,17 +43,17 @@ void zmk_hsl_to_rgb(const struct zmk_color_hsl *hsl, struct zmk_color_rgb *rgb);
* Converts the internal RGB representation into a led_rgb struct
* for use with led_strip drivers.
*
* @param rgb [description]
* @param led [description]
* @param rgb Color to convert
* @param led Converted color
*/
void zmk_rgb_to_led_rgb(const struct zmk_color_rgb *rgb, struct led_rgb *led);
/**
* Returns true if two HSL colors are the same.
*
* @param a [description]
* @param b [description]
* @return [description]
* @param a HSL color to compare
* @param b HSL color to compare
* @return True when colors share the same values
*/
bool zmk_cmp_hsl(const struct zmk_color_hsl *a, const struct zmk_color_hsl *b);
@ -61,10 +61,10 @@ bool zmk_cmp_hsl(const struct zmk_color_hsl *a, const struct zmk_color_hsl *b);
* Perform linear interpolation between HSL values of two colors
* at a given distance (step) and store the resulting value in the given pointer.
*
* @param from [description]
* @param to [description]
* @param result [description]
* @param step [description]
* @param from HSL color to interpolate
* @param to HSL color to interpolate
* @param result Resulting HSL color
* @param step Interpolation step
*/
void zmk_interpolate_hsl(const struct zmk_color_hsl *from, const struct zmk_color_hsl *to,
struct zmk_color_hsl *result, float step);

View file

@ -25,18 +25,18 @@ LOG_MODULE_DECLARE(zmk, CONFIG_ZMK_LOG_LEVEL);
#define ZMK_DT_INST_FOREACH_PROP_ELEM(inst, prop, fn) \
UTIL_LISTIFY(DT_INST_PROP_LEN(inst, prop), fn, DT_DRV_INST(inst), prop)
#define PHANDLE_TO_DEVICE(idx, node_id, prop) \
DEVICE_DT_GET(DT_PHANDLE_BY_IDX(node_id, prop, idx)),
#define PHANDLE_TO_DEVICE(idx, node_id, prop) DEVICE_DT_GET(DT_PHANDLE_BY_IDX(node_id, prop, idx)),
#define PHANDLE_TO_CHAIN_LENGTH(idx, node_id, prop) \
DT_PROP_BY_PHANDLE_IDX(node_id, prop, idx, chain_length),
#define PHANDLE_TO_PIXEL(idx, node_id, prop) \
{ \
.animation = PHANDLE_TO_DEVICE(idx, node_id, prop) \
.position = { \
.x = DT_PHA_BY_IDX(node_id, prop, idx, position_x),\
.y = DT_PHA_BY_IDX(node_id, prop, idx, position_y),\
.animation = DEVICE_DT_GET(DT_PHANDLE_BY_IDX(node_id, prop, idx)), \
.position = \
{ \
.x = DT_PHA_BY_IDX(node_id, prop, idx, position_x), \
.y = DT_PHA_BY_IDX(node_id, prop, idx, position_y), \
}, \
},
@ -44,8 +44,7 @@ LOG_MODULE_DECLARE(zmk, CONFIG_ZMK_LOG_LEVEL);
* LED Driver device pointers.
*/
static const struct device *drivers[] = {
ZMK_DT_INST_FOREACH_PROP_ELEM(0, drivers, PHANDLE_TO_DEVICE)
};
ZMK_DT_INST_FOREACH_PROP_ELEM(0, drivers, PHANDLE_TO_DEVICE)};
/**
* Size of the LED driver device pointers array.
@ -56,15 +55,13 @@ static const size_t drivers_size = DT_INST_PROP_LEN(0, drivers);
* Array containing the number of LEDs handled by each device.
*/
static const uint8_t pixels_per_driver[] = {
ZMK_DT_INST_FOREACH_PROP_ELEM(0, drivers, PHANDLE_TO_CHAIN_LENGTH)
};
ZMK_DT_INST_FOREACH_PROP_ELEM(0, drivers, PHANDLE_TO_CHAIN_LENGTH)};
/**
* Pointers to all active animation devices.
*/
static const struct device *animations[] = {
ZMK_DT_INST_FOREACH_PROP_ELEM(0, animations, PHANDLE_TO_DEVICE)
};
ZMK_DT_INST_FOREACH_PROP_ELEM(0, animations, PHANDLE_TO_DEVICE)};
/**
* Size of the animation device pointers array.
@ -75,8 +72,7 @@ static const size_t animations_size = DT_INST_PROP_LEN(0, animations);
* Pixel configuration.
*/
static const struct animation_pixel pixels[] = {
ZMK_DT_INST_FOREACH_PROP_ELEM(0, pixels, PHANDLE_TO_PIXEL)
};
ZMK_DT_INST_FOREACH_PROP_ELEM(0, pixels, PHANDLE_TO_PIXEL)};
/**
* Size of the pixels array.
@ -108,21 +104,15 @@ static void zmk_animation_tick(struct k_work *work) {
size_t pixels_updated = 0;
for (size_t i = 0; i < drivers_size; ++i) {
led_strip_update_rgb(
drivers[i],
&px_buffer[pixels_updated],
pixels_per_driver[i]
);
led_strip_update_rgb(drivers[i], &px_buffer[pixels_updated], pixels_per_driver[i]);
pixels_updated += (size_t) pixels_per_driver;
pixels_updated += (size_t)pixels_per_driver;
}
}
K_WORK_DEFINE(animation_work, zmk_animation_tick);
static void zmk_animation_tick_handler(struct k_timer *timer) {
k_work_submit(&animation_work);
}
static void zmk_animation_tick_handler(struct k_timer *timer) { k_work_submit(&animation_work); }
K_TIMER_DEFINE(animation_tick, zmk_animation_tick_handler, NULL);

View file

@ -45,12 +45,9 @@ static void animation_solid_prep_next_frame(const struct device *dev) {
struct zmk_color_hsl next_hsl;
zmk_interpolate_hsl(
&config->colors[from],
&config->colors[to],
&next_hsl,
(data->counter % config->transition_duration) / (float) config->transition_duration
);
zmk_interpolate_hsl(&config->colors[from], &config->colors[to], &next_hsl,
(data->counter % config->transition_duration) /
(float)config->transition_duration);
data->has_changed = !zmk_cmp_hsl(&data->current_hsl, &next_hsl);
@ -60,7 +57,8 @@ static void animation_solid_prep_next_frame(const struct device *dev) {
data->counter = (data->counter + 1) % config->duration;
}
static void animation_solid_get_pixel(const struct device *dev, const struct animation_pixel_position *position,
static void animation_solid_get_pixel(const struct device *dev,
const struct animation_pixel_position *position,
struct zmk_color_rgb *value) {
const struct animation_solid_data *data = dev->data;
@ -90,55 +88,19 @@ static const struct animation_api animation_solid_api = {
\
static struct animation_solid_data animation_solid_##idx##_data; \
\
static uint32_t animation_solid_##idx##_colors[DT_INST_PROP_LEN(idx, colors)] = DT_INST_PROP(idx, colors); \
static uint32_t animation_solid_##idx##_colors[DT_INST_PROP_LEN(idx, colors)] = \
DT_INST_PROP(idx, colors); \
\
static struct animation_solid_config animation_solid_##idx##_config = { \
.colors = (struct zmk_color_hsl *) animation_solid_##idx##_colors, \
.colors = (struct zmk_color_hsl *)animation_solid_##idx##_colors, \
.num_colors = DT_INST_PROP_LEN(idx, colors), \
.duration = DT_INST_PROP(idx, duration) * CONFIG_ZMK_ANIMATION_FPS, \
.transition_duration = (DT_INST_PROP(idx, duration) * CONFIG_ZMK_ANIMATION_FPS) / DT_INST_PROP_LEN(idx, colors), \
.transition_duration = (DT_INST_PROP(idx, duration) * CONFIG_ZMK_ANIMATION_FPS) / \
DT_INST_PROP_LEN(idx, colors), \
}; \
\
DEVICE_DT_INST_DEFINE(idx, &animation_solid_init, NULL, &animation_solid_##idx##_data, \
&animation_solid_##idx##_config, POST_KERNEL, CONFIG_LED_STRIP_INIT_PRIORITY, \
&animation_solid_api);
&animation_solid_##idx##_config, POST_KERNEL, \
CONFIG_APPLICATION_INIT_PRIORITY, &animation_solid_api);
DT_INST_FOREACH_STATUS_OKAY(ANIMATION_SOLID_DEVICE);
// To do:
//
// STEP 1: single animation
// - Start with a single animation, just color
// - Add layer for taking the output from here and putting it to the led strip
// - Make it work
//
// STEP 2: areas, in fact, instead of defining them explicitly we can just use appropriate x,y coordinates and animation.
// - Split keyboard in two independent areas
// - Make it work
//
// STEP 3: add additional animation effects
// - Basically, carry over rgb_underglow.
// - Make it work
//
// STEP 4: add animation triggers
// - Allow an animation to be triggered by behaviors or key-presses
// - Make it work
//
// STEP 5: add animation layers and a MULTIPLY mode (again, opacity would be set on individual pixels so... that affects some optimizations I guess)
// - Normal mode: overrides layers below
// - Multiply mode: auguments whatever is below (opacity, whatever)
//
// Voila! Animation composition!
//
// STEP 6, BONUS!:
// - Figure out a way to switch animations during runtime?
//
// Notes:
// - Any animation settings go into 'driver' config & data, so they can be updated at runtime.
// - Main limitation is space, so the amount of different animations one can have loaded
//
// More notes:
// - Solid color would be one animation (just transitions between colors)
// - Gradient (SPECTRUM) would be another, you choose how they're distributed accross the keys and if they move?
// - Effects like 'breathe' can be implemented by specifying #000 as one of the colors or using a multiply layer?

View file

@ -19,28 +19,27 @@ static float fmod(float a, float b) {
return a < 0 ? -mod : mod;
}
static float fabs(float a) {
return a < 0 ? -a : a;
}
static float fabs(float a) { return a < 0 ? -a : a; }
/**
* HSL chosen over HSV/HSB as it shares the same parameters with LCh or HSLuv.
* The latter color spaces could be interesting to experiment with because of their
* perceptual uniformity, but it would come at the cost of some performance.
* Using the same parameters would make it easy to toggle any such behavior using a single config flag.
* Using the same parameters would make it easy to toggle any such behavior
* using a single config flag.
*
* Algorithm source: https://www.tlbx.app/color-converter
*/
void zmk_hsl_to_rgb(const struct zmk_color_hsl *hsl, struct zmk_color_rgb *rgb) {
float s = (float) hsl->s / 100;
float l = (float) hsl->l / 100;
float s = (float)hsl->s / 100;
float l = (float)hsl->l / 100;
float a = (float) hsl->h / 60;
float a = (float)hsl->h / 60;
float chroma = s * (1 - fabs(2 * l - 1));
float x = chroma * (1 - fabs(fmod(a, 2) - 1));
float m = l - chroma / 2;
switch ((uint8_t) a % 6) {
switch ((uint8_t)a % 6) {
case 0:
rgb->r = m + chroma;
rgb->g = m + x;
@ -78,9 +77,9 @@ void zmk_hsl_to_rgb(const struct zmk_color_hsl *hsl, struct zmk_color_rgb *rgb)
* Converts ZMKs RGB (float) to Zephyr's led_rgb (uint8_t) format.
*/
void zmk_rgb_to_led_rgb(const struct zmk_color_rgb *rgb, struct led_rgb *led) {
led->r = (uint8_t) (rgb->r * 255);
led->g = (uint8_t) (rgb->g * 255);
led->b = (uint8_t) (rgb->b * 255);
led->r = rgb->r * 255;
led->g = rgb->g * 255;
led->b = rgb->b * 255;
}
/**
@ -100,7 +99,7 @@ void zmk_interpolate_hsl(const struct zmk_color_hsl *from, const struct zmk_colo
hue_delta = from->h - to->h;
hue_delta = hue_delta + (180 < abs(hue_delta) ? (hue_delta < 0 ? 360 : -360) : 0);
result->h = (uint16_t) (360 + from->h - (hue_delta * step)) % 360;
result->h = (uint16_t)(360 + from->h - (hue_delta * step)) % 360;
result->s = from->s - (from->s - to->s) * step;
result->l = from->l - (from->l - to->l) * step;
}