Introduction: Easy Bluetooth Controlled Scrolling Text

Picture of Easy Bluetooth Controlled Scrolling Text

Hi all,

In this Instructable, I'll show you how to create a simple scrolling text, using led matrix modules. These modules are cheap and easy to use. And, to make this project more fun, a bluetooth feature was added : you will be able to send a message to the system using a mobile phone !

I'll show you how to wire the system with an arduino card, how the program works, and how to use the device with a smart-phone. If you don't want to use the bluetooth feature, just check the last step to see how to do the same with the arduino serial port.

Follow these simple steps to get a nice gadget !!

Any comments for help, tips, and ideas are welcome !

10k views ! Many thanks !!

Step 1: Stuff Needed

Picture of Stuff Needed

Ok, to create this, you will need :

  • an arduino card, with 3v3 logic levels : here, an arduino Nano. You can also use an UNO, but you will have to add a level converter.
  • a HC06 bluetooth serial module. Search for "arduino bluetooth serial module" on the web. You will be able to find it easily.
  • one or more led matrix modules. You can find them on the web, check "MAX7219 led matrix modules". You can find them ready to sue, or as a kit "ready for soldering".
  • breadboard wire, and a breadboard.
  • Usb cable for the arduino card.
  • (optional) rubbers
  • (optional) power supply for the arduino card.

Step 2: Note on the Matrix Modules

Picture of Note on the Matrix Modules

Again, these modules are cheap, and easy to find. The great thing about these is that you can wire them in series (8 max), all the boring hardware aspects are handled by the library and the MAX7219 chip.

The problem is that you can't directly put them side by side, because of the connectors. You can put them side by side vertically, but the wiring is complicated. (The wires are under the modules...)

The solution is to put them head to tail, like the final picture. You will say "it will not work, as the rows and columns are toggled". Yes, but don't worry, my program handles this, and flip the pixels every two modules, to get a perfect rendering !

My tip : use small rubbers to keep them in contact. Of course, for a nice finishing, you can fix them on a piece of wood, or similar.

Step 3: How It Works

Ok, the program is quite simple :

  • the arduino starts. A sample message is displayed on the led matrices.
  • if nothing happens on the bluetooth module, the stored message stays on the screens.
  • meanwhile, the arduino program check the serial port (where the bluetooth module is connected). If nothing is on the buffer, the same message keeps "turning".
  • if some data is available on the virtual serial port, the message is downloaded, and replaces the previous message.

The bluetooth modules acts as a serial client. All the boring connecting/security aspects are handled by the module. In fact, the bluetooth module is connected by two TX/RX signals, and acts as a serial port, just like a computer. A bluetooth client terminal on the phone handles the connection, and allow the user to send and receive text.

Step 4: Wiring the Led Matrices

Picture of Wiring the Led Matrices

Ok, the wiring is simple :

The "input" pins are on the left side of the module, when the MAX7219 chip is on the left.

  • VCC : on the 5v pin of the arduino. Use the breadboard as you will need more 5v pins.
  • GND : Gnd port of the arduino. Again, use the breadboard.
  • DIN : pin 12 of the arduino (It's the "Data In" signal of the SPI link)
  • CS : pin 10 (the "chip select" signal)
  • CLK : pin 11 (the clock signal)

You can put up to 8 modules in series. In my case, I've got 5 of them.

Put the modules head to tail, make sure the input pins of the first module are on the top (check the pictures). Wire them in series, like the pictures. My tip : wire the modules before putting the rubbers, to avoid errors in the wiring.

Use small rubbers to keep the modules together.

Step 5: Wiring the Bluetooth Module

Picture of Wiring the Bluetooth Module

Ok, the bluetooth module is also easy to wire :

  • Vcc : 5v pin of the arduino
  • GND : ground pin
  • Tx : arduino pin 8
  • Rx : arduino pin 9


Watch out, the module only handles 3v3 logical levels on TX and RX pins. Don't connect them on a 5v pin ! Use a level converter instead.

When on, a led on the module should blink. In fact, the led blinks when the module starts, then stays ON when the module is connected with the phone. Great for debugging !

My wiring is quite ugly... due to a lack of wires, I had to do something not very good with the breadboard... sorry...!

Step 6: The Program

Picture of The Program

Ok, the program is attached on this step.

You will need the "Led Control" libraries to compile the sketch. Informations are here.

You can download the libs here (there is a button "download zip" on the right):

Remember, you have to unzip them in the "libraries" folder of the main arduino folder. Make sure the folder name is "LedControl". Make sure that the .H and .CPP files are directly inside.

  • Connect the arduino nano to the computer.
  • In the arduino IDE, make sure that the correct board is selected (The nano in my case).
  • In the program, change the line 40, and put the number of matrices used. 5, in my case. You can use up to 8 modules.
  • On the line 48, you can adjust the speed of the text. Put a bigger value if you want to reduce the speed.(It's the delay in ms between a "step" on the screens)
  • Compile and upload the program. The modules will blink randomly during the upload process. It's normal !

You should see the welcome message on the led display...

Step 7: On the Phone

Picture of On the Phone

Ok, you will have to setup a bluetooth terminal client on your mobile phone.

On the android store, you can find them for free. For this project, I'll use "Bluetooth SPP", but any similar app should work. Just search for "bluetooth serial" or "bluetooth terminal" on the app store.

  • Turn on the bluetooth on the phone.
  • Use the phone utility to find and locate bluetooth emitters.
  • The emitter name is "HC-06". Select Connect. The password is 1234.
  • Launch the Bluetooth SPP app. Hit the menu button on your phone, select Connect. Select the HC06 module.
  • In the operating mode screen, select Real-time mode.
  • The phone will work, then says that the connection is ok.
  • Check the bluetooth module, the led should stay ON (no more blinking)

When running again the app, you can use a "Restore last connection" feature to get the connection with the module. Works great !

The app you use may be different, of course.

Step 8: Send a Message !

Picture of Send a Message !
  • Ok, so make sure that the phone is correctly connected to the module.
  • Push the reset pin of the arduino.(Optional, but show the initial message)
  • Check the phone, you should see "Hi ! I'm waiting for a message. Type it and press SEND."
  • Type any message you want, then click on Send.
  • The select message should be now on the led display !


Congrats, you make it work !

Step 9: Final Words

Ok, this project is great, because it's based on a very simple modules, and the result is quite useful. You may want to use this as a general-purpose message display... You can finish this project by making an enclosure to hide the wires and make something beautiful...

If you don't want to use the bluetooth, just use the program given here. Use the arduino serial monitor (or other terminal program) to send a message.

I hope my steps are clear... If you need more explanations, just ask !!

Thanks for reading !!

Comments

pinakoza made it! (author)2017-11-25

Thank you Yoruk. It works great. But, HOW CAN I SPEED IT UP? Also when I send longer line, it becomes too too slow!

Thanks to Enjsof too for sharing changes in code to make it work with FC-16 modules.

Yoruk (author)pinakoza2017-11-26

Thanks for sharing the result !

To speed it up, you can reduce the value of the SpeedDelay variable. If it's still too slow, it means that we reached the top speed of the arduino. :-( Maybe it can be possible to use a board with a fastest crystal (the Mega, maybe.)

Same explanations for the long sentence...

pinakoza (author)Yoruk2017-11-26

Thank you Yoruk, I will try using Arduino Mega. I really want to have one just for fun :)

Yoruk (author)pinakoza2017-12-09

And the arduino mega is very powerful and can be useful for a lot of other projects.....!

enjsof (author)2016-11-26

What should I change in the code if I want to put them side by side?

Yoruk (author)enjsof2016-11-28

Check the end of the code : you have one "if" statement to remove.

This one :

if (m % 2 == 0) //check is the module is upside-down or not...

enjsof (author)Yoruk2016-11-28

I tried that and it doesnt work. My leds are setup where the connectors are side by side, instead of top and bottom like yours.

Yoruk (author)enjsof2016-11-28

Ok I see... In this case you will have to modify an other statement at the end of the code. You can try to change the

lc.setRow(m,i,Buffer_inverse[i+k+8*m]);


by

lc.setColumn(m,i,Buffer_inverse[i+k+8*m]);

(not tested !!)

As your modules are in a different way. You will not write the data on rows, but on the colums instead.

enjsof (author)Yoruk2016-11-29

Thanks! I got it to work side by side, but now its reading the LED in reverse

<--------xt-----------Te-------------<

<------LED 2------LED1----------<

nice code!

Yoruk (author)enjsof2016-11-30

Ahhh... Hmmm... In this case you should try

lc.setColumn(MatrixNumber-m,i,Buffer_inverse[i+k+8*m]);

to reverse the order. Maybe add 1 or -1 to make sure you use all the modules.
Let me know...

enjsof (author)Yoruk2016-11-30

Aha! I got it to work with this code:

void DrawText( byte stringLength) {

for(int k = 0; k < stringLength*6; k++) {

delay(SpeedDelay);

for (int m = 0; m < MatrixNumber; m++) {

for (int i = 0; i < 8; i++) {

lc.setColumn(m,7-i,Buffer_inverse[i+k+8*m]);

}

}

}

}

Much thanks!

pinakoza (author)enjsof2017-11-25

Thanks Enjsof for making it possible to work with FC-16 modules :-)

