Analizar contraste de uma imagem

14 respostas
M

Hey Galerinha!

Estou tentando faz um programa que detecta a posição dos meus olhos com a webcam e preciso de um algoritmo que encontre pontos de alto contrante no meio de uma imagem (no caso os olhos).

Alguem sabe me informar como eu posso medir o contraste entre dois pontos?

Valew

14 Respostas

A

Segundo a wikipedia, contraste é a diferença de cor e brilho entre dois objetos… Como o brilho é sempre igual, suponho que o contraste seja a diferença entre 2 cores… eu mediria essa diferença pegando o RGB de cada um dos pontos e fazendo uma conta do tipo:
Contraste = Math.abs(R1-R2) + Math.abs(G1-G2) + Math.abs(B1-B2);

Aí vc teria como resultado um valor entre 0 e 765, em que o zero indicaria cores iguais e 765 totalmente diferentes (preto e branco).

Bom, nunca fiz isso… a idéia é um chute mesmo.

T

Se você quer algo que seja suficientemente rápido para acompanhar seus olhos, você não pode usar Java. Você tem de usar uma biblioteca muito famosa, a OpenCV.

http://opencvlibrary.sourceforge.net/wiki-static/FaceDetection.html

T

Se não me engano, mesmo aquelas aplicações (que às vezes vêm junto com sua web cam e permitem que você não precise ficar ajustando a câmera, porque essas aplicações “acham” sua cara na imagem) usam a OpenCV.

M

Valew cara… vou tentar usar essa tecnica ai.

Hmm… mas sera que eu preciso de tanta velocidade ou o java que é lento assim???

Bem.
Vou tentar com java mesmo por que não tenho idea de como se programa em C/C++

T

É que C++ também é lento quando se trata de processar imagens. A OpenCV tem código em assembly criado pela Intel e super-otimizado para fazer tais processamentos de imagens.

T

Quanto a achar os olhos pelo contraste, seu algoritmo vai ter problemas se a pessoa usar óculos, ou tiver olhos claros.
Normalmente você acha uma face (usando uma coleção de dados estatísticos que diz que uma determinada coisa na imagem é uma face) e deduz mais ou menos onde estão os olhos a partir da posição da face.

M

thingol:
Quanto a achar os olhos pelo contraste, seu algoritmo vai ter problemas se a pessoa usar óculos, ou tiver olhos claros.
Normalmente você acha uma face (usando uma coleção de dados estatísticos que diz que uma determinada coisa na imagem é uma face) e deduz mais ou menos onde estão os olhos a partir da posição da face.

Na verdade eu não pretendo usar a camera “nua”.

Achei uma técnica que envolve um filtro de cor e lampadas de luz infra-vermelha. Dessa maneira os olhos vao se destacar bastante do resto. Tipo quando voce tira uma foto e seus olhos ficam vermelhos.

A

Isso é um “pedaço” do meu tema de mestrado, que vou fazer daqui a 2 anos (espero!).
Pra fazer detecção de faces (eu sei que não é o seu caso, mas enfim), muitos trabalhos usaram wavelets.
Agora… é o que o thingol falou… E se ele usar óculos ou piscar durante um período de tempo maior que o normal? Outra coisa, e se ele “pendular” para um lado ou até mesmo virar o rosto?
Eu não sei se seria o ideal, mas uma coisa que você poderia usar são técnicas de I.A. (tipo uma rede neural), para saber o que é um olho. Você treina ela com, digamos 100 imagens de um olho e coloca ela pra procurar na imagem real. Não sei se funcionaria, na verdade, vou fazer isso só ano que vem, mas é interessante discutir essas técnicas.
Se estiver interessado, procure por trabalhos do grupo IMAGO, que é um grupo de pesquisa na área de processamento de imagens. Eles fizeram umas coisas muito interessante (por exemplo, o cursor do mouse ser controladora pelo nariz da pessoa). Eu acho que vale a pena.

thingol,
Você falou que Java e C++ são lentos em processametno de imagens. Mas quando são imagens dinâmicas, né? Se for só pegar uma imagem, pegar os pixels dela, redimensionar ela, acho que não tem muito problema de velocidade, tem?

T

Bom, se você tiver tempo e puder esperar…
Eu ainda prefiro usar as bibliotecas especializadas.
Por exemplo, a JAI (Java Advanced Imaging) da Sun também é escrita em C, com algumas rotinas em Assembly (para efetuar aquelas instruções de máquina que não estão acessíveis diretamente pelo C e que fazem multiplicações, adições etc. muito mais rapidamente que o código equivalente em C ou então Java.)

M

Achei essas formulas aqui

Brilho de uma cor = ((valor vermelho X 299) + (valor verde X 587) + (valor azul X 114)) / 1000
varia de 0 a 125

diferença de duas cores = (máximo (vermelho1, vermelho2) - mínimo (vermelho1, vermelho2)) + (máximo (verde1, verde2) - mínimo (verde1, verde2)) + (máximo (azul1, azul2) - mínimo (azul1, azul2))
varia de 0 a 500

A

thingol,

Eu soube de umas histórias bem interessantes da JAI. Estou pensando seriamente em usar ela no meu projeto da faculdade. Basicamente, é um rede neural lidando com imagens PGM. Eu consegui fazer sem a JAI, mas ainda vou redimensionar a imagem e mais algumas coisas. Até agora não vi a necessidade de usar a JAI.
Você acha que vale a pena ou só vai trazer mais dificuldades na implementação?

T

Bom, veja que tipos de coisas a JAI disponibiliza para você e veja se é adequado usá-la. Como ela é escrita em C e assembly, ela é bem rápida para os tipos de coisas que ela pode fazer.

M

Fiz um algoritmo baseado nessas formulas que passei…

Ele procura uma area onde a diferença do contraste medio da periferia contra o contraste medio do centro é maior.

Esta funcionando na maioria dos meus testes :thumbup:

mas infelizmente ele é incrivelmente lento :frowning:

A

Mikhas,
Mas você não está usando o JAI, né?
Bom, independente da velocidade, teste com algumas entradas diferentes (tipo uma pessoa de ponta cabeça ou teste com um cachorro na frente).

Criado 16 de outubro de 2008
Ultima resposta 17 de out. de 2008
Respostas 14
Participantes 4