我的应用程序有两个方面,一方面我使用C ++来使用Pleora的EBUS SDK从相机读取帧。当首次接收到该流时,在将缓冲区转换为图像之前,我能够一次读取16位流,以便为每个像素执行一些计算,即每个像素存在16位数据块
现在下半部分是一个Django网络应用程序,我也提供了这个视频输出,这次是通过ffmpeg,nginx,hls流。当用户点击视频时,我希望能够获取当前帧及其点击的坐标,并执行与上述C ++部分相同的计算。
现在我使用html5画布捕获帧,我使用canvas.toDataURL()
将帧转换为base64编码图像,然后传递base64图像,坐标和框架的尺寸通过AJAX到python。
在python中,我试图以每像素16位的方式操作这个base64编码的图像。目前我做了以下事情:
pos = json.loads(request.GET['pos'])
str_frame = json.loads(request.GET['frame'])
dimensions = json.loads(request.GET['dimensions'])
pixel_index = (dimensions['width'] * pos['y']) + pos['x'] + 1
b64decoded_frame = base64.b64decode(str_frame.encode('utf-8'))
然而,b64decoded_frame
中的索引要少得多,那么图像中就有像素,而整数值并不像预期的那么高。我已经检查过,图像完好无损,因为我可以将其保存为png。
总结一下,如何将base64图像转换为序列化二进制流,其中每个像素由16位表示。
更新
我忘了提到我正在使用python3.2
经过一些更多的研究后,我认为我正在尝试做的是获得给定像素的mono16值。我不确定这是否是我想做的,但如果有人能解释如何将图像转换为mono16或像素转换为mono16我可以探索它,看看它是否实际上是解决方案。
答案 0 :(得分:0)
我选择的解决方案是将图像转换为8位灰度图像,然后将所需像素转换为16位对应图像。解决方案如下所示:
import base64
import io
from PIL import Image
if request.method == 'GET':
if request.GET['pos'] and request.GET['frame']:
pos = json.loads(request.GET['pos'])
str_frame = json.loads(request.GET['frame'])
# Converts the base64 string into a byte string, we need to encode
# str_frame as utf-8 first otherwise python3.2 complains about unicode
b64decoded_frame = base64.b64decode(str_frame.encode('utf-8'))
# This puts the decoded image into a buffer so that I don't need to save
# it to disk to use it in PIL
byte_stream = io.BytesIO(b64decoded_frame)
# Open the image and convert it to 8-bit greyscale (mono8)
img = Image.open(byte_stream).convert('L')
# Get the 8-bit pixel value
pixel_val = img.getpixel((pos['x'], pos['y']))
# Convert the 8-bit pixel value to 16-bit by holding the rations
# i.e. n8 / (2^8 - 1) == x16 / (2^16 - 1)
pixel_val = int(pixel_val / 255 * 65535)