Newhaven Display Forum

Newhaven Products => OLEDs => Topic started by: Kon-L on September 30, 2017, 05:06:48 AM

Title: OLED Multi-Font IC Problems
Post by: Kon-L on September 30, 2017, 05:06:48 AM
Hello folks,

I have been working for some time now with the NHD-3.12-25664UMB3.  It is a great display.  However I have yet to be able to use the Multi-font functionality.  I wrote a program based on the datasheets sample program, but nothing will display.  Everything else in my program works and will display, but when it comes time to use the Multi-font IC the display stays blank.  It was the main reason this display was chosen was to keep from having to write the code for multiple languages.  Storing the Japanese or Chinese fonts takes up too much memory space in my PIC chip.  I am using 4 wire SPI connection with a PIC18F.  Below is the relevant code for those who are interested, but I have yet to get it to work.  Does anyone have any suggestion to get it to work?  Has anyone ever got it to work?


/*********************************************************************
Function Name:  SetOLEDAddress                                               
Return Value:                                             
Parameters:  oled_column, oled_row                       
Description: sets pointer to to write/read operations
********************************************************************/
void SetOLEDAddress(unsigned char x, unsigned char y){         //Starts at 0, 0 going to 255, 63
   
    OLED_command(0x15);    //column command
   OLED_data(x);
   OLED_data(0x77);           //total columns divided by 2 (Default 77)
   
    OLED_command(0x75);    //row command
   OLED_data(y);
   OLED_data(0x7F);           // default 7F
}


/*************************************************************
   Function Name:  Delay_ms                                         
   Return Value:   void                                           
   Parameters:     Number of milliseconds                   
   Description:    Delay function
                   TMR1 times out every ~170.666 us     
**************************************************************/
void Delay_ms(long num_ms){                                          //JFR Used in the Key Scan function
   long n;                                             
 
   for(n = 0; n < num_ms; n++){
      INTCONbits.TMR0IF = 0;      // Clear flag
      TMR0H = 0xFC;                                                //We only count from FC18h to FFFF
      TMR0L = 0x1A;                                                               //Deducting one because each line takes time to execute also
      while(!INTCONbits.TMR0IF);  // Wait for timer flag to set
   }
}




/******************************************************************
   Function Name:    OLED_char                               
   Return Value:                                             
   Parameters:       character, oled_column, oled_row                       
   Description:      Gets character data from the Multi-Font IC of the OLED Disable
******************************************************************/
void OLED_char (unsigned char character, unsigned char oled_column, unsigned char oled_row, char line){

   unsigned char MSB, LSB, byte1, byte2, byte3;
   unsigned char readByte, i;
    unsigned char *readByte_ptr;
   unsigned char FontBuffer[4][32];               //5 for 5 lines of text. 1-4 are the lines and 5 is going to be volume display characters
   unsigned short long Address;                  //unsigned short long is 24-bits
   //Need to split character into 2 8-bit words MSB and LSB   
   MSB = (character >> 8) & 0xFF;                  //Could define each or the array as int or char or whatever
   LSB = character & 0xFF;
   
    //readByte_ptr = &readByte;
   
   //Parameters: JIS0208 Japanese                                 
   //MSB: Higher byte of JIS code                     I think we should use Japanese JIS 0208
   //LSB: Lower byte of JIS code                     This will include English and the Infinity symbol
   //Address: Address of character data               Note though ALL characters will be double height 15x16 pixels
   if((MSB >= 1 && MSB <= 94) && (LSB >= 1 && LSB <= 94))
   Address = (((((MSB - 1) * 94) + (LSB - 1)) * 32) + 490,624);
   
   //To split the resulting number into bytes
   byte1 = (Address >> 16) & 0xFF;               
   byte2 = (Address >> 8) & 0xFF;            //uses Bitwise AND to form 8-bit values
   byte3 = Address & 0xFF;      //source: https://stackoverflow.com/questions/3784263/converting-an-int-into-a-4-byte-char-array-c
   
   //Send READ command and Address to Multi-Font IC.
    OLEDen = 1;
   MuFen = 0;                  //make rc5 of PIC18 go low to enable the Multi-Font IC
   MultiFont_OUT(0x0B); //READ command                  This SPI_OUT is for the Multi-Font IC NOT the OLED
   MultiFont_OUT(byte1); //Address Byte1 (MSB)      
   MultiFont_OUT(byte2); //Address Byte2            
   MultiFont_OUT(byte3); //Address Byte3 (LSB)      
   MultiFont_OUT(0xFF); //Dummy Byte               Datasheet says 0x00, but their example has 0xFF
   
   
      for(i = 0 ; i < 32 ; i++ ){               //For i number of bytes to gather from Multi-Font IC.  In this case its 32.
            FontBuffer[1] = MultiFont_IN();         //JFR Modified for testing!!!
      }   
   
   MuFen = 1;               //make rc5 of PIC18 go high to disable the Multi-Font IC
   OLEDen = 0;
   
      SetOLEDAddress(oled_column, oled_row);          //set address location for font to be displayed
      wram();                                                            //Write to OLED Ram instruction
      for(i = 0 ; i < 16 ; i++ ){                //for the first 16 bytes of font data
         OLED_data(FontBuffer[1]);       //write byte to display
         oled_column++;                            //next byte will be for the next column
         SetOLEDAddress(oled_column, oled_row);       //set address location for next column
         wram();
      }
   
      oled_column = oled_column - 16;                      //go back to first column of the font
      oled_row = oled_row + 8;                         //move down to show the bottom half of font  example had +16
      SetOLEDAddress(oled_column, oled_row);          //set address for bottom half of font
         
      for(i = 16 ; i < 32 ; i++ ){                //for the second 16 bytes of font data
         wram();
         OLED_data(FontBuffer[1]);       //write byte to display
         oled_column++;                            //next byte will be for the next column
         SetOLEDAddress(oled_column, oled_row);       //set address location for next column
         
      }
      
}

