2014-09-13 125 views
5

你知道如何在GTK 3中創建自定義小部件?我試圖在C中繼承GtkDrawingArea數小時。 Gnome.org僅提供了關於如何繼承G_OBJECT的簡潔教程。我的問題是,G_Object/GTK失敗GTK_WIDGET鑄造時查看我的自定義StrokerNodalContainerGtkWidget一個子類,甚至是艱難的我的定義struct包含這樣一行:如何在C中的GTK3中創建自定義小部件?

GtkDrawingArea parent_instance; 

它說:

invalid cast from 'StrokerNodalContainer' to 'GtkWidget' 

這裏是完整的代碼,如果你懷疑別的東西可能是錯的。這是最小的,所以我沒有看到任何外部代碼搞亂的原因。

司爐-nodalcontainer.h

#ifndef __STROKER_NODALCONTAINER_H__ 
#define __STROKER_NODALCONTAINER_H__ 

#ifndef NO_INCLUDE_WITHIN_HEADERS 
#include <gtk/gtk.h> 
#endif 

#define STROKER_TYPE_NODAL_CONTAINER     (stroker_nodal_container_get_type()) 
#define STROKER_NODAL_CONTAINER(obj)     (G_TYPE_CHECK_INSTANCE_CAST ((obj), STROKER_TYPE_NODAL_CONTAINER, StrokerNodalContainer)) 
#define STROKER_NODAL_CONTAINER_CLASS(klass)   (G_TYPE_CHECK_CLASS_CAST ((klass), STROKER_TYPE_NODAL_CONTAINER, StrokerNodalContainerClass)) 
#define STROKER_IS_NODAL_CONTAINER(obj)    (G_TYPE_CHECK_INSTANCE_TYPE ((obj), STROKER_TYPE_NODAL_CONTAINER)) 
#define STROKER_IS_NODAL_CONTAINER_CLASS(klass)  (G_TYPE_CHECK_CLASS_TYPE ((klass), STROKER_TYPE_NODAL_CONTAINER)) 
#define STROKER_NODAL_CONTAINER_GET_CLASS(obj)  (G_TYPE_INSTANCE_GET_CLASS ((obj), STROKER_TYPE_NODAL_CONTAINER, StrokerNodalContainerClass)) 

typedef struct _StrokerNodalContainer  StrokerNodalContainer; 
typedef struct _StrokerNodalContainerClass StrokerNodalContainerClass; 

struct _StrokerNodalContainer 
{ 
    GtkDrawingArea parent_instance; 
}; 

struct _StrokerNodalContainerClass 
{ 
    GtkDrawingAreaClass parent_class; 
}; 

GType stroker_nodal_container_get_type(void); 

//StrokerNodalContainer* stroker_nodalcontainer_new(void); 

#endif /* __STROKER_NODALCONTAINER_H__ */ 

司爐-nodalcontainer.c

#include <gtk/gtk.h> 
#include "stroker-nodalcontainer.h" 

G_DEFINE_TYPE(StrokerNodalContainer, stroker_nodal_container, G_TYPE_OBJECT) 

static void stroker_nodal_container_class_init(StrokerNodalContainerClass* klass) 
    {} 

static void stroker_nodal_container_init(StrokerNodalContainer* self) 
{ 
    GdkRGBA c; 
    GtkWidget *widget; 

    gdk_rgba_parse(&c, "blue"); 
    widget = GTK_WIDGET(self); 

    gtk_widget_override_background_color(widget, GTK_STATE_FLAG_NORMAL, &c); 
} 

的main.c

#include <stdlib.h> 
#include <stdio.h> 
#include <gtk/gtk.h> 
#include <cairo/cairo.h> 

#include "stroker-nodalcontainer.h" 

int main(int argc, char *argv[]) 
{ 
    GtkWidget *window; 
    GtkWidget *nodalWidget; 

    gtk_init(&argc, &argv); 

    window = gtk_window_new(GTK_WINDOW_TOPLEVEL); 
    gtk_window_set_title (GTK_WINDOW (window), "Stroker"); 
    g_signal_connect(window, "destroy", G_CALLBACK (gtk_main_quit), NULL); 
    gtk_container_set_border_width(GTK_CONTAINER(window), 10); 
    gtk_widget_show (window); 

    nodalWidget = g_object_new(STROKER_TYPE_NODAL_CONTAINER,NULL); 
    gtk_container_add(GTK_CONTAINER(window), nodalWidget); 
    gtk_widget_show (nodalWidget); 

    gtk_main(); 


    return EXIT_SUCCESS; 
} 

Ť要求任何幫助!

+0

在官方wiki上有一個例子,但它使用的是Vala,而不是C,https://wiki.gnome.org/Projects/Vala/CustomWidgetSamples – user2485710 2014-09-13 15:10:10

+0

是的,但Vala或C++或Java或Python非常簡單:類繼承特性是語言的核心,所以他們只是使用它。我無法識別我的GObject繼承。 – 2014-09-13 16:09:46

+0

Vala編譯爲C89 + Glib + Gobject,我建議如下:在Vala中編寫基本的代碼,將Vala編譯爲C,檢查生成的C代碼。 – user2485710 2014-09-13 16:13:35

回答

3

錯誤消息是,可能是因爲此:

G_DEFINE_TYPE(StrokerNodalContainer, stroker_nodal_container, G_TYPE_OBJECT) 

如果你看一下documentation for G_DEFINE_TYPE()你會看到第三個參數應該是父類型:您可能希望GTK_TYPE_DRAWING_AREA這裏。

+0

就是這樣。該教程非常快,並說「父GType」。 – 2014-09-13 22:07:07

相關問題