9

gtkmm を使用してカスタム ウィジェットを作成していますが、空き地で動作させることができませんでした。(ウィジェット自体はほとんど機能しません。動作します。次のステップに進む前に、Grade で動作させたいと思います。) Glade はウィジェットを見つけますが、ウィンドウに配置しようとすると、glade がクラッシュします。

さまざまな検索中に見つけたヒントに基づいて、次のコードをメイン ソース ファイルに追加しました。

extern "C"
{
    GType date_chooser_get_type(void)
    {
        return DateChooser::get_type();
    }
}

上記のコードが正しくないのではないかと疑っていますが、この関数が何をすべきかについての gtkmm やグレードのドキュメントが見つかりません。

グレードのカタログ ドキュメントに基づいて、次の XML を作成しました。

<?xml version="1.0" encoding="UTF-8"?>
<glade-catalog name="gtk-date-chooser" library="libgtkdatechooser-0.1.so" language="c++">
  <glade-widget-classes>
    <glade-widget-class name="DateChooser" generic-name="date-chooser" title="Date Chooser" />
  </glade-widget-classes>
  <glade-widget-group name="date" title="Date">
    <glade-widget-class-ref name="DateChooser"/>
  </glade-widget-group>
</glade-catalog>

これは、ウィジェットのソース ディレクトリのルートにあり、名前はgtk-date-chooser.xml. 次を使用して、そのディレクトリでグレードを実行します。

GLADE_CATALOG_SEARCH_PATH=. GLADE_MODULE_SEARCH_PATH=./.libs glade

ウィンドウが表示されると、ウィジェットはカタログで指定された特別な「日付」グループにデフォルトのアイコンで表示されます。ウィンドウを配置し、ウィンドウに配置するウィジェットを選択すると、glade がクラッシュします。コンソールに次のように表示されます。

GladeUI-Message: 2 missing displayable value for GtkWidget::events
GladeUI-Message: No displayable values for property GtkTreeSelection::mode
GladeUI-Message: 1 missing displayable value for GtkCellRendererAccel::accel-mode
GladeUI-Message: 14 missing displayable value for GtkCellRendererAccel::accel-mods

(glade:23757): GladeUI-CRITICAL **: gwa_list_signals: assertion `real_type != 0' failed

(glade:23757): GLib-GObject-WARNING **: cannot retrieve class for invalid (unclassed) type `<invalid>'

(glade:23757): GLib-GObject-CRITICAL **: g_object_class_list_properties: assertion `G_IS_OBJECT_CLASS (class)' failed

(glade:23757): GLib-GObject-WARNING **: cannot retrieve class for invalid (unclassed) type `<invalid>'

(glade:23757): Gtk-CRITICAL **: gtk_container_class_list_child_properties: assertion `GTK_IS_CONTAINER_CLASS (cclass)' failed
GladeUI-Message: Glade needs artwork; a default icon will be used for the following classes:
    DateChooser needs an icon named 'widget-gtk-date-chooser-date-chooser'
**
GladeUI:ERROR:glade-signal-model.c:800:glade_signal_model_iter_n_children: code should not be reached

この (未回答の) 質問への回答が手がかりになるようですが、その質問に対する回答や、私の問題を解決する手がかりを見つけることができませんでした。

私が使用しているバージョン:

  • Ubuntu: 12.04
  • gtkmm: 3.4.0-0ubuntu1
  • グレード: 3.12.0-0ubuntu1

(トランクのバージョン、または Centos 6 または Fedora 16 に基づいてソリューションをテストしたいと思います。)

4

1 に答える 1

5

カスタムgtkmmウィジェットをGladeに追加するには、以下が必要です。

  1. 少なくとも1つの純粋なカスタムウィジェットの実装
  2. カスタムウィジェットへのいくつかのGlade関連の追加機能
  3. Gladeへのカスタムウィジェットを説明するカタログファイル
  4. ライブラリには、カスタムウィジェットといくつかのGlade関連の関数が含まれています

最も重要なことは、GladeがC ++ではなくCで記述されているという事実です。したがって、プランCウィジェットをC ++ウィジェットにラップできる必要があり、このラップ関数をカスタムウィジェットに関連するものに登録する必要があります。次のようになります。GType

#include "custom_widget.h"

GType CustomWidget::gtype = 0;

CustomWidget::CustomWidget (GtkEntry *gobj) :
  Gtk::Entry (gobj)
{
}

CustomWidget::CustomWidget () :
  Glib::ObjectBase ("customwidget")
{
}

Glib::ObjectBase *
CustomWidget::wrap_new (GObject *o)
{
  if (gtk_widget_is_toplevel (GTK_WIDGET (o)))
    {
      return new CustomWidget (GTK_ENTRY (o));
    }
  else
    {
      return Gtk::manage(new CustomWidget (GTK_ENTRY (o)));
    }
}

void
CustomWidget::register_type ()
{
  if (gtype)
    return;

  CustomWidget dummy;

  GtkWidget *widget = GTK_WIDGET (dummy.gobj ());

  gtype = G_OBJECT_TYPE (widget);

  Glib::wrap_register (gtype, CustomWidget::wrap_new);
}

カタログファイルは慎重に作成する必要があります。適切な作業を行うには、名前が(特にglade-widget-class)正しくなければなりません。

<?xml version="1.0" encoding="UTF-8" ?>
<glade-catalog name="customwidgets" library="customwidgetsglade" depends="gtk+">

  <init-function>custom_widgets_glade_init</init-function>

  <glade-widget-classes>
    <glade-widget-class name="gtkmm__CustomObject_customwidget" generic-name="customwidget" icon-name="widget-gtk-entry" title="Custom Widget">
    </glade-widget-class>
  </glade-widget-classes>

  <glade-widget-group name="customwidgets" title="Custom Widgets" >
    <glade-widget-class-ref name="gtkmm__CustomObject_customwidget" />
  </glade-widget-group>

</glade-catalog>

何もすることはありませんが、Gladeライブラリの初期化の一部としてウィジェットを登録する関数を実装します。

extern "C" void
custom_widgets_glade_init ()
{
  Gtk::Main::init_gtkmm_internals ();
  custom_widgets_register ();
}

gtkmmの内部を 初期化することcustom_widgets_glade_initは必須です。Gladeから呼び出されます。GladeはC++ではなくCで記述されているため、 GTK+のみを初期化します。

このトピックに興味がある場合は、詳細が記載された私のブログ投稿をここで見つけることができます。

于 2012-06-13T09:30:13.827 に答える