OpenCV avançado - ajuste o contraste do brilho da imagem

transformação de imagem

A transformação da imagem é encontrar uma função para converter a matriz da imagem original na matriz da imagem de destino após ser processada pela função. 
Pode ser dividido em duas maneiras, ou seja, transformação em nível de pixel e transformação em nível de região

  • Operadores de ponto (transformações de pixel)
  • Operadores de bairro (com base na área)

A transformação em nível de pixel é equivalente a P_{depois}(i,j)=f(P_{antes}(i,j))cada valor de pixel após a transformação ter um relacionamento de mapeamento funcional com o valor de pixel na mesma posição antes da transformação.

transformação linear

A mais comumente utilizada é a transformação linear. Ou seja, g(i,j)=\alpha \cdot f(i,j)+\beta
f(i, j) é o valor do pixel original e g(i, j) é o valor do pixel transformado.
α ajusta o contraste e β ajusta o brilho.Às vezes, também é chamado de parâmetros de ganho e polarização.

Contraste e Brilho

O que é contraste? Não é "a diferença entre claro e escuro"? Ou seja, a diferença no tamanho do valor do pixel. Então eu multiplico por um coeficiente alfa. Quando o alfa é grande, a diferença no valor do brilho é ampliada, ou seja, o contraste é melhorado. Quando o alfa é pequeno, a diferença no brilho é reduzida, ou seja, o contraste é reduzido.

Beta é melhor compreendido. Adicione um número diretamente ao valor de brilho do pixel. Um número positivo aumenta o brilho e um número negativo diminui o brilho.

Dê uma olhada em um exemplo do código abaixo:

from __future__ import print_function
from builtins import input
import cv2 as cv
import numpy as np
import argparse

# Read image given by user
parser = argparse.ArgumentParser(description='Code for Changing the contrast and brightness of an image! tutorial.')
parser.add_argument('--input', help='Path to input image.', default='lena.jpg')
args = parser.parse_args()
image = cv.imread(cv.samples.findFile(args.input))
if image is None:
    print('Could not open or find the image: ', args.input)
    exit(0)
new_image = np.zeros(image.shape, image.dtype)
alpha = 1.0 # Simple contrast control
beta = 0    # Simple brightness control
# Initialize values
print(' Basic Linear Transforms ')
print('-------------------------')
try:
    alpha = float(input('* Enter the alpha value [1.0-3.0]: '))
    beta = int(input('* Enter the beta value [0-100]: '))
except ValueError:
    print('Error, not a number')
# Do the operation new_image(i,j) = alpha*image(i,j) + beta
# Instead of these 'for' loops we could have used simply:
# new_image = cv.convertScaleAbs(image, alpha=alpha, beta=beta)
# but we wanted to show you how to access the pixels :)
for y in range(image.shape[0]):
    for x in range(image.shape[1]):
        for c in range(image.shape[2]):
            new_image[y,x,c] = np.clip(alpha*image[y,x,c] + beta, 0, 255)
cv.imshow('Original Image', image)
cv.imshow('New Image', new_image)
# Wait until user press some key
cv.waitKey()

Execute: python change_brightness_contrast.py --input ./lights.jpeg

A imagem acima é uma renderização de alpha=2, beta=20.

transformação não linear

Há um problema com a transformação linear, conforme mostrado na figura acima, α=1.3 e β=40, ao aumentar o brilho da imagem original, a nuvem fica quase invisível. Se você quiser ver as nuvens, o brilho do prédio não é suficiente.

Neste momento, uma transformação não linear é introduzida, chamada de correção gama.

O = (\frac{1}{255})^\gamma \times 255
Diferente da transformação linear, a intensidade da mudança é diferente para diferentes valores originais de brilho, que não é linear.


Quando γ<1, o brilho da imagem será aumentado. Quando >1, reduza o brilho.

O diagrama de efeito de transformação de γ = 0,4 é como acima. Pode-se ver que as nuvens e os edifícios são iluminados, mantendo o contraste para que a imagem ainda seja nítida.


Você pode vê-lo se olhar para os histogramas em escala de cinza sob diferentes transformações. No meio está o histograma de tons de cinza da imagem original, você pode ver que há muitos pixels com valores de brilho baixo.
O lado esquerdo é transformado linearmente, o histograma geral é deslocado para a direita e um pico aparece em 255. Porque cada pixel aumenta o brilho. Como resultado, as nuvens brancas e o céu azul são muito brilhantes para serem distinguidos.
À direita, a imagem corrigida por gama tem uma distribuição de brilho relativamente uniforme, o que significa que as partes com baixos valores de brilho podem ser reforçadas, mas não serão superexpostas para que as nuvens brancas não possam ser distinguidas.

O código para implementar a correção Gama é o seguinte.

    lookUpTable = np.empty((1,256), np.uint8)
    for i in range(256):
        lookUpTable[0,i] = np.clip(pow(i / 255.0, gamma) * 255.0, 0, 255)
    res = cv.LUT(img_original, lookUpTable)

Onde cv.LUT é uma função de transformação. Encontre o relacionamento de transformação de lookUpTable e gere uma nova matriz de imagem.

Acho que você gosta

Origin blog.csdn.net/qq_39312146/article/details/130137970
Recomendado
Clasificación