FarahL (author)enjsof2016-12-25

Sorry my english. My display work like you, but when i changed the code, scroll speed not work. If possible, you can post your complete code here ou send to my email (farah.luizaugusto@gmail.com) ? Thanks

Yoruk (author)FarahL2016-12-25

Could you share YOUR code please ? I can take a look.

Maybe the "k" variable is missing somewhere to translate the text...?

FarahL (author)Yoruk2016-12-25

Hi.

I have problems with memory and scroll speed.

O sketch usa 6.018 bytes (19%) de espaço de armazenamento para programas. O máximo são 30.720 bytes.
Variáveis globais usam 1.888 bytes (92%) de memória dinâmica, deixando 160 bytes para variáveis locais. O máximo são 2.048 bytes.
Pouca memória disponível, problemas de estabilidade podem ocorrer.

The code is:


// Easy bluetooth controlled scrolling text


// by Yoruk for Instructable

// 26 02 15 : first code
// 03 03 15 : buffer updating
// 04 03 15 : faster version, both buffers
// 05 03 15 : cleaning and help


/*
WIRING :
pin 12 - DataIn of the first led matrix module
pin 11 - CLK of the first led matrix module
pin 10 - CS of the first led matrix module

pin 9 : RX pin of the bluetooth module
pin 8 : TX pin of the bluetooth module

5V : 5v of the matrix module, 5v of the bluetooth module
GND : the two GND signals of the matrix modules and the bluetooth module

WARNING : Use a 3v3 arduino card (nano...) or a level converter !!!

Wire the matrix modules in serie. See the Instructable steps.

*/



//Librairie for the LEDs matrix
#include "LedControl.h"

// virtual serial lib, used with bluetooth
#include <SoftwareSerial.h>

//How many matrixes we have ?
int MatrixNumber =4;


//virtual serial port bluetooth configuration
SoftwareSerial BT(8, 9); //pin 8 : virtual RX pin 9 : virtual TX


// the delay between each screen display (ms)
int SpeedDelay =1;


//total string lenght. The first message is 25 characters long (including spaces)
int LongueurChaine=25;


char incomingByte; //incoming data from the BT link


// the two pixels arrays
char Buffer[200]; //contient tout les pixels de TOUTE LA PHRASE
char Buffer_inverse[200]; //contient tout les pixels de TOUTE LA PHRASE, mais symetrises pour affichage sur ecran inverses

// the message array
char Phrase[50];

//here we set up the led matrix
LedControl lc=LedControl(12,11,10,MatrixNumber);


