Subversion Repositories HomeAutomation

Rev

Rev 1789 | Rev 2016 | Go to most recent revision | Blame | Compare with Previous | Last modification | View Log | SVN | RSS feed

  1.  
  2. #include "act_ks0108.h"
  3.  
  4. static unsigned char Splash_left[] PROGMEM = {
  5. 0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,//Line 1
  6. 0xff,0xff,0xff,0x3,0x7f,0x7f,0xbf,0xbf,0xdf,0x7,0xff,0xff,0xff,0x3f,0xbf,0xdf,0xdf,0xdf,0x3f,0xff,0xff,0xff,0x3f,0x3f,0xdf,0x9f,0x7f,0x7f,0xbf,0x9f,0x3f,0xff,0xff,0x7f,0xbf,0xdf,0xdf,0x9f,0x3f,0xff,0xff,0xff,0xff,0xff,0xff,0x3f,0xc7,0xf3,0xf,0xff,0xff,0xff,0x1f,0xff,0xff,0xff,0xff,0x3f,0xdf,0xff,0xef,0xef,0xef,0x40,0x5,0xf7,0xff,0xff,0x3f,0xbf,0xdf,0xdf,0xdf,0x3f,0xff,0xff,0xff,0x1f,0x7f,0xdf,0x9f,0x7f,0x7f,0x9f,0xdf,0x3f,0xff,0xff,0xbf,0xbf,0xdf,0xdf,0xdf,0x3f,0xff,0xff,0xef,0xef,0xef,0x40,0x5,0xf7,0xff,0x1d,0xff,0xff,0xff,0xff,0x3f,0xbf,0xdf,0xdf,0xdf,0x3f,0xff,0xff,0xff,0x1f,0xff,0x7f,0x9f,0xdf,0x3f,0xff,0xff,0xff,0xff,0xff,//Line 2
  7. 0xff,0xff,0xff,0xd0,0xff,0xff,0xff,0xff,0xff,0xf0,0xff,0xff,0xe0,0xef,0xdf,0xdf,0xcf,0xe3,0xf8,0xff,0xff,0xff,0xc0,0xfe,0xff,0xff,0xe0,0xfa,0xff,0xff,0xe0,0xff,0xff,0xf8,0xe6,0xee,0xee,0xf6,0xf7,0xfb,0xff,0xff,0xef,0xf3,0xfc,0xfe,0xfe,0xfe,0xff,0xf0,0xff,0xff,0xf4,0xcf,0xdf,0xe7,0xfb,0xf0,0xe7,0xff,0xff,0xff,0xff,0xff,0xe0,0xff,0xff,0xe0,0xef,0xdf,0xdf,0xcf,0xe3,0xf8,0xff,0xff,0xff,0xc0,0xfe,0xff,0xff,0xe0,0xfa,0xff,0xff,0xe0,0xff,0xff,0xf3,0xeb,0xed,0xed,0xf5,0xf0,0xff,0xff,0xff,0xff,0xff,0xff,0xe0,0xff,0xff,0xe0,0xff,0xff,0xff,0xf0,0xcf,0xdf,0xdf,0xcf,0xe3,0xf8,0xff,0xff,0xff,0xf4,0xf9,0xfe,0xff,0xff,0xe0,0xff,0xff,0xff,0xff,0xff,//Line 3
  8. 0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0x3f,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0x7f,0xff,0xff,0xff,0xff,0xff,//Line 4
  9. 0xff,0xff,0xff,0xff,0xff,0xdf,0xef,0xef,0xef,0x1f,0xff,0xff,0xf,0xff,0xff,0xff,0xff,0x3f,0xcf,0xff,0xff,0x1f,0x9f,0xef,0xcf,0x3f,0x3f,0xdf,0xcf,0x1f,0xff,0xff,0x40,0x2f,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0x3f,0x5f,0xef,0xef,0xef,0xff,0xff,0x3f,0x1f,0x6f,0x6f,0xcf,0x9f,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0x3f,0xcf,0xf3,0xfc,0xff,0xff,0xff,0x47,0xb7,0xf7,0xf7,0xf7,0x77,0x8f,0xff,0xff,0xf,0x7f,0x3f,0xdf,0xdf,0xff,0xff,0x7f,0x9f,0xdf,0xef,0xef,0xef,0x1f,0xff,0xff,0xff,0xff,0xdd,0x3f,0xff,0xff,0xff,0x3f,0x1f,0x6f,0x6f,0xcf,0x9f,0xff,0xff,0xfd,0x3,0x7f,0xbf,0xdf,0xef,0xff,0xff,0xf7,0xf7,0xf7,0xa0,0x2,0xfb,0xff,0xff,0xff,//Line 5
  10. 0xff,0xff,0xff,0xff,0xf9,0xf6,0xf6,0xfa,0xfa,0xf8,0xff,0xff,0xf8,0xe7,0xef,0xf3,0xfd,0xfc,0xf1,0xff,0xff,0xe0,0xff,0xff,0xff,0xf0,0xfd,0xff,0xff,0xf0,0xff,0xff,0xff,0xf8,0xff,0xff,0xff,0xcf,0xc3,0xd3,0xe3,0xff,0xff,0xff,0xf7,0xe7,0xee,0xf6,0xf1,0xff,0xff,0xfc,0xf3,0xf7,0xf7,0xfb,0xfb,0xfd,0xff,0xff,0xff,0xcf,0xf3,0xfc,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0x80,0x5b,0xf9,0xfd,0xfe,0xff,0xff,0xff,0xf4,0xf8,0xff,0xff,0xff,0xff,0xff,0xf8,0xe7,0xef,0xef,0xe7,0xf1,0xfc,0xff,0xff,0xcf,0xbf,0xbf,0xc0,0xff,0xff,0xff,0xfc,0xfb,0xf7,0xf7,0xfb,0xfb,0xfd,0xff,0xff,0xf8,0xfd,0xfd,0xfb,0xfb,0xff,0xff,0xff,0xff,0xff,0xff,0xf0,0xff,0xff,0xff,0xff,//Line 6
  11. 0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,//Line 7
  12. 0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0x0//Line 7
  13. };
  14.  
  15.  
  16.  
  17.  
  18. #define SOLID   0
  19. #define TRANSPARENT 1
  20. uint8_t color=GLCD_COLOR_BLACK;
  21. uint8_t Transparent=SOLID;
  22.  
  23. #if act_ks0108_USE_EXTERNAL_EEPROM==1
  24.  
  25.     void storeImage(uint8_t id, uint8_t size_x , uint8_t size_y);
  26.  
  27.     void saveImageFromScreen(uint8_t id, uint8_t size_x , uint8_t size_y);
  28.  
  29.     #define MEMORY_I2C_ADDR  0x57   // 64K EEPROM - allowed addresses are 0x50 to 0x57
  30.     #define MEMORY_ADDR_MSB  0      // start at base of memory. Next one is 0x01.
  31.     #define MEMORY_ADDR_LSB  0      // start on a page boundary. Next one is 0x80.
  32.     unsigned char messageBuf[MESSAGEBUF_SIZE];
  33. #endif
  34.  
  35.  
  36. void numtoascii( int16_t num, char **str );
  37. void signedtoascii(int16_t num, uint8_t decimalplace, char *string, uint8_t numberofdecimals);
  38. void unsignedtoascii(uint16_t num, uint8_t decimalplace, char *string, uint8_t numberofdecimals);
  39.  
  40. #if act_ks0108_USE_EXTERNAL_EEPROM==1
  41. //valid id is 1 to 255;
  42. void printImage(uint8_t id, uint8_t x_start, uint8_t y_start) {
  43.     if (id == 0 )
  44.         return;     //id=0 not allowed
  45.     uint16_t address = 0;
  46.     uint16_t buf_index = 0;
  47.     uint8_t index;
  48.     uint8_t size_x = 0;
  49.     uint8_t size_y = 0;
  50.     uint16_t max_picture_size;
  51.     index = (id>>5)&0x07;
  52.     //find starting adress of the requested data
  53.     switch (index) {
  54.         case 0:
  55.             address = (index)*1024;
  56.             max_picture_size = 1024;
  57.             break;
  58.         case 1:
  59.             address = 32768+(index)*512;
  60.             max_picture_size = 512;
  61.             break;
  62.         case 2:
  63.             address = 32768+32*512+(index)*256;
  64.             max_picture_size = 256;
  65.             break;
  66.         case 3:
  67.             address = 32768+32*512+32*256+(index)*128;
  68.             max_picture_size = 128;
  69.             break;
  70.         case 4:
  71.             address = 32768+32*512+32*256+32*128+(index)*64;
  72.             max_picture_size = 64;
  73.             break;
  74.         case 5:
  75.             address = 32768+32*512+32*256+32*128+32*64+(index)*32;
  76.             max_picture_size = 32;
  77.             break;
  78.         case 6:
  79.             address = 32768+32*512+32*256+32*128+32*64+32*32+(index)*16;
  80.             max_picture_size = 16;
  81.             break;
  82.         case 7:
  83.             address = 32768+32*512+32*256+32*128+32*64+32*32+32*16+(index)*16;
  84.             max_picture_size = 16;
  85.             break;
  86.     }
  87.     //Get size of picture (every picture has an 4 byte info-tag)
  88.     messageBuf[0] = (MEMORY_I2C_ADDR<<TWI_ADR_BITS); // Read/write bit doesn't matter here
  89.     messageBuf[1] = (uint8_t)(0);       // Starting address in memory
  90.     messageBuf[2] = (uint8_t)(((id&0xe0)>>5) & 0xff);           // Starting address in memory
  91.     TWI_Start_Random_Read( messageBuf, 129, 3 );    // Desired data length plus one (command byte).
  92.     // Could do other actions in here, then get data.
  93.     TWI_Read_Data_From_Buffer( messageBuf, 129 );
  94.     size_x = messageBuf[((id&0x1f)<<2)];
  95.     size_y = messageBuf[((id&0x1f)<<2)+1];
  96.     //more_data = messageBuf[((id&0x1f)<<2)+2];
  97.     //last_data = messageBuf[((id&0x1f)<<2)+3];
  98.  
  99.     // get data from eeprom
  100.     messageBuf[0] = (MEMORY_I2C_ADDR<<TWI_ADR_BITS); // Read/write bit doesn't matter here
  101.     messageBuf[1] = (uint8_t)((address >> 8) & 0xff);       // Starting address in memory
  102.     messageBuf[2] = (uint8_t)(address & 0xff);       // Starting address in memory
  103.     TWI_Start_Random_Read( messageBuf, 129, 3 );    // Desired data length plus one (command byte).
  104.     // Could do other actions in here, then get data.
  105.     TWI_Read_Data_From_Buffer( messageBuf, 129 );
  106.     uint8_t jy = 0;
  107.     uint8_t jx = 0;
  108.     buf_index = 0;
  109.     for (jy = 0; jy< size_y; jy+=8){
  110.         glcdSetXY(x_start,y_start+jy);
  111.         for (jx = 0; jx< size_x ; jx++){
  112.             if (buf_index>=128) {   //get new data if buffer empty
  113.                 address +=128;
  114.                 messageBuf[0] = (MEMORY_I2C_ADDR<<TWI_ADR_BITS); // Read/write bit doesn't matter here
  115.                 messageBuf[1] = (uint8_t)((address >> 8) & 0xff);       // Starting address in memory
  116.                 messageBuf[2] = (uint8_t)(address & 0xff);       // Starting address in memory
  117.                 TWI_Start_Random_Read( messageBuf, 129, 3 );    // Desired data length plus one (command byte).
  118.                 // Could do other actions in here, then get data.
  119.                 TWI_Read_Data_From_Buffer( messageBuf, 129 );
  120.                 buf_index=0;
  121.             }
  122.             glcdWriteData(messageBuf[buf_index+1], GLCD_COLOR_CLEAR);
  123.             buf_index++;
  124.         }
  125.     }
  126. }
  127. volatile uint8_t state;
  128. volatile uint8_t lastId = 255;
  129. #define IDLE    0
  130. #define RECEIVING_DATA 1
  131. void newImageData(StdCan_Msg_t *rxMsg) {
  132.     //State machine for storing new data
  133.     switch (state) {
  134.         case IDLE:
  135.             if (rxMsg->Header.Command == CAN_MODULE_CMD_KS0108_LCD_NEW_IMAGE)
  136.             {
  137.                 storeImage(rxMsg->Data[0],rxMsg->Data[1],rxMsg->Data[2]);
  138.                 state = RECEIVING_DATA;
  139.                 lastId = 255;
  140.                 //response message
  141.                 rxMsg->Length = 1;
  142.                 rxMsg->Header.Command = CAN_MODULE_CMD_KS0108_LCD_ACK;
  143.                 while (StdCan_Put(rxMsg) != StdCan_Ret_OK);  
  144.             }else {
  145.                 //error message
  146.                 rxMsg->Length = 0;
  147.                 rxMsg->Header.Command = CAN_MODULE_CMD_KS0108_LCD_ERROR;
  148.                 while (StdCan_Put(rxMsg) != StdCan_Ret_OK);  
  149.             }
  150.             break;
  151.         case RECEIVING_DATA:
  152.             if (rxMsg->Header.Command == CAN_MODULE_CMD_KS0108_LCD_IMAGE_DATA)
  153.             {
  154.                 if (rxMsg->Data[0] == (lastId+1)) {
  155.                     storeImage(rxMsg->Data[0],rxMsg->Data[1],rxMsg->Data[2]);
  156.                     state = RECEIVING_DATA;
  157.                     lastId++;
  158.  
  159.                     //FIXME: call function that handles the data
  160.  
  161.                     //response message
  162.                     rxMsg->Length = 1;
  163.                     rxMsg->Header.Command = CAN_MODULE_CMD_KS0108_LCD_ACK;
  164.                     while (StdCan_Put(rxMsg) != StdCan_Ret_OK);  
  165.                 } else {
  166.                     //wrong id
  167.                     rxMsg->Length = 1;
  168.                     rxMsg->Header.Command = CAN_MODULE_CMD_KS0108_LCD_DATA_ID_ERROR;
  169.                     rxMsg->Data[0] = (lastId+1);
  170.                     while (StdCan_Put(rxMsg) != StdCan_Ret_OK);  
  171.                 }
  172.             } else if (rxMsg->Header.Command == CAN_MODULE_CMD_KS0108_LCD_DATA_DONE) {
  173.                 //Call function to flush eeprom cache
  174.                 //FIXME
  175.                 state=IDLE;
  176.             } else {
  177.                 //error message
  178.                 rxMsg->Length = 0;
  179.                 rxMsg->Header.Command = CAN_MODULE_CMD_KS0108_LCD_ERROR;
  180.                 while (StdCan_Put(rxMsg) != StdCan_Ret_OK);  
  181.             }
  182.             break;
  183.     }
  184.  
  185. }
  186.  
  187.  
  188. //valid id is 1 to 255;
  189. void storeImage(uint8_t id, uint8_t size_x , uint8_t size_y) {
  190.     if (id == 0 )
  191.         return;     //id=0 not allowed
  192.     //uint16_t address = 0;
  193.     //uint16_t buf_index = 0;
  194.     uint8_t index;
  195.     //uint16_t max_picture_size;
  196.     index = (id>>5)&0x07;
  197.     //find starting adress of the requested data
  198.     //Get size of picture (every picture has an 4 byte info-tag)
  199.     messageBuf[0] = (MEMORY_I2C_ADDR<<TWI_ADR_BITS); // Read/write bit doesn't matter here
  200.     messageBuf[1] = (uint8_t)(0);       // Starting address in memory
  201.     messageBuf[2] = (uint8_t)(((id&0xe0)>>5) & 0xff);           // Starting address in memory
  202.     TWI_Start_Random_Read( messageBuf, 129, 3 );    // Desired data length plus one (command byte).
  203.     // Could do other actions in here, then get data.
  204.     TWI_Read_Data_From_Buffer( messageBuf, 129 );
  205.     messageBuf[((id&0x1f)<<2)+1] = size_x;
  206.     messageBuf[((id&0x1f)<<2)+2] = size_y;
  207.     //more_data = messageBuf[((id&0x1f)<<2)+2];
  208.     //last_data = messageBuf[((id&0x1f)<<2)+3];
  209.  
  210.     //move data in the buffer
  211.     for (index = 128; index > 0; index--) {
  212.         messageBuf[index+2] = messageBuf[index];
  213.     }
  214.     messageBuf[0] = (MEMORY_I2C_ADDR<<TWI_ADR_BITS) | (FALSE<<TWI_READ_BIT);
  215.     messageBuf[1] = (uint8_t)(0);       // Starting address in memory
  216.     messageBuf[2] = (uint8_t)(((id&0xe0)>>5) & 0xff);           // Starting address in memory
  217.     TWI_Start_Read_Write( messageBuf, 131 );
  218.     // Should wait for completion of EEPROM write cycle. Blinking the LED will do this.
  219.     while ( TWI_Transceiver_Busy() );    // Check for an error.
  220.  
  221.     //Now the info-tag is written, only to add data left
  222.  
  223.     //FIXME........ FIX!!!
  224.  
  225. }
  226.  
  227.  
  228. //valid id is 1 to 255;
  229. void saveImageFromScreen(uint8_t id, uint8_t size_x , uint8_t size_y) {
  230.     if (id == 0 )
  231.         return;     //id=0 not allowed
  232.     uint16_t max_picture_size;
  233.     uint8_t index;
  234.     uint8_t bufferIndex;
  235.     uint16_t address = 0;
  236.     index = (id>>5)&0x07;
  237.     //find starting adress of the requested data
  238.     switch (index) {
  239.         case 0:
  240.             address = (index)*1024;
  241.             max_picture_size = 1024;
  242.             break;
  243.         case 1:
  244.             address = 32768+(index)*512;
  245.             max_picture_size = 512;
  246.             break;
  247.         case 2:
  248.             address = 32768+32*512+(index)*256;
  249.             max_picture_size = 256;
  250.             break;
  251.         case 3:
  252.             address = 32768+32*512+32*256+(index)*128;
  253.             max_picture_size = 128;
  254.             break;
  255.         case 4:
  256.             address = 32768+32*512+32*256+32*128+(index)*64;
  257.             max_picture_size = 64;
  258.             break;
  259.         case 5:
  260.             address = 32768+32*512+32*256+32*128+32*64+(index)*32;
  261.             max_picture_size = 32;
  262.             break;
  263.         case 6:
  264.             address = 32768+32*512+32*256+32*128+32*64+32*32+(index)*16;
  265.             max_picture_size = 16;
  266.             break;
  267.         case 7:
  268.             address = 32768+32*512+32*256+32*128+32*64+32*32+32*16+(index)*16;
  269.             max_picture_size = 16;
  270.             break;
  271.     }
  272.     //Get size of picture (every picture has an 4 byte info-tag)
  273.     messageBuf[0] = (MEMORY_I2C_ADDR<<TWI_ADR_BITS); // Read/write bit doesn't matter here
  274.     messageBuf[1] = (uint8_t)(0);       // Starting address in memory
  275.     messageBuf[2] = (uint8_t)(((id&0xe0)>>5) & 0xff);           // Starting address in memory
  276.     TWI_Start_Random_Read( messageBuf, 129, 3 );    // Desired data length plus one (command byte).
  277.     // Could do other actions in here, then get data.
  278.     TWI_Read_Data_From_Buffer( messageBuf, 129 );
  279.     messageBuf[((id&0x1f)<<2)+1] = size_x;
  280.     messageBuf[((id&0x1f)<<2)+2] = size_y;
  281.  
  282.     //move data in the buffer
  283.     for (index = 128; index > 0; index--) {
  284.         messageBuf[index+2] = messageBuf[index];
  285.     }
  286.     messageBuf[0] = (MEMORY_I2C_ADDR<<TWI_ADR_BITS) | (FALSE<<TWI_READ_BIT);
  287.     messageBuf[1] = (uint8_t)(0);       // Starting address in memory
  288.     messageBuf[2] = (uint8_t)(((id&0xe0)>>5) & 0xff);           // Starting address in memory
  289.     TWI_Start_Read_Write( messageBuf, 131 );
  290.     // Should wait for completion of EEPROM write cycle. Blinking the LED will do this.
  291.     while ( TWI_Transceiver_Busy() );    // Check for an error.
  292.  
  293.     //Now the info-tag is written, only to add data left
  294.     uint8_t  h, i ;
  295.        
  296.  
  297.     messageBuf[0] = (MEMORY_I2C_ADDR<<TWI_ADR_BITS) | (FALSE<<TWI_READ_BIT);
  298.     messageBuf[1] = (uint8_t)((address >> 8) & 0xff);       // Starting address in memory
  299.     messageBuf[2] = (uint8_t)(address & 0xff);       // Starting address in memory
  300.     bufferIndex = 3;
  301.  
  302.     h = 0;
  303.     while(h+8 <= size_y) {
  304.         h += 8;
  305.         glcdSetXY(0, h);
  306.        
  307.         for(i=0; i<=size_x; i++) {
  308.             messageBuf[bufferIndex] = glcdReadData();
  309.             bufferIndex++;
  310.             if (bufferIndex >= 131) {
  311.                 TWI_Start_Read_Write( messageBuf, 131 );
  312.                 // Should wait for completion of EEPROM write cycle. Blinking the LED will do this.
  313.                 while ( TWI_Transceiver_Busy() );    // Check for an error.
  314.                 bufferIndex = 3;
  315.                 address+=128;
  316.                 messageBuf[0] = (MEMORY_I2C_ADDR<<TWI_ADR_BITS) | (FALSE<<TWI_READ_BIT);
  317.                 messageBuf[1] = (uint8_t)((address >> 8) & 0xff);       // Starting address in memory
  318.                 messageBuf[2] = (uint8_t)(address & 0xff);       // Starting address in memory
  319.             }
  320.         }
  321.     }
  322. }
  323. #endif
  324.  
  325. void act_ks0108_Init(void)
  326. {
  327.     /* Set up PWM controlling brightness */
  328. #if GRAPHICS_DRIVER==KS0108
  329.     TCCR0A |= (1<<COM0A1)|(1<<WGM01)|(1<<WGM00);
  330.     TCCR0B |= (1<<CS00);
  331.     OCR0A = act_ks0108_INITIAL_BACKLIGHT;
  332.     DDRD |= (1<<PD6);
  333. #endif
  334. #if GRAPHICS_DRIVER==DOTMATRIX
  335.     TCCR0A |= (1<<COM0B1)|(1<<WGM01)|(1<<WGM00);
  336.     TCCR0B |= (1<<CS00);
  337.     OCR0B = 0xff-act_ks0108_INITIAL_BACKLIGHT;
  338.     DDRD |= (1<<PD5);
  339. #endif
  340.  
  341.  
  342. #if act_ks0108_USE_EXTERNAL_EEPROM==1
  343.     TWI_Master_Initialise();
  344.     uint8_t temp = 0;
  345.     /// Do initial write to EEPROM. Write cycle takes 5 msecs, so flashing the led will delay enough.
  346.     //
  347.    
  348.     messageBuf[0] = (MEMORY_I2C_ADDR<<TWI_ADR_BITS) | (FALSE<<TWI_READ_BIT);
  349.     messageBuf[1] = (((1024+128)>>8)&0xff);             // Starting address MSB
  350.     messageBuf[2] = ((1024+128)&0xff);              // Starting address LSB
  351.    
  352.     for (temp=0; temp<128; temp++)
  353.     {
  354.         messageBuf[temp+3] = 128-temp; 
  355.     }
  356.     TWI_Start_Read_Write( messageBuf, 131 );
  357.     // Should wait for completion of EEPROM write cycle. Blinking the LED will do this.
  358.     while ( TWI_Transceiver_Busy() );    // Check for an error.
  359.    
  360.     //delay 10ms
  361.     uint32_t temp2;
  362.     temp2 =Timer_GetTicks();
  363.     while (Timer_GetTicks() < temp2 + 10);
  364.  
  365.     #define TEMPID 0
  366.     uint16_t address = (TEMPID+1)*1024; //only addresses on page border is allowed
  367.     uint16_t ixa = 0;
  368.     uint8_t jxa = 0;
  369.     for (jxa = 0; jxa< 8; jxa++){
  370.         for (ixa = 0; ixa < 128; ixa++){
  371.             messageBuf[ixa+3] = (((uint8_t)pgm_read_byte((uint16_t)&Splash_left+ixa+jxa*128)) ^ 0xff);
  372.         }
  373.         messageBuf[0] = (MEMORY_I2C_ADDR<<TWI_ADR_BITS) | (FALSE<<TWI_READ_BIT);
  374.         messageBuf[1] = (uint8_t)((address >> 8) & 0xff);       // Starting address in memory
  375.         messageBuf[2] = (uint8_t)(address & 0xff);       // Starting address in memory
  376.         TWI_Start_Read_Write( messageBuf, 131 );
  377.         // Should wait for completion of EEPROM write cycle. Blinking the LED will do this.
  378.         while ( TWI_Transceiver_Busy() );    // Check for an error.
  379.         //delay 10ms
  380.         temp2 =Timer_GetTicks();
  381.         while (Timer_GetTicks() < temp2 + 10);
  382.         address += 128;
  383.     }
  384.  
  385.     address = (TEMPID+2)*1024;  //only addresses on page border is allowed
  386.     ixa = 0;
  387.     jxa = 0;
  388.     for (jxa = 0; jxa< 8; jxa++){
  389.         for (ixa = 0; ixa < 128; ixa++){
  390.             messageBuf[ixa+3] = (uint8_t)pgm_read_byte((uint16_t)&Splash_left+ixa+jxa*128);
  391.         }
  392.         messageBuf[0] = (MEMORY_I2C_ADDR<<TWI_ADR_BITS) | (FALSE<<TWI_READ_BIT);
  393.         messageBuf[1] = (uint8_t)((address >> 8) & 0xff);       // Starting address in memory
  394.         messageBuf[2] = (uint8_t)(address & 0xff);       // Starting address in memory
  395.         TWI_Start_Read_Write( messageBuf, 131 );
  396.         // Should wait for completion of EEPROM write cycle. Blinking the LED will do this.
  397.         while ( TWI_Transceiver_Busy() );    // Check for an error.
  398.         //delay 10ms
  399.         temp2 =Timer_GetTicks();
  400.         while (Timer_GetTicks() < temp2 + 10);
  401.         address += 128;
  402.     }
  403.     for (temp=0; temp<131; temp++)
  404.     {
  405.         messageBuf[temp] = 0;  
  406.     }
  407.  
  408. #endif
  409.  
  410.     glcdInit();
  411.  
  412. #if act_ks0108_USE_EXTERNAL_EEPROM==0
  413.     uint16_t ixa = 0;
  414.     uint8_t jxa = 0;
  415.     for (jxa = 0; jxa< 8; jxa++){
  416.         glcdSetXY(0,jxa*8);
  417.         for (ixa = 0; ixa < 128; ixa++){
  418.             glcdWriteData((uint8_t)pgm_read_byte((uint16_t)&Splash_left+ixa+jxa*128), GLCD_COLOR_CLEAR);
  419.         }
  420.     }
  421. #endif
  422.  
  423. #if act_ks0108_USE_EXTERNAL_EEPROM==1
  424.     printImage(1,0,0);
  425.     //delay 10ms
  426.     temp2 =Timer_GetTicks();
  427.     while (Timer_GetTicks() < temp2 + 5000);
  428.     printImage(0,0,0);
  429. #endif
  430.     //glcdSetXY(0,0);
  431.     //glcdPutStrTransparent("=_-[]_-=",GLCD_COLOR_SET);
  432.     //glcdSetXY(0,8);
  433.     //glcdPutStrTransparent("--------",GLCD_COLOR_SET);
  434.     //glcdSetXY(0,16);
  435.     //glcdPutStr("-_=[]=-_",GLCD_COLOR_SET);
  436.     //glcdDrawRect(32, 32, 40, 16, GLCD_COLOR_SET);
  437.     //glcdDrawLine(10, 10, 100, 60, GLCD_COLOR_SET);
  438.     //glcdFillRect(90, 10, 20, 20, GLCD_COLOR_SET);
  439.     //glcdInvertRect(28, 10, 20, 20);
  440.     //glcdInvert();
  441.     //glcdDrawRoundRect(85, 5, 30, 30, 5, GLCD_COLOR_SET);
  442.     //glcdDrawCircle(64, 32, 10, 1);
  443.     glcdSetXY(87,8);
  444.     glcdPutStrTransparent("Home-",GLCD_COLOR_SET);
  445.     glcdSetXY(80,16);
  446.     glcdPutStrTransparent("Automa-",GLCD_COLOR_SET);
  447.     glcdSetXY(91,24);
  448.     glcdPutStrTransparent("ion",GLCD_COLOR_SET);
  449.     //glcdDrawLine(10, 62, 50, 5, GLCD_COLOR_CLEAR);
  450.    
  451. }
  452.  
  453. void act_ks0108_Process(void)
  454. {
  455.     ///TODO: Stuff that needs doing is done here
  456. }
  457.  
  458. void act_ks0108_HandleMessage(StdCan_Msg_t *rxMsg)
  459. {
  460.     //StdCan_Msg_t txMsg;
  461.     uint8_t n = 0;
  462.  
  463.     if (    StdCan_Ret_class(rxMsg->Header) == CAN_MODULE_CLASS_ACT &&
  464.         StdCan_Ret_direction(rxMsg->Header) == DIRECTIONFLAG_TO_OWNER &&
  465.         rxMsg->Header.ModuleType == CAN_MODULE_TYPE_ACT_KS0108 &&
  466.         rxMsg->Header.ModuleId == act_ks0108_ID)
  467.     {
  468.     switch (rxMsg->Header.Command)
  469.     {
  470.         case CAN_MODULE_CMD_KS0108_LCD_CLEAR:
  471.           if (rxMsg->Length == 1) {
  472.             glcdSetColor((0x80&rxMsg->Data[0])>>7);
  473.           }
  474.           glcdClear();
  475.           rxMsg->Data[0] = glcdGetColor()<<7;
  476.           StdCan_Set_direction(rxMsg->Header, DIRECTIONFLAG_FROM_OWNER);
  477.           rxMsg->Length = 1;
  478.           #if act_ks0108_USE_EXTERNAL_EEPROM==1
  479.               uint8_t temp = 0;
  480.               //    Read the data from Memory. Value of read/write bit doesn't matter.
  481.                 messageBuf[0] = (MEMORY_I2C_ADDR<<TWI_ADR_BITS); // Read/write bit doesn't matter here
  482.                 messageBuf[1] = MEMORY_ADDR_MSB;       // Starting address in memory
  483.                 messageBuf[2] = MEMORY_ADDR_LSB;       // Starting address in memory
  484.                 TWI_Start_Random_Read( messageBuf, 129, 3 );    // Desired data length plus one (command byte).
  485.                 // Could do other actions in here, then get data.
  486.                 temp = TWI_Read_Data_From_Buffer( messageBuf, 129 );
  487.               rxMsg->Length = 6;
  488.               rxMsg->Data[1] = temp;
  489.               rxMsg->Data[2] = messageBuf[0+3];
  490.               rxMsg->Data[3] = messageBuf[0+4];
  491.               rxMsg->Data[4] = messageBuf[0+5];
  492.               rxMsg->Data[5] = messageBuf[0+80];
  493.           #endif
  494.           while (StdCan_Put(rxMsg) != StdCan_Ret_OK);
  495.           break;
  496.         case CAN_MODULE_CMD_KS0108_LCD_INVERT:
  497.           if (rxMsg->Length == 1) {
  498.             if ((0x80&rxMsg->Data[0])>>7 != glcdGetColor())
  499.                 glcdInvert();
  500.           } else
  501.             glcdInvert();
  502.           rxMsg->Data[0] = glcdGetColor()<<7;
  503.           StdCan_Set_direction(rxMsg->Header, DIRECTIONFLAG_FROM_OWNER);
  504.           rxMsg->Length = 1;
  505.           while (StdCan_Put(rxMsg) != StdCan_Ret_OK);
  506.           break;
  507.         case CAN_MODULE_CMD_KS0108_LCD_CURSOR:
  508.           if (rxMsg->Length == 2) {
  509.             glcdSetXY((0x3f&rxMsg->Data[0])*6, rxMsg->Data[1]*8);
  510.             color = ((0x80&rxMsg->Data[2])>>7);
  511.             Transparent = ((0x40&rxMsg->Data[2])>>6);
  512.           }
  513.           rxMsg->Data[0] = glcdGetColor()<<7;
  514.           rxMsg->Data[0] = Transparent<<6;
  515.           rxMsg->Data[0] |= (0x3f & (glcdGetX()/6));
  516.           rxMsg->Data[1] |= ((glcdGetY()/8));
  517.           StdCan_Set_direction(rxMsg->Header, DIRECTIONFLAG_FROM_OWNER);
  518.           rxMsg->Length = 2;
  519.           while (StdCan_Put(rxMsg) != StdCan_Ret_OK);
  520.  
  521.           break;
  522.  
  523.         case CAN_MODULE_CMD_KS0108_LCD_TEXTAT:
  524.           glcdSetXY((0x3f&rxMsg->Data[0])*6, rxMsg->Data[1]*8);
  525.           for (n = 2; n < rxMsg->Length; n++)
  526.           {
  527.               if (((0x40&rxMsg->Data[0])>>6)== TRANSPARENT)
  528.                 glcdWriteCharTransparent((char)rxMsg->Data[n], (0x80&rxMsg->Data[0])>>7);
  529.               else
  530.                 glcdWriteChar((char)rxMsg->Data[n], (0x80&rxMsg->Data[0])>>7);
  531.           }
  532.         break;
  533.  
  534.         case CAN_MODULE_CMD_KS0108_LCD_TEXT:
  535.         for (n = 0; n < rxMsg->Length; n++)
  536.         {
  537.             if (Transparent == TRANSPARENT)
  538.                 glcdWriteCharTransparent((char)rxMsg->Data[n], color);
  539.             else
  540.                 glcdWriteChar((char)rxMsg->Data[n], color);
  541.         }
  542.         break;
  543.  
  544.         case CAN_MODULE_CMD_KS0108_LCD_BACKLIGHT:
  545.             if (rxMsg->Length > 0) {
  546.                 if ( rxMsg->Data[0] == 0) {
  547.                     TCCR0A &= ~(1<<COM0A0);
  548.                     TCCR0A &= ~(1<<COM0A1);
  549.                     PORTD &= ~(1<<PD6);
  550.                     OCR0A = rxMsg->Data[0];
  551.                 } else {
  552.                     TCCR0A |= (1<<COM0A1)|(1<<WGM01)|(1<<WGM00);
  553.                     OCR0A = rxMsg->Data[0];
  554.                 }
  555.  
  556.             }
  557.             StdCan_Msg_t txMsg;
  558.             StdCan_Set_class(txMsg.Header, CAN_MODULE_CLASS_ACT);
  559.             StdCan_Set_direction(txMsg.Header, DIRECTIONFLAG_FROM_OWNER);
  560.             txMsg.Header.ModuleType = CAN_MODULE_TYPE_ACT_KS0108;
  561.             txMsg.Header.ModuleId = act_ks0108_ID;
  562.             txMsg.Header.Command = CAN_MODULE_CMD_KS0108_LCD_BACKLIGHT;
  563.             txMsg.Length = 1;
  564.             txMsg.Data[0] = OCR0A;
  565.             while (StdCan_Put(&txMsg) != StdCan_Ret_OK);
  566.         break;
  567.        
  568.         case CAN_MODULE_CMD_KS0108_LCD_DRAWRECT:
  569.           if ((0x40&rxMsg->Data[0])>>6)
  570.             glcdFillRect(rxMsg->Data[1], rxMsg->Data[2], rxMsg->Data[3], rxMsg->Data[4], (0x80&rxMsg->Data[0])>>7);
  571.           else
  572.             if (rxMsg->Data[5] == 0)
  573.                 glcdDrawRect(rxMsg->Data[1], rxMsg->Data[2], rxMsg->Data[3], rxMsg->Data[4], (0x80&rxMsg->Data[0])>>7);
  574.             else
  575.                 glcdDrawRoundRect(rxMsg->Data[1], rxMsg->Data[2], rxMsg->Data[3], rxMsg->Data[4], rxMsg->Data[5],(0x80&rxMsg->Data[0])>>7);
  576.           break;
  577.        
  578.         case CAN_MODULE_CMD_KS0108_LCD_DRAWLINE:
  579.           glcdDrawLine(rxMsg->Data[1], rxMsg->Data[2], rxMsg->Data[3], rxMsg->Data[4], (0x80&rxMsg->Data[0])>>7);
  580.           break;
  581.  
  582.         case CAN_MODULE_CMD_KS0108_LCD_DRAWCIRCLE:
  583.           glcdDrawCircle(rxMsg->Data[1], rxMsg->Data[2], rxMsg->Data[3], (0x80&rxMsg->Data[0])>>7);
  584.           break;
  585.    
  586.         case CAN_MODULE_CMD_KS0108_LCD_INVERTRECT:
  587.           glcdInvertRect(rxMsg->Data[0], rxMsg->Data[1], rxMsg->Data[2], rxMsg->Data[3]);
  588.           break;
  589.  
  590.         }
  591.     }
  592. /*
  593.     static uint8_t saer=0;
  594.     static uint8_t saer2=0;
  595.     saer++;
  596.     if (saer>10) {
  597.         saer2++;
  598.         uint8_t ixa = 0;
  599.         uint8_t jxa = 0;
  600.         for (jxa = 0; jxa< 8; jxa++){
  601.             glcdSetXY(0,jxa);
  602.             for (ixa = 0; ixa < 128; ixa++){
  603.                 glcdWriteData((uint8_t)pgm_read_byte((uint16_t)&Splash_left+ixa+jxa*128));
  604.             }
  605.         }
  606.         saer=0;
  607.         glcdSetXY(83,1);
  608.         glcdPutStr("Tycker ");
  609.         glcdSetXY(83,2);
  610.         glcdPutStr(" detta ");
  611.         glcdSetXY(83,3);
  612.         glcdPutStr("funkar!");
  613.         glcdSetXY(83,4);
  614.         char buffer[20];   
  615.         //numtoascii((int16_t)saer2 ,*buffer);
  616.         unsignedtoascii((int16_t)saer2,0,buffer,1);
  617.         glcdPutStr(buffer);
  618.     }
  619. */
  620. }
  621.  
  622. void act_ks0108_List(uint8_t ModuleSequenceNumber)
  623. {
  624.     StdCan_Msg_t txMsg;
  625.  
  626.     StdCan_Set_class(txMsg.Header, CAN_MODULE_CLASS_ACT);
  627.     StdCan_Set_direction(txMsg.Header, DIRECTIONFLAG_FROM_OWNER);
  628.     txMsg.Header.ModuleType = CAN_MODULE_TYPE_ACT_KS0108;
  629.     txMsg.Header.ModuleId = act_ks0108_ID;
  630.     txMsg.Header.Command = CAN_MODULE_CMD_GLOBAL_LIST;
  631.     txMsg.Length = 6;
  632.  
  633.     txMsg.Data[0] = NODE_HW_ID_BYTE0;
  634.     txMsg.Data[1] = NODE_HW_ID_BYTE1;
  635.     txMsg.Data[2] = NODE_HW_ID_BYTE2;
  636.     txMsg.Data[3] = NODE_HW_ID_BYTE3;
  637.  
  638.     txMsg.Data[4] = NUMBER_OF_MODULES;
  639.     txMsg.Data[5] = ModuleSequenceNumber;
  640.  
  641.     while (StdCan_Put(&txMsg) != StdCan_Ret_OK);
  642. }
  643.  
  644. //� la pengi. Skall libbifieras.
  645.     void numtoascii( int16_t num, char **str ) {
  646.         if( num==0 ) return;
  647.         numtoascii( num/10, str );
  648.         **str = '0' + (num%10);
  649.         (*str)++;
  650.     }
  651.  
  652.     void signedtoascii(int16_t num, uint8_t decimalplace, char *string, uint8_t numberofdecimals){ //decimalplace is number of decimals
  653.         uint8_t i;
  654.  
  655.         if( num<0 ) {
  656.             *(string++) = '-';
  657.             num = -num;
  658.         }
  659.         numtoascii(num>>decimalplace, &string );
  660.         if(numberofdecimals!=0) *(string++) = '.';
  661.         for(i=0;i<numberofdecimals;i++) {
  662.             num %= 1<<decimalplace;
  663.             num *= 10;
  664.             *(string++) = '0' + (num>>decimalplace);
  665.         }
  666.         *(string++) = 0;
  667.     }
  668.  
  669.     void unsignedtoascii(uint16_t num, uint8_t decimalplace, char *string, uint8_t numberofdecimals){ //decimalplace is number of decimals
  670.         uint8_t i;
  671.         numtoascii(num>>decimalplace, &string );
  672.         if(numberofdecimals!=0) *(string++) = '.';
  673.         for(i=0;i<numberofdecimals;i++) {
  674.             num %= 1<<decimalplace;
  675.             num *= 10;
  676.             *(string++) = '0' + (num>>decimalplace);
  677.         }
  678.         *(string++) = 0;
  679.     }
  680.