我有一个DIY家庭照片工作室,想要拍摄的照片背景是纯白色(#FFFFFF),并且尽量减少用户交互。
这是我原始的图片(没有进行任何处理,只是从相机中获取的原始JPG格式图片):
我使用opencv和Tkinter UI实现了一个简单的python程序。
1) 获取包含对象的矩形区域(ROI)
我决定通过UI选择ROI,也许以后我会编写代码来自动识别照片上的对象。
2) 使用cv2.grabCut函数尝试从这个矩形中裁剪背景
并获得这样的结果:
看起来不错,除了对象右侧的一些伪影。这似乎是我的掩码不够好。这不是真正的问题。真正的问题是:无缝克隆给我的背景并不是真正的白色。看一下级别:
一些奇怪的渐变和底部右侧的背景不是真正的白色。我尝试了很多图片,通常会出现这种情况。
我的问题是:有什么正确的方法可以做到我想要的吗?我的方法可用于此任务吗?如何使真正的白色(#FFFFFF)背景没有这样的渐变。谢谢
这是我原始的图片(没有进行任何处理,只是从相机中获取的原始JPG格式图片):
![original image](https://istack.dev59.com/16nH2.webp)
1) 获取包含对象的矩形区域(ROI)
我决定通过UI选择ROI,也许以后我会编写代码来自动识别照片上的对象。
![select ROI](https://istack.dev59.com/vXi70.webp)
![grab cut with rect](https://istack.dev59.com/33DxM.webp)
cv2.grabCut(image, self.mask, rect, bgdmodel, fgdmodel, 5, cv2.GC_INIT_WITH_RECT)
3) 如果需要,我会创建自定义蒙版用于 GrabCut,以提供更准确的对象提取。
cv2.grabCut(image, self.mask, rect, bgdmodel, fgdmodel, 5, cv2.GC_INIT_WITH_MASK)
4)在这一步之后,我可以创建包含我的对象的遮罩。我还将遮罩大小调整了30像素。
mask = cv2.resize(mask, ( crop_img.shape[1] + 30, crop_img.shape[0] + 30))
mask = mask[30 : crop_img.shape[0], 30 : crop_img.shape[1]]
所以这个掩码具有更大的宽度和高度。
5) 我将使用这个掩码来进行seamlessClone方法
src_bg = 255 * np.ones(self.src.shape, self.src.dtype)
width, height, channels = src_bg.shape
center = (int(height / 2), int((width / 2)))
output = cv2.seamlessClone(crop_img, src_bg, mask, center, cv2.MIXED_CLONE)
并获得这样的结果:
![output](https://istack.dev59.com/AxLVq.webp)
![levels](https://istack.dev59.com/Kq19c.webp)
我的问题是:有什么正确的方法可以做到我想要的吗?我的方法可用于此任务吗?如何使真正的白色(#FFFFFF)背景没有这样的渐变。谢谢