From: "Earl F. Glynn" Subject: Re: Scanline ? Date: Monday, March 05, 2001 9:34 AM "Sean" wrote in message news:3aa37f5d_2@dnews... > Hi, > > I got this off efg2's site. ... > WITH Row[i] DO > BEGIN > rgbtRed := 255; // yellow pixels > rgbtGreen := 255; > rgbtBlue := 0; > END > If I wanted to use Tcolor instead of the rgbt*, what would I do ? What kind of TColor do you have? Find info about a TColor here: http://homepages.borland.com/efg2lab/Library/Delphi/Graphics/VCLRTL.htm The internal format of TColor can have five formats: 1. $00bbggrr -- Create using the RGB function 2. $010000nn -- Create using the PaletteIndex function 3. $02bbggrr -- Create using the PaletteRGB function 4. $800000nn -- Defined in Graphics.PAS using Windows constants COLOR_SCOLLBAR, etc. These negative values must be passed to the ColorToRGB function to have R, G and B components defined. 5. $FFFFFFFF -- f you create a TBitmap and do not define its height and width, the Pixels value will be -1 ($FFFFFFFF) and may cause range-check errors. If you're manipulating a lot of pf24bit pixels and must work with individual color components, it's usually easier to work with a TRGBTriple since each Scanline is just an Array of TRGBTriple. Here's a conversion from the #1 format (see above) of TColor to a TRGBTriple. This allows quick conversion from a TColor to a TRGBTriple. The inverse function is fairly simple too: FUNCTION ColorToRGBTriple(CONST Color: TColor): TRGBTriple; BEGIN WITH RESULT DO BEGIN rgbtRed := GetRValue(Color); rgbtGreen := GetGValue(Color); rgbtBlue := GetBValue(Color) END END {ColorToRGBTriple}; And if you have to define the TColor using the RGB function anyway, just assign a TRGBTriple value instead. You can always use a TRGBTriple constant for a defined color, for example: // Set bitmap to yellow using Scanline and a TRGBTriple constant // Delphi 4.02 or later procedure TForm1.Button2Click(Sender: TObject); CONST Yellow: TRGBTriple = (rgbtBlue: 0; rgbtGreen: 255; rgbtRed: 255); TYPE TRGBTripleArray = ARRAY[WORD] OF TRGBTriple; pRGBTripleArray = ^TRGBTripleArray; VAR Bitmap: TBitmap; i : INTEGER; j : INTEGER; row : pRGBTripleArray; begin Bitmap := TBitmap.Create; TRY Bitmap.Width := Image.Width; Bitmap.Height := Image.Height; Bitmap.PixelFormat := pf24bit; FOR j := 0 TO Bitmap.Height-1 DO BEGIN row := Bitmap.Scanline[j]; FOR i := 0 TO Bitmap.Width-1 DO BEGIN row[i] := Yellow END END; Image.Picture.Graphic := Bitmap; FINALLY Bitmap.Free END end; You might be tempted to use a pf32bit Scanline and try to cast a TColor to a TRGBQuad, like this: procedure TForm1.Button3Click(Sender: TObject); TYPE TRGBQuadArray = ARRAY[WORD] OF TRGBQuad; pRGBQuadArray = ^TRGBQuadArray; VAR Bitmap: TBitmap; Color : TColor; i : INTEGER; j : INTEGER; row : pRGBQuadArray; yellow: TRGBQuad; begin Color := clYellow; yellow := TRGBQuad(Color); Bitmap := TBitmap.Create; TRY Bitmap.Width := Image.Width; Bitmap.Height := Image.Height; Bitmap.PixelFormat := pf32bit; FOR j := 0 TO Bitmap.Height-1 DO BEGIN row := Bitmap.Scanline[j]; FOR i := 0 TO Bitmap.Width-1 DO BEGIN row[i] := Yellow END END; Image.Picture.Graphic := Bitmap; FINALLY Bitmap.Free END end; But why isn't the color right? If you use the #1 TColor format (described above), you have: $00bbggrr. If you lookup a TRGBQuad in the windows.pas unit: PRGBQuad = ^TRGBQuad; {$EXTERNALSYM tagRGBQUAD} tagRGBQUAD = packed record rgbBlue: Byte; rgbGreen: Byte; rgbRed: Byte; rgbReserved: Byte; end; TRGBQuad = tagRGBQUAD; So a TRGBQuad is really $bbggrr00. A TColor is really just an integer, so you could shift it 8 bits to the left and this does work in the Button3Click above: Color := clYellow; yellow := TRGBQuad(Color SHL 8); So starting with a TColor, $00bbggrr, if you shift this 8 bits left, you get $bbggrr00, which matches a TRGBQuad and the above typecast then give you what you want -- an easy way to map a TColor to a pixel in a scanline. -- efg efg2@efg2.com Earl F. Glynn, Overland Park, KS USA efg's Computer Lab: http://www.efg2.com/Lab Mirror: http://homepages.borland.com/efg2lab/Default.htm