Draw Images
Prev | Chapter 14. The Drawing Area Widget | Next

## Draw Images

There are a couple of drawing methods for putting image data into a drawing area. `draw_pixmap()` can copy the contents of a `Gdk::Drawable` (the window of a drawing area is one) into the drawing area. There is also `draw_bitmap()` for drawing a two-color image into the drawing area, and `draw_image()` for drawing an image with more than two colors.

For all of these methods, the first argument is the `Gdk::GC`. The second argument is the object of the appropriate type to copy in: `Gdk::Drawable`, `Gdk::Bitmap`, `Gdk::Image`. The next two arguments are the x and y points in the image to begin copying from. Then come the x and y points in the drawing area to copy to. The final two arguments are the width and heigh of the area to copy.

There is also a method in GTK+ for drawing from a `GdkRGB`. A `GdkRGB` buffer is an array of characters. Every three elements in the array define a color, the first element being the red component, the second green and the last blue. 3*width*height defines the number of elements needed for an rgb buffer of a given size. The rgb buffer is useful where pixel manipulation is needed.

The methods for manipulating the `GdkRGB` are not included in gtkmm, so the GTK+ methods are used directly. First off, if you use this construct directly, you must call `gdk_rgb_init()` before using any other methods, or the program will crash. Then construct your array. To draw it into a drawing area use `gdk_draw_rgb_image()`. Being a GTK+ function, it needs more arguments. The first argument is the `GdkDrawable` which you can get from your drawing area with the call `draw_area->get_window()`. Next is the `GdkGC`. A suitable `GdkGC` can be obtained from a call to `draw_area->get_style()->get_fg_gc(GTK_STATE_NORMAL)`. The next two arguments are the x and y points within the drawing area at which to draw the rgb buffer, and then come the width and height of the area to draw.

The next argument is a `GdkRgbDither` specifying the amount of dither to use. Dithering is an effect which causes colors close to each other to be blended by intermixing pixels from each color along the border of the two colors. If you've already calculated dither into your rgb buffer, then you will specify GDK_RGB_DITHER_NONE. Otherwise you can specify GDK_RGB_DITHER_NORMAL for dithering an image at 8 bits per pixel or lower, or GDK_RGB_DITHER_MAX for dithering an image at 16 bits per pixel or lower.

The next argument is the character array holding the rgb color information. The final argument is called rowstride. It is the number of elements in the array that compose one horizontal line of the array. From this number it is possible to draw a subset of the rgb buffer into the drawing area, knowing how wide the buffer is.

Here is a small bit of code to tie it all together:

    int rgb_draw_area::on_expose_event(GdkEventExpose *event)
    {
      gdk_draw_rgb_image(this->get_window(), this->get_style()->get_fg_gc(GTK_STATE_NORMAL), 0, 0, this->width, this->height,
                         GDK_RGB_DITHER_MAX, this->rgbbuff, (this->width)*3);
    }

In this example the custom drawing area contains additional members holding the width, height, and the character array that contains the rgb buffer information. Here is the class's definition:

    //Custom drawing area with modified expose_event.
    class rgb_draw_area: public Gtk::DrawingArea
    {
      int width, height;
      guchar *rgbbuff;
      public:
        rgb_draw_area(int x_size = 0, int y_size = 0);
        int on_expose_event(GdkEventExpose*);
        guchar *get_buffer() const;
    };

Prev | Up | Next
Drawing Text | Home | Chapter 15. Drag and Drop