20141122 【 ARM - 电子音乐相册 】

18 篇文章 1 订阅
13 篇文章 0 订阅

ARM型号我不太记得了(其实也不太懂);

好像是:三星 ARM-Cortex-A9 吧,由粤嵌公司做的一个板子。。。




周六周日两天,由粤嵌公司的工程师带我们做了一个项目——电子音乐相册。


不过这只是初步。。。毕竟我们以前没接触过 ARM 的开发。(部分同学学过单片机,我只是多学了个初等的 Arduino)


本以为这次是从入门到完成,从 Linux 系统上安装 ARM 编译所需--到-- ARM 下驱动编写以及多进程同时调度音乐播放和图片播放。


结果……老师觉得我们不行,都封装好给我们了(Ubuntu的镜像都直接集成了,ARM与计算机的网口通信,还有可怜的音乐图片不能同时播放,以及没有触屏功能)。


所以课程还是比较轻松(对于我来说)。。。


这两天感觉心情不错,主要是做出东西总是有成就感的(虽然这个巨人有点大)。
但也感到很多不足,包括Linux的自大,网络知识的自负,ARM的无知,操作系统的无视,还有体力的自信。。。


总之,要感谢这两天教导我们的 邓工程师,以及粤嵌公司的其它老师。。。


_________________________________________________________











以下,邓工程师的教导笔记(日记吧)

linux 环境编程:  -------> linux 一切都是文件  
  
  
设备文件存放在 /dev   ----> /dev/fb0  
  
  
  
----------------------------安装共享文件夹------------------------------  
  
  
  Vmware    
    
    
  VM   --->  setting  --->  Options  --->  share folders  ---> Always enable   
    
  配置 windows 系统的共享目录:  
    
    D:/share  
      
      
  在 linux系统中:  
    
  cd  /mnt/hgfs/share    
  
  
  
------------------------------tftp32使用-------------------------------------  
  
  
确保开发板与PC的IP同一网段       
  
  
开发板:  
  
ifconfig  eth0  192.168.2.xx    ----->  xx 为开发板的ip  
  
tftp 192.168.2.yy -g -r xxx.bmp    ----> yy 为tftp32的ip  
  
tftp 192.168.2.yy -g -r lcd  
  
------------------------------------------------------------------------  
  
  
  
