|
|
View previous topic :: View next topic |
Author |
Message |
Bollo
Joined: 01 Dec 2010 Posts: 25
|
[SOLVED] Working GLCD S1D13700 driver? |
Posted: Fri Sep 02, 2011 5:55 pm |
|
|
Hi. I have a Powertip PG320240WRF-HE9 which has a S1D13700 controller. I'm using a PIC18F46K20. I have searched the forums here and found a driver modifed by Eduardo Guilherme Brandt in 2006. I looked through it best I can and everything looks like it should be working however for all but one instance it has not. There was one time I managed to get 3/4 of the display filled will 'G'. The last 1/4 was garbled. Sadly I could not repeat the freak occurance. Most of the time the display is garbled. What this does suggest is that my connections are correct (I have also checked them throughly with a scope the signals are reaching the S1D13700) as I can't see how I could have transmitted a 'G' character without them being ok. I suspect a timing issue.
If any one has any experience with this controller I would very much like to hear from you
Here is a link to some other compiler libraries for this specific display. However they seem pretty alien to me.
http://www.cafelogic.com/download/s1d13700-library-schematic-and-example-code/
Many thanks.
Last edited by Bollo on Sat Sep 03, 2011 9:03 am; edited 1 time in total |
|
|
temtronic
Joined: 01 Jul 2010 Posts: 9221 Location: Greensville,Ontario
|
|
Posted: Sat Sep 03, 2011 5:02 am |
|
|
The quick and esay way would be to download the C18 version of the software and program your PIC with the hex file. That will confirm your PIC, wiring and LCD is OK.
You'll have to rewire to be compatible with the program's pin usage though.
Once you see that 'it works', it's not that hard to convert C18 code into CCS C code. Just take one function or section, convert, save and go to the next one. Be sure to save in 'sequential' files so you can go back to a previous working version. |
|
|
Bollo
Joined: 01 Dec 2010 Posts: 25
|
|
Posted: Sat Sep 03, 2011 8:59 am |
|
|
I discovered that the CCS driver structure was actually mostly correct. I took the system settings from the C18 driver and came up with a working driver.
Code: | /////////////////////////////////////////////////////////////////////////
//// S1D13700.c ////
//// ////
//// Example drivers for the S1D13700 LCD controller on a Powertip ////
//// PG320240WRF-HE9 320×240 Graphic LCD. Modified by JAW (bollo) ////
//// using the CCS SED1335 driver as a base and system settings ////
//// from Radoslaw Kwiecien's C18 driver ////
/////////////////////////////////////////////////////////////////////////
//// ////
//// glcd_init(mode) ////
//// * Must be called before any other function. ////
//// - mode can be ON or OFF to turn the LCD on or off ////
//// ////
//// glcd_pixel(x,y,color) ////
//// * Sets the pixel to the given color. ////
//// - color can be ON or OFF ////
//// ////
//// glcd_fillScreen(color) ////
//// * Fills the entire LCD with the given color. ////
//// - color can be ON or OFF ////
//// ////
/////////////////////////////////////////////////////////////////////////
//// (C) Copyright 1996,2003 Custom Computer Services ////
//// This source code may only be used by licensed users of the CCS ////
//// C compiler. This source code may only be distributed to other ////
//// licensed users of the CCS C compiler. No other use, ////
//// reproduction or distribution is permitted without written ////
//// permission. Derivative programs created using this software ////
//// in object code form are not restricted in any way. ////
/////////////////////////////////////////////////////////////////////////
/////////////////////////////////////////////////////////////////////////
#ifndef GLCD_WIDTH
#define GLCD_WIDTH 320
#endif
#ifndef GLCD_HEIGHT
#define GLCD_HEIGHT 240
#endif
#ifndef GLCD_CHAR_WIDTH
#define GLCD_CHAR_WIDTH 8
#endif
#ifndef GLCD_CHAR_HEIGHT
#define GLCD_CHAR_HEIGHT 8
#endif
#ifndef GLCD_RST
#define GLCD_RST PIN_C3
#endif
#ifndef GLCD_RD
#define GLCD_RD PIN_B5
#endif
#ifndef GLCD_WR
#define GLCD_WR PIN_B1
#endif
#ifndef GLCD_CS
#define GLCD_CS PIN_B2
#endif
#ifndef GLCD_A0
#define GLCD_A0 PIN_B4
#endif
#ifndef ON
#define ON 1
#endif
#ifndef OFF
#define OFF 0
#endif
/////////////////////////////////////////////////////////////////////////
/////////////////////////////////////////////////////////////////////////
// The following defines setup the memory used by different regions
// Currenty one text area is defined at the beginning of memory
// and a graphics area follows immediately after
/////////////////////////////////////////////////////////////////////////
#define GLCD_TEXT_ADDR 0x0000
#define GLCD_GRAPHICS_ADDR GLCD_WIDTH * GLCD_HEIGHT / 64
#define GLCD_GRAPHICS_ADDR_END GLCD_GRAPHICS_ADDR + (GLCD_WIDTH * GLCD_HEIGHT / 8)
/////////////////////////////////////////////////////////////////////////
/////////////////////////////////////////////////////////////////////////
#if GLCD_CHAR_WIDTH < 9
#define GLCD_CR (GLCD_WIDTH/8 - 1)
#else
#define GLCD_CR (GLCD_WIDTH/4 - 2)
#endif
/////////////////////////////////////////////////////////////////////////
/////////////////////////////////////////////////////////////////////////
#define TGLCD_COMMAND output_high(GLCD_A0);
#define TGLCD_DATA output_low(GLCD_A0);
/////////////////////////////////////////////////////////////////////////
/////////////////////////////////////////////////////////////////////////
int8 glcd_readByte();
void glcd_sendByte(int8 data);
void glcd_fillScreen(int1 color);
void glcd_fillScreenText(char c);
void setCursorAddress(int16 addr);
void glcd_pixel(int16 x, int16 y, int1 color);
int8 getData(int16 addr);
void glcd_sendCMD(int8 cmd);
/////////////////////////////////////////////////////////////////////////
/////////////////////////////////////////////////////////////////////////
void glcd_systemSetup();
void glcd_scrollSetup();
void glcd_overlaySetup();
void glcd_power(int1 mode);
void glcd_cursorDirection(int8 dir);
void glcd_cursorForm(int8 width, int8 height);
void setData(int16 addr, int8 data);
/////////////////////////////////////////////////////////////////////////
#define GLCD_CMD_SYSTEM 0x40 // General system settings
#define GLCD_CMD_SLEEP 0x53 // Enter into standy mode
#define GLCD_CMD_DISP_OFF 0x58 // Turn the display off
#define GLCD_CMD_DISP_ON 0x59 // Turn the display on
#define GLCD_CMD_SCROLL 0x44 // Setup text and graphics address regions
#define GLCD_CMD_CSR_FORM 0x5D // Set cursor size
#define GLCD_CMD_CSRDIR_RIGHT 0x4C // Cursor moves right after write to display memory
#define GLCD_CMD_CSRDIR_LEFT 0x4D // Cursor moves left after write to display memory
#define GLCD_CMD_CSRDIR_UP 0x4E // Cursor moves up after write to display memory
#define GLCD_CMD_CSRDIR_DN 0x4F // Cursor moves down after write to display memory
#define GLCD_CMD_CGRAM_ADDR 0x5C // Configure character generator RAM address
#define GLCD_CMD_HDOT_SCR 0x5A // Set horizontal scroll rate
#define GLCD_CMD_OVERLAY 0x5B // Configure how layers overlay
#define GLCD_CMD_SET_CSR_ADDR 0x46 // Set the cursor address
#define GLCD_CMD_GET_CSR_ADDR 0x47 // Read the cursor address
#define GLCD_CMD_DISPLAY_WRITE 0x42 // Write to display memory
#define GLCD_CMD_DISPLAY_READ 0x43 // Read from display memory
#define SED1335_SCR_WIDTH 319
#define SED1335_M0 0
#define SED1335_M1 0
#define SED1335_M2 0
#define SED1335_WS 0
#define SED1335_IV 1
#define SED1335_FX 7
#define SED1335_FY 7
#define SED1335_WF 1
#define SED1335_CR 39
#define SED1335_TCR 90
#define SED1335_LF 239
#define SED1335_APL 40
#define SED1335_APH 0
#define SED1335_LINES 30
#define SED1335_SAD1L 0
#define SED1335_SAD1H 0
#define SED1335_SL1 0xEF
#define SED1335_SAD2L 0xB0
#define SED1335_SAD2H 0x04
#define SED1335_SL2 0xEF
#define SED1335_SAD3L 0
#define SED1335_SAD3H 0
#define SED1335_SAD4L 0
#define SED1335_SAD4H 0
#define SED1335_CRX 0x04
#define SED1335_CRY 0x07
#define SED1335_CM 0
#define SED1335_MX0 1
#define SED1335_MX1 0
#define SED1335_DM1 0
#define SED1335_DM2 0
#define SED1335_OV 0
#define SED1335_SAGL 0
#define SED1335_SAGH 0x70
#define SED1335_SCRD 0
#define SED1335_FLASH 0x16
#define SED1335_TEXTSIZE ((SED1335_SAD2H << 8) + SED1335_SAD2L)
#define SED1335_GRAPHICSTART ((SED1335_SAD2H << 8) + SED1335_SAD2L)
#define SED1335_GRAPHICSIZE ((SED1335_SL2+1) * (SED1335_SCR_WIDTH+1))>>3
#define SED1335_MEM_END 10800
#define SED1335_SYS_P1 0x10 | (SED1335_IV << 5) | (SED1335_WS << 3) | (SED1335_M2 << 2) | (SED1335_M1 << 1) | SED1335_M0
#define SED1335_SYS_P2 0x00 | (SED1335_WF << 7) | SED1335_FX
#define SED1335_CSRF_P2 0x00 | (SED1335_CM << 7) | SED1335_CRY
#define SED1335_OVLAY_P1 0x00 | (SED1335_OV << 4) | (SED1335_DM2 << 3) | (SED1335_DM1 << 2) | (SED1335_MX1 << 1) | SED1335_MX0
// Purpose: Initialize the controller
// Inputs: The initialization mode
// OFF - Turns the LCD off
// ON - Turns the LCD on
void glcd_init(int1 mode)
{
// Initialze some pins
output_low(GLCD_RST);
output_high(GLCD_CS);
output_high(GLCD_RD);
output_high(GLCD_WR);
output_high(GLCD_A0);
delay_ms(3);
output_high(GLCD_RST);
delay_ms(10);
glcd_systemSetup();
glcd_scrollSetup();
glcd_overlaySetup();
glcd_power(OFF);
glcd_cursorForm(4, 6);
glcd_fillScreen(OFF);
glcd_fillScreenText(' ');
glcd_power(mode);
glcd_cursorDirection(GLCD_CMD_CSRDIR_RIGHT);
}
// Purpose: Turn a pixel on a graphic LCD on or off
// Inputs: x - the x coordinate of the pixel
// y - the y coordinate of the pixel
// color - ON or OFF
void glcd_pixel(int16 x, int16 y, int1 color)
{
int8 data;
int16 addr;
// Calculate the byte address containing the pixel
addr = 1200 + (40 * y + x/8);
// Read the byte of data at the address
data = getData(addr);
// Turn the pixel on or off
if(color == ON)
bit_set(data, 7 - x%8);
else
bit_clear(data, 7 - x%8);
// Write the new data byte to display memory
setData(addr, data);
}
// Purpose: Initialize the display environment
void glcd_systemSetup()
{
glcd_sendCMD(GLCD_CMD_SYSTEM); // Setup the system
delay_us(500);
TGLCD_DATA // Set for data
glcd_sendByte(SED1335_SYS_P1); // No offset
glcd_sendByte(SED1335_SYS_P2); // Set character width
glcd_sendByte(SED1335_FY); // Set character height
glcd_sendByte(SED1335_CR); // Display line address range
glcd_sendByte(SED1335_TCR); // TC/R changed from 47
glcd_sendByte(SED1335_LF); // Number of lines per frame
glcd_sendByte(SED1335_APL); // Horizontal address range LSB (APL)
glcd_sendByte(SED1335_APH); // Horizontal address range MSB (APH)
}
// Purpose: Set the scroll start address and
// the size of a scroll block
void glcd_scrollSetup()
{
// Currently setup for a text and graphics layer
glcd_sendCMD(GLCD_CMD_SCROLL); // Setup scrolling
TGLCD_DATA // Set for data
glcd_sendByte(SED1335_SAD1L); // SAD1L
glcd_sendByte(SED1335_SAD1H); // SAD1H
glcd_sendByte(SED1335_SL1); // SL1
glcd_sendByte(SED1335_SAD2L); // SAD2L
glcd_sendByte(SED1335_SAD2H); // SAD2H
glcd_sendByte(SED1335_SL2); // SL2
glcd_sendByte(SED1335_SAD3L); // SAD3L
glcd_sendByte(SED1335_SAD3H); // SAD3H
glcd_sendByte(SED1335_SAD4L); // SAD4L
glcd_sendByte(SED1335_SAD4H); // SAD4H
glcd_sendCMD(GLCD_CMD_HDOT_SCR); // Horizontal scroll rate
TGLCD_DATA // Set for data
glcd_sendByte(SED1335_SCRD); // Horizontal pixel shift is 0
}
// Purpose: Setup the overlay functionality for combining
// layers of text and graphics, or multiple
// graphics layers
void glcd_overlaySetup()
{
// Currently setup for a single graphics layer
glcd_sendCMD(GLCD_CMD_OVERLAY); // Text / graphic overlay mode
TGLCD_DATA // Set for data
glcd_sendByte(SED1335_OVLAY_P1); // Area 1 text, others graphics
// Text XOR Graphics
}
// Purpose: Turn the display on or off
// Inputs: ON to turn on or OFF to turn off
void glcd_power(int1 mode)
{
if(mode == ON)
{
glcd_sendCMD(GLCD_CMD_DISP_ON); // Turn the display on
}
else
{
glcd_sendCMD(GLCD_CMD_DISP_OFF); // Turn the display off
}
TGLCD_DATA // Set for data
glcd_sendByte(SED1335_FLASH);
}
// Purpose: Set the direction the cursor moves after
// writing to dispaly memory
// Inputs: Use one of the following to set the direction:
// GLCD_CMD_CSRDIR_RIGHT
// GLCD_CMD_CSRDIR_LEFT
// GLCD_CMD_CSRDIR_UP
// GLCD_CMD_CSRDIR_DOWN
void glcd_cursorDirection(int8 dir)
{
glcd_sendCMD(dir);
}
// Purpose: Set the size of the cursor
// Inputs: 1) The width in pixels - 1 Valid numbers: (0 - 15)
// 2) The height in pixels - 1 Valid numbers: (1 - 15)
void glcd_cursorForm(int8 width, int8 height)
{
glcd_sendCMD(GLCD_CMD_CSR_FORM); // Cursor form and size
TGLCD_DATA // Set for data
glcd_sendByte(SED1335_CRX);
glcd_sendByte(SED1335_CSRF_P2);
}
// Purpose: Fill a graphics layer passed in color
// Works much faster than drawing a rectangle to fill the screen
// Inputs: ON - turn all the pixels on
// OFF - turn all the pixels off
void glcd_fillScreen(int1 color)
{
int16 i;
setCursorAddress(GLCD_GRAPHICS_ADDR);
glcd_sendCMD(GLCD_CMD_DISPLAY_WRITE);
TGLCD_DATA
for(i = GLCD_GRAPHICS_ADDR; i < GLCD_GRAPHICS_ADDR_END; ++i)
{
glcd_sendByte(0xFF * color);
}
}
// Purpose: Fill a text layer with a the passed in character
// Works much faster than drawing a rectangle to fill the screen
// Inputs: ON - turn all the pixels on
// OFF - turn all the pixels off
void glcd_fillScreenText(char c)
{
int16 i;
setCursorAddress(GLCD_TEXT_ADDR);
glcd_sendCMD(GLCD_CMD_DISPLAY_WRITE);
TGLCD_DATA
for(i = GLCD_TEXT_ADDR; i < GLCD_GRAPHICS_ADDR; ++i)
{
glcd_sendByte(c);
}
}
// Purpose: Write a byte of data
// Inputs: The byte of data to write
void glcd_sendByte(byte data)
{
set_tris_d(0x00);
output_d((data));
output_low(GLCD_WR);
output_low(GLCD_CS);
delay_cycles(1);
output_high(GLCD_WR);
output_high(GLCD_CS);
output_d(0);
}
// Purpose: Read a byte of data
// Outputs: The byte of data
int8 glcd_readByte()
{
byte data;
output_low(GLCD_CS);
output_low(GLCD_RD);
set_tris_d(0xFF);
delay_cycles(10);
data = input_d();
output_high(GLCD_CS);
output_high(GLCD_RD);
delay_cycles(10);
return data;
}
// Doesn't look right. Same as getData?
// Purpose: Get the status
// Outputs: The status in an 8 bit integer
/*int8 getStatus()
{
int8 status;
TGLCD_DATA
output_low(GLCD_CS);
output_low(GLCD_RD);
delay_us(1);
status = input_d();
output_high(GLCD_RD);
output_high(GLCD_CS);
return status;
}*/
// Purpose: Get the current address of the cursor
// Outputs: A 16 bit integer containing the cursor address
int16 getCursorAddress()
{
int16 addr;
glcd_sendCMD(GLCD_CMD_GET_CSR_ADDR);
TGLCD_COMMAND
*(int8*)(&addr ) = glcd_readByte(); // Read low part
*((int8*)&addr + 1) = glcd_readByte(); // Read high part
return addr;
}
// Purpose: Set the cursor address
// Inputs: A 16 bit integer containing the new cursor address
void setCursorAddress(int16 addr)
{
glcd_sendCMD(GLCD_CMD_SET_CSR_ADDR);
TGLCD_DATA
glcd_sendByte((unsigned int8)(addr & 0xFF));
glcd_sendByte((unsigned int8)(addr >> 8 ));
}
// Purpose: Get a byte of data from the display at the address
// Inputs: A 16 bit integer containing the address
// Outputs: An 8 bit integer with the read data
int8 getData(int16 addr)
{
setCursorAddress(addr);
glcd_sendCMD(GLCD_CMD_DISPLAY_READ);
TGLCD_COMMAND
return glcd_readByte();
}
// Purpose: Set a byte of display data at an address
// Inputs: 1) A 16 bit address
// 2) 8 bits worth
void setData(int16 addr, int8 data)
{
setCursorAddress(addr);
glcd_sendCMD(GLCD_CMD_DISPLAY_WRITE);
TGLCD_DATA
glcd_sendByte(data);
}
// Purpose: Send an 8 bit command
// Inputs: The command to send
void glcd_sendCMD(int8 cmd)
{
TGLCD_COMMAND
glcd_sendByte(cmd);
}
|
|
|
|
|
|
You cannot post new topics in this forum You cannot reply to topics in this forum You cannot edit your posts in this forum You cannot delete your posts in this forum You cannot vote in polls in this forum
|
Powered by phpBB © 2001, 2005 phpBB Group
|