summaryrefslogtreecommitdiff
path: root/uisimulator/lcd.c
diff options
context:
space:
mode:
Diffstat (limited to 'uisimulator/lcd.c')
-rw-r--r--uisimulator/lcd.c91
1 files changed, 78 insertions, 13 deletions
diff --git a/uisimulator/lcd.c b/uisimulator/lcd.c
index 0db77e09bb..8607477d82 100644
--- a/uisimulator/lcd.c
+++ b/uisimulator/lcd.c
@@ -21,8 +21,10 @@
21 * This file is meant for generic LCD defines and global variables etc. 21 * This file is meant for generic LCD defines and global variables etc.
22 */ 22 */
23 23
24#define DISP_X 112 /* Display width in pixels */ 24#include "lcd.h"
25#define DISP_Y 64 /* Display height in pixels */ 25
26#define DISP_X LCD_WIDTH /* Display width in pixels */
27#define DISP_Y LCD_HEIGHT /* Display height in pixels */
26 28
27#define CHAR_X 6 /* Character width in pixels */ 29#define CHAR_X 6 /* Character width in pixels */
28#define CHAR_Y 8 /* Character height in pixels */ 30#define CHAR_Y 8 /* Character height in pixels */
@@ -38,7 +40,7 @@
38#define ASCII_MIN 0x20 /* First char in table */ 40#define ASCII_MIN 0x20 /* First char in table */
39#define ASCII_MAX 0x7f /* Last char in table */ 41#define ASCII_MAX 0x7f /* Last char in table */
40 42
41static const uchar char_gen[ASCII_MAX-ASCII_MIN+1][CHAR_X-1] = 43static const unsigned char char_gen[ASCII_MAX-ASCII_MIN+1][CHAR_X-1] =
42{ 44{
43 0x00, 0x00, 0x00, 0x00, 0x00, /* 0x20-0x2f */ 45 0x00, 0x00, 0x00, 0x00, 0x00, /* 0x20-0x2f */
44 0x00, 0x00, 0x4f, 0x00, 0x00, 46 0x00, 0x00, 0x4f, 0x00, 0x00,
@@ -150,30 +152,93 @@ static const uchar char_gen[ASCII_MAX-ASCII_MIN+1][CHAR_X-1] =
150 * Bits within a byte are arranged veritcally, LSB at top. 152 * Bits within a byte are arranged veritcally, LSB at top.
151 * Byte 0 is top left, byte 1 is 2nd left, byte DISP_X starts 2nd row. 153 * Byte 0 is top left, byte 1 is 2nd left, byte DISP_X starts 2nd row.
152 */ 154 */
153static uchar display[DISP_Y/8][DISP_X]; 155unsigned char display[LCD_HEIGHT/8][LCD_WIDTH];
154 156
155static uint16 lcd_y; /* Current pixel row */ 157static unsigned char lcd_y; /* Current pixel row */
156static uint16 lcd_x; /* Current pixel column */ 158static unsigned char lcd_x; /* Current pixel column */
157 159
158/* 160/*
159 * Set current x,y position 161 * Set current x,y position
160 */ 162 */
161void lcd_position (int x, int y) 163void lcd_position(int x, int y)
162{ 164{
163 if (x >= 0 && x < DISP_X && y >= 0 && y < DISP_Y) 165 if (x >= 0 && x < DISP_X && y >= 0 && y < DISP_Y) {
164 { 166 lcd_x = x;
165 lcd_x = x; 167 lcd_y = y;
166 lcd_y = y; 168 }
167 }
168} 169}
169 170
170/* 171/*
171 * Clear the display 172 * Clear the display
172 */ 173 */
173void lcd_clear (void) 174void lcd_clear(void)
174{ 175{
175 lcd_x = 0; 176 lcd_x = 0;
176 lcd_y = 0; 177 lcd_y = 0;
177 memset (display, 0, sizeof display); 178 memset (display, 0, sizeof display);
178} 179}
179 180
181/*
182 * Display a character at current position.
183 * This writes a 5x8 character within a 6x8 cell.
184 * The cell does not have to be aligned to a display byte.
185 * The top left of the cell is displayed at the current position.
186 * invert is TRUE to display in reverse video.
187 */
188void lcd_char (int ch, char invert)
189{
190 unsigned char (*dp)[DISP_X] = (void *) &display[lcd_y/8][lcd_x];
191 unsigned long shift, mask, col;
192
193 /* Limit to char generation table */
194 if (ch < ASCII_MIN || ch > ASCII_MAX)
195 ch = ASCII_MAX;
196
197 /* Calculate shift and masks for cell bit position */
198 shift = (lcd_y & 0x7);
199 mask = ~(COL_MASK << shift);
200 if (invert)
201 invert = ~mask;
202
203 /* Write each char column */
204 for (col = 0; col < CHAR_X-1; col++) {
205 unsigned long data = (char_gen[ch-ASCII_MIN][col] << shift) ^ invert;
206 dp[0][col] = (dp[0][col] & mask) | data;
207 if (lcd_y < DISP_Y-8)
208 dp[1][col] = (dp[1][col] & (mask >> 8)) | (data >> 8);
209 }
210
211 /* Column after char */
212 dp[0][CHAR_X-1] = (dp[0][CHAR_X-1] & mask) | invert;
213 if (lcd_y < DISP_Y-8)
214 dp[1][CHAR_X-1] = (dp[1][CHAR_X-1] & (mask >> 8)) | (invert >> 8);
215}
216
217/*
218 * Output a string at current position
219 */
220void lcd_string(const char *text, char invert)
221{
222 int ch;
223
224 while ((ch = *text++) != '\0') {
225 if (lcd_y > DISP_Y-CHAR_Y) {
226 /* Scroll (8 pixels) */
227 memcpy (display[0], display[1], DISP_X*(DISP_Y/8-1));
228 lcd_y -= 8;
229 }
230
231 if (ch == '\n')
232 lcd_x = DISP_X;
233 else {
234 lcd_char (ch, invert);
235 lcd_x += CHAR_X;
236 }
237
238 if (lcd_x > DISP_X-CHAR_X) {
239 /* Wrap to next line */
240 lcd_x = 0;
241 lcd_y += CHAR_Y;
242 }
243 }
244}