Future Electronics / Mbed OS sequana-rgb-led_summmit2019
Committer:
Seb_Sok
Date:
Mon Mar 18 13:17:00 2019 +0000
Revision:
3:b5cec57779aa
Parent:
2:a83100cd9c9a
Child:
4:59c5b7dee5bc
First revision.

Who changed what in which revision?

UserRevisionLine numberNew contents of line
lru 0:da2de84c3c04 1 /*
lru 0:da2de84c3c04 2 * Mbed OS example program for Future Electronics Sequana board.
lru 0:da2de84c3c04 3 *
lru 0:da2de84c3c04 4 * Copyright (c) 2018 Future Electronics
lru 0:da2de84c3c04 5 *
lru 0:da2de84c3c04 6 * Licensed under the Apache License, Version 2.0 (the "License");
lru 0:da2de84c3c04 7 * you may not use this file except in compliance with the License.
lru 0:da2de84c3c04 8 * You may obtain a copy of the License at
lru 0:da2de84c3c04 9 *
lru 0:da2de84c3c04 10 * http://www.apache.org/licenses/LICENSE-2.0
lru 0:da2de84c3c04 11 *
lru 0:da2de84c3c04 12 * Unless required by applicable law or agreed to in writing, software
lru 0:da2de84c3c04 13 * distributed under the License is distributed on an "AS IS" BASIS,
lru 0:da2de84c3c04 14 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
lru 0:da2de84c3c04 15 * See the License for the specific language governing permissions and
lru 0:da2de84c3c04 16 * limitations under the License.
lru 0:da2de84c3c04 17 */
lru 0:da2de84c3c04 18
lru 0:da2de84c3c04 19 // This example demonstrates used of ROHM BD2808 24-channel LED Controller
lru 0:da2de84c3c04 20 // and its driver library on Sequana board.
lru 0:da2de84c3c04 21
lru 0:da2de84c3c04 22 #include "mbed.h"
lru 0:da2de84c3c04 23 #include "BD2808.h"
lru 0:da2de84c3c04 24
lru 0:da2de84c3c04 25 BD2808 leds;
lru 0:da2de84c3c04 26
lru 2:a83100cd9c9a 27 // Return new color value by dimming the current color to x%
lru 0:da2de84c3c04 28 BGR24_color_t dim(BGR24_color_t color, uint8_t percent)
lru 0:da2de84c3c04 29 {
lru 0:da2de84c3c04 30 BGR24_color_t new_color;
lru 0:da2de84c3c04 31
lru 0:da2de84c3c04 32 new_color.r = color.r * percent / 100;
lru 0:da2de84c3c04 33 new_color.g = color.g * percent / 100;
lru 0:da2de84c3c04 34 new_color.b = color.b * percent / 100;
lru 0:da2de84c3c04 35
lru 0:da2de84c3c04 36 return new_color;
lru 0:da2de84c3c04 37 }
lru 0:da2de84c3c04 38
lru 0:da2de84c3c04 39 #define sat(x) (uint8_t)((x) > 255? 255 : (x) < 0? 0 : (x))
lru 0:da2de84c3c04 40
lru 2:a83100cd9c9a 41 // This function generates color sequence. Each call to this function
lru 2:a83100cd9c9a 42 // returns the next color in a sequence.
lru 2:a83100cd9c9a 43 // Color sequence generation algorithm is such, that it provides
lru 2:a83100cd9c9a 44 // smooth color swipe, keeping intensity roughly the same.
lru 0:da2de84c3c04 45 BGR24_color_t gen_color()
lru 0:da2de84c3c04 46 {
lru 2:a83100cd9c9a 47 const uint8_t step = 40;
lru 0:da2de84c3c04 48 const uint8_t max = 200;
lru 2:a83100cd9c9a 49 static uint32_t phase = 0;
lru 0:da2de84c3c04 50 static int32_t r = max;
lru 0:da2de84c3c04 51 static int32_t g = max;
lru 0:da2de84c3c04 52 static int32_t b = 0;
lru 2:a83100cd9c9a 53 static int32_t base_level = 6;
lru 0:da2de84c3c04 54
lru 2:a83100cd9c9a 55 #define step_up(x) do { if ((x += step) > max) x = max; } while(0)
lru 2:a83100cd9c9a 56 #define step_down(x, v) do { x -= step; if (x < v) x = v;} while (0)
lru 0:da2de84c3c04 57
lru 2:a83100cd9c9a 58 switch (phase) {
lru 2:a83100cd9c9a 59 case 0:
lru 2:a83100cd9c9a 60 // swiping from reddish into blueish
lru 2:a83100cd9c9a 61 step_down(r, 0);
lru 2:a83100cd9c9a 62 g = base_level;
lru 2:a83100cd9c9a 63 step_up(b);
lru 2:a83100cd9c9a 64 if (r == 0) phase++;
lru 2:a83100cd9c9a 65 break;
lru 2:a83100cd9c9a 66 case 1:
lru 2:a83100cd9c9a 67 // swiping from blueish into greenish to level off blue
lru 2:a83100cd9c9a 68 r = 0;
lru 2:a83100cd9c9a 69 step_up(g);
lru 2:a83100cd9c9a 70 step_down(b, base_level);
lru 2:a83100cd9c9a 71 if (b == base_level) phase++;
lru 2:a83100cd9c9a 72 break;
lru 2:a83100cd9c9a 73 case 2:
lru 2:a83100cd9c9a 74 // swiping from greenish into reddish
lru 2:a83100cd9c9a 75 step_up(r);
lru 2:a83100cd9c9a 76 step_down(g, 0);
lru 2:a83100cd9c9a 77 b = base_level;
lru 2:a83100cd9c9a 78 if (g == 0) phase++;
lru 2:a83100cd9c9a 79 break;
lru 2:a83100cd9c9a 80 case 3:
lru 2:a83100cd9c9a 81 // swiping from reddish into blueish to level off red
lru 2:a83100cd9c9a 82 step_down(r, base_level);
lru 2:a83100cd9c9a 83 g = 0;
lru 2:a83100cd9c9a 84 step_up(b);
lru 2:a83100cd9c9a 85 if (r == base_level) phase++;
lru 2:a83100cd9c9a 86 break;
lru 2:a83100cd9c9a 87 case 4:
lru 2:a83100cd9c9a 88 // swiping from blueish into greenish
lru 2:a83100cd9c9a 89 r = base_level;
lru 2:a83100cd9c9a 90 step_up(g);
lru 2:a83100cd9c9a 91 step_down(b, 0);
lru 2:a83100cd9c9a 92 if (b == 0) phase++;
lru 2:a83100cd9c9a 93 break;
lru 2:a83100cd9c9a 94 case 5:
lru 2:a83100cd9c9a 95 // swiping from greenish into reddish to level off green
lru 2:a83100cd9c9a 96 step_up(r);
lru 2:a83100cd9c9a 97 step_down(g, base_level);
lru 2:a83100cd9c9a 98 b = 0;
lru 2:a83100cd9c9a 99 if (g == base_level) {
lru 2:a83100cd9c9a 100 phase = 0;
lru 2:a83100cd9c9a 101 base_level *= 2;
lru 2:a83100cd9c9a 102 if (base_level > 200) {
lru 2:a83100cd9c9a 103 base_level = 6;
lru 2:a83100cd9c9a 104 }
lru 2:a83100cd9c9a 105 g = base_level;
lru 0:da2de84c3c04 106 }
lru 2:a83100cd9c9a 107 break;
lru 0:da2de84c3c04 108 }
lru 0:da2de84c3c04 109
lru 0:da2de84c3c04 110 return BGR24_color_t(sat(b), sat(g), sat(r));
lru 0:da2de84c3c04 111 }
lru 0:da2de84c3c04 112
lru 0:da2de84c3c04 113 #define NUM_LEDS_LIGHTING 3
lru 0:da2de84c3c04 114
lru 2:a83100cd9c9a 115 // Keeps indexes of LEDs that should be on in the next step.
Seb_Sok 3:b5cec57779aa 116 uint32_t led_index;
Seb_Sok 3:b5cec57779aa 117 uint32_t dir_flag = 0, button_was_pressed_counter = 0;
Seb_Sok 3:b5cec57779aa 118
lru 2:a83100cd9c9a 119 // Current color.
lru 0:da2de84c3c04 120 BGR24_color_t current_col[NUM_LEDS_LIGHTING];
lru 0:da2de84c3c04 121
Seb_Sok 3:b5cec57779aa 122 // User button initialization
Seb_Sok 3:b5cec57779aa 123 DigitalIn UserButton(P0_4, PullUp);
Seb_Sok 3:b5cec57779aa 124
lru 0:da2de84c3c04 125 // main() runs in its own thread in the OS
lru 0:da2de84c3c04 126 int main() {
Seb_Sok 3:b5cec57779aa 127 int color_step = 0, led_counter = 0;
lru 0:da2de84c3c04 128
lru 0:da2de84c3c04 129 leds.set_dma_usage(DMA_USAGE_ALWAYS);
lru 0:da2de84c3c04 130
Seb_Sok 3:b5cec57779aa 131 // Infinite loop
lru 0:da2de84c3c04 132 while (true) {
Seb_Sok 3:b5cec57779aa 133
Seb_Sok 3:b5cec57779aa 134 // Checks if the button is pressed.
Seb_Sok 3:b5cec57779aa 135 if(UserButton == 0 && button_was_pressed_counter == 0)
Seb_Sok 3:b5cec57779aa 136 {
Seb_Sok 3:b5cec57779aa 137 // Changing the direction of rotation of the leds.
Seb_Sok 3:b5cec57779aa 138 // If dir_flag is 1 then rotate right otherwise rotate left.
Seb_Sok 3:b5cec57779aa 139 if(dir_flag == 1) dir_flag = 0;
Seb_Sok 3:b5cec57779aa 140 else dir_flag = 1;
Seb_Sok 3:b5cec57779aa 141
Seb_Sok 3:b5cec57779aa 142 button_was_pressed_counter = 5;
Seb_Sok 3:b5cec57779aa 143 }
Seb_Sok 3:b5cec57779aa 144
Seb_Sok 3:b5cec57779aa 145 // If the button was pressed wait for 400 ms (5 * 80 ms) to eliminate vibrations contacts.
Seb_Sok 3:b5cec57779aa 146 if(button_was_pressed_counter){
Seb_Sok 3:b5cec57779aa 147 button_was_pressed_counter--;
Seb_Sok 3:b5cec57779aa 148 }
Seb_Sok 3:b5cec57779aa 149
lru 2:a83100cd9c9a 150 // This defines phase relationship between rotating pattern
lru 2:a83100cd9c9a 151 // and color change.
lru 2:a83100cd9c9a 152 // As there are 8 steps for the whole circle (8 LEDs)
lru 2:a83100cd9c9a 153 // value of 6 means the color changes every 3/4 of rotation.
Seb_Sok 3:b5cec57779aa 154 if (++color_step == 6) {
lru 2:a83100cd9c9a 155 color_step = 0;
lru 2:a83100cd9c9a 156 current_col[2] = gen_color();
Seb_Sok 3:b5cec57779aa 157 current_col[1] = dim(current_col[2], 25);
Seb_Sok 3:b5cec57779aa 158 current_col[0] = dim(current_col[2], 5);
lru 2:a83100cd9c9a 159 }
lru 2:a83100cd9c9a 160
lru 2:a83100cd9c9a 161 // Set up lighting pattern for current step.
Seb_Sok 3:b5cec57779aa 162 for (int i = 0; i < NUM_LEDS_LIGHTING; i++) {
Seb_Sok 3:b5cec57779aa 163
Seb_Sok 3:b5cec57779aa 164
Seb_Sok 3:b5cec57779aa 165 if(led_counter + i > 7) led_index = led_counter + i - 8;
Seb_Sok 3:b5cec57779aa 166 else led_index = led_counter + i;
Seb_Sok 3:b5cec57779aa 167
Seb_Sok 3:b5cec57779aa 168 // The function is used to change the direction of the "tail".
Seb_Sok 3:b5cec57779aa 169 //if(dir_flag){
Seb_Sok 3:b5cec57779aa 170 leds.set_color(led_index, current_col[(NUM_LEDS_LIGHTING - 1) - i]);
Seb_Sok 3:b5cec57779aa 171 //}
Seb_Sok 3:b5cec57779aa 172 //else{
Seb_Sok 3:b5cec57779aa 173 // leds.set_color(led_index, current_col[i]);
Seb_Sok 3:b5cec57779aa 174 //}
lru 0:da2de84c3c04 175 }
Seb_Sok 3:b5cec57779aa 176
Seb_Sok 3:b5cec57779aa 177 // Turn off / turn on all the buffer of leds prepared above.
lru 0:da2de84c3c04 178 leds.refresh();
lru 0:da2de84c3c04 179
Seb_Sok 3:b5cec57779aa 180 // Do nothing for 80 ms
Seb_Sok 3:b5cec57779aa 181 wait_ms(80);
Seb_Sok 3:b5cec57779aa 182
Seb_Sok 3:b5cec57779aa 183 // The function is used to change the direction of rotation of the leds depending on "dir_flag".
Seb_Sok 3:b5cec57779aa 184 if(UserButton){
Seb_Sok 3:b5cec57779aa 185 if(++led_counter > 7) led_counter = 0; // Right turn
Seb_Sok 3:b5cec57779aa 186 }
Seb_Sok 3:b5cec57779aa 187 //else{
Seb_Sok 3:b5cec57779aa 188 // if(--led_counter < 0) led_counter = 7; // Left turn
Seb_Sok 3:b5cec57779aa 189 //}
Seb_Sok 3:b5cec57779aa 190
Seb_Sok 3:b5cec57779aa 191 // Turn off all LEDs, so we have a dark frame buffer again.
lru 2:a83100cd9c9a 192 // Must be done after delay, as with DMA refresh() operation
lru 2:a83100cd9c9a 193 // only starts LEDs updating from the frame buffer.
Seb_Sok 3:b5cec57779aa 194 for (int i = 0; i < 8; i++) {
Seb_Sok 3:b5cec57779aa 195 leds.set_color(i, BGR24_color_t(0,0,0));
Seb_Sok 3:b5cec57779aa 196 }
Seb_Sok 3:b5cec57779aa 197
lru 0:da2de84c3c04 198
lru 0:da2de84c3c04 199 }
Seb_Sok 3:b5cec57779aa 200
lru 0:da2de84c3c04 201 }