Skip to content
GitLab
Menu
Projects
Groups
Snippets
Loading...
Help
Help
Support
Community forum
Keyboard shortcuts
?
Submit feedback
Sign in / Register
Toggle navigation
Menu
Open sidebar
Dorota Czaplejewicz
gtk
Commits
2dafbba9
Commit
2dafbba9
authored
Jan 09, 2011
by
Tristan Van Berkom
Browse files
Added GtkBuildable support for specifying <items> in GtkComboBoxText.
parent
cfecb6bf
Changes
1
Hide whitespace changes
Inline
Side-by-side
gtk/gtkcomboboxtext.c
View file @
2dafbba9
...
...
@@ -22,6 +22,10 @@
#include "gtkcombobox.h"
#include "gtkcellrenderertext.h"
#include "gtkcelllayout.h"
#include "gtkbuildable.h"
#include "gtkbuilderprivate.h"
#include <string.h>
/**
* SECTION:gtkcomboboxtext
...
...
@@ -44,9 +48,50 @@
* its contents can be retrieved using gtk_combo_box_text_get_active_text().
* The entry itself can be accessed by calling gtk_bin_get_child() on the
* combo box.
*
* <refsect2 id="GtkComboBoxText-BUILDER-UI">
* <title>GtkComboBoxText as GtkBuildable</title>
* <para>
* The GtkComboBoxText implementation of the GtkBuildable interface
* supports adding items directly using the <items> element
* and specifying <item> elements for each item. Each <item>
* element supports the regular translation attributes "translatable",
* "context" and "comments".
*
* <example>
* <title>A UI definition fragment specifying GtkComboBoxText items</title>
* <programlisting><![CDATA[
* <object class="GtkComboBoxText">
* <items>
* <item translatable="yes">Factory</item>
* <item translatable="yes">Home</item>
* <item translatable="yes">Subway</item>
* </items>
* </object>
* ]]></programlisting>
* </example>
*
*/
G_DEFINE_TYPE
(
GtkComboBoxText
,
gtk_combo_box_text
,
GTK_TYPE_COMBO_BOX
);
static
void
gtk_combo_box_text_buildable_interface_init
(
GtkBuildableIface
*
iface
);
static
gboolean
gtk_combo_box_text_buildable_custom_tag_start
(
GtkBuildable
*
buildable
,
GtkBuilder
*
builder
,
GObject
*
child
,
const
gchar
*
tagname
,
GMarkupParser
*
parser
,
gpointer
*
data
);
static
void
gtk_combo_box_text_buildable_custom_finished
(
GtkBuildable
*
buildable
,
GtkBuilder
*
builder
,
GObject
*
child
,
const
gchar
*
tagname
,
gpointer
user_data
);
static
GtkBuildableIface
*
buildable_parent_iface
=
NULL
;
G_DEFINE_TYPE_WITH_CODE
(
GtkComboBoxText
,
gtk_combo_box_text
,
GTK_TYPE_COMBO_BOX
,
G_IMPLEMENT_INTERFACE
(
GTK_TYPE_BUILDABLE
,
gtk_combo_box_text_buildable_interface_init
));
static
GObject
*
gtk_combo_box_text_constructor
(
GType
type
,
...
...
@@ -91,6 +136,174 @@ gtk_combo_box_text_class_init (GtkComboBoxTextClass *klass)
object_class
->
constructor
=
gtk_combo_box_text_constructor
;
}
static
void
gtk_combo_box_text_buildable_interface_init
(
GtkBuildableIface
*
iface
)
{
buildable_parent_iface
=
g_type_interface_peek_parent
(
iface
);
iface
->
custom_tag_start
=
gtk_combo_box_text_buildable_custom_tag_start
;
iface
->
custom_finished
=
gtk_combo_box_text_buildable_custom_finished
;
}
typedef
struct
{
GtkBuilder
*
builder
;
GObject
*
object
;
const
gchar
*
domain
;
gchar
*
context
;
gchar
*
string
;
guint
translatable
:
1
;
guint
is_text
:
1
;
}
ItemParserData
;
static
void
item_start_element
(
GMarkupParseContext
*
context
,
const
gchar
*
element_name
,
const
gchar
**
names
,
const
gchar
**
values
,
gpointer
user_data
,
GError
**
error
)
{
ItemParserData
*
data
=
(
ItemParserData
*
)
user_data
;
guint
i
;
if
(
strcmp
(
element_name
,
"item"
)
==
0
)
{
data
->
is_text
=
TRUE
;
for
(
i
=
0
;
names
[
i
];
i
++
)
{
if
(
strcmp
(
names
[
i
],
"translatable"
)
==
0
)
{
gboolean
bval
;
if
(
!
_gtk_builder_boolean_from_string
(
values
[
i
],
&
bval
,
error
))
return
;
data
->
translatable
=
bval
;
}
else
if
(
strcmp
(
names
[
i
],
"comments"
)
==
0
)
{
/* do nothing, comments are for translators */
}
else
if
(
strcmp
(
names
[
i
],
"context"
)
==
0
)
data
->
context
=
g_strdup
(
values
[
i
]);
else
g_warning
(
"Unknown custom combo box item attribute: %s"
,
names
[
i
]);
}
}
}
static
void
item_text
(
GMarkupParseContext
*
context
,
const
gchar
*
text
,
gsize
text_len
,
gpointer
user_data
,
GError
**
error
)
{
ItemParserData
*
data
=
(
ItemParserData
*
)
user_data
;
gchar
*
string
;
if
(
!
data
->
is_text
)
return
;
string
=
g_strndup
(
text
,
text_len
);
if
(
data
->
translatable
&&
text_len
)
{
gchar
*
translated
;
/* FIXME: This will not use the domain set in the .ui file,
* since the parser is not telling the builder about the domain.
* However, it will work for gtk_builder_set_translation_domain() calls.
*/
translated
=
_gtk_builder_parser_translate
(
data
->
domain
,
data
->
context
,
string
);
g_free
(
string
);
string
=
translated
;
}
data
->
string
=
string
;
}
static
void
item_end_element
(
GMarkupParseContext
*
context
,
const
gchar
*
element_name
,
gpointer
user_data
,
GError
**
error
)
{
ItemParserData
*
data
=
(
ItemParserData
*
)
user_data
;
/* Append the translated strings */
if
(
data
->
string
)
gtk_combo_box_text_append_text
(
GTK_COMBO_BOX_TEXT
(
data
->
object
),
data
->
string
);
data
->
translatable
=
FALSE
;
g_free
(
data
->
context
);
g_free
(
data
->
string
);
data
->
context
=
NULL
;
data
->
string
=
NULL
;
data
->
is_text
=
FALSE
;
}
static
const
GMarkupParser
item_parser
=
{
item_start_element
,
item_end_element
,
item_text
};
static
gboolean
gtk_combo_box_text_buildable_custom_tag_start
(
GtkBuildable
*
buildable
,
GtkBuilder
*
builder
,
GObject
*
child
,
const
gchar
*
tagname
,
GMarkupParser
*
parser
,
gpointer
*
data
)
{
if
(
buildable_parent_iface
->
custom_tag_start
(
buildable
,
builder
,
child
,
tagname
,
parser
,
data
))
return
TRUE
;
if
(
strcmp
(
tagname
,
"items"
)
==
0
)
{
ItemParserData
*
parser_data
;
parser_data
=
g_slice_new0
(
ItemParserData
);
parser_data
->
builder
=
g_object_ref
(
builder
);
parser_data
->
object
=
g_object_ref
(
buildable
);
parser_data
->
domain
=
gtk_builder_get_translation_domain
(
builder
);
*
parser
=
item_parser
;
*
data
=
parser_data
;
return
TRUE
;
}
return
FALSE
;
}
static
void
gtk_combo_box_text_buildable_custom_finished
(
GtkBuildable
*
buildable
,
GtkBuilder
*
builder
,
GObject
*
child
,
const
gchar
*
tagname
,
gpointer
user_data
)
{
ItemParserData
*
data
;
buildable_parent_iface
->
custom_finished
(
buildable
,
builder
,
child
,
tagname
,
user_data
);
if
(
strcmp
(
tagname
,
"items"
)
==
0
)
{
data
=
(
ItemParserData
*
)
user_data
;
g_object_unref
(
data
->
object
);
g_object_unref
(
data
->
builder
);
g_slice_free
(
ItemParserData
,
data
);
}
}
/**
* gtk_combo_box_text_new:
...
...
@@ -265,17 +478,24 @@ gtk_combo_box_text_insert (GtkComboBoxText *combo_box,
g_return_if_fail
(
GTK_IS_COMBO_BOX_TEXT
(
combo_box
));
g_return_if_fail
(
text
!=
NULL
);
if
(
position
<
0
)
position
=
G_MAXINT
;
store
=
GTK_LIST_STORE
(
gtk_combo_box_get_model
(
GTK_COMBO_BOX
(
combo_box
)));
g_return_if_fail
(
GTK_IS_LIST_STORE
(
store
));
text_column
=
gtk_combo_box_get_entry_text_column
(
GTK_COMBO_BOX
(
combo_box
));
g_return_if_fail
(
text_column
>=
0
);
if
(
gtk_combo_box_get_has_entry
(
GTK_COMBO_BOX
(
combo_box
)))
g_return_if_fail
(
text_column
>=
0
);
else
if
(
text_column
<
0
)
text_column
=
0
;
column_type
=
gtk_tree_model_get_column_type
(
GTK_TREE_MODEL
(
store
),
text_column
);
g_return_if_fail
(
column_type
==
G_TYPE_STRING
);
gtk_list_store_insert
(
store
,
&
iter
,
position
);
if
(
position
<
0
)
gtk_list_store_append
(
store
,
&
iter
);
else
gtk_list_store_insert
(
store
,
&
iter
,
position
);
gtk_list_store_set
(
store
,
&
iter
,
text_column
,
text
,
-
1
);
if
(
id
!=
NULL
)
...
...
Write
Preview
Markdown
is supported
0%
Try again
or
attach a new file
.
Attach a file
Cancel
You are about to add
0
people
to the discussion. Proceed with caution.
Finish editing this message first!
Cancel
Please
register
or
sign in
to comment