// character lib
int fontDefinitions[480] = {
0x00,0x00,0x00,0x00,0x00,/*space*/ // is 32 in ASCII
0x00,0xF6,0xF6,0x00,0x00,/*!*/
0x00,0xE0,0x00,0xE0,0x00,/*"*/
0x28,0xFE,0x28,0xFE,0x28,/*#*/
0x00,0x64,0xD6,0x54,0x08,/*$*/
0xC2,0xCC,0x10,0x26,0xC6,/*%*/
0x4C,0xB2,0x92,0x6C,0x0A,/*&*/
0x00,0x00,0xE0,0x00,0x00,/*'*/
0x00,0x38,0x44,0x82,0x00,/*(*/
0x00,0x82,0x44,0x38,0x00,/*)*/
0x88,0x50,0xF8,0x50,0x88,/***/
0x08,0x08,0x3E,0x08,0x08,/*+*/
0x00,0x00,0x05,0x06,0x00,/*,*/
0x08,0x08,0x08,0x08,0x08,/*-*/
0x00,0x00,0x06,0x06,0x00,/*.*/
0x02,0x0C,0x10,0x60,0x80,/*/*/
0x7C,0x8A,0x92,0xA2,0x7C,/*0*/
0x00,0x42,0xFE,0x02,0x00,/*1*/
0x42,0x86,0x8A,0x92,0x62,/*2*/
0x44,0x82,0x92,0x92,0x6C,/*3*/
0x10,0x30,0x50,0xFE,0x10,/*4*/
0xE4,0xA2,0xA2,0xA2,0x9C,/*5*/
0x3C,0x52,0x92,0x92,0x0C,/*6*/
0x80,0x86,0x98,0xE0,0x80,/*7*/
0x6C,0x92,0x92,0x92,0x6C,/*8*/
0x60,0x92,0x92,0x94,0x78,/*9*/
0x00,0x00,0x36,0x36,0x00,/*:*/
0x00,0x00,0x35,0x36,0x00,/*;*/
0x10,0x28,0x44,0x82,0x00,/*<*/
0x28,0x28,0x28,0x28,0x28,/*=*/
0x00,0x82,0x44,0x28,0x10,/*>*/
0x40,0x80,0x8A,0x90,0x60,/*?*/
0x7C,0x82,0xBA,0xBA,0x62,/*@*/
0x3E,0x48,0x88,0x48,0x3E,/*A*/
0xFE,0x92,0x92,0x92,0x6C,/*B*/
0x7C,0x82,0x82,0x82,0x44,/*C*/
0xFE,0x82,0x82,0x82,0x7C,/*D*/
0xFE,0x92,0x92,0x92,0x82,/*E*/
0xFE,0x90,0x90,0x90,0x80,/*F*/
0x7C,0x82,0x82,0x8A,0x4E,/*G*/
0xFE,0x10,0x10,0x10,0xFE,/*H*/
0x82,0x82,0xFE,0x82,0x82,/*I*/
0x84,0x82,0xFC,0x80,0x80,/*J*/
0xFE,0x10,0x28,0x44,0x82,/*K*/
0xFE,0x02,0x02,0x02,0x02,/*L*/
0xFE,0x40,0x20,0x40,0xFE,/*M*/
0xFE,0x60,0x10,0x0C,0xFE,/*N*/
0x7C,0x82,0x82,0x82,0x7C,/*O*/
0xFE,0x90,0x90,0x90,0x60,/*P*/
0x7C,0x82,0x82,0x86,0x7E,/*Q*/
0xFE,0x90,0x98,0x94,0x62,/*R*/
0x64,0x92,0x92,0x92,0x4C,/*S*/
0x80,0x80,0xFE,0x80,0x80,/*T*/
0xFC,0x02,0x02,0x02,0xFC,/*U*/
0xF8,0x04,0x02,0x04,0xF8,/*V*/
0xFC,0x02,0x0C,0x02,0xFC,/*W*/
0xC6,0x28,0x10,0x28,0xC6,/*X*/
0xC0,0x20,0x1E,0x20,0xC0,/*Y*/
0x86,0x8A,0x92,0xA2,0xC2,/*Z*/
0x00,0x00,0xFE,0x82,0x00,/*[*/
0x00,0x00,0x00,0x00,0x00,/*this should be / */
0x80,0x60,0x10,0x0C,0x02,/*]*/
0x20,0x40,0x80,0x40,0x20,/*^*/
0x01,0x01,0x01,0x01,0x01,/*_*/
0x80,0x40,0x20,0x00,0x00,/*`*/
0x04,0x2A,0x2A,0x2A,0x1E,/*a*/
0xFE,0x12,0x22,0x22,0x1C,/*b*/
0x1C,0x22,0x22,0x22,0x14,/*c*/
0x1C,0x22,0x22,0x12,0xFE,/*d*/
0x1C,0x2A,0x2A,0x2A,0x18,/*e*/
0x10,0x7E,0x90,0x80,0x40,/*f*/
0x18,0x25,0x25,0x25,0x1E,/*g*/
0xFE,0x10,0x10,0x10,0x0E,/*h*/
0x00,0x12,0x5E,0x02,0x00,/*i*/
0x02,0x01,0x01,0x11,0x5E,/*j*/
0xFE,0x08,0x08,0x14,0x22,/*k*/
0x00,0x82,0xFE,0x02,0x00,/*l*/
0x3E,0x20,0x1C,0x20,0x1E,/*m*/
0x3E,0x20,0x20,0x20,0x1E,/*n*/
0x1C,0x22,0x22,0x22,0x1C,/*o*/
0x3F,0x24,0x24,0x24,0x18,/*p*/
0x18,0x24,0x24,0x3F,0x01,/*q*/
0x3E,0x10,0x20,0x20,0x10,/*r*/
0x12,0x2A,0x2A,0x2A,0x04,/*s*/
0x00,0x10,0x3C,0x12,0x04,/*t*/
0x3C,0x02,0x02,0x02,0x3E,/*u*/
0x30,0x0C,0x02,0x0C,0x30,/*v*/
0x38,0x06,0x18,0x06,0x38,/*w*/
0x22,0x14,0x08,0x14,0x22,/*x*/
0x38,0x05,0x05,0x05,0x3E,/*y*/
0x22,0x26,0x2A,0x32,0x22,/*z*/
0x00,0x10,0x6C,0x82,0x82,/*{*/
0x00,0x00,0xFF,0x00,0x00,/*|*/
0x04,0x02,0xFF,0x02,0x04,/*|, arrow*/
0x82,0x82,0x6C,0x10,0x00,/*}*/
0x08,0x10,0x18,0x08,0x10/*~*/
};



void setup() {

//matrix modules init
for(int adresse=0;adresse<MatrixNumber;adresse++) {
/*The MAX72XX is in power-saving mode on startup*/
lc.shutdown(adresse,false);
/* Set the brightness to a medium values */
lc.setIntensity(adresse,1);
/* and clear the display */
lc.clearDisplay(adresse);
}

// BufferBuilding("Hi ! Sent me a message...", 25); //first message on the led screen


BufferBuilding(" lfarah", 9); //first message on the led screen


Serial.begin(9600); //we also set the normal serial link, for debug

BT.begin(9600); // bluetooth initialisation

//we sent a message on the phone to tell the user that he can do someting...
BT.println("Hi ! I'm waiting for a message. Type it and press SEND.");

}



