GdkPixbuf/X/backingstore interaction

Carl Nygard cjn at telomeric.com
Wed Jan 5 13:40:36 PST 2005


On Wed, 2005-01-05 at 15:19 -0500, Owen Taylor wrote:
> On Wed, 2005-01-05 at 14:43 -0500, Carl Nygard wrote:
> > This may not be the proper list, but perhaps someone knows what's up.
> > I've got an app that (due to institutional inertia) has an unholy mix of
> > X/Motif under a Zaf layer with Gdk::Pixbuf rendering rasters.  So yeah,
> > who knows where the problem is coming from.
> > 
> > But the problem:  when a X DrawingArea widget is obscured by any other
> > window, the Gdk::Pixbuf doesn't render to that area obscured by the
> > other window.  backing-store is turned on, so vector/polygon rendering
> > using regular Xlib function calls are displayed when the window is
> > moved.
> 
> What do you mean by Gdk::Pixbuf? What particular library, function
> call, etc?
> 
> GdkPixbuf in current versions of GTK+ is just a bundle of image bits
> and doesn't do any drawing.


gtk+-1.2.10-29.1.1
gtkmm2-2.2.12-1.1.fc2.fr

Here's some sample code of what's going on.  Beware the c++ (gtkmm).  If
it's not enough, let me know...


void RasterObject::Render(const RasterDest& dst) const 
{
    Debug dbg(_dbg, "Render");

    if(_animationFlag){
        dbg(2) << "Rendering..." << endl;
        _pix->render_to_drawable_alpha(dst.Drawable(), 0, 0, 0, 0, 
                                       _pix->get_width(), _pix->get_height(), 
                                       Gdk::PIXBUF_ALPHA_FULL, 128, 
                                       Gdk::RGB_DITHER_MAX, 0, 0);
    }else{

        Glib::RefPtr<Gdk::Pixbuf> cpb = 
            Gdk::Pixbuf::create(Gdk::COLORSPACE_RGB,
                                true, 8,
                                dst.Width(),
                                dst.Height());
        dbg(2) << "Dest: " << dst.Size() << endl;
        // Figure out the zoom/pan
        float scale = _ComputeScale(dst.Size(), 
                                    _OrientDims(_angle, _data->Dimensions()),
                                    _ratio);
        GeoPt offset = _ComputeOffset(dst.Size(),
                                      _OrientDims(_angle, _data->Dimensions()),
                                      _RotatePos(_angle, _location), 
                                      scale);

        dbg(2) << "Ratio: " << _ratio << " Scaling: " << scale << endl;
        dbg(2) << "Offset: " << offset << endl;
        dbg(2) << "Size: " << cpb->get_width() << "," 
               << cpb->get_height() << endl;

        // now figure out which parts of the pixbuf get rendered
        int xoff((int)rint(offset.X()));
        int yoff((int)rint(offset.Y()));
        int minx = max(0, xoff);
        int miny = max(0, yoff);
        int cols = (int)(_pix->get_width() * scale) + min(0, xoff);
        int rows = (int)(_pix->get_height() * scale) + min(0, yoff);
        int width = min(cols, cpb->get_width()-minx);
        int height = min(rows, cpb->get_height()-miny);
        dbg(2) << "Scaling..." << endl;
        _pix->scale(cpb, minx, miny, width, height, xoff, yoff,
                    scale, scale, Gdk::INTERP_HYPER/*BILINEAR NEAREST TILES HYPER*/);

    
        dbg(2) << "Rendering..." << endl;
        cpb->render_to_drawable_alpha(dst.Drawable(), 0, 0, 0, 0, 
                                      cpb->get_width(), cpb->get_height(), 
                                      Gdk::PIXBUF_ALPHA_FULL, 128, 
                                      Gdk::RGB_DITHER_MAX, 0, 0);
    }

    dbg(2) << "Flushing" << endl;
    XFlush(gdk_x11_drawable_get_xdisplay(dst.Drawable()->gobj()));
}






More information about the xorg mailing list