python - Numpy (OpenCV) 图像数组到 OpenGL 纹理 (pi3d)

标签 python opencv numpy opengl-es raspberry-pi

我正在使用 pi3d 在屏幕上显示一个 ImageSprite,其纹理来 self 正在加载的图像。

displayTexture = pi3d.Texture("display/display.jpg", blend=True, mipmap=True) 
displaySlide = pi3d.ImageSprite(texture=displayTexture, shader=shader, w=800, h=600)

这个纹理图像实际上是我在程序中创建的。这是一个 openCV2 图像,因此只是一个 numpy 数组。目前我保存它只是为了将它作为纹理再次加载,但是有没有办法用不断变化的 numpy 数组值不断更新 Sprite 的纹理?

我查看了 openCV OpenGL 支持,但据我所知,它现阶段仅支持 Windows,因此不适合这种用途。

编辑:应该提到我也很高兴有一个较低级别的解决方案。我目前正在尝试在图像数组上使用 .toString() 并将生成的字节列表与 glTexImage2D 一起使用来生成纹理,但到目前为止还没有骰子。

最佳答案

是的,您可以将 PIL.Image 传递给 pi3d.Texture,它将使用它创建一个新的纹理。那里涉及一些工作,所以如果它是一个大纹理,它会影响帧速率。此外,您还需要更新保存纹理数组的缓冲区中的指针,以便使用新的纹理。

有一种方法可以将 numpy 数组加载到 PIL.Image (Image.fromarray()),因此这是一条简单的路线。然而,它有点复杂,因为 pi3d 已经将 PIL.Image 转换为一个 numpy 数组,请参阅 https://github.com/tipam/pi3d/blob/master/pi3d/Texture.py#L163

下面的代码可以作为 pi3d.Texture 工作的捷径,但调用“私有(private)”函数 _load_opengl 有点麻烦。我可能会考虑制作一种更强大的方法来执行此操作(即将视频映射到 3D 对象等)

#!/usr/bin/python
from __future__ import absolute_import, division, print_function, unicode_literals

import demo
import pi3d
import random
import numpy as np
from PIL import Image, ImageDraw
DISPLAY = pi3d.Display.create(x=150, y=150)
shader = pi3d.Shader("uv_flat")
im = Image.open("textures/PATRN.PNG")
#draw = ImageDraw.Draw(im) # there are various PIL libraries you could use
nparr = np.array(im)
tex = pi3d.Texture(im) # can pass PIL.Image rather than path as string
sprite = pi3d.ImageSprite(tex, shader, w=10.0, h=10.0)
mykeys = pi3d.Keyboard()
while DISPLAY.loop_running():
  #draw.line((random.randint(0,im.size[0]),
  #           random.randint(0,im.size[1]),
  #           random.randint(0,im.size[0]),
  #           random.randint(0,im.size[1])), fill=128) # draw random lines
  #nparr = np.array(im)
  nparr += np.random.randint(-2, 2, nparr.shape) # random noise
  tex.image = nparr
  tex._load_opengl()
  sprite.draw()
  if mykeys.read() == 27:
    mykeys.close()
    DISPLAY.destroy()
    break

PS 我不记得切换到 numpy 纹理的 pi3d 版本是什么,但它是最近的,所以你可能需要升级

编辑:

从 Texture.image 作为字节对象到 numpy 数组的转换是 v1.14 发布于 18Mar15

阐明使用 numpy 数组初始化和刷新变化图像的步骤:

...
im = Image.fromarray(cv2im)       # cv2im is a numpy array
tex = pi3d.Texture(im)            # create Texture from PIL image
sprite = pi3d.ImageSprite(tex, shader, w=10.0, h=10.0)
...
  tex.image = cv2im               # set Texture.image to modified numpy array
  tex._load_opengl()              # re-run OpenGLESv2 routines

关于python - Numpy (OpenCV) 图像数组到 OpenGL 纹理 (pi3d),我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/30066324/

相关文章:

python - 我可以将 3 个大小相同的子图排列成三角形吗?

Python Opencv 仅将颜色减少为 RGB

python - 获取 numpy 数组中 N 个最大值的索引,并随机打破平局

python - Pandas 直方图的权重

python - 过滤嵌套列表

c++ - "The C++ compiler "/usr/bin/c++ "is not able to compile a simple test program."尝试安装 OpenCV 时

opencv - SWT基于投票的色彩还原

opencv - OpenCV:对齐多个图像时内存损坏

python - numpy数组形状的差异

python - 代码看起来 "not pythonic"- 嵌套 np.where() 将列添加到 pd.dataframe