项目总结报告
- 项目介绍
本项目用硬禾学堂的基于树莓派rp2040的开发套件,制作了一款可操控其LCD屏及PC指针的“鼠标”。此次设计用micropython进行编程。
主要功能为控制电脑的鼠标移动及点击,实现鼠标功能,并在LCD显示屏上显示鼠标,可控制该鼠标的模式(对电脑或对LCD),并通过点击改变控制电脑的灵敏度。其中鼠标的模式(对电脑或对LCD)通过select键来改变,LCD的点击通过start键来操作。
- 设计思路
首先需写好画LCD屏上主界面的函数,要在LCD屏上显示“模式”、“灵敏度”两个信息。通过st7789显示屏的驱动程序历的函数及字体程序,进行绘图及文本显示。其中模式显示“PC”或“LCD”,由一个受select键所控制的参数决定。灵敏度条的显示状况由参数sensitivity决定,来画不同的显示状态。
然后要用micropython自带的machine库来配置GPIO口和ADC口,来实现数字输入和模拟输入,配置好各个按键。通过摇杆电位计使ADC接口输入不同参数,并通过参数来控制鼠标。
还要实现灵敏度的调节,通过判断LCD屏中鼠标的坐标及select键的状态来调整sensitivity参数。
- 硬件介绍
此套件芯片为树莓派Pico核心芯片RP2040,此芯片含30个GPIO接口,含5个ADC接口。开发套件包含一个摇杆,一个红外接收管,一个红外发射管,一个三轴姿态传感器MMA7660,一个蜂鸣器和USB-TypeC连接器用于供电、程序下载,含有一st7789为控制器的240*240的LCD显示屏,外接按键及LED灯。
但本次项目仅用到按键AB,按键select,按键start、LCD屏、摇杆电位计几个外接硬件。
- 实现的功能及图片展示
主要功能为控制电脑的鼠标移动及点击,实现鼠标功能,并在LCD显示屏上显示鼠标,可控制该鼠标的模式(对电脑或对LCD),并通过点击改变控制电脑的灵敏度。其中鼠标的模式(对电脑或对LCD)通过select键来改变,LCD的点击通过start键来操作。
主要代码说明(代码均有注释,不做额外说明,附件含代码)
- 遇到的难题及解决办法
首先是对鼠标的控制,刚开始我不知道硬禾学堂开源资料里含有hid库及其配置的固件,所以我刚开始打算用circruitpython进行编程,circruitpython有有关hid的扩展库,可以用pypi进行下载安装。
但是学好了circruitpython并写好控制鼠标的代码后,发现circruitpython没有有关st7789的驱动程序,无法简单地对显示屏进行编程。
于是又转回了micropython,找到了hid库及固件。
还有最基本的就是自己本身python没有学过,需要现学,对类、对象、方法灯概念及应用都不够熟悉。对python语言的运用不够熟练。以及对micropython和circruitpython的不熟悉。
还有一个问题就是鼠标在LCD屏上的移动,将前一个动作的鼠标融入背景,再画下一个鼠标,会出现鼠标闪烁的情况,这个到最后也没能解决。
- 未来的计划
首先如果有时间我会对本次项目进行一下优化改造,使其更加流畅等等。
我打算之后如果有空余时间尽量把没玩完的硬件都玩一遍,都自己动手进行下编程设计,提高自己对单片机及嵌入式系统的理解,提高下自己对python这门编程语言的熟练度。此次活动还有剩余的几个项目,我会挑几个自己感兴趣的来完成,提高下自己的综合能力。
- 总结
本次活动可以说是收获满满。首先提高了自己查资料的能力,并接触了树莓派及python中的micropython和circruitpython,提高了自己对嵌入式系统的理解。对图形编程有了更深的认识,对编程及项目构思能力有了提高。
import st7789
from fonts import vga2_8x8 as font1
from fonts import vga1_16x32 as font2
import board
import time
import hid
from machine import Pin,ADC
sensitivity=2
mode=1
#配置LCD的环境
st7789_res = 0
st7789_dc = 1
disp_width = 240
disp_height = 240
spi_sck=machine.Pin(2)
spi_tx=machine.Pin(3)
spi0=machine.SPI(0,baudrate=4000000, phase=1, polarity=1, sck=spi_sck, mosi=spi_tx)
display = st7789.ST7789(spi0, disp_width, disp_width,
reset=machine.Pin(st7789_res, machine.Pin.OUT),
dc=machine.Pin(st7789_dc, machine.Pin.OUT),
xstart=0, ystart=0, rotation=0)
#LCD指针坐标初始化
x=120
y=120
x_next=120
y_next=120
#画灵敏度条
def bar():
display.rect(30,150,180,60,0xffffff)
display.vline(90,150,60,0xffffff)
display.vline(150,150,60,0xffffff)
#LCD界面
def interface():
display.rect(10,10,220,220,0xffffff)
bar()
display.text(font1,"mode:",40,40)
if mode==1:
display.text(font2,"LCD",90,40)
if mode==0:
display.text(font2,"PC ",90,40)
display.text(font1,"sensitivity",75,135)
if sensitivity==1:
display.fill_rect(32,152,56,56,0x878700)
display.fill_rect(92,152,56,56,0x000000)
display.fill_rect(152,152,56,56,0x000000)
if sensitivity==2:
display.fill_rect(32,152,56,56,0x878700)
display.fill_rect(92,152,56,56,0x878700)
display.fill_rect(152,152,56,56,0x000000)
if sensitivity==3:
display.fill_rect(32,152,56,56,0x878700)
display.fill_rect(92,152,56,56,0x878700)
display.fill_rect(152,152,56,56,0x878700)
#画指针
def draw_cursor(x,y,color):
for i in range(10):
display.pixel(x+2*i,y+i,color)
for i in range(10):
display.pixel(x+10+i,y+10,color)
for i in range(20):
display.pixel(x,y+i,color)
for i in range(10):
display.pixel(x+i,y+20-i,color)
#画初始指针
draw_cursor(x,y,0xffffff)
#配置鼠标
mouse = hid.Mouse()
#配置两个adc引脚
ADC3_x=ADC(Pin(29))
ADC2_y=ADC(Pin(28))
#配置四个按键的GPIO引脚
left=Pin(5,Pin.IN,Pin.PULL_UP)
right=Pin(6,Pin.IN,Pin.PULL_UP)
select=Pin(8,Pin.IN,Pin.PULL_UP)
start=Pin(7,Pin.IN,Pin.PULL_UP)
while 1:
if select.value()==0:
mode=not mode
time.sleep(0.2)
#判断灵敏度
if y>150 and y<210:
if x>30 and x<90 and start.value()==0:
sensitivity=1
if x>90 and x<150 and start.value()==0:
sensitivity=2
if x>150 and x<180 and start.value()==0:
sensitivity=3
interface()
#得出摇杆两个方向的坐标(中央为(10,10)极值为0,20)
rocker_x=ADC3_x.read_u16()*20/65536
rocker_y=ADC2_y.read_u16()*20/65536
#摇杆控制
if rocker_x>11:
if mode==0:
mouse.move(x=1*sensitivity)
else:
x_next=x+2
if rocker_x>19:
if mode==0:
mouse.move(x=8*sensitivity)
else:
x_next=x+8
if rocker_x<9:
if mode==0:
mouse.move(x=-1*sensitivity)
else:
x_next=x-2
if rocker_x<1:
if mode==0:
mouse.move(x=-8*sensitivity)
else:
x_next=x-8
if rocker_y>11:
if mode==0:
mouse.move(y=1*sensitivity)
else:
y_next=y+2
if rocker_y>19:
if mode==0:
mouse.move(y=8*sensitivity)
else:
y_next=y+8
if rocker_y<9:
if mode==0:
mouse.move(y=-1*sensitivity)
else:
y_next=y-2
if rocker_y<1:
if mode==0:
mouse.move(y=-8*sensitivity)
else:
y_next=y-8
#
if x_next!=x or y_next!=y:
draw_cursor(x,y,0)
x=x_next
y=y_next
draw_cursor(x,y,0x0000ff)
#按键控制
if left.value()==0:
mouse.click(1)
time.sleep(0.2)
if right.value()==0:
mouse.click(2)
time.sleep(0.2)