Skip to content
Travis Goodspeed edited this page Jul 31, 2018 · 5 revisions

The Casio 3208 LCD is a bit different from those in devkits that nicely separate each character into groups of pins. This document will explain its pinout from a software perspective, but you ought to be able to work backward from the datasheet to get the hardware arrangement.

Available Cells

The CC430 has fewer LCD segment pins than the chip on Casio's board, so we had to be a bit tricky about layout. In the process, we lost the cells used to indicate the day of the week, but most other cells work fine. These are the cells that we can darken.

Digit Map

Each digit looks like the following, with exceptions for special things like the colons and the upper row of symbols.

     AAAAA
    F     B
    F     B
    F     B
     GGGGG
    E     C
    E     C
    E     C
     DDDDD  dp

We can arrange each digit into an array, so that by an array lookup we can locate a cell of a character on the screen. In this table, the upper byte of each 16-bit word indicates the index into the lcdm (LCD Memory) or lcdbm (LCD Blink Memory).

// A,      B,      C,      D,      E,      F,      G,     dp         digit
const int map[10][8]={
  {0x0b04, 0x0b40, 0x0b20, 0x0b01, 0x0a10, 0x0a20, 0x0b02, 0x0b10}, //0
  {0x0940, 0x0a04, 0x0a02, 0x0910, 0x0901, 0x0902, 0x0920, 0x0a01}, //1
  {0x0804, 0x0840, 0x0820, 0x0801, 0x0710, 0x0720, 0x0802, 0x0810}, //2
  {0x0640, 0x0704, 0x0702, 0x0610, 0x0601, 0x0602, 0x0620, 0x0701}, //3
  {0x0504, 0x0540, 0x0520, 0x0501, 0x0410, 0x0420, 0x0502, 0x0510}, //4
  {0x0c02, 0x0404, 0x0402, 0x0310, 0x0302, 0x0304, 0x0340, 0x0401}, //5
  {0x0204, 0x0220, 0x0210, 0x0201, 0x0110, 0x0120, 0x0202, 0x0301}, //6
  {0x0040, 0x0104, 0x0102, 0x0010, 0x0001, 0x0002, 0x0020, 0x0201}, //7
};

Font

We also need a font, to convert from a digit to something displayable. There are presently two fonts, one for numbers and a second for letters, in the lcdtext.c module.

enum mappos {A=1, B=2, C=4, D=8, E=0x10, F=0x20, G=0x40, DP=0x80};
const int numfont[]={
  A|B|C|D|E|F,   //0
  B|C,           //1
  A|B|G|E|D,     //2
  A|B|G|C|D,     //3
  F|G|B|C,       //4
  A|F|G|C|D,     //5
  A|F|G|E|C|D,   //6
  A|B|C,         //7
  A|B|C|D|E|F|G, //8
  A|B|G|F|C|D,   //9
  A|F|B|G|E|C,   //A
  F|E|G|C|D,     //B
  A|F|E|D,       //C
  E|G|C|D|B,     //D
  A|F|E|G|D,     //E
  A|G|F|E        //F
};

Software Support

Except for the Clock, each application has its ->draw() handler called every 250ms by the WDT_VECTOR handler in main.c. This handler takes an int as its parameter, which is 0 during times called (by the watchdog handler) and non-zero if the return value of the ->keypress() handler is non-zero, in which case an extra LCD frame will be drawn after the keypress for a better user experience.

To take a specific example in the RPN Calculator applet, rpn_keypress() returns 1 after each keypress. So when rpn_draw(0) is called every 250ms, it doesn't draw anything, because it knows that the stack has not changed. After a keypress, rpn_draw(1) is called and the watch can quickly redraw the new frame without waiting for the next 250ms callback.

See lcdtext.h for high-level LCD functions, and lcd.h for the low-level ones. While they work in the ->keypress() handler, it is better to call them from the ->draw() handler to take advantage of double buffering.

Clone this wiki locally