当前位置:   article > 正文

基于ARM开发板的嵌入式项目设计(C完整代码)_基于arm的嵌入式设计

基于arm的嵌入式设计

大三马上就进入尾声了,这次的小学期也算是不负所望,比较有意思,学到了许多东西。

接下来就展开说说,首先是对arm开发板的认识,再到和VM虚拟机Linux的交互操作,最后是钢琴小项目的完成过程。

一、arm开发板简述

A:A8(GEC210)单核,A53(GEC6818)八核

R:面向实时性的一些产品

M:M3,M4

函数详解
http://【金山文档】 函数详解 https://kdocs.cn/l/cqWbx504NxuN

1.GEC6818开发平台,核心板采用10层板工艺设计,确保稳定可靠。

2.该平台搭载三星Cortex-A53系列高性能八核处理器S5P6818,最高主频高达1.4GHz

3.开发板留有丰富的外设,支持千兆以太网、板载LVDS接口、MIPI接口、USB接口等。

4.可应用于嵌入式LinuxAndroid等操作系统的驱动、应用开发。

5.搭载7.0英寸LCD屏支持32位真彩色,触摸屏使用电容屏触点多达1,536,000个以上0761df5ca1f44a64a0318787c78677d1.jpeg6ea2f073ab72420d80bf257481fcc2ca.png

 设备清单

设备备注
GEC6818开发平台
母对母串口线与电脑通信
电源线提供电源
安卓USB烧写系统
网线开发板联网
USB转串口线与电脑通信
secureCRT终端仿真程序
CH340USB转串口驱动

二、具体步骤

1、安装VMware和Ubuntu

万万没想到这个过程也会出问题,由于今年换了新电脑,出厂就是win11的系统,对老师给的虚拟机不兼容,这个时候就会出现电脑一直重启的过程。最后下载了最新的 版本得以解决(但又由于序列号的问题最后选择了试用30天,这个倒是无伤大雅)

2、(1)安装usb转串口的驱动
      (2)安装secureCRT超级终端软件

2、交叉编译:

每一个不同的平台可执行程序的格式都不尽相同,我们需要在搭载Linux的ARM平台执行程序,故需要使用arm-linux交叉编译工具

普通编译:gcc 源程序 -o 目标文件  gcc:编译工具

交叉编译:arm-linux-gcc 源程序 -o  目标文件  -o:生成可执行文件

3、项目开发流程:

1、使用C语言编写项目源代码

2、使用交叉编译工具编译项目源码

3、将编译生成的可执行程序下载到ARM开发板

4、在ARM开发板执行项目程序

5、验证项目程序的准确性

三、项目作业总结:

 

(1)以德国国旗的样式颜色为例(无不良引导和个人逾矩及不尊重他国行为)

【注】传送文件到开发板的两种方法:

方法一:
[root@GEC6818 /]#mkdir 文件名
[root@GEC6818 /]#cd 文件名/
[root@GEC6818 /文件名]#ls
[root@GEC6818 /文件名]#rx 传输文件名  (传输---发送Xmode)
CCCCCC
开始 xmodem 传输。  按 Ctrl+C 取消。
  100%       5 KB    5 KB/s 00:00:01       0 Errors

方法二:(最常用)
[root@GEC6818 /文件名]#rx 传输文件名  (用鼠标直接拖进来)
CCCC
开始 xmodem 传输。  按 Ctrl+C 取消。
  100%       5 KB    5 KB/s 00:00:01       0 Errors
 

代码如下:

  1. #include <stdio.h>
  2. #include <sys/types.h>
  3. #include <sys/stat.h>
  4. #include <fcntl.h>
  5. #include <unistd.h>
  6. int main()
  7. {
  8. //定义一个lcd的buf
  9. int buf[800*480] = {2};
  10. int black = 000000;
  11. int red = FF0000;
  12. int yellow = FFFF00;
  13. //写LCD
  14. int x;//x表示横轴
  15. int y;//y表示纵轴
  16. for(y=0;y<160;y++)
  17. {
  18. for(x=0;x<800;x++)
  19. {
  20. buf[y*800+x] = black;
  21. }
  22. }
  23. for (y = 160; y < 320; y++)
  24. {
  25. for (x = 0; x < 800; x++)
  26. {
  27. buf[y * 800 + x] = red;
  28. }
  29. }
  30. for (y = 320; y < 480; y++)
  31. {
  32. for (x = 0; x < 800; x++)
  33. {
  34. buf[y * 800 + x] = yellow;
  35. }
  36. }
  37. //写LCD
  38. write(fd,buf,800*480*4);
  39. //关闭文件
  40. close(fd);
  41. return 0;//正常退出
  42. }