void loop() {

DrawText( LongueurChaine); //draw the message, in a loop


//or, if we get something on the virtual bluetooth port...
if (BT.available() > 0) {

LongueurChaine = BT.available(); //incoming string lenght

for (int i = 0; i < LongueurChaine; i++) {

// read the incoming byte:
incomingByte = BT.read();

Phrase[i] = incomingByte; ///store the character into the string array

}

//debug features, to check :
Serial.print("Display: ");
Serial.println(Phrase);
Serial.print("Length : ");
Serial.println(LongueurChaine);

//buffers cleaning, to store the new message
for(int k = 0; k < 200; k++) {
Buffer[k]=0;
Buffer_inverse[k]=0;

}

//we create the new buffers, so the new message will be drawn when leaving the sub
BufferBuilding(Phrase, LongueurChaine);
}

}



void BufferBuilding(char * stringToDisplay, byte stringLength)
{
int i =0;

//loop on every characters (on the string)
for(int k = 0; k < stringLength; k++) {
//here we call the characters library
int caract= k;
Buffer[i+0] = fontDefinitions[((stringToDisplay[caract] - 32) * 5) + 0];
Buffer[i+1] = fontDefinitions[((stringToDisplay[caract] - 32) * 5) + 1];
Buffer[i+2] = fontDefinitions[((stringToDisplay[caract] - 32) * 5) + 2];
Buffer[i+3] = fontDefinitions[((stringToDisplay[caract] - 32) * 5) + 3];
Buffer[i+4] = fontDefinitions[((stringToDisplay[caract] - 32) * 5) + 4];
Buffer[i+5] = B00000000; //one blank column of leds between two characters
i=i+6;
}

// here, we create a second buffer, to display the message on the switched matrixes
for(int k = 0; k < stringLength*6; k++) {
for(int i = 0; i < 8; i++) {
bitWrite( Buffer_inverse[k] ,i, bitRead(Buffer[k] ,7-i) ) ;
}
}
}



void DrawText( byte stringLength) {

for(int k = 0; k < stringLength*6; k++) {
delay(SpeedDelay);
for (int m = 0; m < MatrixNumber; m++) {

for (int i = 0; i < 8; i++) {

lc.setColumn(m,7-i,Buffer_inverse[i+k+8*m]);

}

}

}

}

Yoruk (author)FarahL2016-12-25

For the scrolling problem, can you describe what do you see ? No scrolling ? Wrong direction ?

FarahL (author)Yoruk2016-12-25

Yoruk, in your original code, the scrolling is the wrong direction in my display.. With a enjsof modification, my display scrolling right but no change speed. Speed is very slow same changed SpeedDelay.

Yoruk (author)FarahL2016-12-26

So the translation works, but very slow ? How many time there is between two "translations" ?
The code seems fine, for now I don't see what can be the problem...

What Arduino board are you using ?

FarahL (author)enjsof2016-12-24

Hi, in this case, scroll speed working for you ?

Yoruk (author)FarahL2016-12-25

It should work the same, we just swap lines and columns for the display.

Yoruk (author)enjsof2016-11-30

You are welcome !!

Fawwaz ihsanR made it! (author)2017-10-14

Hey man! That's Great project! i made it, but i have a little problem. the text is not horizontal but it's vertical. Can you help me?

Yoruk (author)Fawwaz ihsanR2017-10-16

Thanks for sharing, it's always a pleasure to see someone made the project !
For the text problem, check the last function in the program (DrawText). Try to replace the two "setRow" by "setColumn" and let me know...

highlightz.md (author)2017-09-15

Hello,

nice project man!!

I build it too and works great. the only problem that i have is that i have an " i " infront of every message i send.

when i send " test " the displays shows " itest "

here is my code..i hope you can help me! thank you!!


// Easy bluetooth controlled scrolling text


// by Yoruk for Instructable

// 26 02 15 : first code
// 03 03 15 : buffer updating
// 04 03 15 : faster version, both buffers
// 05 03 15 : cleaning and help


/*
WIRING :
pin 12 - DataIn of the first led matrix module
pin 11 - CLK of the first led matrix module
pin 10 - CS of the first led matrix module

pin 9 : RX pin of the bluetooth module
pin 8 : TX pin of the bluetooth module

5V : 5v of the matrix module, 5v of the bluetooth module
GND : the two GND signals of the matrix modules and the bluetooth module

WARNING : Use a 3v3 arduino card (nano...) or a level converter !!!

Wire the matrix modules in serie. See the Instructable steps.

*/



//Librairie for the LEDs matrix
#include "LedControl.h"

// virtual serial lib, used with bluetooth
#include <SoftwareSerial.h>

//How many matrixes we have ?
int MatrixNumber =1;


//virtual serial port bluetooth configuration
SoftwareSerial BT(8, 9); //pin 8 : virtual RX pin 9 : virtual TX


// the delay between each screen display (ms)
int SpeedDelay = 40;


//total string lenght. The first message is 25 characters long (including spaces)
int LongueurChaine=25;


char incomingByte; //incoming data from the BT link


// the two pixels arrays
char Buffer[200]; //contient tout les pixels de TOUTE LA PHRASE
char Buffer_inverse[200]; //contient tout les pixels de TOUTE LA PHRASE, mais symetrises pour affichage sur ecran inverses

// the message array
char Phrase[50];

//here we set up the led matrix
LedControl lc=LedControl(12,11,10,MatrixNumber);


