summaryrefslogtreecommitdiff
path: root/firmware/target/arm/as3525/sansa-e200v2/lcd-e200v2.c
diff options
context:
space:
mode:
Diffstat (limited to 'firmware/target/arm/as3525/sansa-e200v2/lcd-e200v2.c')
-rw-r--r--firmware/target/arm/as3525/sansa-e200v2/lcd-e200v2.c67
1 files changed, 37 insertions, 30 deletions
diff --git a/firmware/target/arm/as3525/sansa-e200v2/lcd-e200v2.c b/firmware/target/arm/as3525/sansa-e200v2/lcd-e200v2.c
index 517aa6a979..cc5275d29b 100644
--- a/firmware/target/arm/as3525/sansa-e200v2/lcd-e200v2.c
+++ b/firmware/target/arm/as3525/sansa-e200v2/lcd-e200v2.c
@@ -84,9 +84,16 @@ static volatile bool lcd_busy = false;
84#define R_HORIZ_RAM_ADDR_POS 0x44 84#define R_HORIZ_RAM_ADDR_POS 0x44
85#define R_VERT_RAM_ADDR_POS 0x45 85#define R_VERT_RAM_ADDR_POS 0x45
86 86
87#define R_ENTRY_MODE_HORZ 0x7030 87#define R_ENTRY_MODE_HORZ_NORMAL 0x7030
88#define R_ENTRY_MODE_HORZ_FLIPPED 0x7000
88#define R_ENTRY_MODE_VERT 0x7038 89#define R_ENTRY_MODE_VERT 0x7038
89#define R_ENTRY_MODE_SOLID_VERT 0x1038 90#define R_ENTRY_MODE_SOLID_VERT 0x1038
91static unsigned short r_entry_mode = R_ENTRY_MODE_HORZ_NORMAL;
92
93/* Reverse Flag */
94#define R_DISP_CONTROL_NORMAL 0x0004
95#define R_DISP_CONTROL_REV 0x0000
96static unsigned short r_disp_control_rev = R_DISP_CONTROL_NORMAL;
90 97
91/* TODO: Implement this function */ 98/* TODO: Implement this function */
92static void lcd_delay(int x) 99static void lcd_delay(int x)
@@ -160,32 +167,41 @@ void lcd_set_contrast(int val)
160 167
161void lcd_set_invert_display(bool yesno) 168void lcd_set_invert_display(bool yesno)
162{ 169{
163 (void)yesno; 170 r_disp_control_rev = yesno ? R_DISP_CONTROL_REV :
164} 171 R_DISP_CONTROL_NORMAL;
165 172
166static void flip_lcd(bool yesno) 173 if (display_on)
167{ 174 {
168 (void)yesno; 175 lcd_write_reg(R_DISP_CONTROL1, 0x0033 | r_disp_control_rev);
169} 176 }
170 177
178}
171 179
172/* turn the display upside down (call lcd_update() afterwards) */ 180/* turn the display upside down (call lcd_update() afterwards) */
173void lcd_set_flip(bool yesno) 181void lcd_set_flip(bool yesno)
174{ 182{
175 display_flipped = yesno; 183 display_flipped = yesno;
176 y_offset = yesno ? 4 : 0; /* FIXME: Is a y_offset needed? */ 184
177 185 r_entry_mode = yesno ? R_ENTRY_MODE_HORZ_FLIPPED :
178 if (display_on) 186 R_ENTRY_MODE_HORZ_NORMAL;
179 flip_lcd(yesno);
180} 187}
181 188
182static void lcd_window(int xmin, int ymin, int xmax, int ymax) 189static void lcd_window(int xmin, int ymin, int xmax, int ymax)
183{ 190{
184 ymin += y_offset; 191 ymin += y_offset;
185 ymax += y_offset; 192 ymax += y_offset;
186 lcd_write_reg(R_HORIZ_RAM_ADDR_POS, (xmax << 8) | xmin); 193 if (!display_flipped)
187 lcd_write_reg(R_VERT_RAM_ADDR_POS, (ymax << 8) | ymin); 194 {
188 lcd_write_reg(R_RAM_ADDR_SET, (ymin << 8) | xmin); 195 lcd_write_reg(R_HORIZ_RAM_ADDR_POS, (xmax << 8) | xmin);
196 lcd_write_reg(R_VERT_RAM_ADDR_POS, (ymax << 8) | ymin);
197 lcd_write_reg(R_RAM_ADDR_SET, (ymin << 8) | xmin);
198 }
199 else
200 {
201 lcd_write_reg(R_HORIZ_RAM_ADDR_POS, ((LCD_WIDTH-1 - xmin) << 8) | (LCD_WIDTH-1 - xmax));
202 lcd_write_reg(R_VERT_RAM_ADDR_POS, ((LCD_HEIGHT-1 - ymin) << 8) | (LCD_HEIGHT-1 - ymax));
203 lcd_write_reg(R_RAM_ADDR_SET, ((LCD_HEIGHT-1 - ymin) << 8) | (LCD_WIDTH-1 - xmin));
204 }
189} 205}
190 206
191static void _display_on(void) 207static void _display_on(void)
@@ -205,13 +221,13 @@ static void _display_on(void)
205 /* Address counter updated in horizontal direction; left to right; 221 /* Address counter updated in horizontal direction; left to right;
206 * vertical increment horizontal increment. 222 * vertical increment horizontal increment.
207 * data format for 8bit transfer or spi = 65k (5,6,5) */ 223 * data format for 8bit transfer or spi = 65k (5,6,5) */
208 lcd_write_reg(R_ENTRY_MODE, 0x0030); 224 lcd_write_reg(R_ENTRY_MODE, r_entry_mode);
209 225
210 /* Replace data on writing to GRAM */ 226 /* Replace data on writing to GRAM */
211 lcd_write_reg(R_COMPARE_REG1, 0); 227 lcd_write_reg(R_COMPARE_REG1, 0);
212 lcd_write_reg(R_COMPARE_REG2, 0); 228 lcd_write_reg(R_COMPARE_REG2, 0);
213 229
214 lcd_write_reg(R_DISP_CONTROL1, 0x0000); /* GON = 0, DTE = 0, D1-0 = 00b */ 230 lcd_write_reg(R_DISP_CONTROL1, 0x0000 | r_disp_control_rev); /* GON = 0, DTE = 0, D1-0 = 00b */
215 231
216 /* Front porch lines: 2; Back porch lines: 2; */ 232 /* Front porch lines: 2; Back porch lines: 2; */
217 lcd_write_reg(R_DISP_CONTROL2, 0x0203); 233 lcd_write_reg(R_DISP_CONTROL2, 0x0203);
@@ -285,7 +301,7 @@ static void _display_on(void)
285 lcd_write_reg(R_1ST_SCR_DRV_POS, (LCD_HEIGHT-1) << 8); 301 lcd_write_reg(R_1ST_SCR_DRV_POS, (LCD_HEIGHT-1) << 8);
286 lcd_write_reg(R_2ND_SCR_DRV_POS, (LCD_HEIGHT-1) << 8); 302 lcd_write_reg(R_2ND_SCR_DRV_POS, (LCD_HEIGHT-1) << 8);
287 303
288 lcd_write_reg(R_DISP_CONTROL1, 0x0037); 304 lcd_write_reg(R_DISP_CONTROL1, 0x0033 | r_disp_control_rev);
289 305
290 display_on=true; /* must be done before calling lcd_update() */ 306 display_on=true; /* must be done before calling lcd_update() */
291 lcd_update(); 307 lcd_update();
@@ -301,17 +317,8 @@ void lcd_init_device(void)
301 GPIOA_DIR |= (1<<5); 317 GPIOA_DIR |= (1<<5);
302 GPIOA_PIN(5) = 0; 318 GPIOA_PIN(5) = 0;
303 319
304 GPIOA_PIN(3) = (1<<3);
305
306 GPIOA_DIR |= (3<<3);
307
308 GPIOA_PIN(3) = (1<<3);
309
310 GPIOA_PIN(4) = 0; /*c80b0040 := 0;*/ 320 GPIOA_PIN(4) = 0; /*c80b0040 := 0;*/
311 321
312 GPIOA_DIR |= (1<<7);
313 GPIOA_PIN(7) = 0;
314
315 lcd_delay(1); 322 lcd_delay(1);
316 323
317 GPIOA_PIN(5) = (1<<5); 324 GPIOA_PIN(5) = (1<<5);
@@ -333,8 +340,8 @@ void lcd_enable(bool on)
333 } 340 }
334 else 341 else
335 { 342 {
336 /* TODO: Implement off sequence */
337 display_on=false; 343 display_on=false;
344 lcd_write_reg(R_POWER_CONTROL1, 0x0001);
338 } 345 }
339 } 346 }
340} 347}
@@ -375,7 +382,7 @@ void lcd_update(void)
375 if (!display_on) 382 if (!display_on)
376 return; 383 return;
377 384
378 lcd_write_reg(R_ENTRY_MODE, R_ENTRY_MODE_HORZ); 385 lcd_write_reg(R_ENTRY_MODE, r_entry_mode);
379 386
380 lcd_busy = true; 387 lcd_busy = true;
381 /* Set start position and window */ 388 /* Set start position and window */
@@ -417,7 +424,7 @@ void lcd_update_rect(int x, int y, int width, int height)
417 if (y >= ymax) 424 if (y >= ymax)
418 return; /* nothing left to do */ 425 return; /* nothing left to do */
419 426
420 lcd_write_reg(R_ENTRY_MODE, R_ENTRY_MODE_HORZ); 427 lcd_write_reg(R_ENTRY_MODE, r_entry_mode);
421 lcd_busy = true; 428 lcd_busy = true;
422 lcd_window(x, y, xmax, ymax); 429 lcd_window(x, y, xmax, ymax);
423 lcd_write_cmd(R_WRITE_DATA_2_GRAM); 430 lcd_write_cmd(R_WRITE_DATA_2_GRAM);
@@ -442,7 +449,7 @@ bool lcd_button_support(void)
442 if (lcd_busy) 449 if (lcd_busy)
443 return false; 450 return false;
444 451
445 lcd_write_reg(R_ENTRY_MODE, R_ENTRY_MODE_HORZ); 452 lcd_write_reg(R_ENTRY_MODE, r_entry_mode);
446 /* Set start position and window */ 453 /* Set start position and window */
447 lcd_window(LCD_WIDTH+1, LCD_HEIGHT+1, LCD_WIDTH+2, LCD_HEIGHT+2); 454 lcd_window(LCD_WIDTH+1, LCD_HEIGHT+1, LCD_WIDTH+2, LCD_HEIGHT+2);
448 455