Exercício 5 de IA639-2009

Autor: Matias
Data: 16/04/2009

Questão 1

  1. Estudar a função iaapplylut, fazendo alguns exemplos.

A função iaapplylut utiliza uma matriz de tranformação de cores para alterar a imagem fornecida. O indice da matriz representa a cor atual, e seus valores os novos mapeamentos.

Para entender seu funcionamento, foram feitos alguns exemplos:

01. imagem = mmreadgray('keyb.pgm')
02. 
03. T = arange(256)
04. imagem_nova = iaapplylut(imagem,T)
05. mmplot([[T]],['set yrange [0:255]','set xrange [0:255]'])
06. adshow(imagem_nova,title = "Uma transformação que não altera nada")
07. 
08. T = 255 - arange(256)
09. imagem_nova = iaapplylut(imagem,T)
10. mmplot([[T]],['set yrange [0:255]','set xrange [0:255]'])
11. adshow(imagem_nova,title = "Mapeamento negativo")
12. 
13. T = arange(256)
14. T[0:210]=0
15. T[211:256]=255
16. imagem_nova = iaapplylut(imagem,T)
17. mmplot([[T]],['set yrange [0:255]','set xrange [0:255]'])
18. adshow(imagem_nova,title = "Apenas uma faixa de cores (211-255) selecionada e mapeada para 255.")

Uma transformação que não altera nada

Mapeamento negativo

Apenas uma faixa de cores (211-255) selecionada e mapeada para 255.

Questão 2

Reprogramar a função iaapplylut para que ela seja mais simples. Se possível.

A forma mais simples de reprogramar essa função é utilizar os recursos do Python de indexação:

1. def iaapplylut(imagem,T):
2.     return T[imagem]
3. 
4. T = 255 - arange(256)
5. imagem_nova = iaapplylut(imagem,T)
6. mmplot([[T]],['set yrange [0:255]','set xrange [0:255]'])
7. adshow(imagem_nova,title = "Mapeamento negativo, iaapplylut simplificada")

Mapeamento negativo, iaapplylut simplificada

Questão 3

  1. Implementar uma função interativa de melhoria de contraste da imagem. Deve-se usar a função monotonicamente crescente de intensidade formada por 3 segmentos de retas. Os dois pontos de inflexão destas retas devem ser calculados em função de 4 parâmetros: Wi,Li largura e intensidade média de entrada, e Wo, Lo, largura e intensidade média de saída. Existem algumas situações que vocês precisam prever o comportamento desta operação dependendo dos parâmetros passados. Utilizar algumas imagens para ilustrar o uso desta função interativa. Uma ilustração desta função, porém apenas com os parâmetros Wi e Li podem ser vistas em http://www.dca.fee.unicamp.br/DIPcourse/html-dip/c4/s3/front-page.html

Li indica o ponto no eixo de entrada onde a região de largura Wi é centrada. Da mesma forma, Lo indica o ponto onde a região de largura Wo é centrada no eixo de saída.

Utilizando os parâmetros Wi, Li, Wo, Lo, a função determina os pontos de encontro das três retas, e então calcula os coeeficientes angulares e de deslocamento de cada uma.

01. def contrast_enhancement(imagem,Li,Wi,Lo,Wo,plotfunc=0):
02.     # Wi,Li - Largura de entrada e intensidade de entrada
03.     # Wo,Lo - Largura de saide e  intensidade de saida
04. 
05.     # determina coordenadas dos pontos das de união das retas
06.     P0 = [ 0 , 0 ]
07.     P1 = [ Li-(Wi/2), Lo-(Wo/2)]
08.     P2 = [ Li+(Wi/2), Lo+(Wo/2)]
09.     P3 = [ 255, 255 ]
10. 
11.     # determina tangente de cada reta
12.     tangente_reta_1 = float(P1[1])/float(P1[0])
13.     tangente_reta_2 = float(P2[1]-P1[1])/float(P2[0]-P1[0])
14.     tangente_reta_3 = float(255-P2[1])/float(255-P2[0])
15. 
16.     # determina o coeficiente de deslocamento das retas
17.     coef_b_1 = P0[0]
18.     coef_b_2 = P1[1]-tangente_reta_2*P1[0]
19.     coef_b_3 = P2[1]-tangente_reta_3*P2[0]
20. 
21.     # calcula cada ponto da transoformação
22.     T = arange(256)
23. 
24.     T[P0[0]:P1[0]]= (tangente_reta_1 * T[P0[0]:P1[0]]) + coef_b_1
25.     T[P1[0]:P2[0]]= (tangente_reta_2 * T[P1[0]:P2[0]]) + coef_b_2
26.     T[P2[0]:P3[0]]= (tangente_reta_3 * T[P2[0]:P3[0]]) + coef_b_3
27. 
28.     # plota funcao se tiver sido pedido
29.     if (plotfunc==1):
30.         mmplot([[T]],['set yrange [0:255]','set xrange [0:255]'])
31. 
32.     return T[imagem]
33. 
34. imagem = mmreadgray('boat.ppm')
35. 
36. histograma=iahistogram(imagem);
37. mmplot([[histograma]],['set yrange [0:'+str(histograma.max())+']','set xrange [0:255]'],ptitle='Histograma')
38. adshow(imagem,title = "Imagem Original")