编程控制设备:  
  
      1)  文件IO API  
        
      2)  linux 管理系统  
        
      3)  设备访问规则  
        
        3.1) 获取资源许可:   ----->  man  man  
          
              open();  
                
              获得LCD控制许可:  
                  
              #include <sys/types.h>  
              #include <sys/stat.h>  
              #include <fcntl.h>                   
              int open(const char *pathname, int flags);  
                
              pathname: “/dev/fb0”  
              flags:      O_RDWR   
                
                
        3.2) 控制LCD  
          
                #include <unistd.h>  
                write/read  
                  
                ssize_t write(int fd, const void *buf, size_t count);  
                  
                fd:  lcd的文件描述符 ,open成功返回的int 值  
                buf: 写入LCD的图形数据  
                count: 写入数据的大小  
                  
                // cat  /bin/busybox  >  /dev/fb0  
                // LCD 显示的是颜色 ---> RGB数值  --->  32bit =》 8:8:8:8(透明度:红色:绿色:蓝色)  
                // LCD 显示的大小   ---> 分辨率   --->  800*480  
                // LCD 显示一帧图像的 存储容量:  800*480*4 = 1536000字节  = 1.5M  
                // RGB =》  0xFFFFFF  ---> 白色    0x00000000  --> 黑色  
                  
                  
          3.3)回收资源  
            
          #include <unistd.h>  
  
          int close(int fd);  
            
          fd: lcd的文件描述符 ,open成功返回的int 值  
            
            
            
          3.4) 图片操作  
            
            open();  
              
            read();  
              
              
            ssize_t read(int fd, void *buf, size_t count);  
                    fd:图片的文件描述符 ,open成功返回的int 值  
                    buf: 图片内容  
                    count: 读取图片内容的大小  
                      
                      
                      
           文件指针移动  
             
           lseek(int fd, off_t offset, int whence);  
           fd:图片的文件描述符 ,open成功返回的int 值   
           offset:  文件操作指针移动偏移量  
           whence:  文件指针操作的起始位置  
                     SEEK_SET  文件头部  
                     SEEK_CUR  文件当前位置  
                     SEEK_END  文件尾部  
             
             
           lseek(bmp_fd,54,SEEK_SET);  
             
             
             
             
           3.5 ) 多张图片操作  
             
                  3.5.1) 文件夹操作  
                    
                       #include <sys/types.h>  
                       #include <dirent.h>  
                         
                       //打开文件目录,获取目录流指针  
                       DIR *opendir(const char *name);  
                       name : 文件目录名称  
                       DIR:  文件目录流结构  
                         
                       //读取目录流指针,获取当前的struct dirent目录项指针  
                       struct dirent *readdir(DIR *dirp);  
                              
              struct dirent {  
               ino_t          d_ino;       /* inode number */  
               off_t          d_off;       /* offset to the next dirent */  
               unsigned short d_reclen;    /* length of this record */  
               unsigned char  d_type;      /* type of file; not supported  
                                              by all file system types */  
               char           d_name[256]; /* filename */  
           };  
          
             
             
           在开发板建立图片目录:  
             
             
          mkdir pic  
                   
          将图片下载到pic中,让后通过代码进行目录访问:  
            
            
          DIR *  pic_dir = opendir("/pic");  
          struct dirent * pic_dirent ;  
          char pathname[30];  
            
          while( (pic_dirent= readdir(pic_dir)) != NULL )  
          {  
              if(strstr(pic_dirent->d_name,".bmp"))  
              {  
                 snprintf(pathname,30,"/pic/%s",pic_dirent->d_name);  
                 bmp_fd[i] = open(pathname,O_RDWR);   
                 ...   
              }     
                
          }  
            
          closedir(pic_dir);  
  
                      
       3.6) 图片翻转  
            
            
            //24bit to 32bit  
            for(i=0,j=800*480*4-1;i<800*480*3;i+=3)  
            {  
             pic_mem[j-3] = bmp_mem[i] ;  
                 pic_mem[j-2] = bmp_mem[i+1] ;  
                 pic_mem[j-1] = bmp_mem[i+2] ;  
                 j-=4;  
            }           
            
            
            
            
       3.7) 微缩图操作  
            
            
        char narrow_buf[4][400*240*3];    
            
        for(i=0,j=0;i<pic_count;i++)  
        {  
          //移动文件读取指针位置,从头部54字节地方开始  
          lseek(bmp_fd[i],54,SEEK_SET);  
            
          //读取图片数据800*480*3+54  
          read(bmp_fd[i],bmp_mem,800*480*3);  
  
                
          j=0;  
          for(y=479;y>=0;y-=2)  
            for(x=0;x<800*3;x+=3)  
            {  
                  for(count=0;count<3;count++)  
                        narrow_buf[i][j++] = bmp_mem[y*800*3+x++] ;  
            }     
  
        }  
     
      for(i=0,j=0;i<pic_count;i++)  
        {  
          j=0;  
          for(y=0+(i/2)*240;y<240+(i/2)*240;y++)  
            for(x=0+(i%2)*400*4;x<400*4+(i%2)*400*4;x++)  
              {  
                pic_mem[y*800+x] = narrow_buf[i][j++];  
                if( x!= 0 && x%3 == 0)  
                    x++;  
              }  
        }           
            
            
          3.8)按键操作  
            
            
               1) 通过open对按键发起访问  
                 
                open("/dev/eventX",O_RDWR);  
                 
               2)通过read 获取按键的数据  
                 
               struct input_event {  
                struct timeval time;  
                __u16 type;      // 事件类型  
                __u16 code;       //按键键值  
                __s32 value;     //按键状态   1按下  0 弹起  
               };  
                 
               struct input_event  key_event;  
                 
               read(fd,&key_event,sizeof(key_event));  
                 
               if(key_event.type == EV_KEY)  //是否读到一个按键事件  
               {  
                    if(key_event.code == KEY_LEFT) //如果是左键按下  
                    {  
                         ... //放大微缩图  
                      
                    }  
                    if(key_event.code == KEY_RIGHT) //如果是右键按下  
                    {  
                         ... //显示微缩图  
                      
                    }    
                    ....               
                 
               }  
                 
                 
          ----------------具体操作-------------------       
                 
            
          1、将驱动下载到开发板,并加载:  
            
             input_key.ko  
               
               
             在开发板安装驱动:   insmod input_key.ko  
             在开发板卸载驱动:   rmmod input_key  
             查看安装的驱动:     lsmod  
               
               
         2、修改代码,访问按键按键驱动:  
           
  #include <linux/input.h>  
            
  int key_fd;  
    struct input_event key_event;  
    key_fd = open("/dev/event1",O_RDWR);  
    if(key_fd < 0)  
        {  
            perror(" open key err !");  
            return -1;  
        }  
  
    read(key_fd,&key_event,sizeof(key_event));  
    if(key_event.type == EV_KEY)  
        {  
            if(key_event.code == KEY_LEFT)  
                {  
                    //显示放大图片  
  
                }  
            if(key_event.code == KEY_RIGHT)  
                {  
                    //显示微缩图  
  
                }  
  
        }            
            
     close(key_fd)       
            
            
            
            
            
            
            
          3.9) 幻灯片播放  
            
            
            
            
            
          4.0)音乐播放  
            
            
            
            
            
            
            
            
             
         
        --------------------------------------------------------------------------------------------     
            
          程序编译:  
            
            本地编译:   运行与编译的环境一致 (PC 编程)  
              
            交叉编译:   运行与编译的环境不一致 (在一个平台编译另外一个平台的代码,PC --> ARM)  
              
            编译器: 本地编译器 ,交叉编译器  
              
                         gcc      arm-linux-gcc  
            
  
              使用:  
                
                      cd /mnt/hgfs/share  
                
                      arm-linux-gcc  lcd.c  -o  lcd    //得到执行程序 lcd    
                        
                        
                      查看文件的类型属性:  
                         
                      file  a.out  
  
  
              
              
            在开饭的超级终端中将应用程序下载到开发板运行测试:  
              
              
            输入: rx  lcd   回车  
              
            超级终端选择:“传送” --->  发送文件  ---->  协议: Xmodem  文件: d:/share/lcd  回车  
              
              
            修改文件执行权限:  chmod  777 lcd  
              
              
            执行测试:   ./lcd  
              
              
              
              
              
            -------------------------BMP图片下载-----------------------------  
              
              
            rx  1.bmp   回车  
              
            pwd 查看当前路径  
               
                  
  
