【问题标题】:GTK+ Replace gdk_draw_pixbuf with CairoGTK+ 将 gdk_draw_pixbuf 替换为 Cairo
【发布时间】:2016-07-27 13:32:36
【问题描述】:

我正在开发一个 GtkDrawingArea,在 Expose 事件中,它以平铺的方式绘制一个 pixbuf 的一部分。平铺类型因源图像而异;它可以是正交的、等距的或六边形的。用 gdk_draw_pixmap 绘制它很简单;这是一个关于如何查找等距平铺的示例:

for(y=0,row=0; y+tile_height<height; y+=tile_half_height,++row)
  for(x=((row&1)? tile_half_width : 0); x+tile_width<width; x+=tile_width)
    gdk_draw_pixbuf(widget->window,NULL,
                    pixbuf,src_x,src_y,
                    x,y,tile_width,tile_height,
                    GDK_RGB_DITHER_NONE,0,0);

结果:

然而,事实证明,在开罗绘制相同的图是完全不同的。这是我到目前为止所拥有的,但它不起作用:

cairo_t *cr = gdk_cairo_create(widget->window);
gdk_cairo_set_source_pixbuf(cr,pixbuf,src_x,src_y);
for(y=0,row=0; y+tile_height<height; y+=tile_half_height,++row)
  for(x=((row&1)? tile_half_width : 0); x+tile_width<width; x+=tile_width) {
    cairo_rectangle(cr,x,y,tile_width,tile_height);
    cairo_paint(cr);
  }
}
cairo_destroy(cr);

结果:

Cairo 只是拒绝绘制图像,因为会绘制正常的光栅图像。我做错了什么,如何解决?

【问题讨论】:

  • cairo_paint() fills the clip region, not the current path;您需要将使用cairo_rectangle() 创建的路径转换为使用cairo_clip() 的剪辑区域。 (请记住,剪辑区域会随着时间的推移而保留,因此您的 for 循环中还需要 cairo_save()cairo_restore()。)
  • 不知道cairo_fill是怎么处理图片源的;你可以试试。我只用过纯色。
  • 不,同样的结果。问题是整个源图像都被用作图案,即使我只想使用它的一部分。我需要修复 src_x, src_y,这在开罗没有发生 - src_x, src_y 只是源图像中的起点,然后它在源图像中相应地调整 x, y。
  • 我也尝试过cairo_translate() 的组合,但在这种情况下,试错似乎无穷无尽,这就是我问的原因。

标签: c gtk cairo gdkpixbuf


【解决方案1】:

未经测试,但可能有效。如果没有,请回来报告,我会再试一次:

static void _cairo_gdk_draw_pixbuf(cairo_t *cr, cairo_surface_t *source,
        int src_x, int src_y,
        int dest_x, int dest_y,
        int width, int height)
{
    cairo_save(cr);

    /* Move (0, 0) to the destination position */
    cairo_translate(cr, dest_x, dest_y);

    /* Set up the source surface in such a way that (src_x, src_y) maps to
     * (0, 0) in user coordinates. */
    cairo_set_source_surface(cr, source, -src_x, -src_y);

    /* Do the drawing */
    cairo_rectangle(cr, 0, 0, width, height);
    cairo_fill(cr);

    /* Undo all of our modifications to the drawing state */
    cairo_restore(cr);
}

上面的函数应该像gdk_draw_pixbuf一样工作(嗯,类似)。

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2014-04-21
    • 2012-01-07
    • 2012-09-04
    • 1970-01-01
    • 2012-10-23
    相关资源
    最近更新 更多