通过 GdkPixbuf 绘图绘制在错误的像素坐标
Drawing through GdkPixbuf draws at wrong pixel coordinates
这是我当前的代码:
static void put_pixel (GdkPixbuf *pixbuf, int x, int y, guchar red, guchar green, guchar blue, guchar alpha)
{
int width, height, rowstride, n_channels;
guchar *pixels, *p;
rowstride = gdk_pixbuf_get_rowstride (pixbuf);
pixels = gdk_pixbuf_get_pixels (pixbuf);
p = pixels + y * rowstride + x * 8;
p[0] = red;
p[1] = green;
p[2] = blue;
p[3] = alpha;
}
int main(int argc, char *argv[] ) {
gtk_init(&argc, &argv);
GtkWidget *window;
GdkColorspace colorspace = GDK_COLORSPACE_RGB;
GdkPixbuf *pixbuf;
GtkWidget *image;
window = gtk_dialog_new();
gtk_widget_set_size_request(window, 512, 512);
g_signal_connect(window, "destroy", G_CALLBACK (G_CALLBACK(gtk_main_quit)), NULL);
pixbuf = gdk_pixbuf_new(colorspace, TRUE, 8, 512, 512);
for(int i=0; i<512; i++) {
put_pixel(pixbuf, i, i, 255, 0, 255, 255);
}
image = gtk_image_new_from_pixbuf(pixbuf);
gtk_box_pack_start(GTK_BOX (GTK_DIALOG(window)->vbox), image, FALSE, FALSE, 0);
gtk_widget_show_all(window);
gtk_main();
}
我预计会有一条从 (0, 0) 到 (512, 512) 的紫色线。相反,我有一条从 (0, 0) 到 (256, 512) 的紫色线和一条从 (256, 0) 到 (512, 512) 的紫色线。
为什么会这样,我该如何解决?
您定义了变量但没有使用它(在 put_pixel
函数上)
解法:
static void put_pixel (GdkPixbuf *pixbuf, int x, int y, guchar red, guchar green, guchar blue, guchar alpha)
{
int width, height, rowstride, n_channels;
guchar *pixels, *p;
rowstride = gdk_pixbuf_get_rowstride (pixbuf);
pixels = gdk_pixbuf_get_pixels (pixbuf);
n_channels = gdk_pixbuf_get_n_channels (pixbuf);
p = pixels + y * rowstride + x * n_channels;
p[0] = red;
p[1] = green;
p[2] = blue;
p[3] = alpha;
}
您将 X 偏移了 8,应该是 4 (RGBA)。 Rowstride 也与通道数相关,在这种情况下你的图像高度是 512 所以 512 * n_channels = 2048.
结论:
在put_pixel
函数中,添加:
n_channels = gdk_pixbuf_get_n_channels (pixbuf);
并更改:
p = pixels + y * rowstride + x * 8;
至:
p = pixels + y * rowstride + x * n_channels;
这是我当前的代码:
static void put_pixel (GdkPixbuf *pixbuf, int x, int y, guchar red, guchar green, guchar blue, guchar alpha)
{
int width, height, rowstride, n_channels;
guchar *pixels, *p;
rowstride = gdk_pixbuf_get_rowstride (pixbuf);
pixels = gdk_pixbuf_get_pixels (pixbuf);
p = pixels + y * rowstride + x * 8;
p[0] = red;
p[1] = green;
p[2] = blue;
p[3] = alpha;
}
int main(int argc, char *argv[] ) {
gtk_init(&argc, &argv);
GtkWidget *window;
GdkColorspace colorspace = GDK_COLORSPACE_RGB;
GdkPixbuf *pixbuf;
GtkWidget *image;
window = gtk_dialog_new();
gtk_widget_set_size_request(window, 512, 512);
g_signal_connect(window, "destroy", G_CALLBACK (G_CALLBACK(gtk_main_quit)), NULL);
pixbuf = gdk_pixbuf_new(colorspace, TRUE, 8, 512, 512);
for(int i=0; i<512; i++) {
put_pixel(pixbuf, i, i, 255, 0, 255, 255);
}
image = gtk_image_new_from_pixbuf(pixbuf);
gtk_box_pack_start(GTK_BOX (GTK_DIALOG(window)->vbox), image, FALSE, FALSE, 0);
gtk_widget_show_all(window);
gtk_main();
}
我预计会有一条从 (0, 0) 到 (512, 512) 的紫色线。相反,我有一条从 (0, 0) 到 (256, 512) 的紫色线和一条从 (256, 0) 到 (512, 512) 的紫色线。
为什么会这样,我该如何解决?
您定义了变量但没有使用它(在 put_pixel
函数上)
解法:
static void put_pixel (GdkPixbuf *pixbuf, int x, int y, guchar red, guchar green, guchar blue, guchar alpha)
{
int width, height, rowstride, n_channels;
guchar *pixels, *p;
rowstride = gdk_pixbuf_get_rowstride (pixbuf);
pixels = gdk_pixbuf_get_pixels (pixbuf);
n_channels = gdk_pixbuf_get_n_channels (pixbuf);
p = pixels + y * rowstride + x * n_channels;
p[0] = red;
p[1] = green;
p[2] = blue;
p[3] = alpha;
}
您将 X 偏移了 8,应该是 4 (RGBA)。 Rowstride 也与通道数相关,在这种情况下你的图像高度是 512 所以 512 * n_channels = 2048.
结论:
在put_pixel
函数中,添加:
n_channels = gdk_pixbuf_get_n_channels (pixbuf);
并更改:
p = pixels + y * rowstride + x * 8;
至:
p = pixels + y * rowstride + x * n_channels;