------------man   man ---(q 退出)---------  
  
       1   Executable programs or shell commands  
       2   System calls (functions provided by the kernel)  
       3   Library calls (functions within program libraries)  
  
-------------------------------------------------------





第一天

关于图片的读取与打印屏幕,文件目录文件的读取与24位位图转成32位图

#include <sys/types.h>
#include <sys/stat.h>
#include <fcntl.h> 
#include <unistd.h>
#include <stdio.h>
#include <string.h>
#include <sys/types.h>
#include <dirent.h>


char bmp_mem[800*480*3];
char pic_mem[800*480*4];


DIR * pic_dir;
struct dirent *pic_dirent;
char pathname[30];
int pic_count;

int main(int argc,char **argv)
{
	int fd,bmp_fd[30];
	int i=0,j,k;

	
	//获取LCD资源
	fd = open("/dev/fb0",O_RDWR);
	//获取失败处理
	if(fd < 0)
		{
			perror(" open LCD Err !");
			return -1;
		}

	//写屏幕
	memset(pic_mem, 0xFF, 800*480*4);
	write(fd, pic_mem, 800*480*4);

	sleep(3);


	//打开目录
	pic_dir = opendir("/pic");
	
	//读目录
	while( ( pic_dirent =  readdir(pic_dir)) != NULL )
	{
              if(strstr(pic_dirent->d_name,".bmp"))
              {
                 snprintf(pathname,30,"/pic/%s",pic_dirent->d_name);
		  //打开图片,获取图片操作许可
		  //打开文件,将文件描述符写入文件描述符数组
                 bmp_fd[i++] = open(pathname,O_RDWR); 
		  if( bmp_fd[i] <0)
			{
				perror(" open bmp err ");
				return -1;
			}
		  pic_count = i;
              }   		

	}

	



	for(k=0;k<pic_count;k++)   
		{
			//移动文件读取指针位置,从头部54字节地方开始
			lseek(bmp_fd[k],54,SEEK_SET);

			//读取图片数据800*480*3+54
			read(bmp_fd[k],bmp_mem,800*480*3);

			//24bit to 32bit
			for(i=0,j=0;i<800*480*3;i+=3)
			{
		                pic_mem[j] = bmp_mem[i] ;
				 pic_mem[j+1] = bmp_mem[i+1] ;
				 pic_mem[j+2] = bmp_mem[i+2] ;
				 j+=4;
			}

			//移动显存指针位置,从头部开始
			lseek(fd,0,SEEK_SET);
			//将读到的图片数据写入LCD
			write(fd,pic_mem,800*480*4);

			//休眠3秒
			sleep(3);
		}
	

       //回收资源
	close(fd);
	closedir(pic_dir);

	for(i=0;i<pic_count;i++)   
		close(bmp_fd[i]);

	
	

	return 0;   //成功返回 0  ;失败返回的是负数: -1
}







【个人的打印屏幕代码】

#include <sys/types.h>
#include <sys/stat.h>
#include <fcntl.h>
#include <unistd.h>
#include <string.h>
//控制LCD屏幕

char pic_mem[800*480*4];				/* 图像地址? */
void pic_set(int ss, int ee, char color){
	int i;
	for(i=ss; i<=ee; i++){
		pic_mem[i] = color;
	}
}

int main(int argc, char **argv){
	char pathname[] = "/dev/fb0";		/* 文件路径 */
	int flags = O_RDWR;					/* 访问方式 */
	int fd = open(pathname, flags);		/* 获取文件句柄 */
	if( fd < 0 ){						/* 获取失败 处理 */
		printf("OPEN LCD ERROR!\n");
		return -1;
	}

	//memset(pic_mem, 0xFF, sizeof(pic_mem));
	
    pic_set(0, 500000, 0x00);
	pic_set(500000, 1000000, 0xFF);
	pic_set(1000000,1500000, 0x00);
    pic_set(1500000,2000000, 0xFF);
	pic_set(2500000,3000000, 0x00);
	pic_set(3500000,4000000, 0xFF);
    pic_set(4500000,5000000, 0x00);
    
	/**	写屏幕 */
	write(fd, pic_mem, 800*480*4);		/* 写位置,来源,需要写多少 */		
	/* LCD 颜色8:8:8:8(透明度,红,绿,蓝) */
	/* LCD 大小 分辨率 800*480 *4Byte */
	/* 故, 写一张图片大小 1.5M */
	/* WHITE=0xFFFFFFFF, BLACK=0x00000000 */

	

	close(fd);	/* 关闭文件,回收资源 */
	return 0;	/**	SUCCESS 0, ERROR -1 */
}








