1、实现思路
输入信号
常规sensor端输出视频数据为RAW格式,与我们熟知的RGB不同,该格式每个像素数据根据不同的位数常见为10位或12位。其排列方式如下图所示,每个格子都有一个感光元件去将透射到的光转化为电信号,最终由我们对其进行数字信号处理。
亮度计算
我们在很多软件平台上做图像处理会将RGB图像转换为灰度图像,这个灰度我们就可以理解为亮度。我们根据人眼对红色、绿色和蓝色的敏感程度不同将其进行加权计算出亮度信息,当然这个权值也有不同的标准,大家可以自行深入了解。
我们上述的是常规的软件平台上针对输入为RGB的格式图像,对于RAW的处理稍有不同,在RAW中我们将G通道还细分为了Gr(与R在同一行的G)和Gb(与B在同一行的G),这样对于Gr和Gb的分别根据科学方式加权可以得到更加真实的亮度信息。
总结
综上所述我们的目标就很明确了,统计R、Gr、Gb、B四个通道的均值计算亮度。同时为了提高自动曝光的性能,采取多区域的采集,将图像分割成32*32的区域分别统计。
2、Verilog实现思路
遍历方式
首先我们需要对我们划分格子的步长进行预设,余数可以舍弃也可以加到边缘的区域。将每行的像素隔一个相加,保证为同一个通道。在一个区域列步长结束后将该区域的和值用RAM存起来,当下下一行开始前再读取该值。在区域前两行时不用读取,直接在区域最后两行时不用存储,直接输出。
代码涉及其他内容就不贴了。讲解比较粗略,有细节问题实现问题可以私信(附上一份RAW的文本文件和python的转换代码方便大家尝试)
#RAW8转BGR
import cv2
import numpy as np
content = ""
with open('raw.txt', 'r') as f:
content = f.read()
x=content.split(' ')[0:160000]
xx=[]
for i in range(160000):
a = int(x[i], 16)
xx.append(a)
temp = np.array(xx,dtype='uint8')
temp = temp.reshape((400,400))
temp = cv2.cvtColor(temp, cv2.COLOR_BayerGBRG2BGR)
cv2.imshow("1",temp)
cv2.waitKey(0)