00零基础7-2
为第十届广东科学中心创意机器大赛,写了一系列的零基础入门代码,进行了详细注释
实在没有太多时间,如果有错,请指出,以后会少写点注释了,比写代码花的时候还要多。by傅20210828
希望对于热爱编程的学生有所帮助。前面的ShowCN1函数,显示小字还勉强,显示大字太慢了!!
如何进行优化呢?请仔细看思路
下面展示一些 内联代码片
。
from machine import I2C, Pin
from ssd1306 import SSD1306_I2C
import time
oled = None
def check():
global oled
while True:
i2c = I2C(scl=Pin(2), sda=Pin(14))
addr = i2c.scan()
if len(addr):
oled = SSD1306_I2C(128, 64, i2c, addr=addr[0])
oled.write_cmd(0xA0)
oled.write_cmd(0xC0)
oled.text("OLED OK!",10,10)
oled.show()
time.sleep_ms(300)
break
else:
print("连接128*64的OLED屏不成功,当前代码的管脚要求GPIO2和GPIO14")
return
#还是一样的字模数据:
fonts = {
"科": # 32号,宋体
[0x00,0x00,0x00,0x00,0x00,0x07,0x38,0x00,0x00,0x00,0x00,0x00,0x3F,0x00,0x00,0x01,0x01,0x03,0x02,0x06,
0x04,0x08,0x10,0x20,0x40,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x0C,0x3C,0xE0,0xC0,0xC0,
0xC0,0xC0,0xC0,0xC4,0xFE,0xC0,0xC0,0xC0,0xF0,0xDC,0xCC,0xC4,0xC4,0xC1,0xC6,0xC0,0xC0,0xC0,0xC0,0xC0,
0xC0,0xC0,0x80,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x60,0x30,0x18,0x18,0x00,0x00,0x00,0x40,0x60,
0x30,0x10,0x00,0x00,0x0F,0xF0,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x80,0xE0,
0xC0,0xC0,0xC0,0xC0,0xC0,0xC0,0xC0,0xC0,0xC0,0xC0,0xC0,0xC0,0xC0,0xC0,0xCC,0xFC,0xC0,0xC0,0xC0,0xC0,
0xC0,0xC0,0xC0,0xC0,0xC0,0xC0,0x80,0x00],#不要忘记这里和行末的逗号,隔开数据
"学": # 24号宋体
[0x00,0x00,0x04,0x02,0x03,0x01,0x01,0x1F,0x10,0x10,0x37,0x00,0x00,0x00,0x00,0x7F,0x00,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x00,0x20,0x30,0x18,0x18,0x18,0x01,0xFF,0x00,0x00,0xFF,0x01,0x02,0x04,0x08,0xFF,
0x08,0x08,0x08,0x08,0x98,0x78,0x10,0x00,0x00,0x40,0x60,0xC0,0x80,0x80,0x00,0xFC,0x0C,0x10,0xC0,0x80,
0x00,0x00,0x08,0xFC,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00],
"中":#16号宋体
[0x01,0x01,0x01,0x01,0x3F,0x21,0x21,0x21,0x21,0x21,0x3F,0x21,0x01,0x01,0x01,0x01,0x00,0x00,0x00,0x00,
0xF8,0x08,0x08,0x08,0x08,0x08,0xF8,0x08,0x00,0x00,0x00,0x00],
"心":#12号字,黑体,加粗
[0x00,0x03,0x01,0x01,0x06,0x36,0x36,0x76,0x66,0x66,0x06,0x06,0x07,0x00,0x00,0x00,0x80,0x80,0x00,0x38,
0x18,0x0C,0x0C,0x00,0x30,0x30,0xF0,0x00],
"K":# “科”,大号,48号字,黑体,加粗
[0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x01,0x0E,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x1F,0x00,0x00,
0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x01,0x03,0x07,0x06,0x0C,0x18,0x30,0x00,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x01,0x1F,0xFE,0x06,0x06,0x06,0x06,
0x06,0x06,0x06,0x06,0x06,0xFF,0x0E,0x0E,0x0E,0x1E,0x1F,0x3E,0x36,0x76,0x66,0xE6,0xC6,0x86,0x06,0x06,
0x06,0x06,0x06,0x06,0x06,0x0E,0x0E,0x0E,0x0E,0x0E,0x0E,0x0E,0x0E,0x08,0x00,0x00,0x00,0x00,0x00,0x10,
0x78,0xFC,0xF0,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x08,0x1C,0xFE,0x00,0x00,0x00,0x00,0x00,0xC0,
0x70,0x78,0x38,0x1C,0x18,0x08,0x00,0x01,0x1F,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x60,0x38,0x1E,0x0E,0x0E,0x06,0x00,
0x00,0x00,0x00,0x00,0x60,0x30,0x3C,0x1C,0x0E,0x0C,0x0C,0x00,0x00,0x00,0x07,0xF8,0x00,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x08,0x0E,0x0F,0x0C,0x0C,0x0C,
0x0C,0x0C,0x0C,0x0C,0x0C,0x0C,0x0C,0x0C,0x0C,0x0C,0x0C,0x0C,0x0C,0x0C,0x0C,0x0C,0x0C,0x0C,0x0C,0x0C,
0x0D,0x3E,0xEC,0x0C,0x0C,0x0C,0x0C,0x0C,0x0C,0x0C,0x0C,0x0C,0x0C,0x0E,0x0E,0x0E,0x0E,0x08,0x00,0x00,
0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x00,0x20,0x30,0x78,0xF8,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00],
"M":#“科”,拉长的,长24,宽16,非正方形,本程序将无法显示
[0x00,0x00,0x02,0x0E,0x78,0x08,0x08,0x08,0x0A,0x7C,0x08,0x08,0x1E,0x1A,0x2A,0x28,0x29,0x48,0x08,0x08,
0x08,0x08,0x08,0x00,0x00,0x00,0x08,0x08,0x08,0x48,0x48,0x08,0x08,0x08,0x88,0x48,0x48,0x4A,0x0E,0x38,
0xC8,0x08,0x08,0x08,0x08,0x08,0x08,0x00]
}
'''
=======================================
从数据入手,发现数据当中大量=零的数据,这在屏幕上全是黑点,是不用显示的,
如果跳过这些数据,程序应该会有较大改善,按此思路优化一下看看!
注意代码中优化的地方
=======================================
'''
def ShowCN2(ch_str, x_axis, y_axis):
global oled
words = 0
for k in ch_str:
byte_data = fonts[k]
data_len=len(byte_data)
ch_size=0
for i in range(8,65):
num=int((i-1)/8)+1
if((data_len/num)==i):
ch_size=i
break
if ch_size==0:
print(k,"字模,数据量不匹配,无法显示。")
else:
for i in range(0,num):
for y in range(ch_size*i,ch_size*(i+1)):
if(byte_data[y]!=0): ##优化: 8个点都不亮灯的数据直接跳过,速度能快蛮多!特别是针对大字,效果很明显
a = bin(byte_data[y]) ##优化:转换为2进制时,不再进行补0操作,字符串的增减操作是相对较慢的
ss=len(a) # 取得a字符串长度
for x in range(2,ss): # a是二进制的字符串,前面有“0b”,所以从2开始取字符。当然也可以在上面使用[2:]截取,但增加了操作
if(int(a[x])):#优化:只有发光的点才需要运行下面的描点语句,又能快一点点!
oled.pixel(x_axis +8-ss+ words + x+8*i, y % ch_size + y_axis, 1)#第三个参数直接置1=亮。
# 注意描点位置的变化:8-ss,因为a前面没有补0,直接在亮点的位置描亮点!
#也可以试试其他符号代替像素点,看看速度和显示效果:
#oled.fill_rect(x_axis +8-ss+ words + x+8*i, y % ch_size + y_axis, 1,1,int(a[x]))#用长宽都=1的正方形
#oled.fill_rect(x_axis +8-ss + words + x+8*i, y % ch_size + y_axis, 3,3,1)#试试看
#oled.text('/',x_axis +8-ss + words + x+8*i, y % ch_size + y_axis, int(a[x]))#用“/”符号
words += ch_size
oled.show()
'''
==============================================================================
调用函数,显示汉字,看看显示速度。速度提升明显!从原来的2000多毫秒,提升到约950毫秒
==============================================================================
'''
check()
oled.fill(0)#熄屏
print('请观察OLED屏,等待结果....')
starttime = time.ticks_us() #开始计时,统计时间,看看程序的效率
for i in range(4):#测试多次,求平均值
ShowCN2("心学K科", 0, 0)
endtime=time.ticks_diff(time.ticks_us(), starttime)/4000
print("ShowCN1显示4个字的平均时间:", endtime, "毫秒")
oled.text("OK!"+str(endtime)+"ms",0,52)
oled.show()