本人因为此阶段精力有限,没有时间去整理代码格式,还请见谅。
//功能;自动左右切换,每一秒切换一次;(自动切换)
#include<stdio.h>
#include <sys/types.h>
#include <dirent.h>
#include<sys/stat.h>
#include<unistd.h>
#include<string.h>
#include<stdlib.h>
#include <fcntl.h>
#include <linux/input.h>
#include <sys/ioctl.h>
#include <linux/fb.h>
#include <sys/mman.h>
#include <jpeglib.h>
int fd;
int *plcd=NULL;
void LCD_Draw_Point(int x,int y,int color)
{
if(x >=0 && x < 800 && y >=0 && y < 480)
{
*(plcd + 800*y + x) = color;
}
}
void bmp_display(char *pathname)
{
int fdBmp;
int w,h;
unsigned char buf[4];
int color_depth;
//打开对应的文件
fdBmp = open(pathname,O_RDONLY);
if(fdBmp<0)
{
perror("bmp open fail");
return;
}
//判断是不是BMP图片
read(fdBmp,buf,2);
if(buf[0] != 0x42 || buf[1] != 0x4d)
{
printf("This is not a BMP picture\n");
return;
}
//读图片的宽度
lseek(fdBmp,0x12,SEEK_SET);
read(fdBmp,buf,4);
w = buf[3] << 24 | buf[2] << 16 | buf[1] << 8 | buf[0];
//读图片的高度
lseek(fdBmp,0x16,SEEK_SET);
read(fdBmp,buf,4);
h = buf[3] << 24 | buf[2] << 16 | buf[1] << 8 | buf[0];
printf("w=%d h=%d\n",w,h);
//读图片的色深
lseek(fdBmp,0x1c,SEEK_SET);
read(fdBmp,buf,2);
color_depth = buf[1] << 8 | buf[0];
//计算图片数据的大小
int size = abs(w*h*color_depth/8) ;
//分配用来保存图片数据的内存空间
unsigned char *pixel = malloc(size);
lseek(fdBmp,54,SEEK_SET);
read(fdBmp,pixel,size);
int x,y;
int i=0;
unsigned char a,r,g,b;
int color;
for(y=0;y < abs(h); y++)
{
for(x=0;x<abs(w);x++){
b = pixel[i++];
g = pixel[i++];
r = pixel[i++];
a = (color_depth == 32) ? pixel[i++] : 0;
color = a << 24 | r << 16 | g << 8 | b; //组合成一个新的颜色值ARGB
int dy = h > 0 ? (h - 1 - y) : y; //判断图片是从左下角还是左上角开始显示
LCD_Draw_Point(x,dy,color);
}
}
free(pixel);
close(fdBmp);
}
void jpeg_display(char *pathname)
{
//1)、分配并且初始化一个jpeg的解压对象
struct jpeg_decompress_struct cinfo; //jpeg解压对象
struct jpeg_error_mgr jerr; //jpeg解压出错处理的结构体
cinfo.err = jpeg_std_error(&jerr); //初始化这两个对象
jpeg_create_decompress(&cinfo);
//2)、将需要解压的JPEG图片读进来
FILE * infile;
if ((infile = fopen(pathname, "r")) == NULL) {
fprintf(stderr, "can't open \n");
exit(1);
}
jpeg_stdio_src(&cinfo, infile);
//3)、读取JPEG的头信息
jpeg_read_header(&cinfo, TRUE);
//4)、设置解压的参数,如果不需要修改,就不需要做什么,采用默认的解压参数就可以了。
//5)、调用对应的函数,进行解压操作
//printf("cinfo.output_components=%d cinfo.output_height=%d\n",cinfo.output_components,cinfo.output_height);
jpeg_start_decompress(&cinfo);
printf(" cinfo.output_height=%d\n",cinfo.output_height);
printf("components=%d width=%d\n",cinfo.output_components,cinfo.output_width);
unsigned char *buffer = malloc(cinfo.output_width * cinfo.output_components);
//6)、逐行读入JPEG的数据,并且解压
int x,y=0;
while ( cinfo.output_scanline < cinfo.output_height )
{
y=cinfo.output_scanline;
jpeg_read_scanlines(&cinfo, &buffer, 1);
unsigned char a,r,g,b;
int color;
unsigned char *p = buffer;
for(x=0;x < cinfo.output_width;x++)
{
if(cinfo.output_components == 3)
{
a=0; //如果cinfo.output_components == 3 它只有RGB的值
}
else
{
a=*p++; //否则是ARGB的格式
}
r = *p++;
g = *p++;
b = *p++;
color = a << 24 | r << 16 | g << 8 | b;
if(y<480 && x < 800)
{
LCD_Draw_Point( x, y, color);
}
}
}
//7)、调用函数完成解压操作
jpeg_finish_decompress(&cinfo);
//8)、释放JPEG解压对象
jpeg_destroy_decompress(&cinfo);
fclose(infile);
}
struct picnode
{
char name[32];
struct picnode *pre;
struct picnode *next;
int mode;
};
struct pichead
{
struct picnode *next;
struct picnode *pre;
};
struct pichead *creathead()
{
struct pichead *dhead=(struct pichead *)malloc(sizeof(*dhead));
dhead->next=NULL;
dhead->pre=NULL;
return dhead;
}
void addnode(struct pichead *head,struct picnode *p)
{
if(head==NULL||p==NULL)
{
return;
}
if(head->next==NULL)
{
head->next=p;
head->pre=p;
}
else
{
head->pre->next=p;
p->pre=head->pre;
head->pre=p;
}
}
void printklink(struct pichead *head)//打印链表,调用jpeg图片显示
{
struct picnode *p=head->next;
while(p)
{
printf("%s %d\n",p->name,p->mode);
if(p->mode==1)
{
jpeg_display(p->name);
}
else if(p->mode==0)
{
bmp_display(p->name);
}
sleep(1);
p=p->next;
}
printf("********\n");
p=head->pre;
while(p)
{
printf("%s %d\n",p->name,p->mode);
if(p->mode==1)
{
jpeg_display(p->name);
}
else if(p->mode==0)
{
bmp_display(p->name);
}
sleep(1);
p=p->pre;
}
}
struct pichead * dirsize(char *pathname,struct pichead *head)//把图片路径放入链表;
{
DIR *dir;
dir=opendir(pathname);
struct stat st;
char filename[520];
int size=0;
if(dir==NULL)
{
perror("open dir fail");
}
struct dirent *dirp=NULL;
while(dirp=readdir(dir))
{
if(strcmp(dirp->d_name,".")==0||strcmp(dirp->d_name,"..")==0)//过滤掉当前目录和上一级目录
{
continue;
}
sprintf(filename,"%s/%s",pathname,dirp->d_name);
if(strcmp(filename+strlen(filename)-4,".jpg")==0)
{
// printf("==> %s\n",filename);
struct picnode *p=(struct picnode *)malloc(sizeof(*p));
strcpy(p->name,filename);
p->mode=1;
p->next=NULL;
p->pre=NULL;
addnode(head,p);
}
if(strcmp(filename+strlen(filename)-4,".bmp")==0)
{
// printf("==> %s\n",filename);
struct picnode *p=(struct picnode *)malloc(sizeof(*p));
strcpy(p->name,filename);
p->mode=0;
p->next=NULL;
p->pre=NULL;
addnode(head,p);
}
stat(filename,&st);
if(S_ISDIR(st.st_mode))
{
dirsize(filename,head);
}
else
{
size+=st.st_size;//可以不要,用来计算文件总大小的;
}
}
closedir(dir);
return head;
}
int main(int argc,char *argv[])
{
fd = open("/dev/fb0",O_RDWR);
if(fd < 0)
{
perror("open lcd fail");
return -1;
}
struct fb_var_screeninfo fbinfo;
ioctl(fd,FBIOGET_VSCREENINFO,&fbinfo);
printf("x:%d y:%d bit_per_pixel:%d\n",fbinfo.xres,fbinfo.yres,fbinfo.bits_per_pixel);
plcd = mmap(
NULL ,//表示映射的地址,为空让系统自动分配
fbinfo.xres*fbinfo.yres*fbinfo.bits_per_pixel/8,//分配内存的大小
PROT_WRITE,//对这个内存区域访问的权限
MAP_SHARED,//其他进程访问的权限
fd,
0//偏移量
);
if(plcd == MAP_FAILED)
{
perror("mmap fail");
close(fd);
return -1;
}
int x,y;
struct pichead *head=creathead();//创建单链表;
head=dirsize(argv[1],head);//把图片文件名加到链表里面去;
printklink(head);//打印图片;
munmap(plcd,fbinfo.xres*fbinfo.yres*fbinfo.bits_per_pixel/8);//解映射;
close(fd);
return 0;
}
//功能;能实现通过左右滑动实现图片切换;
#include<stdio.h>
#include<sys/types.h>
#include<dirent.h>
#include<sys/stat.h>
#include<unistd.h>
#include<string.h>
#include<stdlib.h>
#include<fcntl.h>
#include<sys/ioctl.h>
#include<linux/fb.h>
#include<sys/mman.h>
#include<jpeglib.h>
#include<setjmp.h>
#include<linux/input.h>
int fd;
int *plcd=NULL;
void bmp_display(char *pathname);
void jpeg_display(char *pathname);
struct picnode//定义结点结构体
{
char name[32];
struct picnode *pre;
struct picnode *next;
int mode;
};
struct pichead//定义头节点结构体,里面没有内容
{
struct picnode *next;
struct picnode *pre;
};
struct pichead *creathead()//创建头节点
{
struct pichead *dhead=(struct pichead *)malloc(sizeof(*dhead));
dhead->next=NULL;
dhead->pre=NULL;
return dhead;
}
void addnode(struct pichead *head,struct picnode *p)//将结点一个一个加入到链表里面,注意头
//节点的pre和最后一个结点的next为NULL;
{
if(head==NULL||p==NULL)
{
return;
}
if(head->next==NULL)
{
head->next=p;
head->pre=p;
}
else
{
head->pre->next=p;
p->pre=head->pre;
head->pre=p;
}
}
struct picnode *printklink(struct picnode *p,int ff)
{
if(ff==1)//ff为1时,显示左滑的照片;
{
p=p->pre;
printf("%s %d\n",p->name,p->mode);
if(p->mode==1)
{
jpeg_display(p->name);
}
else if(p->mode==0)
{
bmp_display(p->name);
}
}
else if(ff==0)//为0时显示向右的照片;
{
p=p->next;
printf("%s %d\n",p->name,p->mode);
if(p->mode==1)
{
jpeg_display(p->name);
}
else if(p->mode==0)
{
bmp_display(p->name);
}
}
return p;
}
struct pichead * dirsize(char *pathname,struct pichead *head)//把图片路径都搜索出来
//放入链表的name里面
{
DIR *dir;
dir=opendir(pathname);
struct stat st;
char filename[520];
int size=0;
if(dir==NULL)
{
perror("open dir fail");
}
struct dirent *dirp=NULL;
while(dirp=readdir(dir))//while循环不断读取目录里面的内容;
{
if(strcmp(dirp->d_name,".")==0||strcmp(dirp->d_name,"..")==0)
{
continue;
}
sprintf(filename,"%s/%s",pathname,dirp->d_name);
if(strcmp(filename+strlen(filename)-4,".jpg")==0)//筛选.jpg格式照片;
{
struct picnode *p=(struct picnode *)malloc(sizeof(*p));
strcpy(p->name,filename);
p->mode=1;
p->next=NULL;
p->pre=NULL;
addnode(head,p);
}
if(strcmp(filename+strlen(filename)-4,".bmp")==0)//筛选.bmp格式照片;
{
struct picnode *p=(struct picnode *)malloc(sizeof(*p));
strcpy(p->name,filename);
p->mode=0;
p->next=NULL;
p->pre=NULL;
addnode(head,p);
}
stat(filename,&st);
if(S_ISDIR(st.st_mode))//如果是目录,继续调用函数遍历;
{
dirsize(filename,head);
}
}
closedir(dir);
return head;
}
void LCD_Draw_Point(int x,int y,int color)//画点函数
{
if(x >=0 && x < 800 && y >=0 && y < 480)
{
*(plcd + 800*y + x) = color;
}
}
void bmp_display(char *pathname)//bmp格式图片显示
{
int fdBmp;
int w,h;
unsigned char buf[4];
int color_depth;
//打开对应的文件
fdBmp = open(pathname,O_RDONLY);
if(fdBmp<0)
{
perror("bmp open fail");
return;
}
//判断是不是BMP图片
read(fdBmp,buf,2);
if(buf[0] != 0x42 || buf[1] != 0x4d)
{
printf("This is not a BMP picture\n");
return;
}
//读图片的宽度
lseek(fdBmp,0x12,SEEK_SET);
read(fdBmp,buf,4);
w = buf[3] << 24 | buf[2] << 16 | buf[1] << 8 | buf[0];
//读图片的高度
lseek(fdBmp,0x16,SEEK_SET);
read(fdBmp,buf,4);
h = buf[3] << 24 | buf[2] << 16 | buf[1] << 8 | buf[0];
printf("w=%d h=%d\n",w,h);
//读图片的色深
lseek(fdBmp,0x1c,SEEK_SET);
read(fdBmp,buf,2);
color_depth = buf[1] << 8 | buf[0];
//计算图片数据的大小
int size = abs(w*h*color_depth/8) ;
//分配用来保存图片数据的内存空间
unsigned char *pixel = malloc(size);
lseek(fdBmp,54,SEEK_SET);
read(fdBmp,pixel,size);
int x,y;
int i=0;
unsigned char a,r,g,b;
int color;
for(y=0;y < abs(h); y++)
{
for(x=0;x<abs(w);x++){
b = pixel[i++];
g = pixel[i++];
r = pixel[i++];
a = (color_depth == 32) ? pixel[i++] : 0;
color = a << 24 | r << 16 | g << 8 | b; //组合成一个新的颜色值ARGB
int dy = h > 0 ? (h - 1 - y) : y; //判断图片是从左下角还是左上角开始显示
LCD_Draw_Point(x,dy,color);
}
}
free(pixel);
close(fdBmp);
}
void jpeg_display(char *pathname)//jpeg图片显示函数
{
//1)、分配并且初始化一个jpeg的解压对象
struct jpeg_decompress_struct cinfo; //jpeg解压对象
struct jpeg_error_mgr jerr; //jpeg解压出错处理的结构体
cinfo.err = jpeg_std_error(&jerr); //初始化这两个对象
jpeg_create_decompress(&cinfo);
//2)、将需要解压的JPEG图片读进来
FILE * infile;
if ((infile = fopen(pathname, "r")) == NULL) {
fprintf(stderr, "can't open \n");
exit(1);
}
jpeg_stdio_src(&cinfo, infile);
//3)、读取JPEG的头信息
jpeg_read_header(&cinfo, TRUE);
//4)、设置解压的参数,如果不需要修改,就不需要做什么,采用默认的解压参数就可以了。
//5)、调用对应的函数,进行解压操作
//printf("cinfo.output_components=%d cinfo.output_height=%d\n",cinfo.output_components,cinfo.output_height);
jpeg_start_decompress(&cinfo);
printf(" cinfo.output_height=%d\n",cinfo.output_height);
printf("components=%d width=%d\n",cinfo.output_components,cinfo.output_width);
unsigned char *buffer = malloc(cinfo.output_width * cinfo.output_components);
//6)、逐行读入JPEG的数据,并且解压
int x,y=0;
while ( cinfo.output_scanline < cinfo.output_height )
{
y=cinfo.output_scanline;
jpeg_read_scanlines(&cinfo, &buffer, 1);
unsigned char a,r,g,b;
int color;
unsigned char *p = buffer;
for(x=0;x < cinfo.output_width;x++)
{
if(cinfo.output_components == 3)
{
a=0; //如果cinfo.output_components == 3 它只有RGB的值
}
else
{
a=*p++; //否则是ARGB的格式
}
r = *p++;
g = *p++;
b = *p++;
color = a << 24 | r << 16 | g << 8 | b;
if(y<480 && x < 800)
{
LCD_Draw_Point( x, y, color);
}
}
}
//7)、调用函数完成解压操作
jpeg_finish_decompress(&cinfo);
//8)、释放JPEG解压对象
jpeg_destroy_decompress(&cinfo);
fclose(infile);
}
int main(int argc,char *argv[])
{
fd = open("/dev/fb0",O_RDWR);//打开framebuffer,相当于显存;
if(fd < 0)
{
perror("open lcd fail");
return -1;
}
struct fb_var_screeninfo fbinfo;
ioctl(fd,FBIOGET_VSCREENINFO,&fbinfo);
printf("x:%d y:%d bit_per_pixel:%d\n",fbinfo.xres,fbinfo.yres,fbinfo.bits_per_pixel);
plcd = mmap(
NULL ,//表示映射的地址,为空让系统自动分配
fbinfo.xres*fbinfo.yres*fbinfo.bits_per_pixel/8,//分配内存的大小
PROT_WRITE,//对这个内存区域访问的权限
MAP_SHARED,//其他进程访问的权限
fd,
0//偏移量
);
if(plcd == MAP_FAILED)
{
perror("mmap fail");
close(fd);
return -1;
}
int x,y;
for(y=0;y<480;y++)
{
for(x=0;x<800;x++)
{
*(plcd + x + y*800) = 0x000000FF;//显示蓝色屏幕;
}
}
struct pichead * head=creathead();
head=dirsize(argv[1],head);
struct picnode *p=head->next;
if(p->mode==1)
{
jpeg_display(p->name);
}
else if(p->mode==0)
{
bmp_display(p->name);
}//创建头结点,并显示头节点下一节点的图片,因为头节点没内荣;
int fdts;
struct input_event ts;//事件结构体;
fdts = open("/dev/input/event0",O_RDONLY);
if(fdts < 0)
{
perror("ts open fail");
return -1;
}
while(1)
{
int m1=0,m2=0,flag=0;
while(1)
{
read(fdts,&ts,sizeof(struct input_event));
if(ts.type == EV_KEY && ts.code == 0x14a )//按键事件,只有在按下时值为1,滑动过程没值,值为触摸屏事件;
{
if(ts.value==1)//按下
{
flag=1;//标志位;
}
else if(ts.value==0)//松开
{
if(m1>m2)
{
if(p->pre==NULL)
{
p=head->pre;
}//因为头节点pre为空
p=printklink(p,1);
break;//左滑;
}
else if(m1<m2)
{
if(p->next==NULL)
{
p=head->next;
}//最后一个节点的next为NULL;
p=printklink(p,0);
break;//右滑;
}
}
}
else if(ts.type == EV_ABS&&ts.code == ABS_X)//采集两点的x坐标;
{
if (flag==1)
{
m1=ts.value;
flag=2;
}
else if(flag==2)
{
m2=ts.value;
}
}
}
}
mummap(plcd,fbinfo.xres*fbinfo.yres*fbinfo.bits_per_pixel/8);//解映射;
close(fdts);
close(fd);
return 0;
}
//功能:实现左右点切换图片
#include <stdio.h>
#include <fcntl.h>
#include <linux/input.h>
#include <sys/ioctl.h>
#include <linux/fb.h>
#include <sys/mman.h>
#include <stdlib.h>
#include <jpeglib.h>
int fd;
int *plcd=NULL;
void LCD_Draw_Point(int x,int y,int color)
{
if(x >=0 && x < 800 && y >=0 && y < 480)
{
*(plcd + 800*y + x) = color;
}
}
void jpeg_display(char *pathname)
{
//1)、分配并且初始化一个jpeg的解压对象
struct jpeg_decompress_struct cinfo; //jpeg解压对象
struct jpeg_error_mgr jerr; //jpeg解压出错处理的结构体
cinfo.err = jpeg_std_error(&jerr); //初始化这两个对象
jpeg_create_decompress(&cinfo);
//2)、将需要解压的JPEG图片读进来
FILE * infile;
if ((infile = fopen(pathname, "r")) == NULL) {
fprintf(stderr, "can't open \n");
exit(1);
}
jpeg_stdio_src(&cinfo, infile);
//3)、读取JPEG的头信息
jpeg_read_header(&cinfo, TRUE);
//4)、设置解压的参数,如果不需要修改,就不需要做什么,采用默认的解压参数就可以了。
//5)、调用对应的函数,进行解压操作
//printf("cinfo.output_components=%d cinfo.output_height=%d\n",cinfo.output_components,cinfo.output_height);
jpeg_start_decompress(&cinfo);
printf(" cinfo.output_height=%d\n",cinfo.output_height);
printf("components=%d width=%d\n",cinfo.output_components,cinfo.output_width);
unsigned char *buffer = malloc(cinfo.output_width * cinfo.output_components);
//6)、逐行读入JPEG的数据,并且解压
int x,y=0;
while ( cinfo.output_scanline < cinfo.output_height )
{
y=cinfo.output_scanline;
jpeg_read_scanlines(&cinfo, &buffer, 1);
unsigned char a,r,g,b;
int color;
unsigned char *p = buffer;
for(x=0;x < cinfo.output_width;x++)
{
if(cinfo.output_components == 3)
{
a=0; //如果cinfo.output_components == 3 它只有RGB的值
}
else
{
a=*p++; //否则是ARGB的格式
}
r = *p++;
g = *p++;
b = *p++;
color = a << 24 | r << 16 | g << 8 | b;
if(y<480 && x < 800)
{
LCD_Draw_Point( x, y, color);
}
}
}
//7)、调用函数完成解压操作
jpeg_finish_decompress(&cinfo);
//8)、释放JPEG解压对象
jpeg_destroy_decompress(&cinfo);
fclose(infile);
}
int main()
{
fd = open("/dev/fb0",O_RDWR);
if(fd < 0)
{
perror("open lcd fail");
return -1;
}
struct fb_var_screeninfo fbinfo;
ioctl(fd,FBIOGET_VSCREENINFO,&fbinfo);
printf("x:%d y:%d bit_per_pixel:%d\n",fbinfo.xres,fbinfo.yres,fbinfo.bits_per_pixel);
plcd = mmap(
NULL ,//表示映射的地址,为空让系统自动分配
fbinfo.xres*fbinfo.yres*fbinfo.bits_per_pixel/8,//分配内存的大小
PROT_WRITE,//对这个内存区域访问的权限
MAP_SHARED,//其他进程访问的权限
fd,
0//偏移量
);
if(plcd == MAP_FAILED)
{
perror("mmap fail");
close(fd);
return -1;
}
int x,y;
for(y=0;y<480;y++)
{
for(x=0;x<800;x++)
{
*(plcd + x + y*800) = 0x000000FF;
}
}
int fdts;
struct input_event ts;
fdts = open("/dev/input/event0",O_RDONLY);
if(fdts < 0)
{
perror("ts open fail");
return -1;
}
while(1)
{
read(fdts,&ts,sizeof(struct input_event));
if(ts.type == EV_ABS)
{
if(ts.code == ABS_X)
{
printf("x=%d\n",ts.value);
if(ts.value<=400)
{
jpeg_display("caobo/1.jpg");
}
else
{
jpeg_display("caobo/2.jpg");
}
}
else if(ts.code == ABS_Y)
{
printf("y=%d\n",ts.value);
}
}
}
close(fdts);
return 0;
}