PDA

Ver la Versión Completa : Como Obtener RGB de unos pixeles...


waly2k1
22-08-2008, 18:07:26
Hola amigos del foro, nuevamente acudo a uds. para ver si existe un componente o si es mas sencillo de lo que me parece realizar esto con los componentes estándares de Delphi:

Dada una imagen ('C:\MyImage.jpg'),
1) Cargarla en un TImage (u otro componente nose)
2) Al pasar el mouse sobre la imagen, pintar la zona donde pasa
3) Antes de pintar obtener la escala de colores RGB de dicha selección

En realidad la parte importante es obtener los colores de la selección, pero no de un solo pixel sino de varios, o sea un promedio de varios pixeles al estilo cuentagotas del photoshop u otro editor de imagenes.

Antes de postear he buscado en post anteriores y no he logrado encontrar
algo así.

Bueno espero encontrar solución a esto y desde ya eternamente agradecido como siempre!!!

Saludos,
Walter

coso
22-08-2008, 19:23:22
function TForm1.Red(c : TColor) : integer;
begin
Red := c and $FF;
end;

function TForm1.Green(c : TColor) : integer;
begin
Green := (c and $FF00) div $100;
end;

function TForm1.Blue(c : TColor) : integer;
begin
Blue := (c and $FF0000) div $10000;
end;


para volver a componer el color seria


Pixel[x,y] := r + g*$100 + b*$10000;

waly2k1
22-08-2008, 19:39:03
Hola coso, muchas gracias por tu rta, el tema es como obtengo el pixel, o sea estoy un poco máas que perdido.

Por si no fui del todo claro, describo nuevamente el enfoque
la cosa es pintar una parte de la imagen, pero antes de pintar obtener
un promedio de RGB de la parte pintada, nose si se entiende

Igualmente muchas gracias y seguiré investigando un poco mas
Saludos,
Walter

coso
22-08-2008, 19:56:37
Para obtener un pixel debes mirar en el objeto canvas, por ejemplo :

color := PaintBox1.Canvas.Pixels[x,y]

o si es una imagen

Image1.Picture.Bitmap.Canvas.Pixels[x,y]

para hacer el promedio que decias, por ejemplo pasando a grises, seria algo como


for i := 0 to PaintBox1.Width do
for j := 0 to PaintBox1.Height do
begin
c := PaintBox1.Canvas.Pixels[i,j]
PaintBox1.Canvas.Pixels[i,j] := (Red(c) + Green(c) + Blue(c)) div 3;
end;



echale un vistazo a la ayuda de delphi, buscando 'canvas'

Delphius
22-08-2008, 22:55:25
Hola waly2k1,
Además Pixels[], cuentas con ScanLine() que permite leer "linea por línea" una imagen.
ScanLine es mucho más rápido que el Pixels[]. Cuanto más grande sea la imagen, más se lento se hará, si bien es imperceptible a nuestros ojos.

Si estás pensando en tener un cuenta gotas y quieres hacer cálculos con los valores RGB lo mejor es contar con ScanLine; sobre todo si se debe examinar pixeles vecinos.

Veamos como te explico. Una imagen es una matriz, tiene un largo y un ancho.


+---------+---------+ ...
|255255255|255255255| ...
+---------+---------+ ...
|255255255|255255255| ...
+---------+---------+ ...

Si accedemos mediante Pixel veríamos una cosa así:


+---------+
|255255255|
+---------+


Cada celda es un pixel y tiene un tamaño de 24 bits. El asunto es obtener las correspodencia RGB. Coso te lo facilitó. La idea es que esos 24 bit se dividen en tres: 8 para el Rojo, otros 8 para el Verde y los otro 8 para el Azul. Cada canal puede asumir un valor "decimal" entre 0 y 255.

Si leemos con ScanLine(), obtenemos esto:


+-----------+-----------+ ...
|255|255|255|255|255|255| ...
+-----------+-----------+ ...


Si te fijas, se consigue tener acceso a toda una línea, y no sólo eso: ahora tenemos separado los valores RGB, nada de conversiones solo hay que leelo.

Lo que se obtiene con ScanLine es un puntero al primer pixel. Si queremos ir a un pixel n-ésimo en la fila habrá que incrementar el valor de dicho puntero n veces de a 3. Es decir: n * 3. ¿Por qué ese 3? Ese 3 corresponde a la cantidad de canales: rojo, verde, azul.

Cuando nos posicionamos en el lugar adecuado, tenemos entonces en el puntero ya lo valores:

Rojo := RGB^[1];
Verde := RGB^[2];
Azul := RGB^[3];

Siendo RGB un "vector puntero" de 3 posiciones.

Si buscas sobre ScanLine() vas a encontrar ejemplos de como usarlo.

Saludos,

waly2k1
23-08-2008, 03:59:53
A decir verdad me sirve muchísimo la ayuda brindada. Me surgió un imprevisto y deberé postergar esto un poco, pero ya en cualquier momento lo reanudo, pruebo y les comento como fue todo. Me sorprende sus conocimientos del tema, porque si bien las herramientas 'están', hay que saber utilizarlas.

Nuevamente gracias coso y Delphius por todo el tiempo que me dedicaron. Estamos en contacto por el tema en cualquier momento. Sigan así que siempre
gente como yo les estará muy agradecida!

Saludos,
Walter