// character lib
int fontDefinitions[480] = {
0x00,0x00,0x00,0x00,0x00,/*space*/ // is 32 in ASCII
0x00,0xF6,0xF6,0x00,0x00,/*!*/
0x00,0xE0,0x00,0xE0,0x00,/*"*/
0x28,0xFE,0x28,0xFE,0x28,/*#*/
0x00,0x64,0xD6,0x54,0x08,/*$*/
0xC2,0xCC,0x10,0x26,0xC6,/*%*/
0x4C,0xB2,0x92,0x6C,0x0A,/*&*/
0x00,0x00,0xE0,0x00,0x00,/*'*/
0x00,0x38,0x44,0x82,0x00,/*(*/
0x00,0x82,0x44,0x38,0x00,/*)*/
0x88,0x50,0xF8,0x50,0x88,/***/
0x08,0x08,0x3E,0x08,0x08,/*+*/
0x00,0x00,0x05,0x06,0x00,/*,*/
0x08,0x08,0x08,0x08,0x08,/*-*/
0x00,0x00,0x06,0x06,0x00,/*.*/
0x02,0x0C,0x10,0x60,0x80,/*/*/
0x7C,0x8A,0x92,0xA2,0x7C,/*0*/
0x00,0x42,0xFE,0x02,0x00,/*1*/
0x42,0x86,0x8A,0x92,0x62,/*2*/
0x44,0x82,0x92,0x92,0x6C,/*3*/
0x10,0x30,0x50,0xFE,0x10,/*4*/
0xE4,0xA2,0xA2,0xA2,0x9C,/*5*/
0x3C,0x52,0x92,0x92,0x0C,/*6*/
0x80,0x86,0x98,0xE0,0x80,/*7*/
0x6C,0x92,0x92,0x92,0x6C,/*8*/
0x60,0x92,0x92,0x94,0x78,/*9*/
0x00,0x00,0x36,0x36,0x00,/*:*/
0x00,0x00,0x35,0x36,0x00,/*;*/
0x10,0x28,0x44,0x82,0x00,/*<*/
0x28,0x28,0x28,0x28,0x28,/*=*/
0x00,0x82,0x44,0x28,0x10,/*>*/
0x40,0x80,0x8A,0x90,0x60,/*?*/
0x7C,0x82,0xBA,0xBA,0x62,/*@*/
0x3E,0x48,0x88,0x48,0x3E,/*A*/
0xFE,0x92,0x92,0x92,0x6C,/*B*/
0x7C,0x82,0x82,0x82,0x44,/*C*/
0xFE,0x82,0x82,0x82,0x7C,/*D*/
0xFE,0x92,0x92,0x92,0x82,/*E*/
0xFE,0x90,0x90,0x90,0x80,/*F*/
0x7C,0x82,0x82,0x8A,0x4E,/*G*/
0xFE,0x10,0x10,0x10,0xFE,/*H*/
0x82,0x82,0xFE,0x82,0x82,/*I*/
0x84,0x82,0xFC,0x80,0x80,/*J*/
0xFE,0x10,0x28,0x44,0x82,/*K*/
0xFE,0x02,0x02,0x02,0x02,/*L*/
0xFE,0x40,0x20,0x40,0xFE,/*M*/
0xFE,0x60,0x10,0x0C,0xFE,/*N*/
0x7C,0x82,0x82,0x82,0x7C,/*O*/
0xFE,0x90,0x90,0x90,0x60,/*P*/
0x7C,0x82,0x82,0x86,0x7E,/*Q*/
0xFE,0x90,0x98,0x94,0x62,/*R*/
0x64,0x92,0x92,0x92,0x4C,/*S*/
0x80,0x80,0xFE,0x80,0x80,/*T*/
0xFC,0x02,0x02,0x02,0xFC,/*U*/
0xF8,0x04,0x02,0x04,0xF8,/*V*/
0xFC,0x02,0x0C,0x02,0xFC,/*W*/
0xC6,0x28,0x10,0x28,0xC6,/*X*/
0xC0,0x20,0x1E,0x20,0xC0,/*Y*/
0x86,0x8A,0x92,0xA2,0xC2,/*Z*/
0x00,0x00,0xFE,0x82,0x00,/*[*/
0x00,0x00,0x00,0x00,0x00,/*this should be / */
0x80,0x60,0x10,0x0C,0x02,/*]*/
0x20,0x40,0x80,0x40,0x20,/*^*/
0x01,0x01,0x01,0x01,0x01,/*_*/
0x80,0x40,0x20,0x00,0x00,/*`*/
0x04,0x2A,0x2A,0x2A,0x1E,/*a*/
0xFE,0x12,0x22,0x22,0x1C,/*b*/
0x1C,0x22,0x22,0x22,0x14,/*c*/
0x1C,0x22,0x22,0x12,0xFE,/*d*/
0x1C,0x2A,0x2A,0x2A,0x18,/*e*/
0x10,0x7E,0x90,0x80,0x40,/*f*/
0x18,0x25,0x25,0x25,0x1E,/*g*/
0xFE,0x10,0x10,0x10,0x0E,/*h*/
0x00,0x12,0x5E,0x02,0x00,/*i*/
0x02,0x01,0x01,0x11,0x5E,/*j*/
0xFE,0x08,0x08,0x14,0x22,/*k*/
0x00,0x82,0xFE,0x02,0x00,/*l*/
0x3E,0x20,0x1C,0x20,0x1E,/*m*/
0x3E,0x20,0x20,0x20,0x1E,/*n*/
0x1C,0x22,0x22,0x22,0x1C,/*o*/
0x3F,0x24,0x24,0x24,0x18,/*p*/
0x18,0x24,0x24,0x3F,0x01,/*q*/
0x3E,0x10,0x20,0x20,0x10,/*r*/
0x12,0x2A,0x2A,0x2A,0x04,/*s*/
0x00,0x10,0x3C,0x12,0x04,/*t*/
0x3C,0x02,0x02,0x02,0x3E,/*u*/
0x30,0x0C,0x02,0x0C,0x30,/*v*/
0x38,0x06,0x18,0x06,0x38,/*w*/
0x22,0x14,0x08,0x14,0x22,/*x*/
0x38,0x05,0x05,0x05,0x3E,/*y*/
0x22,0x26,0x2A,0x32,0x22,/*z*/
0x00,0x10,0x6C,0x82,0x82,/*{*/
0x00,0x00,0xFF,0x00,0x00,/*|*/
0x04,0x02,0xFF,0x02,0x04,/*|, arrow*/
0x82,0x82,0x6C,0x10,0x00,/*}*/
0x08,0x10,0x18,0x08,0x10/*~*/
};



void setup() {

//matrix modules init
for(int adresse=0;adresse<MatrixNumber;adresse++) {
/*The MAX72XX is in power-saving mode on startup*/
lc.shutdown(adresse,false);
/* Set the brightness to a medium values */
lc.setIntensity(adresse,4);
/* and clear the display */
lc.clearDisplay(adresse);
}

// BufferBuilding("Hi ! Sent me a message...", 25); //first message on the led screen


BufferBuilding("text", 4); //first message on the led screen


Serial.begin(9600); //we also set the normal serial link, for debug

BT.begin(9600); // bluetooth initialisation

//we sent a message on the phone to tell the user that he can do someting...
BT.println("Hi ! I'm waiting for a message. Type it and press SEND.");

}



