Got your Blink to blink? Great! Now, let’s make a Blink blush
If successful, this code will make it so that when the button is pushed, the blink should glow pink in the cheeks. On a single click, the cheeks will ramp up and then back down.
This example introduces #define
as a way of setting some global variables that will not change in addition to static const
, another way of doing the same. I’ve chosen to calculate our static const
variables from our #define
.
We respond to input from the button using buttonSingleClicked()
and use setFaceColor()
to illuminate only two of our 6 display LEDs.
To get started, let’s set some values that we know we’ll need, such as the duration of blushing (1.25s seconds), the rate at which we’ll change the blush brightness (every 30ms or ~33Hz), and the maximum brightness of our blushing.
#define BLUSH_DURATION_MS 1250
#define BLUSH_STEP_RATE_MS 30
#define MAX_BRIGHTNESS 255
We’ll need to know how much to increase our brightness each time we step up or down, so we compute how much to change based on the duration of our blush and how often we step.
First we calculate the number of steps that fit into a single blush
static const byte blushStepCount = BLUSH_DURATION_MS / BLUSH_STEP_RATE_MS;
Then we divide the maximum brightness by that number of steps
static const byte blushStepSize = MAX_BRIGHTNESS / blushStepCount;
Timers are going to make sure that we update as a specific rate. Since loop()
runs at a variable rate, depending on how many instructions are given inside of loop()
, we can’t count on it as a time accurate source. Timers are perfect for this.
We’ll use one for how long to blush for, and one to keep a constant pace for our brightness steps.
Timer blushTimer;
Timer blushStepTimer;
Lastly, we’ll want to know whether we are increasing or decreasing our blush and our current blush brightness.
bool isBlushIncreasing;
byte blushBrightness = 0;
Our setup is simple, it only needs to start us out with blush not increasing
void setup() {
// this only happens once
isBlushIncreasing = false;
}
Now let’s start on the logic:
First we check to see our inputs. Did the button get clicked?
if(buttonSingleClicked()) {
blushTimer.set(BLUSH_DURATION_MS );
isBlushIncreasing = true;
}
The entire application looks like:
/*
* Your second Blinks application
* that makes me blush :)
*/
#define BLUSH_DURATION_MS 1250
#define BLUSH_STEP_RATE_MS 30
#define MAX_BRIGHTNESS 255
static const byte blushStepCount = BLUSH_DURATION_MS / BLUSH_STEP_RATE_MS;
static const byte blushStepSize = MAX_BRIGHTNESS / blushStepCount;
Timer blushTimer;
Timer blushStepTimer;
bool isBlushIncreasing;
byte blushBrightness = 0;
void setup() {
// this only happens once
isBlushIncreasing = false;
}
void loop() {
// put your main code here, to run repeatedly:
if(buttonSingleClicked()) {
blushTimer.set(BLUSH_DURATION_MS );
isBlushIncreasing = true;
}
if(blushTimer.isExpired()) {
if(isBlushIncreasing) {
blushTimer.set(BLUSH_DURATION_MS );
isBlushIncreasing = false;
}
else {
// wait to be tickled pink again :)
}
}
if(blushStepTimer.isExpired()) {
if(isBlushIncreasing) {
if(blushBrightness < MAX_BRIGHTNESS - blushStepSize) {
blushBrightness += blushStepSize;
}
}
else {
if(blushBrightness > blushStepSize) {
blushBrightness -= blushStepSize;
}
}
blushStepTimer.set(BLUSH_STEP_RATE_MS);
}
// display brightness in "cheeks"
setFaceColor(0, dim(RED, blushBrightness));
setFaceColor(3, dim(RED, blushBrightness));
}