【个人代码,随机循环变色(还没加图片处理)】

#include <sys/types.h>
#include <sys/stat.h>
#include <fcntl.h>
#include <unistd.h>
#include <string.h>
#include <time.h>
#include <stdlib.h>
//控制LCD屏幕

char pic_mem[800*480*4];				/* 图像地址? */

#define SET_COLOR(color, no)	(char)( ((color)>>(8*no))&0xFF )

unsigned int rand_color(){
	unsigned int res = 0;
	int i;
	for(i=0; i<4; i++)
		res |= (res<<8) | ( rand()%256 );
	return res;
}

void pic_set(int ss, int ee, unsigned int color){
	int i, j;
	for(i=ss; i<=ee; i+=4)
		for(j=3; j>=0; j--)			
			pic_mem[i+j] = SET_COLOR(color, j);
}

int open_err(char path[], int st){
	int pd = open(path, st);
	if( pd < 0 ){
		perror("OPEN file Error!\n");
		return -1;
	}
	return pd;
}

int main(int argc, char **argv){
	char pathname[] = "/dev/fb0";		/* 文件路径 */
	char p01name[] = "/p01.bmp"
	int flags = O_RDWR;					/* 访问方式 */
	
	srand(time(NULL));
	//memset(pic_mem, 0xaa, sizeof(pic_mem));
	unsigned int c[2] = {0x520A0B0C , 0x00AABBCC}, delay_time;
	int flag = 0;
	int fd = open(pathname, flags);		/* 获取文件句柄 */
		if( fd < 0 ){						/* 获取失败 处理 */
			printf("OPEN LCD ERROR!\n");
			return -1;
		}
		
	while( 1 ){
		/* 打开图片 */
	//int bmp_fd = open_err(p01name, flags);

	int bmp_fd;
	read(bmp_fd, p01name, 800*480*3);
			
	    pic_set(0*480*4, 400*480*4, rand_color());
		pic_set(400*480*4, 800*480*4, rand_color());
		flag = 1-flag;
	    
		/**	写屏幕 */
		write(fd, pic_mem, 800*480*4);		/* 写位置,来源,需要写多少 */		

	
	
	/* LCD 颜色8:8:8:8(透明度,红,绿,蓝) */
	/* LCD 大小 分辨率 800*480 *4Byte */
	/* 故, 写一张图片大小 1.5M */
	/* WHITE=0xFFFFFFFF, BLACK=0x00000000 */

			/* 关闭文件,回收资源 */
		for(delay_time=0x00FFFFFF; delay_time; delay_time--);
	}
	close(fd);
	return 0;	/**	SUCCESS 0, ERROR -1 */
}








【个人代码,24位图拓展为32位图(多余Byte为透明度控制),没加翻转处理】

果然没有 邓工程师 NB,人家处理的时候带翻转的,那速度可不是一个数量级的。。

#include <sys/types.h>
#include <sys/stat.h>
#include <fcntl.h>
#include <unistd.h>
#include <dirent.h>
#include <string.h>
#include <time.h>
#include <stdlib.h>

void delay(unsigned int dt){
	int i;
	while( dt-- )
		for(i=80000; i; i--);
}
char p_tmp[800*480*4];
char picture[800*480*4];

void execute_picture(char picture[]){
	int i, j, len = 800*480*3;
	for(i=0, j=0; i<len; i++, j++){
		if( j%4==3 ){
			p_tmp[j] = 0x33;
			j++;
		}
		p_tmp[j] = picture[i];
	}
	memcpy(picture, p_tmp, 800*480*4);
}

int main(int argc, char **argv){
	int fd, fds[100], plen=0;
	char printpath[] = "/dev/fb0";
	char dir_path[] = "/test";
	char tmp_path[123];
	
	DIR * pic_dir = opendir(dir_path);
	struct dirent * pic_dirent;

	while( ( pic_dirent = readdir( pic_dir ) ) != NULL ){
		if( strstr(pic_dirent->d_name, ".bmp") != NULL ){
			snprintf(tmp_path, 111, "%s/%s", dir_path, pic_dirent->d_name);
			fds[plen] = open(tmp_path, O_RDWR);
			if( fds[plen] < 0 ){
				perror("ERROR!\n");
				return -1;
			}
			plen++;
		}
	};

	fd = open(printpath, O_RDWR);
	if( fd<0 ){
		perror("ERROR");
		return -1;
	}

	int i;
	while( 1 ){
		for(i=0; i<plen; i++){
			lseek(fds[i], 54, SEEK_SET);
			read(fds[i], picture, 800*480*3);
			execute_picture(picture);
			write(fd, p_tmp, 800*480*4);
			lseek(fd, 0, SEEK_SET);

			sleep(3);
		}
	}
	for(i=0; i<plen; i++)
		close(fds[i]);
	close(fd);
	return 0;
}













