I've run up against a very peculiar problem, replicated with test code. When upgrading my project from single to multiple LED channel control (via creating instances of the LED control class I created), I noticed both LED channels were selecting the -exact- same random colour to fade between, every time, without fail.
what I discovered, is that:
- when instance 0 chose a new colour, instance 1 would be expected to immediately choose a new one too, but it acts as if it already picked a colour, and begins following the identical colour of the first instance. This should be impossible, because the members in each class have their own private static variables which stores the led state data.
I replicated the problem with test code. Sorry for the length! It's as short as I can get it, while still replicating the programming style used. My gut feeling is a bug with the 'new' operator.
P.S. Defensive disclaimer: I'm not the best programmer of frameworks/structures in the world, but it works ;p I know there's a million and one moral crusades with regards to how certain things should be done, but in this case I'm working under the assumption the designers wouldn't leave broken features available if they knew they didn't work as intended. this is a stable release after all, perish the thought.
Tested under V1.0.3, V1.0.5, same issues.
Win 7, Arduino Mega 2560 Rev3
#include <Arduino.h>
class randomInstance {
public:
uint8_t id;
randomInstance (uint8_t instanceNum);
void memberWithStatics (bool showVars = false);
};
randomInstance::randomInstance(uint8_t instanceNum){
this->id = instanceNum;
this->memberWithStatics(); //Initialize the members with a first-run of colour selection.
};
void randomInstance::memberWithStatics(bool showVars){
static uint32_t lastExecute = millis(), ticks=0;
static uint32_t colour = random(0x0, 0xFFFFFF);
static uint32_t lastColour = 0;
if(showVars){
Serial.print(F("memberWithStatics: lastColour ")); Serial.print(lastColour, HEX);
Serial.print(F(" colour: ")); Serial.print(colour, HEX);
Serial.print(F(" ticks: ")); Serial.print(ticks);
Serial.print(F(" lastExecute: ")); Serial.print(lastExecute);
Serial.print(F(" instanceID ")); Serial.println(this->id);
return;
};
//If user didin't want variables dumped, assign new variables to everything
lastColour = colour;
colour = random(0x0, 0xFFFFFF);
lastExecute = millis();
ticks++;
};
randomInstance *instances[2]; //Pointer array for our class instances.
void setup(){
Serial.begin(115200);
//Allocate & initialize our instances
instances[0] = new randomInstance(0);
instances[1] = new randomInstance(1);
};
void loop(){
Serial.println(F("Main: Dumping current data: "));
instances[0]->memberWithStatics(true);
instances[1]->memberWithStatics(true);
//Make instance 0 pick a new colour
instances[0]->memberWithStatics();
Serial.println(F("\nMain: Instance 0 called, new dump: "));
instances[0]->memberWithStatics(true);
instances[1]->memberWithStatics(true);
//Make instance 1 pick a new colour
instances[1]->memberWithStatics();
Serial.println(F("\nMain: Instance 1 called, new dump: "));
instances[0]->memberWithStatics(true);
instances[1]->memberWithStatics(true);
delay(10000);
};
Output:
Main: Dumping current data:
memberWithStatics: lastColour 6DAE4 colour: 58EDE ticks: 2 lastExecute: 1 instanceID 0
memberWithStatics: lastColour 6DAE4 colour: 58EDE ticks: 2 lastExecute: 1 instanceID 1
Main: Instance 0 called, new dump:
memberWithStatics: lastColour 58EDE colour: E50A54 ticks: 3 lastExecute: 12 instanceID 0
memberWithStatics: lastColour 58EDE colour: E50A54 ticks: 3 lastExecute: 12 instanceID 1
Main: Instance 1 called, new dump:
memberWithStatics: lastColour E50A54 colour: F32F99 ticks: 4 lastExecute: 30 instanceID 0
memberWithStatics: lastColour E50A54 colour: F32F99 ticks: 4 lastExecute: 30 instanceID 1