GEC6818:颜色显示
LCD屏幕结构分析
GEC6818开发平台的显示设备选用7.0英寸(高:480,宽:800)的32位真彩色(必须是由RGB三原色构成
其组成部分:被光模块、偏光片、彩色滤光片等,其显示方式是将设备收到的数据转换为像素点进行显示,每个像素点默认是4个字节(32位)这样的二进制。
显示原理
1.RGB三原色每种颜色的取值范围0~255,共有256个不同的值,也就是每种颜色对应1个字节(8位),RGB共3个字节(24位)。为了对齐4个字节(屏幕每个像素点是4个字节),解决方案是增加灰度(无本质影响,只是为了占个位置,保证颜色值能与像素点对其)A,颜色就变为了ARGB.
2.Linux下一切皆文件,也就是LCD屏幕也是文件(所有的设备都会被内核映射成设备文件),在GEC6818开发平台上,工程师将LCD屏幕设备定义为 fb,LCD设备文件位于`/dev下,操作LCD屏幕时,只需操作该设备文件即可。因此想要在GEC6818屏幕上显示颜色只需要将每个像素点的颜色数据写入到LCD设备文件即可。LCD液晶屏对应的文件路径:/dev/fba。
颜色加载过程
1.打开LCD设备文件(/dev/fb0)
2.准备显示的颜色数据(存入缓冲区)
3.将颜色数据写入到LCD屏幕设备文件(文件写入(/dev/fb0))
4.关闭LCD设备文件
案例:绘制纯色
#include <stdio.h>
#include <sys/types.h>
#include <sys/stat.h>
#include <fcntl.h>
#include <unistd.h>
int main(int argc,char *argv[])
{
int lcd = open("/dev/fb0",O_RDWR);
if(lcd == -1){
perror("打开错误");
return -1;
}
int buf[800*400];
for(int i=0;i<800*400;i++){
buf[i]=0x0001aef0;
}
int ret = write(lcd,buf,800*400*4);
if(ret ==-1){
perror("写入错误");
return -1;
}
close(lcd);
return 0;
}
绘制荷兰国旗
第0步:引入头文件
第一步:打开/dev/fb0(打开方式:O_RDWR),open();
第二步:定义缓冲区:int buf[800*400];
顶部:
x:0-800含头不含尾
y:0-160
颜色值:0x00ae1c29
中部:
x:0-800含头不含尾
y:0-320
颜色值:0x00ffffff(白)
底部:
x:0-800
y:320-480
颜色:0x0021458b;
第三步:将缓冲区的颜色数据写入fb0(LCD屏幕设备文件),write(lcd,buf,800*480*4);
第四部:关闭fb0,close(lcd);
代码:
#include <stdio.h>
#include <sys/stat.h>
#include <sys/types.h>
#include <fcntl.h>
#include <unistd.h>
int main(int argc,char *argv[])
{
int lcd = open("/dev/fb0",O_RDWR);
if(lcd==-1){
perror("打开失败");
return -1;
}
int i;
int buf[800*480];
for(i=0;i<800*180;i++){
buf[i]=0x00ae1c29;
}
for(;i<800*320;i++){
buf[i]=0x00ffffff;
}
for(;i<800*480;i++){
buf[i]=0x0021458b;
}
int rec = write(lcd,buf,800*480*4);
if(rec==-1){
perror("写入失败");
return -1;
}
close(lcd);
return 0;
}
绘制法国国旗:
第0步:引入头文件
第一步:打开/dev/fb0(打开方式:O_RDWR),open();
第二步:定义缓冲区:int buf[800*400];
左:
x:0-266 含头不含尾
y:0-480
颜色:0x0000254
中:
x:266-532 含头不含尾
y:0-480
颜色:0x00ffffff
右:
x:532-800 含头不含尾
y:0-480
颜色:0x000cd1125
第三步:将缓冲区的颜色数据写入fb0(LCD屏幕设备文件),write(lcd,buf,800*480*4);
第四部:关闭fb0,close(lcd);
代码:
练习:
七色彩虹(横向)
#include <stdio.h>
#include <sys/stat.h>
#include <sys/types.h>
#include <fcntl.h>
#include <unistd.h>
int main(int argc,char *argv[])
{
int lcd = open("/dev/fb0",O_RDWR);
if(lcd==-1){
perror("打开失败");
return -1;
}
int i;
int buf[800*480];
for(i=0;i<800*70;i++){
buf[i]=0x00ae1c29;
}
for(;i<800*140;i++){
buf[i]=0x00ffffff;
}
for(;i<800*210;i++){
buf[i]=0x0021458b;
}
for(;i<800*280;i++){
buf[i]=0x00020012;
}
for(;i<800*350;i++){
buf[i]=0x00fce94f;
}
for(;i<800*420;i++){
buf[i]=0x0c42b1c;
}
for(;i<800*480;i++){
buf[i]=0x006c2236;
}
int rec = write(lcd,buf,800*480*4);
if(rec==-1){
perror("写入失败");
return -1;
}
close(lcd);
return 0;
}
七色旗(纵向)
#include <stdio.h>
#include <sys/stat.h>
#include <sys/types.h>
#include <unistd.h>
#include <fcntl.h>
int main(int argc,char *argv[])
{
int lcd = open("/dev/fb0",O_RDWR);
if(lcd==-1)
{
perror("打开失败");
}
int buf[800*480];
int x,y;
for(y=0;y<480;y++){
for (x=0;x<100;x++){
buf[x+800*y]=0x0021458b;
}
for(;x<200;x++){
buf[x+800*y]=0x00ffffff;
}
for(;x<300;x++){
buf[x+800*y]=0x00cd1125;
}
for(;x<400;x++){
buf[x+800*y]=0x00aa1347;
}
for(;x<500;x++){
buf[x+800*y]=0x002b2536;
}
for(;x<600;x++){
buf[x+800*y]=0x00ce7890;
}
for(;x<700;x++){
buf[x+800*y]=0x007d5e22;
}
for(;x<800;x++){
buf[x+800*y]=0x003451ad;
}
}
int rec = write(lcd,buf,800*480*4);
if(rec==-1){
perror("写入失败");
return -1;
}
close(lcd);
return 0;
}
黑白棋盘:
#include <stdio.h>
#include <sys/stat.h>
#include <sys/types.h>
#include <unistd.h>
#include <fcntl.h>
int main(int argc,char *argv[])
{
int lcd = open("/dev/fb0",O_RDWR);
if(lcd==-1)
{
perror("打开失败");
}
int buf[800*480];
int x,y;
for(y=0;y<240;y++){
for(x=0;x<200;x++){
buf[x+100*y]=0x00ffffff;
}
for(;x<400;x++){
buf[x+800*y]=0x00000000;
}
for(;x<600;x++){
buf[x+800*y]=0x00ffffff;
}
for(;x<800;x++){
buf[x+800*y]=0x00000000;
}
}
for(;y<480;y++){
for(x=0;x<200;x++){
buf[x+800*y]=0x00000000;
}
for(;x<400;x++){
buf[x+800*y]=0x00ffffff;
}
for (;x<600;x++){
buf[x+800*y]=0x00000000;
}
for(;x<800;x++){
buf[x+800*y]=0x00ffffff;
}
}
int rec = write(lcd,buf,800*480*4);
if(rec==-1){
perror("写入失败");
return -1;
}
close(lcd);
return 0;
}
图片显示:
LCD液晶屏图片显示
- 常见格式
JPEG/JPG:采用专用的图像压缩算法进行压缩
BMP:它采用位映射存储格式,除了图像深度可选,不可以采用其他压缩
好处:在显示和保存的时候不需要算法来进行压缩和解压
坏处:占用空间较大(用24位)
-
BMP基本特征
24位:BMP图片的数据是由:基本信息域(54个字节)+数据域(像素点,由RGB构成),也就是3个字节。
RGB:3个字节(R:红色,G:绿色,B:蓝色)。
思考:
如何将24位的图片显示到32位的LCD屏上?答:增加灰度,实现字节对齐
图片中的54个基本信息域如何处理?答:对前54个字节进行截切,lseek();
24位图(RGB)8004803=1152000字节≈1.09M(图像域)+54字节(基本域);
BMP图片的准备
图片的来源
- 使用windows电脑自带的画图工具
- 使用PPT设计,使用画图共聚进行处理
- 通过网络获取其他格式图片,使用画图工具处理
BMP图片的数据是由:基本信息域(54个字节)+数据域(像素点,由RGB构成),也就是3个字节。
RGB:3个字节(R:红色,G:绿色,B:蓝色)。
思考:
如何将24位的图片显示到32位的LCD屏上?答:增加灰度,实现字节对齐
图片中的54个基本信息域如何处理?答:对前54个字节进行截切,lseek();
24位图(RGB)8004803=1152000字节≈1.09M(图像域)+54字节(基本域);
BMP图片的准备
图片的来源
- 使用windows电脑自带的画图工具
- 使用PPT设计,使用画图共聚进行处理
- 通过网络获取其他格式图片,使用画图工具处理