第二天

图像压缩,按键监控,音频播放

#include <sys/types.h>
#include <sys/stat.h>
#include <fcntl.h> 
#include <unistd.h>
#include <stdio.h>
#include <string.h>
#include <sys/types.h>
#include <dirent.h>
#include <linux/input.h>

char bmp_mem[800*480*3];
char swap_bmp[800*480*3];
char pic_mem[800*480*4];
char narrow_buf[4][400*240*3];

DIR * pic_dir;
struct dirent *pic_dirent;
char pathname[30];
int pic_count;

int main(int argc,char **argv)
{
	int fd,bmp_fd[30];
	int i=0,j,k,x,y,count;
	int key_fd;
	struct input_event key_event;

	
	//获取LCD资源
	fd = open("/dev/fb0",O_RDWR);
	//获取失败处理
	if(fd < 0)
		{
			perror(" open LCD Err !");
			return -1;
		}

	//写屏幕
	memset(pic_mem, 0xFF, 800*480*4);
	write(fd, pic_mem, 800*480*4);

	sleep(3);


	//打开目录
	pic_dir = opendir("/pic");
	
	//读目录
	while( ( pic_dirent =  readdir(pic_dir)) != NULL )
	{
              if(strstr(pic_dirent->d_name,".bmp"))
              {
                 snprintf(pathname,30,"/pic/%s",pic_dirent->d_name);
		  //打开图片,获取图片操作许可
		  //打开文件,将文件描述符写入文件描述符数组
                 bmp_fd[i++] = open(pathname,O_RDWR); 
		  if( bmp_fd[i] <0)
			{
				perror(" open bmp err ");
				return -1;
			}
		  pic_count = i;
              }   		

	}


        //获取微缩图
	for(k=0;k<pic_count;k++)
        {
          //移动文件读取指针位置,从头部54字节地方开始
          lseek(bmp_fd[k],54,SEEK_SET);
          
          //读取图片数据800*480*3+54
          read(bmp_fd[k],bmp_mem,800*480*3);

	//24bit to 32bit
	for(i=0,j=800*480*4-1;i<800*480*3;i+=3,j-=4)
	{
                pic_mem[j-3] = bmp_mem[i] ;
		 pic_mem[j-2] = bmp_mem[i+1] ;
		 pic_mem[j-1] = bmp_mem[i+2] ;	 
	}


	//移动显存指针位置,从头部开始
	lseek(fd,0,SEEK_SET);
	//将读到的图片数据写入LCD
	write(fd,pic_mem,800*480*4);

	printf("  pic:%d    sleep 1 s ,goto  next \n",k);
	sleep(1);
	
	
	  j=0;
          for(y=479;y>=2;y-=2)
            for(x=0;x<800*3;x+=3)
            {
                  for(count=0;count<3;count++)
                        narrow_buf[k][j++] = bmp_mem[y*800*3+x++] ;
            }	

        }

	//清屏,白屏
	lseek(fd,0,SEEK_SET);
	memset(pic_mem,0xff,800*480*4);
	write(fd,pic_mem,800*480*4);


     //将微缩图填充到帧图像数组
      for(i=0;i<pic_count;i++)
        {
          j=0;
          for(y=0+(i/2)*240;y<240+(i/2)*240;y++)
            for(x=0+(i%2)*400*4;x<400*4+(i%2)*400*4;)
              {
                     //.....
                     

              }
        }  


	//移动显存指针位置,从头部开始
	lseek(fd,0,SEEK_SET);
	//将读到的帧图像数据写入LCD
	write(fd,pic_mem,800*480*4);


	key_fd = open("/dev/event1",O_RDWR);
	if(key_fd < 0)
		{
			perror(" open key err !");
			return -1;
		}


       while(1)
       	{
       	
		read(key_fd,&key_event,sizeof(key_event));
		if(key_event.type == EV_KEY)
			{
				if(key_event.code == KEY_LEFT  && key_event.value == 1)
					{
						//显示放大图片
						printf(" KEY_LEFT !\n ");
						

					}
				if(key_event.code == KEY_RIGHT && key_event.value == 1)
					{
						//显示微缩图
						printf(" KEY_RIGHT !\n ");
					}

			}
       	}

	
#if 0


       //正常循环显示图片
	for(k=0;k<pic_count;k++)   
		{
			//移动文件读取指针位置,从头部54字节地方开始
			lseek(bmp_fd[k],54,SEEK_SET);

			//读取图片数据800*480*3+54
			read(bmp_fd[k],bmp_mem,800*480*3);

			//24bit to 32bit
			for(i=0,j=800*480*4-1;i<800*480*3;i+=3)
			{
		                pic_mem[j-3] = bmp_mem[i] ;
				 pic_mem[j-2] = bmp_mem[i+1] ;
				 pic_mem[j-1] = bmp_mem[i+2] ;
				 j-=4;
			}

			//移动显存指针位置,从头部开始
			lseek(fd,0,SEEK_SET);
			//将读到的图片数据写入LCD
			write(fd,pic_mem,800*480*4);

			//休眠3秒
			sleep(3);
		}
	
#endif

       //回收资源
	close(fd);
	close(key_fd);
	closedir(pic_dir);

	for(i=0;i<pic_count;i++)   
		close(bmp_fd[i]);

	
	

	return 0;   //成功返回 0  ;失败返回的是负数: -1
}




