我想创建一个脚本,该脚本将一个.HDR
文件并色调映射到一个.JPG
中。我看了几个OpenCV tutorials,看来应该可以做到这一点。
我写了这个脚本:
import cv2
import numpy as np
filename = "image/gg.hdr"
im = cv2.imread(filename)
cv2.imshow('', im.astype(np.uint8))
cv2.waitKey(0)
tonemapDurand = cv2.createTonemapDurand(2.2)
ldrDurand = tonemapDurand.process(im.copy())
new_filename = filename + ".jpg"
im2_8bit = np.clip(ldrDurand * 255, 0, 255).astype('uint8')
cv2.imwrite(new_filename, ldrDurand)
cv2.imshow('', ldrDurand.astype(np.uint8))
根据教程的指导应该起作用。最后我得到的是黑色图像。我已经验证它保存的结果是.JPG
,以及输入图像(1.6兆像素HDR环境图)是有效的.HDR
。
OpenCV应该能够根据the documentation加载.HDR
。
我尝试重现链接的教程,并且该教程正常工作,所以问题出在.HDR
图片中,有人知道该怎么做吗?
谢谢
编辑:我使用了this HDR image。由于版权等原因,提供链接而不是直接下载。
答案 0 :(得分:2)
除了两个小错误外,您几乎就在那儿。
第一个错误是使用cv2.imread
加载HDR图像而不指定任何flags。除非您使用IMREAD_ANYDEPTH
进行调用,否则数据将被缩减为8位,并且您将失去所有如此高的动态范围。
当您指定IMREAD_ANYDEPTH
时,图像将以32位浮点格式加载。该强度通常在[0.0,1.0]范围内,但是由于是HDR,所以该值超过1.0(在这种特殊情况下,它们达到约22)。这意味着您将无法通过简单地将数据转换为np.uint8
来可视化它(以一种有用的方式)。您也许可以先将其归一化到标称范围内,或者使用缩放和修剪方法...随便找到合适的方法。由于早期可视化与结果无关,因此我将其跳过。
第二个问题微不足道。您可以正确缩放并将色调映射的图像裁剪回np.uint8
,但随后再也不会使用它。
脚本
import cv2
import numpy as np
filename = "GoldenGate_2k.hdr"
im = cv2.imread(filename, cv2.IMREAD_ANYDEPTH)
tonemapDurand = cv2.createTonemapDurand(2.2)
ldrDurand = tonemapDurand.process(im)
im2_8bit = np.clip(ldrDurand * 255, 0, 255).astype('uint8')
new_filename = filename + ".jpg"
cv2.imwrite(new_filename, im2_8bit)
输出