/******************************************************************
   Function Name: display_oled_init                                         
   Return Value:  1 (used in main initialization routine)                                           
   Parameters:    void                     
   Description:   Detects the OLED display and initializes it 
*******************************************************************/
void display_oled_init(void)
{
    unsigned char m;
    unsigned int i;
    unsigned char n;
    unsigned char character;
    unsigned char charcolumn;
   unsigned char num_char = 16;               //Maximum characters per line.
   
   //Delay_ms(250);
   
    //oled_setup();

    int init_text[2][16] = {{0x2121, 0x2121, 0x2349, 0x236E, 0x2369, 0x2374, 0x2369, 0x2361, 0x236C, 0x2369, 0x237A, 0x2369, 0x236E, 0x2367, 0x2121, 0x2121},
                     {0x2121, 0x2350, 0x236C, 0x2365, 0x2361, 0x2373, 0x2365, 0x2124, 0x2121, 0x2377, 0x2361, 0x2369, 0x2374, 0x2125, 0x2121, 0x2121}};
                                 //Displays 'Intializing' on line 2, and 'Please, wait.' on line 3.
                                 //line 3 needs to be shifted by half a character to center under line 2.
   
   SetOLEDAddress(0,16);      //First the 'Initializing' line.
   
   for(n = 0; n < num_char; n++){            //num_char should be changed to the exact number of characters in line_text
        character = init_text[1][n];      //JFR Changed for testing!!!
      charcolumn = (n * 16);
      OLED_char(character, charcolumn, 16, 1);      
   }
   
   //for(n = 0; n < num_char; n++){            //num_char should be changed to the exact number of characters in line_text
      //  character = init_text[0][n];
      //OLED_char(character, 0, 32, 1);      
   //}
   
   SetOLEDAddress(8,32);      //Then the 'Please, wait.' line. Shift it right by half a charater.  Thats 8 pixels.

   //for(n = 0; n < num_char; n++){            //num_char should be changed to the exact number of characters in line_text
    //    character = init_text[1][n];
   //   OLED_char(character, 0, 16, 2);      
   //}
   
   for(n = 0; n < num_char; n++){            //num_char should be changed to the exact number of characters in line_text
        character = init_text[1][n];
      OLED_char(character, 0, 32, 2);      
   }
   //Would like to have these two lines centered.  Can do this by adding blank spaces in front of each line.
   Delay_ms(750);
   
   //clear_oled_display();            //clears oled display
}