1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
|
#include <config.h>
#include "diacellrendererenum.h"
#include "properties.h"
enum
{
COLUMN_ENUM_NAME,
COLUMN_ENUM_VALUE,
NUM_ENUM_COLUMNS
};
/*!
* \brief Signal handler GtkCellRendererCombo::changed:
*
* From GTK+:
*
* @renderer: the object on which the signal is emitted
* @path_string: a string of the path identifying the edited cell
* (relative to the tree view model)
* @iter: the new iter selected in the combo box
* (relative to the combo box model)
*
* This signal is emitted each time after the user selected an item in
* the combo box, either by using the mouse or the arrow keys. Contrary
* to GtkComboBox, GtkCellRendererCombo::changed is not emitted for
* changes made to a selected item in the entry. The argument 'iter'
* corresponds to the newly selected item in the combo box and it is relative
* to the GtkTreeModel set via the model property on GtkCellRendererCombo.
*
* Note that as soon as you change the model displayed in the tree view,
* the tree view will immediately cease the editing operating. This
* means that you most probably want to refrain from changing the model
* until the combo cell renderer emits the edited or editing_canceled signal.
*/
static void
_enum_changed (GtkCellRenderer *renderer,
const char *path_string,
GtkTreeIter *iter,
GtkTreeView *tree_view)
{
GtkTreeModel *store = gtk_tree_view_get_model (tree_view);
int val, column;
GtkTreeModel *model;
GtkTreeIter store_iter;
g_object_get (G_OBJECT (renderer), "model", &model, NULL);
/* read the enum value from the combobox model */
gtk_tree_model_get (model, iter, COLUMN_ENUM_VALUE, &val, -1);
/* put it into the store model */
column = GPOINTER_TO_INT (g_object_get_data (G_OBJECT (renderer), COLUMN_KEY));
if (gtk_tree_model_get_iter_from_string (store, &store_iter, path_string))
gtk_tree_store_set (GTK_TREE_STORE (store), &store_iter, column, val, -1);
g_print ("changed: %d - %s\n", val, path_string);
}
/*!
* \brief Signal handler GtkCellRendererText::edited
'
* From GTK+:
* This signal is emitted after @renderer has been edited.
*
* It is the responsibility of the application to update the model
* and store @new_text at the position indicated by @path.
*/
static void
_enum_edited (GtkCellRenderer *renderer,
const char *path_string,
const char *new_string,
GtkTreeView *tree_view)
{
GtkTreeModel *store = gtk_tree_view_get_model (tree_view);
/* Despite the comment for _enum_changed we have changed the model already
* there. Changing it here would involve some caching of the value there
* or translating new_string back to the enumv we need for the store.
* But we have to mark the store to be modified otherwise only the UI state
* would change without transferring back in _arrayprop_set_from_widget()
*/
g_object_set_data (G_OBJECT (store), "modified", GINT_TO_POINTER (1));
g_print ("edited: %d - %s\n", new_string);
}
GtkCellRenderer *
dia_cell_renderer_enum_new (const PropEnumData *enum_data, GtkTreeView *tree_view)
{
/* The combo-renderer should be customized for better rendering,
* e.g. using a shorter name like visible_char[]={ '+', '-', '#', ' ' } instead of
* the full of _uml_visibilities[]; likewise for line style there or arrows there
* should be a pixbuf preview instead of strings ...
*/
GtkCellRenderer *cell_renderer = gtk_cell_renderer_combo_new ();
/* create the model from enum_data */
GtkListStore *model;
GtkTreeIter iter;
int i;
model = gtk_list_store_new (NUM_ENUM_COLUMNS, G_TYPE_STRING, G_TYPE_INT);
for (i = 0; enum_data[i].name != NULL; ++i) {
gtk_list_store_append (model, &iter);
gtk_list_store_set (model, &iter,
COLUMN_ENUM_NAME, enum_data[i].name,
COLUMN_ENUM_VALUE, enum_data[i].enumv,
-1);
}
g_object_set (cell_renderer,
"model", model,
"text-column", COLUMN_ENUM_NAME,
"has-entry", FALSE,
"editable", TRUE,
NULL);
g_signal_connect (G_OBJECT (cell_renderer), "changed",
G_CALLBACK (_enum_changed), tree_view);
g_signal_connect (G_OBJECT (cell_renderer), "edited",
G_CALLBACK (_enum_edited), tree_view);
return cell_renderer;
}
|