输出结果如下图:

(2)球球大作战,动态的小球碰撞,此处以两个小球为例:

  1. #include <stdio.h>
  2. #include <sys/types.h>
  3. #include <sys/stat.h>
  4. #include <fcntl.h>
  5. #include <unistd.h>
  6. #include <sys/mman.h>
  7. int main()
  8. {
  9. int fd;
  10. fd = open("/dev/fb0",O_RDWR);
  11. if(fd<0)
  12. {
  13. printf("open icd fail");
  14. return -1;
  15. }
  16. //lcd映射(效率高)
  17. int *addr;
  18. addr = mmap(NULL,
  19. 800*480*4, //长度
  20. PROT_READ|PROT_WRITE, //权限
  21. MAP_SHARED, //标志量
  22. fd, //文件描述符
  23. 0 //偏移量
  24. );
  25. int red=0x00ff0000;
  26. int green=0x0000ff00;
  27. int blue=0x000000ff;
  28. int black=0x00000000;
  29. int white=0x00ffffff;
  30. int gold=0x00FFD700;
  31. int fen = 0x00ff80c0;
  32. int color[]={green,red,blue,fen,black,gold};
  33. int c1=1,c2=0;
  34. int x,y;
  35. int a=400,b=240,r=50;
  36. int m=3,n=6; //移动速度
  37. int a1 = 600,b1 = 300,r1 = 80;//一大一小两球
  38. int m1=3,n1=6;
  39. while(1)
  40. {
  41. for(y=0;y<480;y++)
  42. {
  43. for(x=0;x<800;x++)
  44. {
  45. //背景色
  46. *(addr+y*800+x)=white;
  47. //圆1
  48. if((x-a)*(x-a)+(y-b)*(y-b)<=r*r)
  49. *(addr+y*800+x)=color[c1];
  50. //圆2
  51. if((x-a1)*(x-a1)+(y-b1)*(y-b1)<=r1*r1)
  52. *(addr+y*800+x)=color[c2];
  53. }
  54. }
  55. //颜色循环
  56. if(c1>5)c1=0;
  57. if(c2>5)c2=0;
  58. //圆1反弹
  59. a+=m,b+=n;
  60. if(a>800-r || a<r)
  61. {
  62. m=0-m;
  63. c1++;
  64. }
  65. if(b>480-r || b<r)
  66. {
  67. n=0-n;
  68. c1++;
  69. }
  70. //圆2反弹
  71. a1+=m1,b1+=n1;
  72. if(a1>800-r1 || a1<r1)
  73. {
  74. m1=0-m1;
  75. c2++;
  76. }
  77. if(b1>480-r1 || b1<r1)
  78. {
  79. n1=0-n1;
  80. c2++;
  81. }
  82. if((a1-a)*(a1-a)+(b1-b)*(b1-b)<=(r1+r)*(r1+r))
  83. {
  84. //两球相碰反弹
  85. m=0-m;n=0-n;
  86. m1=0-m1;n1=0-n1;
  87. c1++;
  88. c2++;
  89. }
  90. }
  91. close(fd);
  92. return 0;
  93. }

输出要求及效果图如下:

9df8cb6e9c5a46358101422f6066c0bc.png

aaddf741397f45f4aceb15b997df5cfd.jpeg cca2bd0e19f44564b7fa33490096c131.jpeg

 

 

(3)BMP图片的轮播输出(此处以三张照片为例)