void loop() {

DrawText( LongueurChaine); //draw the message, in a loop


//or, if we get something on the virtual bluetooth port...
if (BT.available() > 0) {

LongueurChaine = BT.available(); //incoming string lenght

for (int i = 0; i < LongueurChaine; i++) {

// read the incoming byte:
incomingByte = BT.read();

Phrase[i] = incomingByte; ///store the character into the string array

}

//debug features, to check :
Serial.print("Display: ");
Serial.println(Phrase);
Serial.print("Length : ");
Serial.println(LongueurChaine);

//buffers cleaning, to store the new message
for(int k = 0; k < 200; k++) {
Buffer[k]=0;
Buffer_inverse[k]=0;

}

//we create the new buffers, so the new message will be drawn when leaving the sub
BufferBuilding(Phrase, LongueurChaine);
}

}



void BufferBuilding(char * stringToDisplay, byte stringLength)
{
int i =0;

//loop on every characters (on the string)
for(int k = 0; k < stringLength; k++) {
//here we call the characters library
int caract= k;
Buffer[i+0] = fontDefinitions[((stringToDisplay[caract] - 32) * 5) + 0];
Buffer[i+1] = fontDefinitions[((stringToDisplay[caract] - 32) * 5) + 1];
Buffer[i+2] = fontDefinitions[((stringToDisplay[caract] - 32) * 5) + 2];
Buffer[i+3] = fontDefinitions[((stringToDisplay[caract] - 32) * 5) + 3];
Buffer[i+4] = fontDefinitions[((stringToDisplay[caract] - 32) * 5) + 4];
Buffer[i+5] = B00000000; //one blank column of leds between two characters
i=i+6;
}

// here, we create a second buffer, to display the message on the switched matrixes
for(int k = 0; k < stringLength*6; k++) {
for(int i = 0; i < 8; i++) {
bitWrite( Buffer_inverse[k] ,i, bitRead(Buffer[k] ,7-i) ) ;
}
}
}



void DrawText( byte stringLength) {

for(int k = 0; k < stringLength*6; k++) {

delay(SpeedDelay);


//delay(10000);
//k is the column

//buffer drawing
for (int m = 0; m < MatrixNumber; m++) { //loop on the matrix
if (m % 2 == 0) //check is the module is upside-down or not...
{
//here, the matrix is flipped upside-down
for (int i = 0; i < 8; i++) { //loop on the columns

lc.setRow(m,7-i,Buffer[i+k+8*m]);
}
}
else
{
//classical
for (int i = 0; i < 8; i++) { //loop on the columns


lc.setRow(m,i,Buffer_inverse[i+k+8*m]);
}
}
}
}

}

Yoruk (author)highlightz.md2017-09-16

Weird... What do you have at first start ? (before uploading a message)

You can try in the DrawText function to change

