Oppure

Loading
12/06/10 21:34
systemgvp
salve,
volevo sapere come era possibile convertire una Bitmap in scala di grigi con Lazarus dato che non utilizza la funzione ScanLine di delphi, esiste qualche comando simile anche per Lazarus?
aaa
13/06/10 12:45
TheKaneB
una volta ottenuta una bitmap, avrai da qualche parte un array che contiene i valori dei pixel.

Per un tipico sistema RGB a 24 bit, dovresti ritrovarti una situazione del genere


Pixel:                0    |1    |2    |3    |4...
Array of byte: R G B|R G B|R G B|R G B|R ...



Ogni 3 byte formano un pixel. Per convertirlo in scala di grigio ti basta convertire i colori dallo spazio RGB (Red Green Blue) allo spazio Y'CbCr (Luminanza, Crominanza), usando una semplicissima formuletta:


for i=0 to NUM_PIXEL_IMMAGINE step 3
var 
  R, G, B: byte; 
  Y: byte; 
begin
R := pixel[i];
G := pixel[i+1];
B := pixel[i+2];

(* Y è il valore di luminanza standard *)
Y := 0.299 * R + 0.587 * G + 0.114 * B;

(* sovrascrivo i vecchi valori RGB *)
R := Y;
G := Y;
B := Y;

pixel[i] := R;
pixel[i+1] := G;
pixel[i+2] := B;
end;



PS: ho scritto questo codice senza testarlo, e sono 5-6 anni circa che non tocco più il delphi, quidi prendilo con le pinze :-)

Ciao!
Ultima modifica effettuata da TheKaneB 13/06/10 12:46
aaa
13/06/10 16:55
systemgvp
io usavo la funzione

Procedure GrayScale(Bitmap:TBitmap);
var
Row:^TRGBTriple;
H,V,Index:Integer;
begin
Bitmap.PixelFormat:=pf24bit;
for V:=0 to Bitmap.Height-1 do
begin
Row:=Bitmap.ScanLine[V];
for H:=0 to Bitmap.Width -1 do
begin
Index := ((Row.rgbtRed * 77 + Row.rgbtGreen* 150 + Row.rgbtBlue * 29) shr 8);
Row.rgbtBlue:=Index;
Row.rgbtGreen:=Index;
Row.rgbtRed:=Index;
inc(Row);
end;
end;
end;

che fa la stessa cosa praticamente ma utilizzando il comando ScanLine[] progettato appositamente per l'elaborazione di immagini (da fonti Borland) ed è così perchè il procedimento è istantaneo si può dire, a differenza di andare a convertire pixel per pixel
aaa
13/06/10 21:20
TheKaneB
il mio procedimento è più veloce, perchè non prevede la separazione dell'immagine in scanlines, eliminando quindi l'overhead relativo al doppio ciclo for... :-)
aaa
14/06/10 19:30
systemgvp
si ma non va perchè non c'è una variabile che tiene conto del numero di pixel di un'immagine!
aaa
14/06/10 19:31
systemgvp
E non ti permette di vare elaborazioni di riconoscimento degli elementi persenti nell'immagine, ecco perchè mi necessita anche ScanLine
aaa