madplay 音频播放命令

命令格式:

madplay  option    filename



option:

-v  获取播放时间
-q  不存在任何打印,但现实警告
-Q  不存在任何打印
–downsample  只采用一半数据
-i  忽略CRC校验错误
-o PATH/xx.wav 可以用来转码,将mp3转为wav
也可以是其他格式,见说明;.raw  表示是元素pcm,.hex等
-a 开启衰减音量,增加音量,衰减系统为-175~+18    (当然通过键盘+ —也可以调整音量)
-A 同-a
-1 -2 -m -S 分别指左声道,右声道,双声道,立体声
-s  用于seek播放如:0:1:20:11 ,seek到1小时,2分钟,11秒时开始播放
-t  用于播放时间现在  0:1:20:11 ,播放到1小时,2分钟,11秒时就停止
-z  用于随机播放列表
-r, –repeat[=MAX]   循环播放无限次或Max次
–tty-control            enable keyboard controls  默认是使能热键
–no-tty-control         disable keyboard controls
热键使用
下一首歌曲; f,或ctrl+n 或者>
上一首歌曲  b ,或ctrl+p 或者<
退出:q, Q,获取ctrl+c
获取播放状态信息: i  ?
调节音量: – + _ =
暂停恢复:p
停止:s






【个人代码,图片处理,翻转,压缩,移动】

还是一样的分步处理,邓工程师 可是 处理+翻转 or 处理+翻转+压缩。。。

#include <sys/types.h>
#include <sys/stat.h>
#include <fcntl.h>
#include <unistd.h>
#include <dirent.h>
#include <string.h>
#include <time.h>
#include <stdlib.h>
#include <errno.h>
#include <stdio.h>
#include <stdarg.h>

void delay(unsigned int dt){
	int i;
	while( dt-- )
		for(i=80000; i; i--);
}
char p_tmp[800*480*4];
char picture[800*480*4];
char p_pic[800*480*4];
char pcom[16][480*800*4/4];

int s_d[4][2] = { 0*800+0,400,	0*800+400,400,	240*800+0,400,	240*800+400,400 };

void re_row(char s[], char t[], int row, int col){
	int i, j;
	col *= 4;
	for(i=0; i<row; i++)
		for(j=0; j<col; j++)
			s[ (row-1-i)*col + j ] = t[ i*col + j ];
}
	
void execute_picture(char picture[]){
	int i, j, len = 800*480*3;
	for(i=0, j=0; i<len; i++, j++){
		if( j%4==3 ){
			p_tmp[j] = 0x33;
			j++;
		}
		p_tmp[j] = picture[i];
	}
	memcpy(picture, p_tmp, 800*480*4);
	//re_row(picture, p_tmp, 480, 800);
}

void compress_picture(int bb, char s[], char t[], int row, int col, int rb, int cb){
	int i, j, k, len=0;
	for(i=row-1; i>=0; i-=rb){
		for(j=0; j<col*bb; j+=bb){
			for(k=0; k<bb; k++)
				s[len++] = t[ i*col*bb + j++ ];
		}
	}
}	

void set_picture(int bb, int no, char s[], char t[], int row, int col, int rb, int cb){
	int i, j, k=0, len=0;
	for(i=0+(no/rb)*(row/rb); i<(row/rb)+(no/rb)*(row/rb); i++){
		for(j=0+(no%cb)*(col/cb); j<(col/cb)+(no%cb)*(col/cb); j++){
			for(k=0; k<bb; k++)
				s[ (i*col + j)*bb + k ] = t[len++];
		}
	}
}


int main(int argc, char **argv){
	int fd, fds[100], plen=0;
	char printpath[] = "/dev/fb0";
	char dir_path[] = "/test";
	char tmp_path[123];
	
	DIR * pic_dir = opendir(dir_path);
	struct dirent * pic_dirent;

	while( ( pic_dirent = readdir( pic_dir ) ) != NULL ){
		if( strstr(pic_dirent->d_name, ".bmp") != NULL ){
			snprintf(tmp_path, 111, "%s/%s", dir_path, pic_dirent->d_name);
			fds[plen] = open(tmp_path, O_RDWR);
			if( fds[plen] < 0 ){
				perror("ERROR!\n");
				return -1;
			}
			plen++;
		}
	};

	fd = open(printpath, O_RDWR);
	if( fd<0 ){
		perror("ERROR");
		return -1;
	}

	int i=0, cnt, part = 9;
	while( 1 ){
		for(cnt=0; cnt<part; cnt++){

			lseek(fds[i], 54, SEEK_SET);
			read(fds[i], picture, 480*800*3);
			
			compress_picture(3, pcom[i], picture, 480, 800, 2, 2);
			set_picture(3, cnt, p_pic, pcom[i], 480, 800, 2, 2);
			
			i = (i+1)%plen;
		}
		
			execute_picture(p_pic);
			lseek(fd, 0, SEEK_SET);
			write(fd, p_pic, 800*480*4);
		
			sleep(3);
	}
	for(i=0; i<plen; i++)
		close(fds[i]);
	close(fd);
	return 0;
}


