[Home]
[Edit this page]
[Recent Changes]
[Special Pages]
[Help]
Star7 » J2SE » IEvents » structure » talk:TurboCpp » address » Prolog » PnP » QbasicFAQ_Gosub » Hypertext » CppVclGraphics
RGB is a macro. TPaintBox gets updated after every change in pixel. This makes it slow.
The function ScanLine returns a void pointer, therefore it needs to be cast to an unsigned char pointer. Note that red, green and blue are reversed in the obtained pointer.
Also a function I often use is this:
Note that in the single-buffered example, I need to call TImage::Refresh() as otherwise the graphics will not flicker. This is because the VCL will not redraw the screen while running this code. Fact is, that the code shown is a trivial example. In more complex programs, double-buffering will always look nice, single-buffering might flicker.
[Edit this page] [Page history] [What links here] [Discuss this topic] [Printer Friendly]
Star7 » J2SE » IEvents » structure » talk:TurboCpp » address » Prolog » PnP » QbasicFAQ_Gosub » Hypertext » CppVclGraphics
(C++ VCL) Graphics
Graphics in the VCL can be accomplished using a TPaintBox or a TImage component. The first is easier, yet slower and gives flicker.Example using TPaintBox
const int maxx = PaintBox1->Width;
const int maxy = PaintBox1->Height;
for (int y = 0; y != maxy; ++y)
{
for (int x = 0; x != maxx; ++x)
{
PaintBox1->Canvas->Pixels[x][y] = RGB(x,y,x+y);
}
}
RGB is a macro. TPaintBox gets updated after every change in pixel. This makes it slow.
Example using TImage
Displays a nice gradient on the Image.
const int maxx = Image1->Picture->Bitmap->Width;
const int maxy = Image1->Picture->Bitmap->Height;
for (int y = 0; y != maxy; ++y)
{
unsigned char * myLine = static_cast<unsigned char*>( Image1->Picture->Bitmap->ScanLine[y]);
for (int x = 0; x != maxx; ++x)
{
myLine[x*3+2] = x ; //Red
myLine[x*3+1] = y ; //Green
myLine[x*3+0] = x+y; //Blue
}
}
The function ScanLine returns a void pointer, therefore it needs to be cast to an unsigned char pointer. Note that red, green and blue are reversed in the obtained pointer.
Also a function I often use is this:
void paint(TImage * image,
const char& red,
const char& green,
const char& blue )
{
const int maxx = image->Picture->Bitmap->Width;
const int maxy = image->Picture->Bitmap->Height;
for (int y = 0; y != maxy; ++y)
{
unsigned char * myLine = static_cast<unsigned char*>(image->Picture->Bitmap->ScanLine[y]);
for (int x = 0; x != maxx; ++x)
{
myLine[x*3+2] = red ; //Red
myLine[x*3+1] = green; //Green
myLine[x*3+0] = blue ; //Blue
}
}
}
Example using double-buffering
When you use double-buffering, you have one TImage, which is invisible, on which you do all your graphics on. When it is done, you bitblit it on a TCanvas. I also show a single-buffered application below this example.
//A suitable method to put this in is for example TTimer::OnTimer
//Double buffered
Image1->Visible = false;
++Tag;
const int maxx = Image1->Picture->Bitmap->Width;
const int maxy = Image1->Picture->Bitmap->Height;
for (int y = 0; y != maxy; ++y)
{
//First draw a nice gradient
unsigned char * myLine = static_cast<unsigned char*>( Image1->Picture->Bitmap->ScanLine[y]);
for (int x = 0; x != maxx; ++x)
{
myLine[x*3+2] = (x+Tag )%256; //Red
myLine[x*3+1] = (y+Tag )%256; //Green
myLine[x*3+0] = (x+y+Tag)%256; //Blue
}
}
//Draw a rectangle
Image1->Canvas->Rectangle(128,128,384,384);
Canvas->Draw(0,0,Image1->Picture->Graphic); //Bitblit to TForm's Canvas!
//A suitable method to put this in is for example TTimer::OnTimer
//Single buffered
Image1->Visible = true;
++Tag;
const int maxx = Image1->Picture->Bitmap->Width;
const int maxy = Image1->Picture->Bitmap->Height;
for (int y = 0; y != maxy; ++y)
{
//First draw a nice gradient
unsigned char * myLine = static_cast<unsigned char*>( Image1->Picture->Bitmap->ScanLine[y]);
for (int x = 0; x != maxx; ++x)
{
myLine[x*3+2] = (x+Tag )%256; //Red
myLine[x*3+1] = (y+Tag )%256; //Green
myLine[x*3+0] = (x+y+Tag)%256; //Blue
}
}
//Needed to cause flicker (see below for explanation):
Image1->Refresh();
//Draw a rectangle
Image1->Canvas->Rectangle(128,128,384,384);
Note that in the single-buffered example, I need to call TImage::Refresh() as otherwise the graphics will not flicker. This is because the VCL will not redraw the screen while running this code. Fact is, that the code shown is a trivial example. In more complex programs, double-buffering will always look nice, single-buffering might flicker.
Other examples
'Graphics' links
- general
- C
- C++
- C++ Builder
- C++ CLX
- Pascal VCL
- Pascal CLX
[Edit this page] [Page history] [What links here] [Discuss this topic] [Printer Friendly]
