Go Down

Topic: U8glib refreshing delay, communicating trough xbee (Read 298 times) previous topic - next topic

matei23

Hello people,

The project contains an EADOG XL 160, Arduino mega 2560 (3.3v version) and a xbee module for wireless communication. I want to print on my display two things, a graphic and some numbers, all data are received trough xbee. Until now I manage to display the numbers but how can I print on the screen, for five seconds lets say, the graphic and then to print the numbers for 5 seconds over and over again without using the "delay()" function because I'm afraid not to lose the data that I receive from the ebee over UART while the microcontroller is in delay function.

Another problem that I have is if I send multiple data to be printed, is created a delay before the display is updated, for example after 6 transmissions to the display there is quite big delay until the data are updated. For the first transmission the display is quick but as the number of transmission is rising the refresh delay is rising too. Do you have  a solution, expecially for the second problem?

Code: [Select]


#include "U8glib.h"
#define font_date u8g_font_ncenB14r
#define font_text u8g_font_gdb12r
String msg="", msg1="";
int len=0,i;

U8GLIB_DOGXL160_2X_BW u8g(10, 11); // SPI Com: SCK = 13, MOSI = 11, CS = 10, A0 = 9

void u8g_prepare(void) {
 u8g.setFont(u8g_font_6x10);
 u8g.setFontRefHeightExtendedText();
 u8g.setDefaultForegroundColor();
 u8g.setFontPosTop();
 

}


void u8g_afisare1() {


 unpack();

 
 int x,y,z;
 x=25; y=23;
 z=1;
 u8g.setFont(font_text);
//   u8g.setPrintPos(0,23);
//  u8g.print("Ct:");
 u8g.setPrintPos(0,48);
 u8g.print("Rl:");
 u8g.setPrintPos(0,73);
 u8g.print("Rc:");
 u8g.setPrintPos(0,98);
 u8g.print("Sf:");
 u8g.setPrintPos(0,123);
 // u8g.setPrintPos(0, 0);
 u8g.setPrintPos(0,y);
 u8g.setFont(font_date);
 for (i=0; i<len; i++)
 {
   
     if (msg1[i]!='#')
     {
       u8g.print(msg1[i]);
     }
     else  {
   
         y=y+25;
         u8g.setPrintPos(x, y);
         //u8g.print(msg1[i+1]);
 }
 }

 }

void draw(void) {
 u8g_prepare();  
 u8g_afisare1();
 }


void setup(void) {

 // flip screen, if required
 u8g.setRot180();

 Serial1.begin(9600);
 Serial.begin(9600);

 pinMode(13, OUTPUT);          
 digitalWrite(13, HIGH);  
 
}

char terminator = '*';
char starter    = '!';
boolean read_flag  = false;
char input;


void loop(void) {
 

 u8g.firstPage();  
 do {
   draw();

 } while( u8g.nextPage() );
 
   delay(150);

}

void unpack(){

 if( Serial1.available() > 0 )
 {
   input = Serial1.read();
   if(input == starter)
    {
      msg1="";
      u8g.begin();
      delay(100);
      read_flag = true;
     
    }    
     
   if(read_flag)
   {  
     
   if( (input >= 'a' && input <= 'z') ||
       (input >= 'A' && input <= 'Z') ||
       (input >= '0' && input <= '9') ||(input=='.')||(input=='#') )
   {
           msg+=input;
           len+=1;
   }
   else if(input == terminator)
   {
      read_flag = false;
      msg1=msg;
      msg = "";
     
   }
   
   
   }
 
     
 }
//Serial1.flush();  
 
}


If you have some questions don't hesitate to ask and sorry if my english is not to good.

Have a great day,
Matei Adrian VIDICAN

olikraus

#1
Jul 26, 2014, 09:13 pm Last Edit: Jul 26, 2014, 09:15 pm by olikraus Reason: 1
Hi

1. Only do graphics output in the draw() procedure (body of the picture loop)
More specific: Do not call unpack() inside the loop body, instead call "unpack" in loop itself:

Code: [Select]
void loop(void) { 
  unpack();
  u8g.firstPage(); 
  do {
    draw();
  } while( u8g.nextPage() );
    delay(150);  // maybe this can be removed or the value can be reduced
}

I guess this will also solve your second problem.

2. Display graphics, then your numbers
The keyword is "state machine". You must introduce a state variable, e.g.:
Code: [Select]

uint8_t dispaly_state = 0;

Then define, what should be shown for which number. Let me define this:
0 = display graphics
1 = display normal content

Then, your main loop will look like this:
Code: [Select]

uint8_t dispaly_state = 0;

void loop(void) { 
  unpack();
  u8g.firstPage(); 
  do {
    if ( display_state == 0 )
      draw_graphics();   // show graphics here
   else
      draw();
  } while( u8g.nextPage() );
    delay(150);
}

Now, because display_state is set to 0 at startup, this will always show your graphics, but will never call draw(). But this is easy, we just need to assign 1 to display_state. As requested, this could be done after 5 seconds:

Code: [Select]

uint8_t dispaly_state = 0;

void loop(void) { 
  unpack();
  u8g.firstPage(); 
  do {
    if ( display_state == 0 )
      draw_graphics();   // show graphics here
   else
      draw();
  } while( u8g.nextPage() );

  if ( display_state == 0 && millis() > 5000 )
    display_state = 1;

  delay(150);
}


Oliver


Go Up