BMP简述:全称Bitmap是Windows操作系统中的标准图像文件格式,可以分成两类:设备相关位图(DDB)和设备无关位图(DIB),使用非常广。它采用位映射存储格式,除了图像深度可选以外,不采用其他任何压缩,因此,BMP文件所占用的空间很大。BMP文件的图像深度可选lbit、4bit、8bit及24bit。BMP文件存储数据时,图像的扫描方式是按从左到右、从下到上的顺序。

采用BMP格式图片的优点是我们可以很方便的得到图片像素数据,而使用JPG/JPEG格式图片则需要先解压图像数据后才可得到图像的像素数据。

  1. #include <stdio.h>
  2. #include <sys/types.h>
  3. #include <sys/stat.h>
  4. #include <fcntl.h>
  5. #include <unistd.h>
  6. #include <sys/mman.h>
  7. int show_bmp(int *addr,char *bmp_path)
  8. {
  9. //打开一张bmp图
  10. int fd_bmp;
  11. fd_bmp = open(bmp_path,O_RDWR);
  12. if(fd_bmp < 0)
  13. {
  14. printf("open bmp fail\n");
  15. return -1;//异常退出
  16. }
  17. //去除掉bmp图片的头54个字节
  18. lseek(fd_bmp,54,SEEK_SET);
  19. char buf_bmp[800*480*3];
  20. //读取bmp图
  21. read(fd_bmp,buf_bmp,800*480*3);
  22. //写LCD
  23. int x;//x表示横轴
  24. int y;//y表示纵轴
  25. for(y=0;y<480;y++)
  26. {
  27. for(x=0;x<800;x++)
  28. {
  29. *(addr+(479-y)*800+x) = buf_bmp[(y*800+x)*3] |(buf_bmp[(y*800+x)*3+1]<<8) |(buf_bmp[(y*800+x)*3+2]<<16);
  30. }
  31. }
  32. close(fd_bmp);
  33. return 0;
  34. }
  35. int main()
  36. {
  37. //打开LCD
  38. int fd_lcd;
  39. fd_lcd = open("/dev/fb0",O_RDWR);
  40. if(fd_lcd < 0)
  41. {
  42. printf("open lcd fail\n");
  43. return -1;//异常退出
  44. }
  45. //lcd的映射
  46. int *addr;
  47. addr = mmap(NULL,800*480*4, PROT_READ|PROT_WRITE,MAP_SHARED,fd_lcd,0);
  48. if(addr == NULL)
  49. {
  50. printf("mmap fail\n");
  51. return -1;
  52. }
  53. show_bmp(addr,"1.bmp");//第一张
  54. show_bmp(addr,"2.bmp");//第二张
  55. show_bmp(addr,"3.bmp");//第三张
  56. //lcd的映射的释放
  57. munmap(addr,800*480*4);
  58. //关闭文件
  59. close(fd_lcd);
  60. return 0;//正常退出
  61. }

输出效果图如下:

2f4884526cca414db3d8fd8a824db1f5.jpeg

 

(4)小钢琴制作

项目要求:可以正常弹奏,可以做出物理按键的key_on和key_off的区别,好的UI设计。

这是最后一个项目,需要用到jpg图片,所以需要对于基础知识安装jpg库有一定要求(具体安装步骤如有疑问可在评论区留言);mp3文件的拖入以及UI设计,参考网上的代码进行整体架构。

(小插曲)由于LIinux虚拟机里都安装成功了,ls下也都齐全,我就默认开发板也有jpg库,忘记最后一步在开发板拖入libjpeg.so.9导致一直不知道问题出在哪里。

