我目前正在进行一个项目,以控制LED条纹连接到一个连接到Windows PC的Teensy 3.2板。它在技术上基于此项目: https://www.pjrc.com/teensy/td_libs_OctoWS2811.html
在vvvv中还实施了一个项目: https://vvvv.org/contribution/realtime-led-control-with-teensy3.xoctows2811
到目前为止,两个都工作得很好。我想做的是移植movie2serial程序(关于pjrc.com网站)到Python。你知道吗
所以我找到了这个项目: https://github.com/agwn/movie2serial_py
它不是开箱即用的,但经过一些修改,我让它运行起来。下面是我的类代码,它接收图像,将其转换为字节数组并将其发送到串行端口:
import serial
import numpy as np
class Teensy:
def __init__(self, port='COM3', baudrate=115200, stripes=4, leds=180):
self.stripes = stripes
self.leds = leds
self.connected = True
try:
self.port = serial.Serial(port, baudrate)
except:
self.connected = False
def close(self):
if not self.connected:
return
self.black_out()
self.port.close()
def send(self, image):
data = list(self.image2data(image))
data.insert(0, 0x00)
data.insert(0, 0x00)
data.insert(0, ord('*'))
if not self.connected:
return
self.port.write(''.join(chr(b) for b in data).encode())
def black_out(self):
self.send(np.zeros((self.leds,self.stripes,3), np.uint8))
def image2data(self, image):
buffer = np.zeros((8*self.leds*3), np.uint8)
byte_count = 0
order = [1,2,0]
for led in range(self.leds):
for channel in range(3):
for bit in range(8):
bits_out = 0
for pin in range(self.stripes):
if 0x80 >> bit & image[led,pin,order[channel]]:
bits_out |= 1 << pin
buffer[byte_count] = bits_out
byte_count += 1
return buffer
它正在工作,但速度很慢(在我的电脑上大约每秒13帧)。你知道吗
解释代码:我正在用cv2创建一个简单的动画,并将图像(numpy ndarray,4 x 180像素,因为我有4个LED条纹,每个都有180个LED)发送到Teensy实例的send方法。send方法将图像发送到image2data方法以将图像转换为字节数组,在开头放置几个字节并将整个内容发送到Teensy。你知道吗
此代码中有两个瓶颈:
但更重要的是:
访问图像阵列(方法image2data中的图像[led,pin,order[channel]]。当我将行更改为例如:
如果0x80>;位&255:
代码运行速度提高了6-7倍(~80fps)。顺便说一下,order[channel]用于将颜色从BGR转换为GRB。你知道吗
长话短说:从图像数组中读取颜色非常慢。如何在image2data方法中加速图像数组到字节数组的转换?你知道吗
当你说到这一点,感谢你的耐心:-)我很抱歉,为长期的职位,但这是一个复杂的项目,不容易为我解释。我真的很感激你的帮助,也许其他人可以从中受益。你知道吗
提前谢谢, 铝
第二个热点可以通过将
order[channel]
提升到内部循环之外(通过将channel_index = order[channel]
保存在order
之上的循环内部)来稍微改进,然后进行写入那将是一个小小的进步。看起来提升
0x80 >> bit
级别还可以节省8次冗余计算。把它另存为mask
,你就会加在一起,这些可能值得几帧。你知道吗
但是看看你的代码,那些循环嵌套的方式看起来有点不对劲。对于180 x 4 RGB LED,我希望您需要向Teensy发送180 x 4 x 3字节。但代码发送的是3 x 180 x 8。有没有可能两个内环需要倒过来?你知道吗
谢谢你的回答和改进。稍后我将实现它们,但我猜它们不会将帧速率提高到所需的60 FPS。你知道吗
代码发送3 x 180 x 8,因为电路板太小。LED通过以太网电缆连接到电路板,以太网电缆有8个管脚,所有8个管脚都需要寻址,否则条纹会显示奇怪的结果。另一方面,在以后的配置中,我需要4个以上的条带,因此目前我不想将数据发送到8个条带而不是4个条带。我不认为代码会运行得更快。你知道吗
当我在我的开场白中赚钱时,这段代码似乎非常慢,我不明白为什么: 图像[led、pin、顺序[channel]]
以下是处理草图中的代码,其运行速度至少是Python脚本的10倍:
我不敢相信Python比Java慢那么多。我仍然希望有人知道访问numpy数组的像素有什么问题。你知道吗
相关问题 更多 >
编程相关推荐