/*
		for(i=0; i<plen; i++){
			
			//srand(time(NULL));			i = rand()%plen;
			
			lseek(fds[i], 54, SEEK_SET);
			read(fds[i], picture, 800*480*3);
			execute_picture(picture);
			//re_row(p_tmp, picture, 480, 800);

			compress_picture(picture, p_tmp, 480, 800, 2, 2);
			set_picture(p_pic, picture, s_d[i][0], s_d[i][1], 240, 400);
			
			//set_picture(p_pic, picture, (i%2*240*800)+(i%2*400), 400, 240, 400);
		}
		*/





/*
void compress_picture(char s[], char t[], int row, int col, int rb, int cb){
	int i, j, k, len=0;
	col *= 4;
	cb *= 4;
	for(i=0; i<row; i+=rb){
		for(j=0; j<col; j+=cb){
			for(k=0; k<4; k++){
				s[len++] = t[ i*col + j + k ];
			}
		}
	}
}
*/

/*
void set_picture(char s[], char t[], int start, int dis, int row, int col){
	int i, j, k;
	start *= 4;
	dis *= 4;
	col *= 4;
	for(i=0, k=start; i<row; i++){
		for(j=0; j<col; j++, k++){
			s[k] = t[ i*col + j ];
		}
		k += dis;
	}
}
*/







【个人代码,按键控制图片缩放】

本来还想加个 缩略图 随机位置显示的,可是没成功 picture_xy() 函数。

#include <sys/types.h>
#include <sys/stat.h>
#include <fcntl.h>
#include <unistd.h>
#include <dirent.h>
#include <string.h>
#include <time.h>
#include <stdlib.h>
#include <errno.h>
#include <stdio.h>
#include <stdarg.h>
#include <linux/input.h>

#define PRINT_PATH		"/dev/fb0"
#define BUTTON_PATH		"/dev/event1"
#define DIR_PATH		"/test"
#define PIC_NAME		".bmp"
#define MUSIC_NAME		".mp3"
#define MUSIC_PLAY		"madplay"
#define MUSICS			"1.mp3"

int fd, fkey;
int options;
int pics[100], pic_count=0;
char nametmp[123];

char picture[480*800*4];
char p_tmp[480*800*4];
char part[16][480*800*3];
char pic_now[480*800*4];

struct input_event key_event;


void execute_picture(char picture[]){
	int i, j, len = 800*480*3;
	for(i=0, j=480*800*4-1; i<800*480*3; i+=3){
		p_tmp[j-3] = picture[i];
		p_tmp[j-2] = picture[i+1];
		p_tmp[j-1] = picture[i+2];
		j -= 4;
	}
	memcpy(picture, p_tmp, 480*800*4);
	
	/*
	for(i=0, j=0; i<len; i++, j++){
		if( j%4==3 ){
			p_tmp[j] = 0x33;
			j++;
		}
		p_tmp[j] = picture[i];
	}
	memcpy(picture, p_tmp, 800*480*4);
	*/
	//re_row(picture, p_tmp, 480, 800);
}

void execute_picture000(char picture[]){
	int i, j, len = 800*480*3;
	for(i=0, j=0; i<len; i++, j++){
		if( j%4==3 ){
			p_tmp[j] = 0x33;
			j++;
		}
		p_tmp[j] = picture[i];
	}
	memcpy(picture, p_tmp, 800*480*4);
}

void re_row(char s[], char t[], int row, int col){
	int i, j;
	col *= 4;
	for(i=0; i<row; i++)
		for(j=0; j<col; j++)
			s[ (row-1-i)*col + j ] = t[ i*col + j ];
}



void compress_picture(int bb, char s[], char t[], int row, int col, int rb, int cb){
	int i, j, k, len=0;
	for(i=row-1; i>=0; i-=rb){
		for(j=0; j<col*bb; j+=bb){
			for(k=0; k<bb; k++)
				s[len++] = t[ i*col*bb + j++ ];
		}
	}
}	

void xy_picture(int bb, int x, int y, char s[], char t[], int dis, int row, int col){
	int i, j, now=0, len=0;
	for(i=0; i<row; i++){
		for(j=0; j<col*bb; j++){
			s[ i*col*bb + j + now ] = t[len++];
		}
		now += dis*bb;
	}
}

