Nokia 1100 LCD Display

vor 3 years 34 weeks

Nokia 1100 LCD

LCD Displays aus Mobiltelefonen sind recht beliebt bei Microcontroller Fricklern. Sie haben oft eine gewisse Große und sind voll grafikfähig. Aber am wichtigsten ist wohl der Umstand, dass man immer irgendwie ein paar defekte Handys rumliegen hat. Und dabei sind die Displays selten kaputt. Geht mir zumindest so.

Dies Projekt hat das Display des Nokia 1100 an einen PIC Microcontroller angeschlossen.

6 Antworten auf “Nokia 1100 LCD Display”


  1. uwe sagt:

    Hallo Alle zusammen

    es geht auch mit dem Arduino.
    Hab den Code von http://www.sunbizhosting.com/~spiral/1100/ auf Arduino umgeschrieben.
    Viele Grüße
    Uwe

    Login or register to post comments

  1. lundgaaj sagt:

    Hello Uwe,

    Can you post the code?

    Thanks in advance,
    Gruss aus Dänemark,
    Jesper

    Login or register to post comments

  1. uwe sagt:

    Hi Jasper
    I answer you and send you the sketch in the eavening.
    Bye Uwe

    Login or register to post comments

  1. lundgaaj sagt:

    Hi Uwe,

    I actually managed to get it working today. The initialization is very different from sunbiz', but this is how I got it working.
    Still curious to see your code though, so please share it?

    Br,
    Jesper

    ----------------------------------------------------------------------------
    // Arduino Dueminalove Atmega328
    // Interfacing with the Nokia 1100 LCD, PCF8814

    // Arduino pinout // Nokia 1100 LCD pinout (VDD & VDDI ==> 3.3V, VLED+ connected via 10 ohm resistor to 3.3V)
    #define PIN_SCE 10 // 2 XCS Connected via resistor-voltage-divider 1.8K & 3.2K
    #define PIN_SDIN 11 // 4 SDA
    #define PIN_RESET 12 // 1 XRES
    #define PIN_SCLK 13 // 5 SCLK

    #define LCD_C LOW // Command
    #define LCD_D HIGH // Data

    static const byte ASCII[][5] ={
    {0x00, 0x00, 0x00, 0x00, 0x00} // 20
    ,{0x00, 0x00, 0x5f, 0x00, 0x00} // 21 !
    ,{0x00, 0x07, 0x00, 0x07, 0x00} // 22 "
    ,{0x14, 0x7f, 0x14, 0x7f, 0x14} // 23 #
    ,{0x24, 0x2a, 0x7f, 0x2a, 0x12} // 24 $
    ,{0x23, 0x13, 0x08, 0x64, 0x62} // 25 %
    ,{0x36, 0x49, 0x55, 0x22, 0x50} // 26 &
    ,{0x00, 0x05, 0x03, 0x00, 0x00} // 27 '
    ,{0x00, 0x1c, 0x22, 0x41, 0x00} // 28 (
    ,{0x00, 0x41, 0x22, 0x1c, 0x00} // 29 )
    ,{0x14, 0x08, 0x3e, 0x08, 0x14} // 2a *
    ,{0x08, 0x08, 0x3e, 0x08, 0x08} // 2b +
    ,{0x00, 0x50, 0x30, 0x00, 0x00} // 2c ,
    ,{0x08, 0x08, 0x08, 0x08, 0x08} // 2d -
    ,{0x00, 0x60, 0x60, 0x00, 0x00} // 2e .
    ,{0x20, 0x10, 0x08, 0x04, 0x02} // 2f /
    ,{0x3e, 0x51, 0x49, 0x45, 0x3e} // 30 0
    ,{0x00, 0x42, 0x7f, 0x40, 0x00} // 31 1
    ,{0x42, 0x61, 0x51, 0x49, 0x46} // 32 2
    ,{0x21, 0x41, 0x45, 0x4b, 0x31} // 33 3
    ,{0x18, 0x14, 0x12, 0x7f, 0x10} // 34 4
    ,{0x27, 0x45, 0x45, 0x45, 0x39} // 35 5
    ,{0x3c, 0x4a, 0x49, 0x49, 0x30} // 36 6
    ,{0x01, 0x71, 0x09, 0x05, 0x03} // 37 7
    ,{0x36, 0x49, 0x49, 0x49, 0x36} // 38 8
    ,{0x06, 0x49, 0x49, 0x29, 0x1e} // 39 9
    ,{0x00, 0x36, 0x36, 0x00, 0x00} // 3a :
    ,{0x00, 0x56, 0x36, 0x00, 0x00} // 3b ;
    ,{0x08, 0x14, 0x22, 0x41, 0x00} // 3c <
    ,{0x14, 0x14, 0x14, 0x14, 0x14} // 3d =
    ,{0x00, 0x41, 0x22, 0x14, 0x08} // 3e >
    ,{0x02, 0x01, 0x51, 0x09, 0x06} // 3f ?
    ,{0x32, 0x49, 0x79, 0x41, 0x3e} // 40 @
    ,{0x7e, 0x11, 0x11, 0x11, 0x7e} // 41 A
    ,{0x7f, 0x49, 0x49, 0x49, 0x36} // 42 B
    ,{0x3e, 0x41, 0x41, 0x41, 0x22} // 43 C
    ,{0x7f, 0x41, 0x41, 0x22, 0x1c} // 44 D
    ,{0x7f, 0x49, 0x49, 0x49, 0x41} // 45 E
    ,{0x7f, 0x09, 0x09, 0x09, 0x01} // 46 F
    ,{0x3e, 0x41, 0x49, 0x49, 0x7a} // 47 G
    ,{0x7f, 0x08, 0x08, 0x08, 0x7f} // 48 H
    ,{0x00, 0x41, 0x7f, 0x41, 0x00} // 49 I
    ,{0x20, 0x40, 0x41, 0x3f, 0x01} // 4a J
    ,{0x7f, 0x08, 0x14, 0x22, 0x41} // 4b K
    ,{0x7f, 0x40, 0x40, 0x40, 0x40} // 4c L
    ,{0x7f, 0x02, 0x0c, 0x02, 0x7f} // 4d M
    ,{0x7f, 0x04, 0x08, 0x10, 0x7f} // 4e N
    ,{0x3e, 0x41, 0x41, 0x41, 0x3e} // 4f O
    ,{0x7f, 0x09, 0x09, 0x09, 0x06} // 50 P
    ,{0x3e, 0x41, 0x51, 0x21, 0x5e} // 51 Q
    ,{0x7f, 0x09, 0x19, 0x29, 0x46} // 52 R
    ,{0x46, 0x49, 0x49, 0x49, 0x31} // 53 S
    ,{0x01, 0x01, 0x7f, 0x01, 0x01} // 54 T
    ,{0x3f, 0x40, 0x40, 0x40, 0x3f} // 55 U
    ,{0x1f, 0x20, 0x40, 0x20, 0x1f} // 56 V
    ,{0x3f, 0x40, 0x38, 0x40, 0x3f} // 57 W
    ,{0x63, 0x14, 0x08, 0x14, 0x63} // 58 X
    ,{0x07, 0x08, 0x70, 0x08, 0x07} // 59 Y
    ,{0x61, 0x51, 0x49, 0x45, 0x43} // 5a Z
    ,{0x00, 0x7f, 0x41, 0x41, 0x00} // 5b [
    ,{0x02, 0x04, 0x08, 0x10, 0x20} // 5c ¥
    ,{0x00, 0x41, 0x41, 0x7f, 0x00} // 5d ]
    ,{0x04, 0x02, 0x01, 0x02, 0x04} // 5e ^
    ,{0x40, 0x40, 0x40, 0x40, 0x40} // 5f _
    ,{0x00, 0x01, 0x02, 0x04, 0x00} // 60 `
    ,{0x20, 0x54, 0x54, 0x54, 0x78} // 61 a
    ,{0x7f, 0x48, 0x44, 0x44, 0x38} // 62 b
    ,{0x38, 0x44, 0x44, 0x44, 0x20} // 63 c
    ,{0x38, 0x44, 0x44, 0x48, 0x7f} // 64 d
    ,{0x38, 0x54, 0x54, 0x54, 0x18} // 65 e
    ,{0x08, 0x7e, 0x09, 0x01, 0x02} // 66 f
    ,{0x0c, 0x52, 0x52, 0x52, 0x3e} // 67 g
    ,{0x7f, 0x08, 0x04, 0x04, 0x78} // 68 h
    ,{0x00, 0x44, 0x7d, 0x40, 0x00} // 69 i
    ,{0x20, 0x40, 0x44, 0x3d, 0x00} // 6a j
    ,{0x7f, 0x10, 0x28, 0x44, 0x00} // 6b k
    ,{0x00, 0x41, 0x7f, 0x40, 0x00} // 6c l
    ,{0x7c, 0x04, 0x18, 0x04, 0x78} // 6d m
    ,{0x7c, 0x08, 0x04, 0x04, 0x78} // 6e n
    ,{0x38, 0x44, 0x44, 0x44, 0x38} // 6f o
    ,{0x7c, 0x14, 0x14, 0x14, 0x08} // 70 p
    ,{0x08, 0x14, 0x14, 0x18, 0x7c} // 71 q
    ,{0x7c, 0x08, 0x04, 0x04, 0x08} // 72 r
    ,{0x48, 0x54, 0x54, 0x54, 0x20} // 73 s
    ,{0x04, 0x3f, 0x44, 0x40, 0x20} // 74 t
    ,{0x3c, 0x40, 0x40, 0x20, 0x7c} // 75 u
    ,{0x1c, 0x20, 0x40, 0x20, 0x1c} // 76 v
    ,{0x3c, 0x40, 0x30, 0x40, 0x3c} // 77 w
    ,{0x44, 0x28, 0x10, 0x28, 0x44} // 78 x
    ,{0x0c, 0x50, 0x50, 0x50, 0x3c} // 79 y
    ,{0x44, 0x64, 0x54, 0x4c, 0x44} // 7a z
    ,{0x00, 0x08, 0x36, 0x41, 0x00} // 7b {
    ,{0x00, 0x00, 0x7f, 0x00, 0x00} // 7c |
    ,{0x00, 0x41, 0x36, 0x08, 0x00} // 7d }
    ,{0x10, 0x08, 0x08, 0x10, 0x08} // 7e ←
    ,{0x78, 0x46, 0x41, 0x46, 0x78} // 7f →
    };

    void LcdCharacter(char character){
    LcdWrite(LCD_D, 0x00);
    for (int index = 0; index < 5; index++)
    LcdWrite(LCD_D, ASCII[character - 0x20]

    );
    }

    void LcdClear(void){
    for (int index = 0; index < 864 ; index++)
    LcdWrite(LCD_D, 0x00);
    }

    void LcdInitialise(void){
    digitalWrite(PIN_RESET, LOW);
    digitalWrite(PIN_RESET, HIGH);
    LcdWrite(LCD_C, 0x2F); // Charge pump ON
    LcdWrite(LCD_C, 0x24); // Vop MSB *Don't change*
    LcdWrite(LCD_C, 0x80); // Vop LSB *Here you can change contrast*
    LcdWrite(LCD_C, 0xA4); // A4 = normal display mode, A5 = all pixels ON
    LcdWrite(LCD_C, 0xAF); // Display ON
    }

    void LcdString(char *characters){
    while (*characters){
    LcdCharacter(*characters++);
    }
    }

    void LcdWrite(byte dc, byte data){
    digitalWrite(PIN_SDIN, dc); // dc is sampled with the first rising SCLK edge
    digitalWrite(PIN_SCE, LOW); // LCD enable
    digitalWrite(PIN_SCLK, HIGH); // First rising SCLK edge
    digitalWrite(PIN_SCLK, LOW);
    shiftOut(PIN_SDIN, PIN_SCLK, MSBFIRST, data); // SDIN is sampled at the rising edge of SCLK.
    digitalWrite(PIN_SCE, HIGH);
    }

    void setup(void){
    pinMode(PIN_SCE, OUTPUT);
    pinMode(PIN_RESET, OUTPUT);
    pinMode(PIN_SDIN, OUTPUT);
    pinMode(PIN_SCLK, OUTPUT);
    digitalWrite(PIN_RESET, LOW);
    digitalWrite(PIN_SCE, HIGH);
    digitalWrite(PIN_SCLK, LOW);
    LcdInitialise();
    LcdClear();
    LcdWrite(LCD_C, 0xA7); // Inverted display
    delay(200);
    LcdWrite(LCD_C, 0xA6); // Normal display
    }

    void loop(void){
    LcdString("Nokia 1100 LCD says Hello World");
    delay(5000);
    LcdInitialise();
    }

    Login or register to post comments

  1. uwe sagt:

    dear Jasper
    Sorrys, yesterday my adsl was not working
    my adaption to Arduino of the program of http://www.sunbizhosting.com/~spiral/1100/

    For better contrast change values Vop in the Lcd_Init(void) function.
    I have test it abu i ars not shure that I have no errors.
    By Uwe

    /*

    _ _ ___ _ __ ___ _ _ _ ___ ___ _ ____ ____
    | \ | | / _ \ | |/ / |_ _| / \ / | / | / _ \ / _ \ | | / ___| | _ \
    | \| | | | | | | ' / | | / _ \ | | | | | | | | | | | | | | | | | | | |
    | |\ | | |_| | | . \ | | / ___ \ | | | | | |_| | | |_| | | |___ | |___ | |_| |
    |_| \_| \___/ |_|\_\ |___| /_/ \_\ |_| |_| \___/ \___/ |_____| \____| |____/

    arduino and Nokia 1100 Display PCF8814

    -------------------------------------------
    display: rear site, pin 1 on left site
    ________________________________
    | |||||||| |
    | 1 8 |
    | |

    display abbreviation description arduino
    1 XRES Reset 5
    2 XCS Chip Select 3
    3 VSS (GND) Ground
    4 SDA Serial Data 4
    5 SCLK Serial Clock 6
    6 VDDI Power supply
    7 VDD Power supply
    8 LED+ Power Led

    function description:
    LcdSendCmd Description : Sends data to display controller. ok nokia 1100
    Argument(s) : data -> Data to be sent
    cd -> Command or data (see/use enum)
    Return value : None.
    -----------------------------
    Lcd_Init Description : Performs MCU SPI & LCD controller initialization. ok nokia 1100
    Argument(s) : None.
    Return value : None.
    -----------------------------
    LcdContrast Description : Set display contrast.
    Argument(s) : contrast -> Contrast value from 0x00 to 0x7F.
    Return value : None.
    Notes : No change visible at ambient temperature.
    ----------------------------
    Lcd_Clear Description : clear display Ram. ok nokia 1100
    Argument(s) : None
    Return value : None.
    ----------------------------
    LcdGotoXY Description : Sets cursor location to xy location corresponding to basic font size.
    Argument(s) : x, y -> Coordinate for new cursor position. Range: 1,1 .. 16,7
    Return value : None.
    ----------------------------
    LcdChr Description : Displays a character at current cursor location and increment cursor location.
    Argument(s) : size -> Font size. See enum.
    ch -> Character to write.
    Return value : None.
    ----------------------------
    LcdStr Description : Displays a character at current cursor location and increment cursor location according to font size.
    Argument(s) : size -> Font size. See enum.
    dataPtr -> Pointer to null terminated ASCII string to display.
    Return value : None.
    ----------------------------
    LcdPixel Description : Displays a pixel at given absolute (x, y) location. ok nokia 1100
    Argument(s) : x, y -> Absolute pixel coordinates; range 1,1 ... 96,65
    mode -> Off, On or Xor. See enum.
    Return value : None.
    ----------------------------
    LcdLine Description : Draws a line between two points on the display. ok nokia 1100
    Argument(s) : x1, y1 -> Absolute pixel coordinates for line origin.
    x2, y2 -> Absolute pixel coordinates for line end.
    mode -> Off, On or Xor. See enum.
    Return value : None.
    ----------------------------
    LcdUpdate Description : Copies the LCD cache into the device RAM. ok nokia 1100
    Argument(s) : None.
    Return value : None.
    ----------------------------

    */

    //int CONTROL_LED=12;
    //int LCD_POWER_PIN = 11;
    //int LCD_DC_PIN = 2; // PB0 4 Data Command

    int LCD_CE_PIN = 3; // PB2 5 /CS active low chip select ??
    int SPI_MOSI_PIN = 4; // PB3 3 Serial line
    int LCD_RST_PIN = 5; // PB4 8 /RES RESET
    int SPI_CLK_PIN = 6; // PB5 2 CLOCK
    int led13_pin = 13; // led L
    int i;
    int j;

    #define LCD_X_RES 96
    #define LCD_Y_RES 65

    #define LCD_CACHE_SIZE ((LCD_X_RES * LCD_Y_RES) / 8)

    /*--------------------------------------------------------------------------------------------------
    Type definitions
    --------------------------------------------------------------------------------------------------*/

    #define LCD_CMD 0 //sended data is a command
    #define LCD_DATA 1 //sended data is data

    #define PIXEL_OFF 0
    #define PIXEL_ON 1
    #define PIXEL_XOR 2

    #define FONT_1X 1 // normal size of caracter
    #define FONT_2X 2 // dubble size of caracter
    #define FONT_1N 3 // normal size of caracter

    typedef unsigned int word;

    // Public function prototypes

    void LcdInit ( void );
    void LcdClear ( void );
    void LcdUpdate ( void );
    void LcdGotoXY ( byte x, byte y );
    void LcdChr ( int size, byte ch );
    void LcdStr ( int size, char *dataPtr );
    void LcdPixel ( byte x, byte y, int mode );
    void LcdLine ( byte x1, byte y1, byte x2, byte y2, int mode );
    void LcdSendCmd ( byte data, int cd );

    // This table defines the standard ASCII characters in a 5x7 dot format.

    // Global Variables

    byte LcdCache [ LCD_CACHE_SIZE ];

    int LcdCacheIdx;
    int LoWaterMark;

    int HiWaterMark;
    boolean UpdateLcd;
    char sign;

    // to do implement proportiona font type like used ba Nokia in the model 1100

    // This table defines the standard ASCII characters in a 5x7 dot format.
    static const byte FontLookup[][5]={
    { 0x00, 0x00, 0x00, 0x00, 0x00 } ,// (space)
    { 0x00, 0x00, 0x5F, 0x00, 0x00 } ,// !
    { 0x00, 0x07, 0x00, 0x07, 0x00 } ,// "
    { 0x14, 0x7F, 0x14, 0x7F, 0x14 } ,// #
    { 0x24, 0x2A, 0x7F, 0x2A, 0x12 } ,// $
    { 0x23, 0x13, 0x08, 0x64, 0x62 } ,// %
    { 0x36, 0x49, 0x55, 0x22, 0x50 } ,// ,// '
    { 0x00, 0x1C, 0x22, 0x41, 0x00 } ,// (
    { 0x00, 0x41, 0x22, 0x1C, 0x00 } ,// )
    { 0x08, 0x2A, 0x1C, 0x2A, 0x08 } ,// *
    { 0x08, 0x08, 0x3E, 0x08, 0x08 } ,// +
    { 0x00, 0x50, 0x30, 0x00, 0x00 } ,// ,
    { 0x08, 0x08, 0x08, 0x08, 0x08 } ,// -
    { 0x00, 0x30, 0x30, 0x00, 0x00 } ,// .
    { 0x20, 0x10, 0x08, 0x04, 0x02 } ,// /
    { 0x3E, 0x51, 0x49, 0x45, 0x3E } ,// 0
    { 0x00, 0x42, 0x7F, 0x40, 0x00 } ,// 1
    { 0x42, 0x61, 0x51, 0x49, 0x46 } ,// 2
    { 0x21, 0x41, 0x45, 0x4B, 0x31 } ,// 3
    { 0x18, 0x14, 0x12, 0x7F, 0x10 } ,// 4
    { 0x27, 0x45, 0x45, 0x45, 0x39 } ,// 5
    { 0x3C, 0x4A, 0x49, 0x49, 0x30 } ,// 6
    { 0x01, 0x71, 0x09, 0x05, 0x03 } ,// 7
    { 0x36, 0x49, 0x49, 0x49, 0x36 } ,// 8
    { 0x06, 0x49, 0x49, 0x29, 0x1E } ,// 9
    { 0x00, 0x36, 0x36, 0x00, 0x00 } ,// :
    { 0x00, 0x56, 0x36, 0x00, 0x00 } ,// ;
    { 0x00, 0x08, 0x14, 0x22, 0x41 } ,// <
    { 0x14, 0x14, 0x14, 0x14, 0x14 } ,// =
    { 0x41, 0x22, 0x14, 0x08, 0x00 } ,// >
    { 0x02, 0x01, 0x51, 0x09, 0x06 } ,// ?
    { 0x32, 0x49, 0x79, 0x41, 0x3E } ,// @
    { 0x7E, 0x11, 0x11, 0x11, 0x7E } ,// A
    { 0x7F, 0x49, 0x49, 0x49, 0x36 } ,// B
    { 0x3E, 0x41, 0x41, 0x41, 0x22 } ,// C
    { 0x7F, 0x41, 0x41, 0x22, 0x1C } ,// D
    { 0x7F, 0x49, 0x49, 0x49, 0x41 } ,// E
    { 0x7F, 0x09, 0x09, 0x01, 0x01 } ,// F
    { 0x3E, 0x41, 0x41, 0x51, 0x32 } ,// G
    { 0x7F, 0x08, 0x08, 0x08, 0x7F } ,// H
    { 0x00, 0x41, 0x7F, 0x41, 0x00 } ,// I
    { 0x20, 0x40, 0x41, 0x3F, 0x01 } ,// J
    { 0x7F, 0x08, 0x14, 0x22, 0x41 } ,// K
    { 0x7F, 0x40, 0x40, 0x40, 0x40 } ,// L
    { 0x7F, 0x02, 0x04, 0x02, 0x7F } ,// M
    { 0x7F, 0x04, 0x08, 0x10, 0x7F } ,// N
    { 0x3E, 0x41, 0x41, 0x41, 0x3E } ,// O
    { 0x7F, 0x09, 0x09, 0x09, 0x06 } ,// P
    { 0x3E, 0x41, 0x51, 0x21, 0x5E } ,// Q
    { 0x7F, 0x09, 0x19, 0x29, 0x46 } ,// R
    { 0x46, 0x49, 0x49, 0x49, 0x31 } ,// S
    { 0x01, 0x01, 0x7F, 0x01, 0x01 } ,// T
    { 0x3F, 0x40, 0x40, 0x40, 0x3F } ,// U
    { 0x1F, 0x20, 0x40, 0x20, 0x1F } ,// V
    { 0x7F, 0x20, 0x18, 0x20, 0x7F } ,// W
    { 0x63, 0x14, 0x08, 0x14, 0x63 } ,// X
    { 0x03, 0x04, 0x78, 0x04, 0x03 } ,// Y
    { 0x61, 0x51, 0x49, 0x45, 0x43 } ,// Z
    { 0x00, 0x00, 0x7F, 0x41, 0x41 } ,// [
    { 0x02, 0x04, 0x08, 0x10, 0x20 } ,// "\"
    { 0x41, 0x41, 0x7F, 0x00, 0x00 } ,// ]
    { 0x04, 0x02, 0x01, 0x02, 0x04 } ,// ^
    { 0x40, 0x40, 0x40, 0x40, 0x40 } ,// _
    { 0x00, 0x01, 0x02, 0x04, 0x00 } ,// `
    { 0x20, 0x54, 0x54, 0x54, 0x78 } ,// a
    { 0x7F, 0x48, 0x44, 0x44, 0x38 } ,// b
    { 0x38, 0x44, 0x44, 0x44, 0x20 } ,// c
    { 0x38, 0x44, 0x44, 0x48, 0x7F } ,// d
    { 0x38, 0x54, 0x54, 0x54, 0x18 } ,// e
    { 0x08, 0x7E, 0x09, 0x01, 0x02 } ,// f
    { 0x08, 0x14, 0x54, 0x54, 0x3C } ,// g
    { 0x7F, 0x08, 0x04, 0x04, 0x78 } ,// h
    { 0x00, 0x44, 0x7D, 0x40, 0x00 } ,// i
    { 0x20, 0x40, 0x44, 0x3D, 0x00 } ,// j
    { 0x00, 0x7F, 0x10, 0x28, 0x44 } ,// k
    { 0x00, 0x41, 0x7F, 0x40, 0x00 } ,// l
    { 0x7C, 0x04, 0x18, 0x04, 0x78 } ,// m
    { 0x7C, 0x08, 0x04, 0x04, 0x78 } ,// n
    { 0x38, 0x44, 0x44, 0x44, 0x38 } ,// o
    { 0x7C, 0x14, 0x14, 0x14, 0x08 } ,// p
    { 0x08, 0x14, 0x14, 0x18, 0x7C } ,// q
    { 0x7C, 0x08, 0x04, 0x04, 0x08 } ,// r
    { 0x48, 0x54, 0x54, 0x54, 0x20 } ,// s
    { 0x04, 0x3F, 0x44, 0x40, 0x20 } ,// t
    { 0x3C, 0x40, 0x40, 0x20, 0x7C } ,// u
    { 0x1C, 0x20, 0x40, 0x20, 0x1C } ,// v
    { 0x3C, 0x40, 0x30, 0x40, 0x3C } ,// w
    { 0x44, 0x28, 0x10, 0x28, 0x44 } ,// x
    { 0x0C, 0x50, 0x50, 0x50, 0x3C } ,// y
    { 0x44, 0x64, 0x54, 0x4C, 0x44 } ,// z
    { 0x00, 0x08, 0x36, 0x41, 0x00 } ,// {
    { 0x00, 0x00, 0x7F, 0x00, 0x00 } ,// |
    { 0x00, 0x41, 0x36, 0x08, 0x00 } ,// }
    { 0x08, 0x08, 0x2A, 0x1C, 0x08 } ,// ->
    { 0x08, 0x1C, 0x2A, 0x08, 0x08 } // <-
    };

    /*--------------------------------------------------------------------------------------------------

    Name : LcdSendCmd ok nokia 1100

    Description : Sends data to display controller.

    Argument(s) : data -> Data to be sent
    cd -> Command or data (see/use enum)

    Return value : None.

    --------------------------------------------------------------------------------------------------*/
    void LcdSendCmd ( byte data, int cd )
    {
    digitalWrite(LCD_CE_PIN, LOW);
    digitalWrite(led13_pin, LOW);

    byte i = 8;
    byte mask;
    digitalWrite(SPI_CLK_PIN,LOW); // tick write C/D bit
    delayMicroseconds(1);
    if ( cd == LCD_DATA )
    {
    digitalWrite(SPI_MOSI_PIN,HIGH);
    }
    else {
    digitalWrite(SPI_MOSI_PIN,LOW) ;
    }
    digitalWrite(SPI_CLK_PIN,HIGH); // tock
    delayMicroseconds(1);

    while(0 < i) {
    mask = 0x01 << --i; // get bitmask and move to least significant bit
    // cause edge to fall
    digitalWrite(SPI_CLK_PIN,LOW); // tick
    delayMicroseconds(1);
    // set out byte
    if(data & mask){ // choose bit
    digitalWrite(SPI_MOSI_PIN,HIGH); // send 1
    }
    else{
    digitalWrite(SPI_MOSI_PIN,LOW); // send 0
    }
    // cause edge to rise
    digitalWrite(SPI_CLK_PIN,HIGH); // tock
    delayMicroseconds(1);
    }
    digitalWrite(LCD_CE_PIN, HIGH);
    digitalWrite(led13_pin, HIGH);
    }

    /*--------------------------------------------------------------------------------------------------

    Name : Lcd_Init ok nokia 1100

    Description : Performs MCU SPI & LCD controller initialization.

    Argument(s) : None.

    Return value : None.

    --------------------------------------------------------------------------------------------------*/

    void Lcd_Clear(void){ // clear LCD
    unsigned int i;
    LcdSendCmd( 0x40, LCD_CMD ); // Y = 0
    LcdSendCmd( 0xb0, LCD_CMD );
    LcdSendCmd( 0x10, LCD_CMD ); // X = 0
    LcdSendCmd( 0x00, LCD_CMD );
    LcdSendCmd( 0xae, LCD_CMD ); // disable display;
    for(i=0;i<864;i++)
    {
    LcdSendCmd( 0x00, LCD_DATA );
    }
    LcdSendCmd( 0xaf, LCD_CMD ); // enable display;
    }

    // init LCD
    void Lcd_Init(void)
    {

    // Toggle display reset pin.
    digitalWrite(LCD_RST_PIN,LOW);
    delay(40);
    digitalWrite(LCD_RST_PIN,HIGH);

    LcdSendCmd( 0x23, LCD_CMD ); // 0010 0100 write VOP register ... contrast
    LcdSendCmd( 0x90, LCD_CMD ); // 1001 0000
    LcdSendCmd( 0xA4, LCD_CMD ); // 1010 0100 all on/normal display
    LcdSendCmd( 0x2F, LCD_CMD ); // 0010 1111 Power control set(charge pump on/off)
    LcdSendCmd( 0x40, LCD_CMD ); // 0100 0000 set start row address = 0
    LcdSendCmd( 0xb0, LCD_CMD ); // 1011 0000 set Y-address = 0
    LcdSendCmd( 0x10, LCD_CMD ); // 0001 0000 set X-address, upper 3 bits =0
    LcdSendCmd( 0x00, LCD_CMD ); // 0000 0000 set X-address, lower 4 bits =0
    //LcdSendCmd( 0xC8, LCD_CMD ); // 1100 1000 mirror Y axis (about X axis)
    //LcdSendCmd( 0xa1, LCD_CMD ); // 1010 0001 Invert screen in horizontal axis
    LcdSendCmd( 0xac, LCD_CMD ); // 1010 1100 set initial row (R0) of the display
    LcdSendCmd( 0x07, LCD_CMD ); // 0000 0111
    LcdSendCmd( 0xaf, LCD_CMD ); // 1010 1111 display ON/OFF

    Lcd_Clear(); // clear LCD
    LcdSendCmd( 0xa7, LCD_CMD ); // 1010 0111 Toggle display to normal to reverse and return at the end of initialisation
    delay(1000);
    LcdSendCmd( 0xa6, LCD_CMD ); // 1010 0110
    delay(1000);
    }

    /*--------------------------------------------------------------------------------------------------

    Name : LcdContrast

    Description : Set display contrast.

    Argument(s) : contrast -> Contrast value from 0x00 to 0x7F.

    Return value : None.

    Notes : No change visible at ambient temperature.

    --------------------------------------------------------------------------------------------------*/
    void LcdContrast ( byte contrast )
    {
    // LCD Extended Commands.
    LcdSendCmd( 0x21, LCD_CMD );

    // Set LCD Vop (Contrast).
    LcdSendCmd( 0x80 | contrast, LCD_CMD );

    // LCD Standard Commands, horizontal addressing mode.
    LcdSendCmd( 0x20, LCD_CMD );
    }

    /*--------------------------------------------------------------------------------------------------

    Name : LcdClear ok nokia 1100

    Description : Clears the display. LcdUpdate must be called next.

    Argument(s) : None.

    Return value : None.

    --------------------------------------------------------------------------------------------------*/
    void LcdClear ( void )
    {
    int i;

    for ( i = 0; i < LCD_CACHE_SIZE; i++ )
    {
    LcdCache[i] = 0x00;
    }

    // Reset watermark pointers.
    LoWaterMark = 0;
    HiWaterMark = LCD_CACHE_SIZE - 1;

    UpdateLcd = true;
    }

    /*--------------------------------------------------------------------------------------------------

    Name : LcdGotoXY ok nokia 1100

    Description : Sets cursor location to xy location corresponding to basic font size.

    Argument(s) : x, y -> Coordinate for new cursor position. Range: 1,1 ... 15,7

    Return value : None.

    --------------------------------------------------------------------------------------------------*/
    void LcdGotoXY ( byte x, byte y )
    {
    LcdCacheIdx = (x - 1) * 6 + (y - 1) * 96;
    }

    /*--------------------------------------------------------------------------------------------------

    Name : LcdChr ok nokia 1100

    Description : Displays a character at current cursor location and increment cursor location.

    Argument(s) : size -> Font size. See enum.
    ch -> Character to write.

    Return value : None.

    --------------------------------------------------------------------------------------------------*/
    void LcdChr ( int size, byte ch )
    {

    //Serial.println(int(ch));
    byte i, c;
    byte b1, b2;
    int tmpIdx;

    if ( LcdCacheIdx < LoWaterMark )
    {
    // Update low marker.
    LoWaterMark = LcdCacheIdx;
    }

    if ( (ch < 0x20) || (ch > 0x7b) )
    {
    ch = 65; // Convert to a printable character.
    }

    if ( size == FONT_1X )
    {
    for ( i = 0; i < 5; i++ )
    {
    LcdCache[LcdCacheIdx++] = FontLookup[ch - 0x20][i] << 1;
    }
    LcdCache[LcdCacheIdx++] = 0x00;
    }
    else if ( size == FONT_1N )
    {
    for ( i = 0; i < 5; i++ )
    {
    LcdCache[LcdCacheIdx++] = (FontLookup[ch - 0x20][i] << 1)^0xff;
    }
    LcdCache[LcdCacheIdx++] = 0xff;
    }
    else if ( size == FONT_2X )
    {
    tmpIdx = LcdCacheIdx - 96;

    if ( tmpIdx < LoWaterMark )
    {
    LoWaterMark = tmpIdx;
    }

    if ( tmpIdx < 0 )
    {
    // Serial.print(tmpIdx);
    // Serial.println("error");
    return;
    }

    for ( i = 0; i < 5; i++ )
    {
    //c = FontLookup[ch - 32][i] << 1;
    c = FontLookup[ch - 0x20][i] << 1;
    //Serial.println(c);
    b1 = (c & 0x01) * 3;
    b1 |= (c & 0x02) * 6;
    b1 |= (c & 0x04) * 12;
    b1 |= (c & 0x08) * 24;

    c >>= 4;
    b2 = (c & 0x01) * 3;
    b2 |= (c & 0x02) * 6;
    b2 |= (c & 0x04) * 12;
    b2 |= (c & 0x08) * 24;

    LcdCache[tmpIdx++] = b1;
    LcdCache[tmpIdx++] = b1;
    LcdCache[tmpIdx + 94] = b2;
    LcdCache[tmpIdx + 95] = b2;
    }

    // Update x cursor position.
    LcdCacheIdx += 11;
    LcdCache[LcdCacheIdx++] = 0x00;
    }

    if ( LcdCacheIdx > HiWaterMark )
    {
    // Update high marker.
    HiWaterMark = LcdCacheIdx;
    }

    // Horizontal gap between characters.
    //LcdCache[LcdCacheIdx++] = 0x00;
    }

    /*--------------------------------------------------------------------------------------------------

    Name : LcdStr ok nokia 1100

    Description : Displays a character at current cursor location and increment cursor location
    according to font size.

    Argument(s) : size -> Font size. See enum.
    dataPtr -> Pointer to null terminated ASCII string to display.

    Return value : None.

    --------------------------------------------------------------------------------------------------*/
    void LcdStr ( int size, char *dataPtr )
    {
    while ( *dataPtr )
    {
    LcdChr( size, *dataPtr++ );
    }
    }

    /*--------------------------------------------------------------------------------------------------

    Name : LcdPixel ok nokia 1100

    Description : Displays a pixel at given absolute (x, y) location.

    Argument(s) : x, y -> Absolute pixel coordinates
    mode -> Off, On or Xor. See enum. range

    Return value : None.

    --------------------------------------------------------------------------------------------------*/
    void LcdPixel ( byte x, byte y, int mode )
    {
    word index;
    byte offset;
    byte data;

    if ( x > LCD_X_RES ) return;
    if ( y > LCD_Y_RES ) return;

    index = ((y / 8) * 96) + x;
    offset = y - ((y / 8) * 8);
    //Serial.print(int(x)); Serial.print (" "); Serial.print(int(y)); Serial.print (" ");Serial.print(index); Serial.print (" ");Serial.println(int(offset));

    data = LcdCache

    ;

    if ( mode == PIXEL_OFF )
    {
    data &= (~(0x01 << offset));
    }
    else if ( mode == PIXEL_ON )
    {
    data |= (0x01 << offset);
    }
    else if ( mode == PIXEL_XOR )
    {
    data ^= (0x01 << offset);
    }

    LcdCache

    = data;

    if ( index < LoWaterMark ) // define range to upload
    {
    // Update low marker.
    LoWaterMark = index;
    }

    if ( index > HiWaterMark ) // define range to upload
    {
    // Update high marker.
    HiWaterMark = index;
    }
    }

    /*--------------------------------------------------------------------------------------------------

    Name : LcdLine ok nokia 1100

    Description : Draws a line between two points on the display.

    Argument(s) : x1, y1 -> Absolute pixel coordinates for line origin.
    x2, y2 -> Absolute pixel coordinates for line end.
    mode -> Off, On or Xor. See enum.

    Return value : None.

    --------------------------------------------------------------------------------------------------*/
    void LcdLine ( byte x1, byte y1, byte x2, byte y2, int mode )
    {
    int dx, dy, stepx, stepy, fraction;

    dy = y2 - y1;
    dx = x2 - x1;

    if ( dy < 0 )
    {
    dy = -dy;
    stepy = -1;
    }
    else
    {
    stepy = 1;
    }

    if ( dx < 0 )
    {
    dx = -dx;
    stepx = -1;
    }
    else
    {
    stepx = 1;
    }

    dx <<= 1;
    dy <<= 1;

    LcdPixel( x1, y1, mode );

    if ( dx > dy )
    {
    fraction = dy - (dx >> 1);
    while ( x1 != x2 )
    {
    if ( fraction >= 0 )
    {
    y1 += stepy;
    fraction -= dx;
    }
    x1 += stepx;
    fraction += dy;
    LcdPixel( x1, y1, mode );
    }
    }
    else
    {
    fraction = dx - (dy >> 1);
    while ( y1 != y2 )
    {
    if ( fraction >= 0 )
    {
    x1 += stepx;
    fraction -= dy;
    }
    y1 += stepy;
    fraction += dx;
    LcdPixel( x1, y1, mode );
    }
    }

    UpdateLcd = true;
    }

    /*--------------------------------------------------------------------------------------------------

    Name : LcdUpdate ok nokia 1100

    Description : Copies the LCD cache into the device RAM.

    Argument(s) : None.

    Return value : None.

    --------------------------------------------------------------------------------------------------*/
    void LcdUpdate ( void ) //write data of cache to display ram
    {
    int i;

    //always update everything for the moment
    LoWaterMark = 0;
    HiWaterMark = LCD_CACHE_SIZE - 1;

    if ( LoWaterMark < 0 ){
    LoWaterMark = 0;
    }
    else if ( LoWaterMark >= LCD_CACHE_SIZE ){
    LoWaterMark = LCD_CACHE_SIZE - 1;
    }

    if ( HiWaterMark < 0 ){
    HiWaterMark = 0;
    }
    else if ( HiWaterMark >= LCD_CACHE_SIZE ){
    HiWaterMark = LCD_CACHE_SIZE - 1;
    }
    //Serial.println(LoWaterMark);
    //Serial.print(((LoWaterMark % LCD_X_RES)/4)&0x07); Serial.print (" "); Serial.print((LoWaterMark % LCD_X_RES)&0x0f);Serial.print (" "); Serial.println((LoWaterMark / LCD_X_RES)&0x0f);

    // Set base address according to LoWaterMark.
    LcdSendCmd( 0x00 | ((LoWaterMark % LCD_X_RES)&0x0f), LCD_CMD ); // set 4 lower bits of x cursor position
    LcdSendCmd( 0x10 | (((LoWaterMark % LCD_X_RES)/8)&0x07), LCD_CMD ); // set 3 higher bits of x cursor positionx position of cursor
    LcdSendCmd( 0xb0 | ((LoWaterMark / LCD_X_RES)&0x0f), LCD_CMD ); // set 4 bit y position of cursor

    // Serialize the video buffer.
    for ( i = LoWaterMark; i <= HiWaterMark; i++ )
    {
    LcdSendCmd( LcdCache[i], LCD_DATA );
    }

    // Reset watermark pointers.
    LoWaterMark = LCD_CACHE_SIZE - 1;
    HiWaterMark = 0;

    UpdateLcd = false;
    }

    // ---------------------------------------------
    void setup() {
    Serial.begin(9600);

    //power control led

    j=0;
    //pinMode(CONTROL_LED,OUTPUT);

    pinMode(LCD_RST_PIN,OUTPUT);
    pinMode(LCD_CE_PIN ,OUTPUT);
    pinMode(SPI_MOSI_PIN ,OUTPUT);
    pinMode(SPI_CLK_PIN,OUTPUT);
    pinMode(led13_pin,OUTPUT);

    //power the display
    //not used in this sketch. the display was powered permanently
    // pinMode(LCD_POWER_PIN,OUTPUT);

    //start
    digitalWrite(LCD_CE_PIN, HIGH);
    //digitalWrite(CONTROL_LED, HIGH);
    Lcd_Init();

    }

    // ---------------------------------------------

    void loop() {

    /*
    LcdSendCmd( 0x40, LCD_CMD ); // Y = 0
    LcdSendCmd( 0xb0, LCD_CMD );
    LcdSendCmd( 0x10, LCD_CMD ); // X = 0
    LcdSendCmd( 0x00, LCD_CMD );
    //LcdSendCmd( 0xae, LCD_CMD ); // disable display;

    for(i=0;i<864;i++)
    {
    LcdSendCmd( j, LCD_DATA );

    }

    j++;
    if (j>255) {j=0;}
    */
    /* test LcdPixwel
    int p,q;

    for (p=0; p<65;p++)
    {
    for (q=0; q<96;q++)
    {
    LcdPixel(q, p , 2);

    }
    LcdUpdate();
    }
    */

    // test LcdLine
    LcdClear ();
    int p,q;
    for (p=0; p<96;p+=10)
    {
    LcdLine ( p, 0, 95-p , 65, 2 );
    LcdUpdate();
    }
    for (p=60; p>5;p-=10)
    {
    LcdLine ( 0, p, 95 , 65-p, 2 );
    LcdUpdate();
    }
    LcdSendCmd( 0xa7, LCD_CMD );
    delay(1500);
    LcdSendCmd( 0xa6, LCD_CMD );
    delay(1500);
    //delay(5000);

    LcdClear ();
    //LcdUpdate();
    /*
    // test caracter
    byte r;
    r=2; q=0;
    LcdGotoXY ( 1, r );
    for (p=66; p<98;p++)
    {
    LcdChr ( 2, p );
    LcdUpdate();
    q++;
    if (q>=8)
    {
    r+=2;
    LcdGotoXY( 1,r );
    q =0;
    }
    }
    */

    LcdSendCmd( 0xa7, LCD_CMD );
    delay(1500);
    LcdSendCmd( 0xa6, LCD_CMD );
    delay(1500);

    //delay(5000);

    //LcdSendCmd( 0xaf, LCD_CMD ); // enable display;
    //delay(200);
    /*

    delay(1000);

    LcdSendCmd( 0xa7, LCD_CMD );
    delay(5000);
    LcdSendCmd( 0xa6, LCD_CMD );
    delay(5000);
    */
    //LcdLine ( 0, 0, 83, 47, 2 );
    //LcdChr(1,(char)'A');
    //LcdStr(1, "BCDEFG");
    //LcdUpdate();
    }
     

    Login or register to post comments

  1. SpiralBrain (not verified) sagt:

    Good Job Lads!

    Login or register to post comments