代码之家  ›  专栏  ›  技术社区  ›  Jaime Manuel Garcia Dominguez

为什么图像结果翻转了90度?

  •  2
  • Jaime Manuel Garcia Dominguez  · 技术社区  · 1 年前

    我试图将此图像中的所有白色像素变为红色,但当我运行程序时,形状很好,但红色像素旋转了90度:

    result

    这是我用于执行此操作的当前代码:

    import cv2 as cv
    import numpy as np
    import os
    from matplotlib import pyplot as plt
    import cv2 as cv
    
    def get_white_pixels(image_as_array):
        threshold = 40
        indices = np.where(image_as_array >= threshold)
        width=image.shape[1]
        height=image.shape[0]
        cartesian_y=height-indices[0]-1
        np_data_points=np.column_stack((indices[1],cartesian_y)) 
        return cartesian_y, np_data_points, width,height
    
    image = cv.imread("framenumber0.jpg")
    ind, pixels, width, height = get_white_pixels(image)
    
    #Goes through every pixel and changes its values
    for i in range(0, len(pixels)):
        loc_x = int(pixels[i][0])
        loc_y = int(pixels[i][1])
        image[loc_x,loc_y] = (0,0,255)
    
    cv.imshow('Modified Image', image)
    cv.waitKey(0)
    cv.destroyAllWindows()
    

    我确实需要白点的位置,因为我稍后将在项目的第二部分使用它们。我怀疑这个问题与np.column_stack()有关。我一直在阅读函数的信息页面,但我仍然不明白为什么会发生这种情况。

    如果你想在这里复制我正在使用的图像:

    source

    2 回复  |  直到 1 年前
        1
  •  1
  •   oOosys    1 年前

    将此行更改为:

        # image[loc_x,loc_y] = (0,0,255)
        image[loc_y,loc_x] = (0,0,255)
    

    随着

        # cartesian_y=height-indices[0]-1
        cartesian_y=indices[0]
    
    

    您需要知道numpy和OpenCV数组是y,x数组,其中其他图像处理包以x,y的方式工作。

    这里是运行固定代码的结果:

    OK

    如在评论中所述 aRTy

    在这一行中,您实际上是在自上而下地翻转y坐标: cartesian_y=height-indices[0]-1 。如果要从OpenCV/numpy方向(其中y=0为顶部)转换为matplotlib方向(其中y=0为底部),则需要在到达matplotlab部分时执行此操作,而不是在此之前。


    获得阈值图像(显然是灰度图像)所需的效果也可以通过使用分离通道的简化代码并在其中一个通道上运行OpenCV阈值来实现:

    import cv2 as cv, numpy as np
    
    threshold = 40
    image = cv.imread("srcImage.jpg")
    _, G, _ = cv.split(image)
    _, thresh = cv.threshold(G, threshold, 255, cv.THRESH_BINARY)
    black=np.zeros_like(thresh)
    red_image = cv.merge([black, black, thresh])
    
    cv.imshow('White areas in source Image marked red', red_image)
    cv.waitKey(0)
    cv.destroyAllWindows()
    

    即使跳过两个通道,结果似乎也是一样的。

        2
  •  1
  •   Mark Setchell    1 年前

    好好想想。你知道白色是 rgb(255,255,255) ,与相同 #fff 当你在HTML/CSS中使用十六进制颜色时。你想把白色变成红色,即。 rgb(255,0,0) ,所以您基本上需要将绿色和蓝色通道归零:

    import cv2 as cv
    
    # Load image
    im = cv.imread('ZXo3LfmS.jpg')
    
    # Zero the blue channel, then the green channel
    im[..., 0] = 0
    im[..., 1] = 0
    
    # Save result
    cv.imwrite('result.png')
    

    enter image description here

    实际上,您可以一次将蓝色和绿色归零,使用:

    im[..., [0,1]] = 0
    

    注意省略号(…)的意思是 “我没有费心列举的所有其他维度” 。如果出于某种原因我想列举它们,我可以使用:

    im[:, :, 0] = 0     # zero the blue channel
    im[:, :, 1] = 0     # zero the green channel