📄 hal_lcd.c
字号:
_ltoa( err, &buf[tmpLen], format2 );
HalLcdWriteString( (char *)buf, line );
#endif /* HAL_LCD */
}
/**************************************************************************************************
* @fn HalLcdDisplayPercentBar
*
* @brief Display percentage bar on the LCD
*
* @param title -
* value -
*
* @return None
**************************************************************************************************/
void HalLcdDisplayPercentBar( char *title, uint8 value )
{
#if (HAL_LCD == TRUE)
uint8 percent;
uint8 leftOver;
uint8 buf[17];
uint32 err;
uint8 x;
/* Write the title: */
HalLcdWriteString( title, HAL_LCD_LINE_1 );
if ( value > 100 )
value = 100;
/* convert to blocks */
percent = (byte)(value / 10);
leftOver = (byte)(value % 10);
/* Make window */
osal_memcpy( buf, "[ ] ", 15 );
for ( x = 0; x < percent; x ++ )
{
buf[1+x] = '>';
}
if ( leftOver >= 5 )
buf[1+x] = '+';
err = (uint32)value;
_ltoa( err, (uint8*)&buf[13], 10 );
HalLcdWriteString( (char*)buf, HAL_LCD_LINE_2 );
#endif /* HAL_LCD */
}
#if (defined LCD_HW) && (HAL_LCD == TRUE)
/*********************************************************************
* @fn initLcd
* @brief Initializes LCD I/O bus and LCD device
* @param void
* @return void
*/
static void initLcd( void )
{
uint8 buffer[8];
// Initialize the serial I/O bus
initSmb();
// Load LCD initialization message
buffer[0] = LCD_ADDR;
buffer[1] = LCD_RS_0; // Instruction Register
buffer[2] = 0x0C; // Display control D = 1: Display On
// C = 0: Cursor Off
// B = 0: Cursor character blink off
buffer[3] = 0x21; // Function set H = 1: Use extended instruction set
buffer[4] = 0xA0; // Set DDRAM address ADD = 0x20
buffer[5] = 0x07; // Display configuration P = 1: Column data right to left
// Q = 1: Row data, bottom to top
buffer[6] = 0x34; // Function set DL= 0: 4 bits
// M = 1: 2-line by 16 display
// SL= 0: MUX1:18
// H = 0: Use basic instruction set
buffer[7] = 0x01; // Clearing display
// Send message to LCD device
smbSend( buffer, 8 );
}
/*********************************************************************
* @fn lcdUpdateLine
* @brief Updates one line of the LCD display
* @param line - LCD line numberptr to string going to LCD line 1
* @param p2 - ptr to string going to LCD line 2
* @return void
*/
static void lcdUpdateLine( uint8 line, uint8 *pLine )
{
uint8 i;
uint8 chr;
uint8 addr;
uint8 *buffer;
if ( line == HAL_LCD_LINE_1 )
addr = LCD_LINE1_ADDR;
else
addr = LCD_LINE2_ADDR;
// Get a buffer to work with
buffer = osal_mem_alloc( 2+HAL_LCD_MAX_CHARS );
if ( buffer != NULL )
{
// Build and send control string
buffer[0] = LCD_ADDR;
buffer[1] = LCD_RS_0;
buffer[2] = addr;
smbSend( buffer, 3 );
// Build and send message string
buffer[0] = LCD_ADDR;
buffer[1] = LCD_RS_1;
// Convert and save message bytes
for( i = 2; i < 2+HAL_LCD_MAX_CHARS; i++ )
{
chr = *pLine++;
if ( chr == '\0' )
{
chr = lcdConvertChar( ' ' );
break;
}
else
buffer[i] = lcdConvertChar( chr );
}
// Fill remainder of line with blanks
for( ; i < 2+HAL_LCD_MAX_CHARS; i++ )
buffer[i] = chr;
// Put it on the display
smbSend( buffer, 2+HAL_LCD_MAX_CHARS );
// Give back buffer memory
osal_mem_free( buffer );
}
}
/*********************************************************************
* @fn lcdConvertChar
* @brief Converts an ASCII character to an LCD character (R sheet)
* @param aChar - ASCII character
* @return lChar - LCD character
*/
static byte lcdConvertChar( byte aChar )
{
uint8 lChar;
if ((aChar >= 'a') && (aChar <= 'z'))
// Lower case
lChar = aChar + ('a' - 0xE1);
else if ((aChar >= 'A') && (aChar <= 'Z'))
// Upper case
lChar = aChar + ('A' - 0xC1);
else if (((aChar >= ' ') && (aChar <= '#')) ||
((aChar >= '%') && (aChar <= '?')))
// Sonme symbols
lChar = aChar + (' ' - 0xA0);
else
{
switch ( aChar )
{
case '$':
lChar = 0x82;
break;
case '?:
lChar = 0xDF;
break;
case '?:
lChar = 0x81;
break;
case '@':
lChar = 0x80;
break;
case '[':
lChar = 0x8A;
break;
case ']':
lChar = 0x54;
break;
case '_':
lChar = 0x5A;
break;
case '?:
lChar = 0x9D;
break;
case '?:
lChar = 0x8C;
break;
case '?:
lChar = 0x8F;
break;
case '?:
lChar = 0x9C;
break;
case '?:
lChar = 0x8B;
break;
case '?:
lChar = 0x8E;
break;
case 0x10:
lChar = 0x10; // Left arrow
break;
case 0x11:
lChar = 0x20; // Right arrow
break;
case 0x12:
lChar = 0x12; // Up arrow
break;
case 0x13:
lChar = 0x30; // Down arrow
break;
default:
lChar = 0x30;
break;
}
}
return ( lChar );
}
/*********************************************************************
* @fn initSmb
* @brief Initializes two-wire serial I/O bus
* @param void
* @return void
*/
static void initSmb( void )
{
// Set port pins as inputs
IO_DIR_PORT_PIN( LCD_CLK_PORT, LCD_CLK_PIN, IO_IN );
IO_DIR_PORT_PIN( LCD_DATA_PORT, LCD_DATA_PIN, IO_IN );
// Set for general I/O operation
IO_FUNC_PORT_PIN( LCD_CLK_PORT, LCD_CLK_PIN, IO_GIO );
IO_FUNC_PORT_PIN( LCD_DATA_PORT, LCD_DATA_PIN, IO_GIO );
// Set I/O mode for pull-up/pull-down
IO_IMODE_PORT_PIN( LCD_CLK_PORT, LCD_CLK_PIN, IO_PUD );
IO_IMODE_PORT_PIN( LCD_DATA_PORT, LCD_DATA_PIN, IO_PUD );
// Set pins to pull-up
IO_PUD_PORT( LCD_CLK_PORT, IO_PUP );
IO_PUD_PORT( LCD_DATA_PORT, IO_PUP );
}
/*********************************************************************
* @fn smbSend
* @brief Sends buffer contents to SM-Bus device
* @param buffer - ptr to buffered data to send
* @param len - number of bytes in buffer
* @return void
*/
static void smbSend( uint8 *buffer, uint8 len )
{
uint8 i;
smbStart();
for ( i = 0; i < len; i++ )
{
while ( !smbSendByte( buffer[i] ) ); // Send until ACK received
}
smbStop();
}
/*********************************************************************
* @fn smbSendByte
* @brief Serialize and send one byte to SM-Bus device
* @param dByte - data byte to send
* @return ACK status - 0=none, 1=received
*/
static bool smbSendByte( uint8 dByte )
{
uint8 i;
for ( i = 0; i < 8; i++ )
{
// Send the MSB
smbWrite( dByte & 0x80 );
// Next bit into MSB
dByte <<= 1;
}
smbClock( 0 );
LCD_DATA_HIGH();
smbClock( 1 );
return ( !LCD_SDA ); // Return ACK status
}
/*********************************************************************
* @fn smbWrite
* @brief Send one bit to SM-Bus device
* @param dBit - data bit to clock onto SM-Bus
* @return void
*/
static void smbWrite( bool dBit )
{
smbClock( 0 );
smbWait();
if ( dBit )
{
LCD_DATA_HIGH();
}
else
{
LCD_DATA_LOW();
}
smbClock( 1 );
smbWait();
}
/*********************************************************************
* @fn smbClock
* @brief Clocks the SM-Bus. If a negative edge is going out, the
* I/O pin is set as an output and driven low. If a positive
* edge is going out, the pin is set as an input and the pin
* pull-up drives the line high. This way, the slave device
* can hold the node low if longer setup time is desired.
* @param dir - clock line direction
* @return void
*/
static void smbClock( bool dir )
{
if ( dir )
{
IO_DIR_PORT_PIN( LCD_CLK_PORT, LCD_CLK_PIN, IO_IN );
}
else
{
IO_DIR_PORT_PIN( LCD_CLK_PORT, LCD_CLK_PIN, IO_OUT );
LCD_SCL = 0;
}
smbWait();
}
/*********************************************************************
* @fn smbStart
* @brief Initiates SM-Bus communication. Makes sure that both the
* clock and data lines of the SM-Bus are high. Then the data
* line is set high and clock line is set low to start I/O.
* @param void
* @return void
*/
static void smbStart( void )
{
// Wait for both clock and data line high
while ( !( LCD_SCL && LCD_SDA) );
LCD_DATA_LOW();
smbWait();
smbClock( 0 );
}
/*********************************************************************
* @fn smbStop
* @brief Terminates SM-Bus communication. Waits unitl the data line
* is low and the clock line is high. Then sets the data line
* high, keeping the clock line high to stop I/O.
* @param void
* @return void
*/
static void smbStop( void )
{
// Wait for clock high and data low
while ( !( LCD_SCL && !LCD_SDA) );
smbClock( 0 );
LCD_DATA_HIGH();
smbWait();
smbClock( 1 );
}
/*********************************************************************
* @fn smbWait
* @brief Wastes a fixed amount of some time.
* @param void
* @return void
*/
static void smbWait( void )
{
uint8 i = 0x01;
while ( i-- );
}
#endif // LCD_HW & HAL_LCD
/**************************************************************************************************
**************************************************************************************************/
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -