20 晶联讯19264液晶屏字库,可以读取字母、字符和数字,但是汉字读取显示错误

发布于 2020-09-14 16:55:02

使用stm32f103-atk-nano BSP做的工程,修改为STM32F103RC。

使用裸机程序测试,功能正常,可以读写LCD液晶屏字库的字母、字符、数字和汉字。代码如下:

//---------------------------LCD端口定义--------------------------                         
#define LCD_SCK        PBout(15)    //对应液晶屏的接口“SCLK”(即:串行时钟输入)
#define LCD_SDA       PCout(6)    //对应液晶屏的接口“SDA”(即:串行数据输入)    
#define LCD_CS          PBout(12)    //对应液晶屏的接口“CS”(即:片选)    
#define LCD_RST       PBout(13)    //对应液晶屏的接口“RESET”(即:复位)    
#define LCD_RS           PBout(14)    //对应液晶屏的接口“RS”(即:指令/数据寄存器选择)

#define Rom_CS          PCout(7)      // 对应字库IC接口“Rom_CS”(也即:字库IC的CS#,片选)
#define Rom_SCK          PCout(8)      // 对应字库IC接口“Rom_SCK”(也即:字库IC的SCK,串行时钟)
#define Rom_OUT          PCin(9)      // 对应字库IC接口“Rom_OUT”(也即:字库IC的SO ,串行数据输出)
#define Rom_IN          PAout(8)      // 对应字库IC接口“Rom_IN”(也即:字库IC的SI,串行数据输入)

void initial_lcd(void)
{  
  GPIO_InitTypeDef  GPIO_InitStructure;
     RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOA|RCC_APB2Periph_GPIOB|RCC_APB2Periph_GPIOC, ENABLE);     //使能PA,B,C端口时钟 (ENABLE开启)
    
     GPIO_InitStructure.GPIO_Pin =GPIO_Pin_8; //PA       
    GPIO_InitStructure.GPIO_Mode = GPIO_Mode_Out_PP;    //推挽输出
    GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz;   //速度50MHz
     GPIO_Init(GPIOA, &GPIO_InitStructure); 

  GPIO_InitStructure.GPIO_Pin =GPIO_Pin_12|GPIO_Pin_13|GPIO_Pin_14|GPIO_Pin_15; //PB
    GPIO_InitStructure.GPIO_Mode = GPIO_Mode_Out_PP;      //推挽输出
     GPIO_Init(GPIOB, &GPIO_InitStructure);

  GPIO_InitStructure.GPIO_Pin =GPIO_Pin_6|GPIO_Pin_7|GPIO_Pin_8|GPIO_Pin_12;          //PC       
    GPIO_InitStructure.GPIO_Mode = GPIO_Mode_Out_PP;  //推挽输出
     GPIO_Init(GPIOC, &GPIO_InitStructure);   
    
    GPIO_InitStructure.GPIO_Pin =GPIO_Pin_9;      //PC
    GPIO_InitStructure.GPIO_Mode = GPIO_Mode_IPU;  //上拉输入
     GPIO_Init(GPIOC, &GPIO_InitStructure);
    
    LCD_LEDA=0;
    
    LCD_RST=0;
    delay_ms(50);
    LCD_RST=1;
    delay_ms(100);

    transfer_command(0xe2);     /*软复位*/
    delay_ms(5);
    transfer_command(0x2c);  /*升压步聚1*/
    delay_ms(5);    
    transfer_command(0x2e);  /*升压步聚2*/
    delay_ms(5);
    transfer_command(0x2f);  /*升压步聚3*/
    delay_ms(5);
    transfer_command(0x24);  /*粗调对比度,可设置范围0x20~0x27*/
    transfer_command(0x81);  /*微调对比度*/
    transfer_command(0x45);  /*0x1a,微调对比度的值,可设置范围0x00~0x3f*/
    transfer_command(0xeb);  /*1/9偏压比(bias)*/
    transfer_command(0xc2);  /*行扫描顺序:从上到下*/
    transfer_command(0xa0);  /*76帧/秒*/
    transfer_command(0xaf);  /*开显示*/
}

//***送指令到晶联讯字库IC**
void send_command_to_ROM( u8 datu )
{
    u8 i;
    for(i=0;i<8;i++ )
    {
        Rom_SCK=0;
        delay_us(1);
        if(datu&0x80)Rom_IN = 1;
        else Rom_IN = 0;
        datu = datu<<1;
        Rom_SCK=1;
        delay_us(1);
    }
}

//***从晶联讯字库IC中取汉字或字符数据(1个字节)**
static u8 get_data_from_ROM(void)
{
    
    u8 i;
    u8 ret_data=0;
    for(i=0;i<8;i++)
    {
        Rom_OUT=1;
        Rom_SCK=0;
        delay_us(1);
        ret_data=ret_data<<1;
        if( Rom_OUT )
            ret_data=ret_data+1;
        else
            ret_data=ret_data+0;
        Rom_SCK=1;
        delay_us(1);
    }
    return(ret_data);
}

移植到rtthread 中,代码如下:

/* defined the DIS_CS pin: PB12 */
#define DIS_CS_PIN    GET_PIN(B, 12)
/* defined the DIS_RST pin: PB13 */
#define DIS_RST_PIN    GET_PIN(B, 13)
/* defined the DIS_RS pin: PB14 */
#define DIS_RS_PIN    GET_PIN(B, 14)
/* defined the DIS_SCK pin: PB15 */
#define DIS_SCK_PIN    GET_PIN(B, 15)
/* defined the DIS_SDA pin: PC6 */
#define DIS_SDA_PIN    GET_PIN(C, 6)
/* defined the DIS_LEDA pin: PC12 */
#define DIS_LEDA_PIN    GET_PIN(C, 12)

#define dis_cs(x) ((x) ? (rt_pin_write(DIS_CS_PIN, PIN_HIGH)) : (rt_pin_write(DIS_CS_PIN, PIN_LOW)))
#define dis_rst(x) ((x) ? (rt_pin_write(DIS_RST_PIN, PIN_HIGH)) : (rt_pin_write(DIS_RST_PIN, PIN_LOW)))
#define dis_rs(x) ((x) ? (rt_pin_write(DIS_RS_PIN, PIN_HIGH)) : (rt_pin_write(DIS_RS_PIN, PIN_LOW)))
#define dis_sck(x) ((x) ? (rt_pin_write(DIS_SCK_PIN, PIN_HIGH)) : (rt_pin_write(DIS_SCK_PIN, PIN_LOW)))
#define dis_sda(x) ((x) ? (rt_pin_write(DIS_SDA_PIN, PIN_HIGH)) : (rt_pin_write(DIS_SDA_PIN, PIN_LOW)))
#define dis_leda(x) ((x) ? (rt_pin_write(DIS_LEDA_PIN, PIN_HIGH)) : (rt_pin_write(DIS_LEDA_PIN, PIN_LOW)))

/*字库 IC 接口定义 Rom_CS 就是字库 IC 的 CS#*/
/* defined the ROM_CS pin: PC7 */
#define ROM_CS_PIN    GET_PIN(C, 7)
/* defined the ROM_SCK pin: PC8 */
#define ROM_SCK_PIN    GET_PIN(C, 8)
/* defined the ROM_OUT pin: PC9 */
#define ROM_OUT_PIN    GET_PIN(C, 9)
/* defined the ROM_IN pin: PA8 */
#define ROM_IN_PIN    GET_PIN(A, 8)

#define rom_cs(x)     ((x) ? (rt_pin_write(ROM_CS_PIN, PIN_HIGH)) : (rt_pin_write(ROM_CS_PIN, PIN_LOW)))
#define rom_sck(x)    ((x) ? (rt_pin_write(ROM_SCK_PIN, PIN_HIGH)) : (rt_pin_write(ROM_SCK_PIN, PIN_LOW)))
#define rom_in(x)     ((x) ? (rt_pin_write(ROM_IN_PIN, PIN_HIGH)) : (rt_pin_write(ROM_IN_PIN, PIN_LOW)))
#define rom_out       (rt_pin_read(ROM_OUT_PIN))
#define Rom_OUT(x)    ((x) ? (rt_pin_write(ROM_OUT_PIN, PIN_HIGH)) : (rt_pin_write(ROM_OUT_PIN, PIN_LOW)))

//LCD 模块初始化
void initial_lcd()
{
        rt_pin_mode(DIS_CS_PIN, PIN_MODE_OUTPUT);
        rt_pin_mode(DIS_RST_PIN, PIN_MODE_OUTPUT);
        rt_pin_mode(DIS_RS_PIN, PIN_MODE_OUTPUT);
        rt_pin_mode(DIS_SCK_PIN, PIN_MODE_OUTPUT);
        rt_pin_mode(DIS_SDA_PIN, PIN_MODE_OUTPUT);
        rt_pin_mode(DIS_LEDA_PIN, PIN_MODE_OUTPUT);

        rt_pin_mode(ROM_CS_PIN, PIN_MODE_OUTPUT);
        rt_pin_mode(ROM_SCK_PIN, PIN_MODE_OUTPUT);
        rt_pin_mode(ROM_OUT_PIN, PIN_MODE_INPUT_PULLUP);
        rt_pin_mode(ROM_IN_PIN, PIN_MODE_OUTPUT);

        /* set DIS_LEDA pin mode to output */
    rt_pin_mode(DIS_LEDA_PIN, PIN_MODE_OUTPUT);
    
        /*DIS_LEDA test*/
        rt_pin_write(DIS_LEDA_PIN, PIN_LOW);
    
    dis_rst(0); //低电平复位
    rt_thread_mdelay(100);
    dis_rst(1); //复位完毕
    rt_thread_mdelay(100);
    transfer_command(0xe2); //软复位
    rt_thread_mdelay(500);
        transfer_command(0x2c);  /*升压步聚1*/
        rt_thread_mdelay(5);    
        transfer_command(0x2e);  /*升压步聚2*/
        rt_thread_mdelay(5);
        transfer_command(0x2f);  /*升压步聚3*/
//    transfer_command(0x2f); //打开内部升压
    rt_thread_mdelay(500);

    transfer_command(0x81); //微调对比度
    transfer_command(0x45); //微调对比度的值,可设置范围 0x00~0xFF
    transfer_command(0xeb); //1/9 偏压比(bias)
    transfer_command(0xc2); //行扫描顺序:从上到下 列扫描顺序:从右到左
    transfer_command(0xa0); //76帧/秒
    transfer_command(0xaf); //开显示
}

void dis_delay(uint time)
{
    uint t;
    for(t=0;t<time;t++)
    {
        __nop();
    }

}
//***送指令到晶联讯字库IC**
void send_command_to_ROM( uchar datu )
{
    uchar i;
    for(i=0;i<8;i++ )
    {
        rom_sck(0);
        dis_delay(1);
        if(datu&0x80) rom_in(1);
        else rom_in(0);
        datu = datu<<1;
        rom_sck(1);
        dis_delay(1);
    }
}

/***从晶联讯字库IC中取汉字或字符数据(1个字节)**/
static uchar get_data_from_ROM(void)
{

    uchar i;
    uchar ret_data=0;
    for(i=0;i<8;i++)
    {
        Rom_OUT(1);
        rom_sck(0);
        dis_delay(1);
        ret_data=ret_data<<1;
        if( rom_out )
            ret_data=ret_data+1;
        else
            ret_data=ret_data+0;
        rom_sck(1);
        dis_delay(1);
    }
    return(ret_data);
}

移植后问题,汉字不能正常读取显示,哪位大神有相关经验,望指正

查看更多

关注者
0
被浏览
169
还没想好
还没想好 2020-09-15
  1. 确保 rt_pin_write 能够正确拉高拉低电平
  2. 确保 rt_pin_write 函数执行时间满足需求,裸机中是直接操作寄存器,速度非常快,这里换成函数调用,速度要慢一些。
  3. 延时函数 dis_delay 延时的时间,是否正确
  4. 逻辑分析仪,抓一下时许。
  5. 不能被打断的程序,锁住调度器,防止线程切换。
static uchar get_data_from_ROM(void)
{

    for(i=0;i<8;i++)
    {
        Rom_OUT(1);
        rom_sck(0);
        dis_delay(1);
        ret_data=ret_data<<1;
        if( rom_out )
            ret_data=ret_data+1;
        else
            ret_data=ret_data+0;
        rom_sck(1);
        dis_delay(1);
    }
}

上面 5 点排查完。一定能成功。

2 个回答
sANT
sANT 2020-09-16

查找测试了两天,各种修改测试。最终发现是汉字被KEIL编译时编码出问题导致的。KEIL默认编码是UTF-8。我的设置是GB2312。
捕获.PNG
然后我修改为ANSI后编译,就正常了。
捕获.PNG
然后再修改为GB2312依然正常了。感觉这个是KEIL的BUG造成的。

撰写答案

请登录后再发布答案,点击登录

发布
问题

分享
好友

手机
浏览

扫码手机浏览