void set_picture(int bb, int no, char s[], char t[], int row, int col, int rb, int cb){
	int i, j, k=0, len=0;
	for(i=0+(no/rb)*(row/rb); i<(row/rb)+(no/rb)*(row/rb); i++){
		/*
		for(j=0+(no%cb)*(col/cb)*bb; j<(col/cb)*bb+(no%cb)*(col/cb)*bb; j++){
			for(k=0; k<3; k++)
				s[i*col + j] = t[len++];
			j++;
		}
		*/
		
		for(j=0+(no%cb)*(col/cb); j<(col/cb)+(no%cb)*(col/cb); j++){
			for(k=0; k<bb; k++)
				s[ (i*col + j)*bb + k ] = t[len++];
		}
		
	}
}


void picture_origin(int pic_fd){
	lseek(pic_fd, 54, SEEK_SET);
	read(pic_fd, picture, 480*800*3);
	execute_picture(picture);
	lseek(fd, 0, SEEK_SET);
	write(fd, picture, 480*800*4);
}

void picture_mini(int pic_fd){
	int i;
	lseek(pic_fd, 54, SEEK_SET);
	read(pic_fd, picture, 480*800*3);		/* 24bit */
	compress_picture(3, p_tmp, picture, 480, 800, 2, 2);
	for(i=0; i<4; i++){
		set_picture(3, i, picture, p_tmp, 480, 800, 2, 2);
	}
	execute_picture000(picture);
	//re_row(picture, pic_now, 480, 800);
	lseek(fd, 0, SEEK_SET);
	write(fd, picture, 480*800*4);
}

void picture_xy(int pic_fd){
	int i, x, y, color;
	x = rand()%240;
	y = rand()%400;
	color = (char)(rand()%256);
	
	lseek(pic_fd, 54, SEEK_SET);
	read(pic_fd, picture, 480*800*3);		/* 24bit */
	compress_picture(3, p_tmp, picture, 480, 800, 2, 2);
	memset(picture, (char)color, 480*800*3);
	
	xy_picture(3, x, y, picture, p_tmp, 800/2, 480, 800);
	
	execute_picture000(picture);
	//re_row(picture, pic_now, 480, 800);
	lseek(fd, x*800*4+y*4, SEEK_SET);
	write(fd, picture, 480*800*4);
}

int no;
void solve(int pic_fd){
	read(fkey, &key_event, sizeof(key_event));
	
		if( key_event.type == EV_KEY ){
			
			if( key_event.code == KEY_LEFT && key_event.value == 1 ){
				puts("KEY_LEFT");
				no = (no+1)%pic_count;
				options = 0;
			}
			else if( key_event.code == KEY_RIGHT && key_event.value == 1 ){
				puts("KEY_RIGHT");
				no = (no+1)%pic_count;
				options = 1;
			}
			else if( key_event.code == KEY_DOWN && key_event.value == 1 ){
				puts("KEY_DOWN");
				no = (no+1)%pic_count;
				options = 2;
			}
			else if( key_event.code == KEY_UP && key_event.value == 1 ){
				puts("KEY_UP");
				snprintf(nametmp, 111, "./%s %s", MUSIC_PLAY, MUSICS);
				system(nametmp);			//system("./madplay 1.mp3");
			}
		}

	pic_fd = pics[no];
	
	switch( options ){
		case 0:	
			picture_origin(pic_fd);
			//sleep(3);
			break;
		case 1:
			picture_mini(pic_fd);
			//sleep(3);
			break;
		case 2:	
			picture_xy(pic_fd);
			//sleep(2);
			break;
		default:
			printf(" hoooooooooo \n");
	}

		
}



int main(){
	fd = open(PRINT_PATH, O_RDWR);
	if( fd < 0 ){
		perror("OPEN PRINT_PATH Error !\n");
		return -1;
	}
	
	DIR * pic_dir = opendir(DIR_PATH);
	struct dirent * pic_dirent;
	
	while( ( pic_dirent = readdir( pic_dir ) ) != NULL ){
		if( ( strstr(pic_dirent->d_name, PIC_NAME) ) != NULL ){
			snprintf(nametmp, 111, "%s/%s", DIR_PATH, pic_dirent->d_name);
			pics[pic_count] = open(nametmp, O_RDWR);
			if( pics[pic_count] < 0 ){
				perror("OPEN nametmp Error !\n");		
				return -1;
			}
			pic_count++;
		}
	}

	
	fkey = open(BUTTON_PATH, O_RDWR);
	if( fkey < 0 ){
		perror("OPEN BUTTON_PATH Error !\n");
		return -1;
	}
	
	
	
	int i, j;
	srand( time(NULL) );
	while( 1 ){
		
		//for(i=0; i<pic_count; i++){
			//picture_origin(pics[i]);
			solve(pics[no]);
			//sleep(1);
		//}
	} 
	

	close(fd);
	close(fkey);
	return 0;
}

















最后,END

  • 1
    点赞
  • 16
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值