代码如下:(黑键有一些小问题,因为白键有key_on和key_off的两种显示,对应的jpg图片和像素点都是算好的,而黑键在两个白键中间,虽然也可以显示可以弹奏,但就像没有设置优先级一样,没办法将黑键永远置顶以至于一按周围的白键,黑键就会消失,再按一次可以显示。试了很多种方法都不行,算是一个小小的遗憾吧,答辩的时候只能将此作为一个按键的不同表现形式。)

  1. #include <stdio.h>
  2. #include "lcdjpg.h"
  3. #include <stdio.h>
  4. #include <sys/types.h>
  5. #include <sys/stat.h>
  6. #include <fcntl.h>
  7. #include <unistd.h>
  8. #include <linux/input.h>
  9. #include <stdlib.h>
  10. int fd;
  11. int get_xy(int *x,int *y)
  12. {
  13. struct input_event ts;
  14. while(1)
  15. {
  16. //读触摸屏
  17. read(fd,&ts,sizeof(struct input_event));
  18. if(ts.type==EV_ABS&&ts.code==ABS_X)
  19. {
  20. *x= ts.value*800/1024;
  21. //printf("x=%d ",ts.value*800/1024);//x轴的坐标(黑色触摸屏)1024*600
  22. //printf("x=%d ",ts.value);//x轴的坐标(蓝色触摸屏)800*480
  23. }
  24. if(ts.type==EV_ABS&&ts.code==ABS_Y)
  25. {
  26. *y=ts.value*480/600;
  27. //printf("y=%d\n",ts.value*480/600);//y轴的坐标(黑色触摸屏)
  28. //printf("y=%d\n",ts.value);//y轴的坐标(蓝色触摸屏)
  29. }
  30. if(ts.type==EV_KEY&&ts.code==BTN_TOUCH&&ts.value == 1)//按下 0表示松手
  31. {
  32. //printf("按下去 x=%d y=%d\n",x,y);
  33. break;
  34. }
  35. }
  36. }
  37. int main()
  38. {
  39. //打开触摸屏
  40. //int fd;
  41. fd = open("/dev/input/event0",O_RDWR);
  42. if(fd < 0)
  43. {
  44. printf("open ts fail\n");
  45. return -1;
  46. }
  47. lcd_draw_jpg(0,0,"./background.jpg",NULL,0,0);
  48. lcd_draw_jpg(233,350,"./logo.jpg",NULL,0,0);
  49. lcd_draw_jpg(0,0,"./bar.jpg",NULL,0,0);
  50. lcd_draw_jpg(60,48,"./key_off.jpg",NULL,0,0);
  51. lcd_draw_jpg(111,48,"./black1.jpg",NULL,0,0);
  52. lcd_draw_jpg(128,48,"./key_off.jpg",NULL,0,0);
  53. lcd_draw_jpg(179,48,"./black1.jpg",NULL,0,0);
  54. lcd_draw_jpg(196,48,"./key_off.jpg",NULL,0,0);
  55. lcd_draw_jpg(264,48,"./key_off.jpg",NULL,0,0);
  56. lcd_draw_jpg(315,48,"./black1.jpg",NULL,0,0);
  57. lcd_draw_jpg(332,48,"./key_off.jpg",NULL,0,0);
  58. lcd_draw_jpg(383,48,"./black1.jpg",NULL,0,0);
  59. lcd_draw_jpg(400,48,"./key_off.jpg",NULL,0,0);
  60. lcd_draw_jpg(468,48,"./key_off.jpg",NULL,0,0);
  61. lcd_draw_jpg(519,48,"./black1.jpg",NULL,0,0);
  62. lcd_draw_jpg(536,48,"./key_off.jpg",NULL,0,0);
  63. lcd_draw_jpg(587,48,"./black1.jpg",NULL,0,0);
  64. lcd_draw_jpg(604,48,"./key_off.jpg",NULL,0,0);
  65. lcd_draw_jpg(655,48,"./black1.jpg",NULL,0,0);
  66. lcd_draw_jpg(672,48,"./key_off.jpg",NULL,0,0);
  67. int x=0,y=0;
  68. while(1)
  69. {
  70. get_xy(&x,&y);
  71. printf("x=%d y=%d\n",x,y);
  72. //白键定位区域
  73. if(x>60&&x<128&&y>48&&y<328)
  74. {
  75. system("killall -SIGKILL madplay");
  76. system("madplay d3.mp3&");
  77. if(x>60&&x<128)
  78. lcd_draw_jpg(60,48,"./key_on.jpg",NULL,0,0);
  79. sleep(0.8);
  80. lcd_draw_jpg(60,48,"./key_off.jpg",NULL,0,0);
  81. }
  82. if(x>128&&x<196&&y>48&&y<328)
  83. {
  84. system("killall -SIGKILL madplay");
  85. system("madplay d4.mp3&");
  86. if(x>128&&x<196)
  87. lcd_draw_jpg(128,48,"./key_on.jpg",NULL,0,0);
  88. sleep(0.8);
  89. lcd_draw_jpg(128,48,"./key_off.jpg",NULL,0,0);
  90. }
  91. if(x>196&&x<264&&y>48&&y<328)
  92. {
  93. system("killall -SIGKILL madplay");
  94. system("madplay d5.mp3&");
  95. if(x>196&&x<264)
  96. lcd_draw_jpg(196,48,"./key_on.jpg",NULL,0,0);
  97. sleep(0.8);
  98. lcd_draw_jpg(196,48,"./key_off.jpg",NULL,0,0);
  99. }
  100. if(x>264&&x<332&&y>48&&y<328)
  101. {
  102. system("killall -SIGKILL madplay");
  103. system("madplay d6.mp3&");
  104. if(x>264&&x<332&&x>315&&x<344)
  105. lcd_draw_jpg(264,48,"./key_on.jpg",NULL,0,0);
  106. sleep(0.8);
  107. lcd_draw_jpg(264,48,"./key_off.jpg",NULL,0,0);
  108. }
  109. if(x>332&&x<400&&y>48&&y<328)
  110. {
  111. system("killall -SIGKILL madplay");
  112. system("madplay d7.mp3&");
  113. if(x>332&&x<400)
  114. lcd_draw_jpg(332,48,"./key_on.jpg",NULL,0,0);
  115. sleep(0.8);
  116. lcd_draw_jpg(332,48,"./key_off.jpg",NULL,0,0);
  117. }
  118. if(x>400&&x<468&&y>48&&y<328)
  119. {
  120. system("killall -SIGKILL madplay");
  121. system("madplay d8.mp3&");
  122. if(x>400&&x<460)
  123. lcd_draw_jpg(400,48,"./key_on.jpg",NULL,0,0);
  124. sleep(0.8);
  125. lcd_draw_jpg(400,48,"./key_off.jpg",NULL,0,0);
  126. }
  127. if(x>468&&x<536&&y>48&&y<328)
  128. {
  129. system("killall -SIGKILL madplay");
  130. system("madplay d9.mp3&");
  131. if(x>468&&x<536)
  132. lcd_draw_jpg(468,48,"./key_on.jpg",NULL,0,0);
  133. sleep(0.8);
  134. lcd_draw_jpg(468,48,"./key_off.jpg",NULL,0,0);
  135. }
  136. if(x>536&&x<604&&y>48&&y<328)
  137. {
  138. system("killall -SIGKILL madplay");
  139. system("madplay d10.mp3&");
  140. if(x>536&&x<604)
  141. lcd_draw_jpg(536,48,"./key_on.jpg",NULL,0,0);
  142. sleep(0.8);
  143. lcd_draw_jpg(536,48,"./key_off.jpg",NULL,0,0);
  144. }
  145. if(x>604&&x<672&&y>48&&y<328)
  146. {
  147. system("killall -SIGKILL madplay");
  148. system("madplay d11.mp3&");
  149. if(x>604&&x<672)
  150. lcd_draw_jpg(604,48,"./key_on.jpg",NULL,0,0);
  151. sleep(0.8);
  152. lcd_draw_jpg(604,48,"./key_off.jpg",NULL,0,0);
  153. }
  154. if(x>672&&x<740&&y>48&&y<328)
  155. {
  156. system("killall -SIGKILL madplay");
  157. system("madplay d12.mp3&");
  158. if(x>672&&x<740)
  159. lcd_draw_jpg(672,48,"./key_on.jpg",NULL,0,0);
  160. sleep(0.8);
  161. lcd_draw_jpg(672,48,"./key_off.jpg",NULL,0,0);
  162. }
  163. //黑键1
  164. if(x>111&&x<145&&y>48&&y<258)
  165. {
  166. system("killall -SIGKILL madplay");
  167. system("madplay d1.mp3&");
  168. if(x>111&&x<145)
  169. lcd_draw_jpg(111,48,"./black.jpg",NULL,0,0);
  170. lcd_draw_jpg(111,48,"./black1.jpg",NULL,0,0);
  171. }
  172. //黑键2
  173. if(x>179&&x<213&&y>48&&y<258)
  174. {
  175. system("killall -SIGKILL madplay");
  176. system("madplay d2.mp3&");
  177. if(x>179&&x<213)
  178. lcd_draw_jpg(179,48,"./black.jpg",NULL,0,0);
  179. lcd_draw_jpg(179,48,"./black1.jpg",NULL,0,0);
  180. }
  181. //黑键3
  182. if(x>315&&x<349&&y>48&&y<258)
  183. {
  184. system("killall -SIGKILL madplay");
  185. system("madplay d1.mp3&");
  186. if(x>315&&x<349)
  187. lcd_draw_jpg(315,48,"./black.jpg",NULL,0,0);
  188. lcd_draw_jpg(315,48,"./black1.jpg",NULL,0,0);
  189. }
  190. //黑键4
  191. if(x>383&&x<417&&y>48&&y<258)
  192. {
  193. system("killall -SIGKILL madplay");
  194. system("madplay d2.mp3&");
  195. if(x>383&&x<417)
  196. lcd_draw_jpg(383,48,"./black.jpg",NULL,0,0);
  197. lcd_draw_jpg(383,48,"./black1.jpg",NULL,0,0);
  198. }
  199. //黑键5
  200. if(x>519&&x<553&&y>48&&y<258)
  201. {
  202. system("killall -SIGKILL madplay");
  203. system("madplay d1.mp3&");
  204. if(x>519&&x<553)
  205. lcd_draw_jpg(519,48,"./black.jpg",NULL,0,0);
  206. lcd_draw_jpg(519,48,"./black1.jpg",NULL,0,0);
  207. }
  208. //黑键6
  209. if(x>587&&x<621&&y>48&&y<258)
  210. {
  211. system("killall -SIGKILL madplay");
  212. system("madplay d2.mp3&");
  213. if(x>587&&x<621)
  214. lcd_draw_jpg(587,48,"./black.jpg",NULL,0,0);
  215. lcd_draw_jpg(587,48,"./black1.jpg",NULL,0,0);
  216. }
  217. //黑键7
  218. if(x>655&&x<689&&y>48&&y<258)
  219. {
  220. system("killall -SIGKILL madplay");
  221. system("madplay d1.mp3&");
  222. if(x>655&&x<689)
  223. lcd_draw_jpg(655,48,"./black.jpg",NULL,0,0);
  224. lcd_draw_jpg(655,48,"./black1.jpg",NULL,0,0);
  225. }
  226. }
  227. //关闭触摸屏
  228. close(fd);
  229. return 0;
  230. }
  231. /*
  232. 编译的方法: arm-linux-gcc *.c -o main -I./libjpeg -L./libjpeg -ljpeg
  233. */

UI设计如下:

目录

一、arm开发板简述

 设备清单

二、具体步骤

1、安装VMware和Ubuntu

2、交叉编译:

3、项目开发流程:

三、项目作业总结:

(1)以德国国旗的样式颜色为例(无不良引导和个人逾矩及不尊重他国行为)

  (2)球球大作战,动态的小球碰撞,此处以两个小球为例:

(3)BMP图片的轮播输出(此处以三张照片为例)

(4)小钢琴制作


 

9e9d1b6532a04e6db18778d95c3eee7d.png

效果展示如下:

8c1dd9db489e453194a041ba3c23c876.jpeg 

 这就是这次的所有分享了。

 

 

 

 

 

声明:本文内容由网友自发贡献,不代表【wpsshop博客】立场,版权归原作者所有,本站不承担相应法律责任。如您发现有侵权的内容,请联系我们。转载请注明出处:https://www.wpsshop.cn/w/繁依Fanyi0/article/detail/773106
推荐阅读
相关标签
  

闽ICP备14008679号