在蒙版帧中填充孔/块

问题描述 投票:0回答:2

我想根据某些标准填充蒙版图像中的“孔”。我有以下原始的frame

enter image description here

接下来,我在此帧上应用蒙版,得到masked

enter image description here

现在我想将帧分成16x16块。为了定义block(x,y),我们在垂直和水平方向上的x-thy-th块中定义了一组像素。如果块内黑色像素的百分比为non-field (field)而不是larger (smaller),则将该块定义为0.5。代码如下:

def blocked_img(img, x_pixels, y_pixels):
   blocked = img.copy()
   gray = cv2.cvtColor(blocked, cv2.COLOR_BGR2GRAY)

   for x in range(0, blocked.shape[1], x_pixels):
      for y in range(0, blocked.shape[0], y_pixels):
         block = gray[y:y+y_pixels, x:x+x_pixels]
         if (cv2.countNonZero(block) / block.size) < 0.5:
            # non-field
            cv2.rectangle(blocked, (x, y), (x+x_pixels, y+y_pixels), (0,255,255), 2)
         else:
            # field
            break

    return blocked

masked.shape返回以下内容:

 (720, 1280, 3)

因此,我使用以下命令调用函数blocked_img

blocked = blocked_img(masked, 80, 45)     #  divide by 16

blocked输出看起来如下:

enter image description here

目前,编写我的代码是,一旦没有达到0.5-threshold,它就会循环到下一行。可以看出,在右边的列中,此方法过早停止(准确地说是第9、11、12、13、16列),因此无法产生理想的结果]

如果要满足以下两个条件之一,我想在列中继续循环:

  • 如果前一个块为非字段且[下一个块为非字段或next_next块为非字段,则当前块为非字段]
  • 如果[previous_previous块为非字段或上一个块为非字段,而下一个块为非字段,则当前块为非字段

重写,

   block(x,y) = 1 if [block(x-1,y) = 1 and {block(x+1,y) = 1 or block(x+2,y) = 1}] or [{block(x-2, y) = 1 or block(x-1, y) = 1} and block(x+1, y) = 1]       # where 1 = non-field

您知道如何将其包含在代码中吗?预先感谢!

python numpy mask
2个回答
0
投票

我建议您多次遍历您的块。这就是我的想法-

def blocked_img(img, x_pixels, y_pixels):
   blocked = img.copy()
   blocks = np.zeros((blocked.shape[1]//x_pixels,blocked.shape[0]//y_pixels)) ##array to keep track of blocks status
   gray = cv2.cvtColor(blocked, cv2.COLOR_BGR2GRAY)
   prev_num_blocks = np.sum(blocks)
   for x in range(0, blocked.shape[1], x_pixels):
      for y in range(0, blocked.shape[0], y_pixels):
         block = gray[y:y+y_pixels, x:x+x_pixels]
         if (cv2.countNonZero(block) / block.size) < 0.5:
            # non-field
            cv2.rectangle(blocked, (x, y), (x+x_pixels, y+y_pixels), (0,255,255), 2)
            blocks[x,y] = 1
         else:
            # field
            continue

while (np.sum(blocks)>prev_num_blocks): ##keep going unless no change occurs in prev loop
for x in range(2, blocks.shape[0]-2, x_pixels):
  for y in range(2, blocks.shape[1]-2, y_pixels):
      ###the advance update rule here
      if (.....):
          blocks[x,y]=1
          cv2.rectangle(blocked,...) ##recreate the rect indices using the x,y

return blocked

从我的角度来看,需要使用while循环,因为在周期1中将块状态更改为非字段会影响列中它之前的块,因为它成为其他块的next_block和next_next块。

这可能不是最有效的方法,但是肯定会收敛并退出while循环。


0
投票
def blocked_img(img, x_pixels, y_pixels):

   blocked = img.copy()
   gray = cv2.cvtColor(blocked, cv2.COLOR_BGR2GRAY)

   for x in range(0, blocked.shape[1], x_pixels):
      for y in range(0, blocked.shape[0], y_pixels):
         block = gray[y:y+y_pixels, x:x+x_pixels]
         next_block = gray[y+y_pixels:y+(2*y_pixels), x:x+x_pixels]
         next_next_block = gray[y+(2*y_pixels):y+(3*y_pixels), x:x+x_pixels]
         if (cv2.countNonZero(block) / block.size) < 0.75:
            # non-field
            cv2.rectangle(blocked, (x, y), (x+x_pixels, y+y_pixels), (0,0,0), -1)
         else:
            if ((cv2.countNonZero(next_block) / block.size) < 0.75) or ((cv2.countNonZero(next_next_block) / block.size) < 0.75):
               # non-field
               cv2.rectangle(blocked, (x, y), (x+x_pixels, y+y_pixels), (0,0,0), -1)
            else:
               # field
               break
return blocked

我不确定这是否是最快的方法吗?

© www.soinside.com 2019 - 2024. All rights reserved.