for(int k = 0; k < stringLength*6; k++) {

by

for(int k = 1; k < stringLength*6; k++) {

(Put k = 1). Untested !!

Let me know...!

giantjuju (author)2017-09-07

hey i'm having trouble compiling the codes

after compiling this shows up

C:\Users\Others\Downloads\FCY1550I6ZTF6H2\FCY1550I6ZTF6H2.ino: In function 'void setup()':

C:\Users\Others\Downloads\FCY1550I6ZTF6H2\FCY1550I6ZTF6H2.ino:186:29: warning: deprecated conversion from string constant to 'char*' [-Wwrite-strings]

BufferBuilding("text", 4); //first message on the led screen

^

Yoruk (author)giantjuju2017-09-08

It's only a warning, it should not be a problem to continue...

What arduino IDE version are you using ?

giantjuju (author)Yoruk2017-09-08

i'm using the latest arduino ide

Yoruk (author)giantjuju2017-09-08

This message should not be an issue to get the compilation done.... Have you got any other messages ?

giantjuju (author)Yoruk2017-09-09

nope. that's all the message i got after compiling. thanks for answering my dilemma

Yoruk (author)giantjuju2017-09-09

So the compilation is OK ?

This warning message is only informative, in this case it SHOULD not be a problem.

mahio4u (author)2017-07-04

nice work. I want to use a bigger led matrix, what do I need to change? this led is cool, but a little too small. let's say I want to use a 5mm 8*8 matrix?

Yoruk (author)mahio4u2017-07-07

The MAX7219 can drive bigger led modules. You have different possibilities : looking for a bigger module with the same pinout, or build the module from scratch with bigger leds. Watch out to not exceed the maximal current given by the MAX.

Also, in this case, you may need to use an external 5v power source; the arduino board can't output a lot of power.

Hope this helps...

mahio4u (author)2017-07-04

also what's the maximum number of modules I one string can I use?

Yoruk (author)mahio4u2017-07-07

You can add up to 8 modules, the limit is given by the MAX

mahio4u (author)2017-07-04

also what's the maximum number of modules I one string can I use?

sarenum49 (author)2017-05-29

Can you help me, please? I use arduino mega 2560, but it doesn't work and have alot of errors.

Yoruk (author)sarenum492017-05-31

What is exactly the problem ?

What are the errors ? (you can copy and paste the contents of the console...)

AndreKusuma (author)2017-05-23

thx Yoruk, imade it but i've modify ur code because i used different Led matrix unit.
i use 4in1 LED Dot Matrix.

but im still confuse to implement PROGMEM library, maybe u can helping me?
but i still conf

Yoruk (author)AndreKusuma2017-05-26

What is exactly your problem ? I'm not sure to understand what you want to do...?

AndreKusuma (author)Yoruk2017-05-28

hello Yoruk.
i already done with PROGMEM and now low memory is gone.

my running text going opposite dirrection but no problem.

spp bluetooth is going well.

Yoruk (author)AndreKusuma2017-05-28

If you want to modify the text direction, you have to check the last lines of code; you may also want to disable the "upside/down" feature...

AndreKusuma (author)Yoruk2017-05-30

here my code

// Easy bluetooth controlled scrolling text

// by Yoruk for Instructable

// 26 02 15 : first code

// 03 03 15 : buffer updating

// 04 03 15 : faster version, both buffers

// 05 03 15 : cleaning and help

/*

WIRING :

pin 12 - DataIn of the first led matrix module

pin 11 - CLK of the first led matrix module

pin 10 - CS of the first led matrix module

pin 9 : RX pin of the bluetooth module

pin 8 : TX pin of the bluetooth module

5V : 5v of the matrix module, 5v of the bluetooth module

GND : the two GND signals of the matrix modules and the bluetooth module

WARNING : Use a 3v3 arduino card (nano...) or a level converter !!!

Wire the matrix modules in serie. See the Instructable steps.

*/

//Librairie for the LEDs matrix

#include "LedControl.h"

//Library Progmem

#include <avr/pgmspace.h>

// virtual serial lib, used with bluetooth

#include <SoftwareSerial.h>

//How many matrixes we have ?

int MatrixNumber =4;

//virtual serial port bluetooth configuration

SoftwareSerial BT(8, 9); //pin 8 : virtual RX pin 9 : virtual TX

// the delay between each screen display (ms)

int SpeedDelay = 0;

//total string lenght. The first message is 25 characters long (including spaces)

int LongueurChaine=25;

char incomingByte; //incoming data from the BT link

// the two pixels arrays

char Buffer[200]; //contient tout les pixels de TOUTE LA PHRASE

char Buffer_inverse[200]; //contient tout les pixels de TOUTE LA PHRASE, mais symetrises pour affichage sur ecran inverses

// the message array

char Phrase[50];

//here we set up the led matrix

LedControl lc=LedControl(12,11,10,MatrixNumber);

// character lib

const int fontDefinitions[480] PROGMEM = {

0x00,0x00,0x00,0x00,0x00,/*space*/ // is 32 in ASCII

0x00,0xF6,0xF6,0x00,0x00,/*!*/

0x00,0xE0,0x00,0xE0,0x00,/*"*/

0x28,0xFE,0x28,0xFE,0x28,/*#*/

0x00,0x64,0xD6,0x54,0x08,/*$*/

0xC2,0xCC,0x10,0x26,0xC6,/*%*/

0x4C,0xB2,0x92,0x6C,0x0A,/*&*/

0x00,0x00,0xE0,0x00,0x00,/*'*/

0x00,0x38,0x44,0x82,0x00,/*(*/

0x00,0x82,0x44,0x38,0x00,/*)*/

0x88,0x50,0xF8,0x50,0x88,/***/

0x08,0x08,0x3E,0x08,0x08,/*+*/

0x00,0x00,0x05,0x06,0x00,/*,*/

0x08,0x08,0x08,0x08,0x08,/*-*/

0x00,0x00,0x06,0x06,0x00,/*.*/

0x02,0x0C,0x10,0x60,0x80,/*/*/

0x7C,0x8A,0x92,0xA2,0x7C,/*0*/

0x00,0x42,0xFE,0x02,0x00,/*1*/

0x42,0x86,0x8A,0x92,0x62,/*2*/

0x44,0x82,0x92,0x92,0x6C,/*3*/

0x10,0x30,0x50,0xFE,0x10,/*4*/

0xE4,0xA2,0xA2,0xA2,0x9C,/*5*/

0x3C,0x52,0x92,0x92,0x0C,/*6*/

0x80,0x86,0x98,0xE0,0x80,/*7*/

0x6C,0x92,0x92,0x92,0x6C,/*8*/

0x60,0x92,0x92,0x94,0x78,/*9*/

0x00,0x00,0x36,0x36,0x00,/*:*/

0x00,0x00,0x35,0x36,0x00,/*;*/

0x10,0x28,0x44,0x82,0x00,/*<*/

0x28,0x28,0x28,0x28,0x28,/*=*/

0x00,0x82,0x44,0x28,0x10,/*>*/

0x40,0x80,0x8A,0x90,0x60,/*?*/

0x7C,0x82,0xBA,0xBA,0x62,/*@*/

0x3E,0x48,0x88,0x48,0x3E,/*A*/

0xFE,0x92,0x92,0x92,0x6C,/*B*/

0x7C,0x82,0x82,0x82,0x44,/*C*/

0xFE,0x82,0x82,0x82,0x7C,/*D*/

0xFE,0x92,0x92,0x92,0x82,/*E*/

0xFE,0x90,0x90,0x90,0x80,/*F*/

0x7C,0x82,0x82,0x8A,0x4E,/*G*/

0xFE,0x10,0x10,0x10,0xFE,/*H*/

0x82,0x82,0xFE,0x82,0x82,/*I*/

0x84,0x82,0xFC,0x80,0x80,/*J*/

0xFE,0x10,0x28,0x44,0x82,/*K*/

0xFE,0x02,0x02,0x02,0x02,/*L*/

0xFE,0x40,0x20,0x40,0xFE,/*M*/

0xFE,0x60,0x10,0x0C,0xFE,/*N*/

0x7C,0x82,0x82,0x82,0x7C,/*O*/

0xFE,0x90,0x90,0x90,0x60,/*P*/

0x7C,0x82,0x82,0x86,0x7E,/*Q*/

0xFE,0x90,0x98,0x94,0x62,/*R*/

0x64,0x92,0x92,0x92,0x4C,/*S*/

0x80,0x80,0xFE,0x80,0x80,/*T*/

0xFC,0x02,0x02,0x02,0xFC,/*U*/

0xF8,0x04,0x02,0x04,0xF8,/*V*/

0xFC,0x02,0x0C,0x02,0xFC,/*W*/

0xC6,0x28,0x10,0x28,0xC6,/*X*/

0xC0,0x20,0x1E,0x20,0xC0,/*Y*/

0x86,0x8A,0x92,0xA2,0xC2,/*Z*/

0x00,0x00,0xFE,0x82,0x00,/*[*/

0x00,0x00,0x00,0x00,0x00,/*this should be / */

0x80,0x60,0x10,0x0C,0x02,/*]*/

0x20,0x40,0x80,0x40,0x20,/*^*/

0x01,0x01,0x01,0x01,0x01,/*_*/

0x80,0x40,0x20,0x00,0x00,/*`*/

0x04,0x2A,0x2A,0x2A,0x1E,/*a*/

0xFE,0x12,0x22,0x22,0x1C,/*b*/

0x1C,0x22,0x22,0x22,0x14,/*c*/

0x1C,0x22,0x22,0x12,0xFE,/*d*/

0x1C,0x2A,0x2A,0x2A,0x18,/*e*/

0x10,0x7E,0x90,0x80,0x40,/*f*/

0x18,0x25,0x25,0x25,0x1E,/*g*/

0xFE,0x10,0x10,0x10,0x0E,/*h*/

0x00,0x12,0x5E,0x02,0x00,/*i*/

0x02,0x01,0x01,0x11,0x5E,/*j*/

0xFE,0x08,0x08,0x14,0x22,/*k*/

0x00,0x82,0xFE,0x02,0x00,/*l*/

0x3E,0x20,0x1C,0x20,0x1E,/*m*/

0x3E,0x20,0x20,0x20,0x1E,/*n*/

0x1C,0x22,0x22,0x22,0x1C,/*o*/

0x3F,0x24,0x24,0x24,0x18,/*p*/

0x18,0x24,0x24,0x3F,0x01,/*q*/

0x3E,0x10,0x20,0x20,0x10,/*r*/

0x12,0x2A,0x2A,0x2A,0x04,/*s*/

0x00,0x10,0x3C,0x12,0x04,/*t*/

0x3C,0x02,0x02,0x02,0x3E,/*u*/

0x30,0x0C,0x02,0x0C,0x30,/*v*/

0x38,0x06,0x18,0x06,0x38,/*w*/

0x22,0x14,0x08,0x14,0x22,/*x*/

0x38,0x05,0x05,0x05,0x3E,/*y*/

0x22,0x26,0x2A,0x32,0x22,/*z*/

0x00,0x10,0x6C,0x82,0x82,/*{*/

0x00,0x00,0xFF,0x00,0x00,/*|*/

0x04,0x02,0xFF,0x02,0x04,/*|, arrow*/

0x82,0x82,0x6C,0x10,0x00,/*}*/

0x08,0x10,0x18,0x08,0x10/*~*/

};

void setup() {

//matrix modules init

for(int adresse=0;adresse<MatrixNumber;adresse++) {

/*The MAX72XX is in power-saving mode on startup*/

lc.shutdown(adresse,false);

/* Set the brightness to a medium values */

lc.setIntensity(adresse,10);

/* and clear the display */

/*lc.clearDisplay(adresse);*/

}

BufferBuilding("HELLO", 5); //first message on the led screen

Serial.begin(9600); //we also set the normal serial link, for debug

BT.begin(9600); // bluetooth initialisation

//we sent a message on the phone to tell the user that he can do someting...

BT.println("Type it and press SEND.");

}

void loop() {

DrawText( LongueurChaine); //draw the message, in a loop

//or, if we get something on the virtual bluetooth port...

if (BT.available() > 0) {

LongueurChaine = BT.available(); //incoming string lenght

for (int i = 0; i < LongueurChaine; i++) {

// read the incoming byte:

incomingByte = BT.read();

Phrase[i] = incomingByte; ///store the character into the string array

}

//debug features, to check :

Serial.print("Display: ");

Serial.println(Phrase);

Serial.print("Length : ");

Serial.println(LongueurChaine);

//buffers cleaning, to store the new message

for(int k = 0; k < 200; k++) {

Buffer[k]=0;

Buffer_inverse[k]=0;

}

//we create the new buffers, so the new message will be drawn when leaving the sub

BufferBuilding(Phrase, LongueurChaine);

}

}

void BufferBuilding(char * stringToDisplay, byte stringLength)

{

int i =0;

//loop on every characters (on the string)

for(int k = 0; k < stringLength; k++) {

//here we call the characters library

int caract= k;

Buffer[i+0] =pgm_read_byte(&(fontDefinitions[((stringToDisplay[caract] - 32) * 5)+ 0]));

Buffer[i+1] =pgm_read_byte(&(fontDefinitions[((stringToDisplay[caract]- 32) * 5) + 1]));

Buffer[i+2] =pgm_read_byte(&(fontDefinitions[((stringToDisplay[caract] - 32) * 5)+ 2]));

Buffer[i+3] =pgm_read_byte(&(fontDefinitions[((stringToDisplay[caract] - 32) * 5)+ 3]));

Buffer[i+4] =pgm_read_byte(&(fontDefinitions[((stringToDisplay[caract] - 32) * 5)+ 4]));

Buffer[i+5] =B00000000;//one blank column of leds between two characters

i=i+6;

}

// here, we create a second buffer, to display the message on the switched matrixes

for(int k = 0; k < stringLength*6; k++) {

for(int i = 0; i < 8; i++) {

bitWrite( Buffer_inverse[k] ,i, bitRead(Buffer[k] ,7-i) ) ;

}

}

}

void DrawText( byte stringLength) {

for(int k = 0; k < stringLength*6; k++) {

delay(SpeedDelay);

for (int m = 0; m < MatrixNumber; m++) {

for (int i = 0; i < 8; i++) {

lc.setColumn(m,7-i,Buffer_inverse[i+k+8*m]);

}

}

}

}

M UdayK (author)2017-03-26

Guyz Plz help me how to make same project using GSM module instead of Bluetooth

Yoruk (author)M UdayK2017-03-27

You have to study the differences between the Bluetooth module and the GSM board in order to understand what you need to update in the code, and if you need to update the hardware.

julioberaldi (author)2017-02-19

Hello, how to solve the problem of low memory?

Yoruk (author)julioberaldi2017-02-21

You have two options :
get a card with more memory (arduino mega...) or you can try to optimize the code. You can for example remove the inverted buffer (to save a LOT of memory) but you will have to invert the data "manually" during the display, but it will be slower....

julioberaldi (author)Yoruk2017-02-21

Você poderia removê-lo para mim como eu não entendo a programação e enviá-lo por e-mail. Obrigado!

Yoruk (author)julioberaldi2017-02-21

I don't get it... Can we keep talk english please ?

julioberaldi (author)2017-02-21

meu e-mail .: jlccomunicacaovisual@hotmail.com

About This Instructable

36,739views

336favorites

License:

Bio: French engineer in robotics. I love Arduino projects / coding / guitar / various electronics. Oh, I like cooking also ! PS : English is not my main language, please ... More »
More by Yoruk:How to create phenakistoscope discsDiscover the Phenakistoscope : a vintage animation systemHow to make a tasty gingerbread
Add instructable to: