I am trying to control a TLC5955 LED driver with an Arduino Uno. The TLC5955 contains a 769 bit shift register which can be used to control the driver. I have studied the datasheet and determined the correct bit values for my project to load into the TLC 5955 register but since the Dot Correction values, Brightness Control values are 7 bits long and some other values are 3 bits long, I am unable to send each value over using the shiftOut() function (as it transfers values in a byte format). I ended up writing a program to concatenate the different values to output 6 "64 bit long integers" so that it can be shifted into the register. I then implemented a simple "for loop" to bitshift each byte of the 64 bit integer into an 8 bit integer variable which is then transferred using the shiftOut() function. This was initially implemented in the main loop of the code for testing purposes.
This seemed to work as verified by an oscilloscope. However, for the TLC5955, I initially need to send out 769 bits to set up the driver and then repeatedly send out PWM values for each of the LEDs. However, when I copy the piece of code, mentioned above, to the setup() function, the shiftOut() function no longer works. I assumed this function cannot run in the setup() section so then I tried implementing the function in the main loop with an if statement which will only allow the "setup data" to be transferred once (please see code below). This also failed to work and I'm not sure why its only failing for this particular case.
The code shown below is a simplified version of the main project code to isolate and test the shiftOut() function. The code, as shown below, is set up to send out an arbitrary 64 bit integer once in the main loop and then do nothing.
#define CLK 13
#define D 11
#define B 8
#define CLOCKOUT 9
bool set = false;
uint8_t out = 0; //final output variable
uint64_t preout = 0; //64 bit integer to hold control values
void setup() {
pinMode(D,OUTPUT);
pinMode(CLK,OUTPUT);
}
void loop() {
if(set==false){
preout = 0b1111110111111111111111111111111111111111111111111010111111111111;
for(int i=7;i>=0;i--){
out = preout >> i*B;
shiftOut(D,CLK,MSBFIRST, out);
}
set = true;
}
//do nothing
}
My Questions are as follows:
Can the shiftOut() function be called in the setup() portion of an Arduino code?
Why is the function failing only when configured to run once?
I'm fairly new to Arduino programming and any help would be greatly appreciated.
Thank you for your response. The CLOCKOUT(9) is an unused part of the code leftover from the main project code.
I also had debugged this using serial and it seemed to work but whenever I probe the data lines with an oscilloscope, I don't see any data coming through during the setup portion. As I mentioned before, the data only appears when the shiftOut() function is in the main loop() and not configured to run once. I am attaching the oscope captures here.
The captures below were taken immediately after hitting the reset button on the Arduino. Ch 1 (yellow) is the clock pin and Ch 2 (Blue) is the data pin. In one of the captures, where the setup data is configured to transfer once, we can see that the clock pin remains idle and no data is transferred.
Your results are certainly bizarre. I have no explanation for what you are seeing. I suspect that the 64-bit operations are encountering some kind of error. Have you tried an 8-byte array?
Oops. Thanks for correcting the bug. The array also works in the loop() section but whenever it is configured to run only once, the shiftOut() function stops working and clock pin remains idle. It seems like the effect is exactly the same as before but instead of pulling the data pin high at the end of setup, it pulls the data pin low. It still doesn't transfer the initial setup data "once".
Is it possible that there are some hardware connection conflicts with the 2 pins that I'm using? I'll try to switch up the pins and see if I can get any different results. Any other advice or suggestions you may have would be greatly appreciated.
In my trials, 64 bit integers did work but only when the shiftOut() was configured to run in a loop. It does not want to run when configured to send the 64 bit value only once during startup. Any suggestions or tips would be appreciated.
That makes me wonder if the problem is in the "do only once" technique. Maybe something is writing into 'set' and changing it to true before loop()?!?
Since you aren't including the SPI library it is unlikely the SPI pins (10, 11, 12, 13) are doing anything you don't tell them to do. Are you testing with nothing connected to the pins?
I just tested with other pins and its the exact same effect. The pins have no load on them. They are only probed with the oscope.
It may be possible. But wouldn't that still allow data to be transmitted when implemented in the setup() section? I just tested the code in setup() and the clock pin remains idle.
#define CLK 9
#define D 6
#define B 8
bool set = false;
uint8_t out = 0; //64bit variable used as output buffer
//uint64_t preout = 0;
const uint8_t preout[8] = {0b11111101, 0b11111111, 0b11111111, 0b11111111, 0b11111111, 0b11111111, 0b10101111, 0b11111111};
void setup() {
pinMode(D,OUTPUT);
pinMode(CLK,OUTPUT);
for(int i=0;i<sizeof(preout);i++){
out = preout[i];
shiftOut(D,CLK,MSBFIRST, out);
}
}
void loop() {
/*
if(set==false){
//preout = 0b1111110111111111111111111111111111111111111111111010111111111111;
for(int i=0;i<sizeof(preout);i++){
out = preout[i];
shiftOut(D,CLK,MSBFIRST, out);
}
set = true;
}
*/
}