• 嵌入式LCD闪烁--emWin使用内存设备避免闪烁


    0、引子

    近日在论坛看到有人说屏幕闪烁,问道怎么解决。在嵌入式gui使用方面,屏幕闪烁一般多出现在多个窗口层叠、多图层层叠、更新图层时。受限于接口速度,即使屏幕有很高的刷新率,也做不到无闪烁,所以要从减少数据传送上下功夫,比如使用内存设备处理好数据再整体搬到LCD上,还有就是使用局部刷新较少刷新的数据量,同时还要注意图层顺序的问题。

    1、内存设备避免闪烁原理

    当在液晶屏上绘制一些文字叠加在图片上的效果时,通常是先在液晶屏上绘制底层的图片,然后再在图片上叠加上文字,多次刷新会出现闪烁。

    存储设备可在各种情况下使用,主要用于防止在绘制重叠项目时出现显示器闪烁。其基本思想很简单,不使用存储设备时,绘制操作直接写入显示器,屏幕在执行绘制操作时随时更新,从而在进行各种更新时使屏幕闪烁。例如,如果要在背景中绘制一个位图,在前景中绘制一些透明文本,应首先绘制位图,然后绘制文本。效果将是文本出现闪烁。但是,如果在此过程中使用存储设备,则所有绘制操作都在存储器中执行。仅在所有操作都完成后才将最终结果显示在屏幕上,实现一次性从内存到LCD绘制,其优点是没有闪烁。

    下图形象的解释了内存设备避免闪烁的原理。

    2、emWin使用内存设备

    emWin使用内存设备需要先打开配置:

    #define GUI_SUPPORT_MEMDEV  (1)  // Memory devices available

    测试例子:

    void MainTask(void) {
        GUI_Init();
        //
        // Check if recommended memory for the sample is available
        //
        if (GUI_ALLOC_GetNumFreeBytes() < RECOMMENDED_MEMORY) {
            GUI_ErrorOut("Not enough memory available.");
            return;
        }
    
        GUI_SetColor(GUI_LIGHTGRAY);
        GUI_RECT rect = { 0, 0, LCD_GetXSize(), 49 };
        GUI_FillRectEx(&rect);
        char title[] = "Draw direct And Use Memory device";
        GUI_SetFont(GUI_FONT_24_ASCII);
        GUI_SetColor(GUI_RED);
        GUI_SetTextMode(GUI_TEXTMODE_TRANS);
        GUI_DispStringInRect(title, &rect, GUI_TA_HCENTER | GUI_TA_VCENTER);
        GUI_DispStringAt("Direct Draw", 70, 200);
        GUI_DispStringAt("Use Memory", 300, 200);
    
        GUI_MEMDEV_Handle hMem = GUI_MEMDEV_Create(280, 50, 150, 150);
        int i = 0;
        while (1)
        {
            GUI_Delay(5);
            Draw(50, 50, 200, 200, i); // 直接在LCD绘制
            GUI_MEMDEV_Select(hMem); //选择内存设备
            Draw(280, 50, 430, 200, i); // 在内存中绘制
            GUI_MEMDEV_Select(0); // 恢复LCD设备
            GUI_MEMDEV_CopyToLCDAt(hMem, 280, 50);
            i++;
            if (i >= 1000) i = 0;
        }
    
      while(1);
    }
    
    
    void Draw(int x0, int y0, int x1, int y1, int i)
    {
        char buf[10] = { 0 };
        
        GUI_SetColor(GUI_BLUE);
        GUI_FillRect(x0, y0, x1, y1);
    
        GUI_SetFont(GUI_FONT_D64);
        GUI_SetTextMode(GUI_TEXTMODE_XOR);
        sprintf(buf, "%d", i);
        GUI_DispStringHCenterAt(buf, x0 + (x1 - x0) / 2, y0 + (y1 - y0) / 2 - 32);
    }

    3、测试效果

    测试截图如下:

    动态效果可以看到,左侧直接绘制有闪烁,尤其是百位数字即使没有更新时候也会闪烁一次。右侧是先在内存中绘制,然后从内存设备拷贝到界面上,只需要更新一次,没有闪烁。

    4、参考文献

    1、《emWin用户参考手册》

    2、野火《emWin应用开发实战指南》

  • 相关阅读:
    rgb随机颜色函数
    mapshaper转geojson
    postgis
    Draw
    ol 聚类ol.source.Cluster的使用
    ol ---- overlay autoPan的使用
    多层数据注入同一个图层源时,要批量删除某一种要素
    js遍历数组,并从数组中删除元素
    echarts加载geojson
    centos65编译安装lamp和lnmp
  • 原文地址:https://www.cnblogs.com/pingwen/p/12584076.html
Copyright © 2020-2023  润新知