Imagem Original

Baseado no histograma da imagem, decidiu-se usar os seguintes parâmetros: Li=100,Wi=180,Lo=127,Wo=240, seguido de outros exemplos:

01. imagem_nova = contrast_enhancement(imagem,100,180,127,250,1);
02. histograma=iahistogram(imagem_nova);
03. mmplot([[histograma]],['set yrange [0:'+str(histograma.max())+']','set xrange [0:255]'],ptitle='Histograma')
04. adshow(imagem_nova,title = "Li=100,Wi=180,Lo=127,Wo=250")
05. 
06. imagem_nova = contrast_enhancement(imagem,127,50,127,200,1);
07. histograma=iahistogram(imagem_nova);
08. mmplot([[histograma]],['set yrange [0:'+str(histograma.max())+']','set xrange [0:255]'],ptitle='Histograma')
09. adshow(imagem_nova,title = "Li=127,Wi=50,Lo=127,Wo=200")
10. 
11. imagem_nova = contrast_enhancement(imagem,127,200,127,20,1);
12. histograma=iahistogram(imagem_nova);
13. mmplot([[histograma]],['set yrange [0:'+str(histograma.max())+']','set xrange [0:255]'],ptitle='Histograma')
14. adshow(imagem_nova,title = "Li=127,Wi=200,Lo=127,Wo=20")
15. 
16. imagem_nova = contrast_enhancement(imagem,50,20,127,200,1);
17. histograma=iahistogram(imagem_nova);
18. mmplot([[histograma]],['set yrange [0:'+str(histograma.max())+']','set xrange [0:255]'],ptitle='Histograma')
19. adshow(imagem_nova,title = "Li=50,Wi=20,Lo=127,Wo=200")

Li=100,Wi=180,Lo=127,Wo=250

Li=127,Wi=50,Lo=127,Wo=200

Li=127,Wi=200,Lo=127,Wo=20

Li=50,Wi=20,Lo=127,Wo=200

Segue o mesmo algoritimo, agora com a opção de se alterar os parametros de entrada.

Bugs e restrições:
  • Valores que criem pontos de encontro das restas fora, ou no limite do quadrado (0,0)-(255,255) podem causar divisão por zero
01. parser = OptionParser()
02. parser.add_option("--Li", type='int', default=127, help='Intensidade de entrada')
03. parser.add_option("--Wi", type='int', default=20, help='Largura de entrada')
04. parser.add_option("--Lo", type='int', default=127, help='Intensidade de saida')
05. parser.add_option("--Wo", type='int', default=100, help='Largura de saida')
06. 
07. opt, arg = parser.parse_args()
08. 
09. imagem = mmreadgray('boat.ppm')
10. imagem_nova = contrast_enhancement(imagem,opt.Li,opt.Wi,opt.Lo,opt.Wo,1);
11. histograma=iahistogram(imagem_nova);
12. mmplot([[histograma]],['set yrange [0:'+str(histograma.max())+']','set xrange [0:255]'],ptitle='Histograma')
13. adshow(imagem_nova,title = "Li=%d,Wi=%d,Lo=%d,Wo=%d" % (opt.Li,opt.Wi,opt.Lo,opt.Wo))

Li=127,Wi=20,Lo=25,Wo=10