第四步,通过SPI通信,将指令或者数据传输到OLED屏幕中。OLED屏幕判断指令还是数据,是通过DC引脚的高低电平实现的。所以需要有一个参数去控制 43引脚的状态。代码如下:
数据先传输进Buffer,通过判断cmd 控制DC_Set/ DC_Clr
然后通过am_hal_iom_spi_write()函数,将数据直接传输到外设。
am_hal_iom_spi_write(uint32_t ui32Module, uint32_t ui32ChipSelect,
uint32_t *pui32Data, uint32_t ui32NumBytes,
uint32_t ui32Options)
{
am_hal_iom_status_e ui32Status;
//
// Validate parameters
//
if ( ui32Module >= AM_REG_IOMSTR_NUM_MODULES )
{
return AM_HAL_IOM_ERR_INVALID_MODULE;
}
// Reset the error status
ui32Status = g_iom_error_status[ui32Module] = AM_HAL_IOM_SUCCESS;
if (ui32NumBytes == 0)
{
g_iom_error_status[ui32Module] = ui32Status = AM_HAL_IOM_ERR_INVALID_PARAM;
return ui32Status;
}
//
// Check to see if queues have been enabled. If they are, we'll actually
// switch to the queued interface.
//
if ( g_psIOMQueue[ui32Module].pui8Data != NULL )
{
//
// If the queue is on, go ahead and add this transaction to the queue.
//
ui32Status = am_hal_iom_queue_spi_write(ui32Module, ui32ChipSelect, pui32Data,
ui32NumBytes, ui32Options, 0);
if (ui32Status == AM_HAL_IOM_SUCCESS)
{
//
// Wait until the transaction actually clears.
//
am_hal_iom_queue_flush(ui32Module);
// g_iom_error_status gets set in the isr handling
ui32Status = g_iom_error_status[ui32Module];
}
//
// At this point, we've completed the transaction, and we can return.
//
}
else
{
//
// Otherwise, we'll just do a polled transaction.
//
ui32Status = am_hal_iom_spi_write_nq(ui32Module, ui32ChipSelect, pui32Data,
ui32NumBytes, ui32Options);
}
return ui32Status;
}
该函数的几个参数定义分别如下:
(1)ui32Module – IOM的Master编号选择
(2)ui32ChipSelect – 外设编号选择
(3)pui32Data – 传输的数据
(4)ui32NumBytes –传输数据的大小
(5)ui32Options – 寄存器偏移量
这里可以根据实际情况去配置各个参数,从而达到传输数据的目的。至此,硬件SPI模式基本配置完成。
5.模拟SPI配置
模拟SPI基本与硬件SPI类似。使用任意两个IO口模拟通信,不需要使用指定的SPI接口,也不需要响应的SPI配置。
第一步,IO口的配置大概如下:
四个引脚如下:SCL – 8脚; SDA – 9脚;RES – 42脚;DC – 43脚 同样需要配置各个IO口的状态:
模拟SPI与硬件SPI的最主要区别是在写函数里面。使用一个引脚模拟时钟,另外一个引脚发送数据。
第二步,发送函数:
判断cmd的操作是必不可少的,接着判断(dat & 0x80) 判断高位是否为‘1’。dat 高位为‘1’,MOSI就输出‘1’;否则输出‘0’。然后移位,次高位变为最高位。就是把dat的数据从MOSI脚输出。
6.了解OLED屏幕
有机发光显示OLED(OrganicLight?EmittingDisplay)是比液晶显示技术更为先进的新一代平板显示技术,是被业界公认为最具发展前景的下一代显示技术。
OLED12864是128*64行点阵的OLED单色,字符,图形显示模块,模块内有64*64的显示数据RAM,其中的每位数据对应于OLED屏上的每一个点的亮,暗状态。
12864OLED的像素矩阵的划分是比较特殊的。 整个屏幕水平方向划分为8个page, 垂直方向则是按像素划分为128 column. 每个page-column包含8个像素, 通过一个十六进制数(其实就是一个字节, 8个bit)来控制, 每个bit控制一个像素。
(图8-1)OLED屏幕像素矩阵
(图8-2)OLED屏幕像素矩阵
7.OLED屏幕配置
与大部分12864 OLED屏幕一样,需要提前给屏幕输入特定的显示指令。代码如家,需要注意的是硬件SPI与模拟SPI选择自己响应的OLED_WR_Byte()即可。配置过程如下:
OLED_WR_Byte(0xAE,OLED_CMD);//--turn off oled panel
OLED_WR_Byte(0x00,OLED_CMD);//---set low column address
OLED_WR_Byte(0x10,OLED_CMD);//---set high column address
OLED_WR_Byte(0x40,OLED_CMD);//--set start line address Set Mapping RAM Display Start Line (0x00~0x3F)
OLED_WR_Byte(0x81,OLED_CMD);//--set contrast control register
OLED_WR_Byte(0xCF,OLED_CMD); // Set SEG Output Current Brightness
OLED_WR_Byte(0xA1,OLED_CMD);//--Set SEG/Column Mapping 0xa0×ó??·??? 0xa1????
OLED_WR_Byte(0xC8,OLED_CMD);//Set COM/Row Scan Direction 0xc0????·??? 0xc8????
OLED_WR_Byte(0xA6,OLED_CMD);//--set normal display
OLED_WR_Byte(0xA8,OLED_CMD);//--set multiplex ratio(1 to 64)
OLED_WR_Byte(0x3f,OLED_CMD);//--1/64 duty
OLED_WR_Byte(0xD3,OLED_CMD);//-set display offset
Shift Mapping RAM Counter (0x00~0x3F)
OLED_WR_Byte(0x00,OLED_CMD);//-not offset
OLED_WR_Byte(0xd5,OLED_CMD);//--set display clock divide ratio/oscillator frequency
OLED_WR_Byte(0x80,OLED_CMD);//--set divide ratio, Set Clock as 100 Frames/Sec
OLED_WR_Byte(0xD9,OLED_CMD);//--set pre-charge period
OLED_WR_Byte(0xF1,OLED_CMD);//Set Pre-Charge as 15 Clocks & Discharge as 1 Clock
OLED_WR_Byte(0xDA,OLED_CMD);//--set com pins hardware configuration
OLED_WR_Byte(0x12,OLED_CMD);
OLED_WR_Byte(0xDB,OLED_CMD);//--set vcomh
OLED_WR_Byte(0x40,OLED_CMD);//Set VCOM Deselect Level
OLED_WR_Byte(0x20,OLED_CMD);//-Set Page Addressing Mode (0x00/0x01/0x02)
OLED_WR_Byte(0x02,OLED_CMD);//
OLED_WR_Byte(0x8D,OLED_CMD);//--set Charge Pump enable/disable
OLED_WR_Byte(0x14,OLED_CMD);//--set(0x10) disable
OLED_WR_Byte(0xA4,OLED_CMD);// Disable Entire Display On (0xa4/0xa5)
OLED_WR_Byte(0xA6,OLED_CMD);// Disable Inverse Display On (0xa6/a7)
OLED_WR_Byte(0xAF,OLED_CMD);//--turn on oled panel
OLED_WR_Byte(0xAF,OLED_CMD); /*display ON*/
OLED_Clear();
OLED_Set_Pos(0,0);
将上述代码发送给OLED屏幕之后,屏幕的初始化也基本完成。
8.OLED屏幕文字显示
下面是使用OLED显示中文汉字的范例。代码如下
OLED_Set_Pos()函数是用来定位文字在屏幕上显示的位置。文字的大小是16*16个像素点,所以for()循环里面的t为16次。Hzk[ ][ ]数组里面存储的是通过取模软件,将文字转换成16进制的数据。
取模工具选用PCtolCD2002 完美版本,这里选择字符模式。输入文字的时候,可以点击生成字模,在下方就会显示出各个文字相对应的16进制数组。
(图9)文字取模
将各个数组分别添加到Hzk数组里面之后,就可以在主函数里面通过OLED_ShowCHinese()进行显示。