Compilation: don't compile dialogs separately.
[gnumeric.git] / src / dialogs / dialog-analysis-tool-kaplan-meier.c
blob55745dd3499bce698810bd0426f2cddc76461d79
1 /* vim: set sw=8: -*- Mode: C; tab-width: 8; indent-tabs-mode: t; c-basic-offset: 8 -*- */
2 /*
3 * dialog-analysis-tool-kaplan-meier.c:
5 * Authors:
6 * Andreas J. Guelzow <aguelzow@taliesin.ca>
8 * (C) Copyright 2008 by Andreas J. Guelzow <aguelzow@pyrshep.ca>
10 * This program is free software; you can redistribute it and/or modify
11 * it under the terms of the GNU General Public License as published by
12 * the Free Software Foundation; either version 2 of the License, or
13 * (at your option) any later version.
15 * This program is distributed in the hope that it will be useful,
16 * but WITHOUT ANY WARRANTY; without even the implied warranty of
17 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
18 * GNU General Public License for more details.
20 * You should have received a copy of the GNU General Public License
21 * along with this program; if not, see <https://www.gnu.org/licenses/>.
24 #include <gnumeric-config.h>
25 #include <glib/gi18n-lib.h>
26 #include <gnumeric.h>
27 #include "dialogs.h"
28 #include "analysis-kaplan-meier.h"
29 #include "analysis-tools.h"
31 #include <workbook.h>
32 #include <workbook-control.h>
33 #include <wbc-gtk.h>
34 #include <workbook-view.h>
35 #include <gui-util.h>
36 #include <parse-util.h>
37 #include <gnm-format.h>
38 #include <tool-dialogs.h>
39 #include <dao-gui-utils.h>
40 #include <sheet.h>
41 #include <expr.h>
42 #include <number-match.h>
43 #include <ranges.h>
44 #include <selection.h>
45 #include <value.h>
46 #include <commands.h>
47 #include "help.h"
49 #include <widgets/gnm-dao.h>
50 #include <widgets/gnumeric-expr-entry.h>
52 #include <string.h>
53 #include <gtk/gtk.h>
55 #define KAPLAN_MEIER_KEY "analysistools-kaplan-meier-dialog"
57 typedef struct {
58 GnmGenericToolState base;
59 GtkWidget *censorship_button;
60 GtkWidget *censor_spin_from;
61 GtkWidget *censor_spin_to;
62 GtkWidget *graph_button;
63 GtkWidget *logrank_button;
64 GtkWidget *tick_button;
65 GtkWidget *add_group_button;
66 GtkWidget *remove_group_button;
67 GtkWidget *std_error_button;
68 GtkWidget *groups_check;
69 GtkWidget *groups_grid;
70 GnmExprEntry *groups_input;
71 GtkTreeView *groups_treeview;
72 GtkListStore *groups_list;
73 } KaplanMeierToolState;
75 enum
77 GROUP_NAME,
78 GROUP_FROM,
79 GROUP_TO,
80 GROUP_ADJUSTMENT_FROM,
81 GROUP_ADJUSTMENT_TO,
82 GROUP_COLUMNS
86 /**
87 * kaplan_meier_tool_update_sensitivity_cb:
88 * @dummy:
89 * @state:
91 * Update the dialog widgets sensitivity
92 **/
93 static void
94 kaplan_meier_tool_update_sensitivity_cb (G_GNUC_UNUSED GtkWidget *dummy,
95 KaplanMeierToolState *state)
97 gboolean censorship;
98 gboolean groups;
99 GnmValue *input_range;
100 GnmValue *input_range_2 = NULL;
101 int height, width;
103 censorship = gtk_toggle_button_get_active (
104 GTK_TOGGLE_BUTTON (state->censorship_button));
105 groups = gtk_toggle_button_get_active (
106 GTK_TOGGLE_BUTTON (state->groups_check));
108 gtk_widget_set_sensitive (state->tick_button, censorship);
110 input_range = gnm_expr_entry_parse_as_value
111 (GNM_EXPR_ENTRY (state->base.input_entry), state->base.sheet);
112 if (input_range == NULL) {
113 gtk_label_set_text (GTK_LABEL (state->base.warning),
114 _("The time column is not valid."));
115 gtk_widget_set_sensitive (state->base.ok_button, FALSE);
116 return;
119 height = input_range->v_range.cell.b.row - input_range->v_range.cell.a.row;
120 width = input_range->v_range.cell.b.col - input_range->v_range.cell.a.col;
122 value_release (input_range);
124 if (width != 0) {
125 gtk_label_set_text (GTK_LABEL (state->base.warning),
126 _("The time column should be part of a single column."));
127 gtk_widget_set_sensitive (state->base.ok_button, FALSE);
128 return;
131 if (censorship) {
132 input_range_2 = gnm_expr_entry_parse_as_value
133 (GNM_EXPR_ENTRY (state->base.input_entry_2), state->base.sheet);
134 if (input_range_2 == NULL) {
135 gtk_label_set_text (GTK_LABEL (state->base.warning),
136 _("The censorship column is not valid."));
137 gtk_widget_set_sensitive (state->base.ok_button, FALSE);
138 return;
141 if (input_range_2->v_range.cell.b.col != input_range_2->v_range.cell.a.col) {
142 gtk_label_set_text (GTK_LABEL (state->base.warning),
143 _("The censorship column should be part of a single column."));
144 gtk_widget_set_sensitive (state->base.ok_button, FALSE);
145 value_release (input_range_2);
146 return;
148 if (input_range_2->v_range.cell.b.row - input_range_2->v_range.cell.a.row != height) {
149 gtk_label_set_text (GTK_LABEL (state->base.warning),
150 _("The censorship and time columns should have the same height."));
151 gtk_widget_set_sensitive (state->base.ok_button, FALSE);
152 value_release (input_range_2);
153 return;
156 value_release (input_range_2);
159 if (groups) {
160 input_range_2 = gnm_expr_entry_parse_as_value
161 (GNM_EXPR_ENTRY (state->groups_input), state->base.sheet);
163 if (input_range_2 == NULL) {
164 gtk_label_set_text (GTK_LABEL (state->base.warning),
165 _("The groups column is not valid."));
166 gtk_widget_set_sensitive (state->base.ok_button, FALSE);
167 return;
169 if (input_range_2->v_range.cell.b.col != input_range_2->v_range.cell.a.col) {
170 gtk_label_set_text (GTK_LABEL (state->base.warning),
171 _("The groups column should be part of a single column."));
172 gtk_widget_set_sensitive (state->base.ok_button, FALSE);
173 value_release (input_range_2);
174 return;
176 if (input_range_2->v_range.cell.b.row - input_range_2->v_range.cell.a.row != height) {
177 gtk_label_set_text (GTK_LABEL (state->base.warning),
178 _("The groups and time columns should have the same height."));
179 gtk_widget_set_sensitive (state->base.ok_button, FALSE);
180 value_release (input_range_2);
181 return;
184 value_release (input_range_2);
187 if (!gnm_dao_is_ready (GNM_DAO (state->base.gdao))) {
188 gtk_label_set_text (GTK_LABEL (state->base.warning),
189 _("The output specification "
190 "is invalid."));
191 gtk_widget_set_sensitive (state->base.ok_button, FALSE);
192 return;
195 gtk_label_set_text (GTK_LABEL (state->base.warning), "");
196 gtk_widget_set_sensitive (state->base.ok_button, TRUE);
198 return;
201 static gboolean
202 kaplan_meier_tool_get_groups_cb (GtkTreeModel *model,
203 G_GNUC_UNUSED GtkTreePath *path,
204 GtkTreeIter *iter,
205 gpointer data)
207 GSList **list = data;
208 analysis_tools_kaplan_meier_group_t *group_item =
209 g_new0 (analysis_tools_kaplan_meier_group_t, 1);
211 gtk_tree_model_get (model, iter,
212 GROUP_NAME, &(group_item->name),
213 GROUP_FROM, &(group_item->group_from),
214 GROUP_TO, &(group_item->group_to),
215 -1);
216 *list = g_slist_prepend (*list, group_item);
218 return FALSE;
221 static GSList *
222 kaplan_meier_tool_get_groups (KaplanMeierToolState *state)
224 GSList *list = NULL;
226 if (!gtk_toggle_button_get_active (GTK_TOGGLE_BUTTON (state->groups_check)))
227 return NULL;
229 gtk_tree_model_foreach (GTK_TREE_MODEL (state->groups_list),
230 kaplan_meier_tool_get_groups_cb,
231 &list);
232 return g_slist_reverse (list);
236 * kaplan_meier_tool_ok_clicked_cb:
237 * @button:
238 * @state:
240 * Retrieve the information from the dialog and call the kaplan_meier_tool.
241 * Note that we assume that the ok_button is only active if the entry fields
242 * contain sensible data.
244 static void
245 kaplan_meier_tool_ok_clicked_cb (G_GNUC_UNUSED GtkWidget *button,
246 KaplanMeierToolState *state)
248 data_analysis_output_t *dao;
249 analysis_tools_data_kaplan_meier_t *data;
251 data = g_new0 (analysis_tools_data_kaplan_meier_t, 1);
252 dao = parse_output ((GnmGenericToolState *)state, NULL);
255 data->base.wbc = GNM_WBC (state->base.wbcg);
257 if (state->base.warning_dialog != NULL)
258 gtk_widget_destroy (state->base.warning_dialog);
260 data->base.range_1 = gnm_expr_entry_parse_as_value
261 (GNM_EXPR_ENTRY (state->base.input_entry), state->base.sheet);
263 data->censored = gtk_toggle_button_get_active (
264 GTK_TOGGLE_BUTTON (state->censorship_button));
266 if (data->censored)
267 data->base.range_2 = gnm_expr_entry_parse_as_value
268 (GNM_EXPR_ENTRY (state->base.input_entry_2), state->base.sheet);
269 else
270 data->base.range_2 = NULL;
272 data->censor_mark = gtk_spin_button_get_value_as_int (GTK_SPIN_BUTTON (state->censor_spin_from));
273 data->censor_mark_to = gtk_spin_button_get_value_as_int (GTK_SPIN_BUTTON (state->censor_spin_to));
275 data->group_list = kaplan_meier_tool_get_groups (state);
276 if (data->group_list == NULL) {
277 data->range_3 = NULL;
278 data->logrank_test = FALSE;
279 } else {
280 data->range_3 = gnm_expr_entry_parse_as_value
281 (GNM_EXPR_ENTRY (state->groups_input), state->base.sheet);
282 data->logrank_test = gtk_toggle_button_get_active (
283 GTK_TOGGLE_BUTTON (state->logrank_button));
286 data->median = gtk_toggle_button_get_active (
287 GTK_TOGGLE_BUTTON (go_gtk_builder_get_widget
288 (state->base.gui,
289 "median-button")));
290 data->chart = gtk_toggle_button_get_active (
291 GTK_TOGGLE_BUTTON (state->graph_button));
292 data->ticks = gtk_toggle_button_get_active (
293 GTK_TOGGLE_BUTTON (state->tick_button));
294 data->std_err = gtk_toggle_button_get_active (
295 GTK_TOGGLE_BUTTON (state->std_error_button));
297 if (!cmd_analysis_tool (GNM_WBC (state->base.wbcg),
298 state->base.sheet,
299 dao, data, analysis_tool_kaplan_meier_engine,
300 TRUE))
301 gtk_widget_destroy (state->base.dialog);
303 return;
307 * kaplan_meier_tool_set_graph:
308 * @widget:
309 * @focus_widget:
310 * @state:
314 static gboolean
315 kaplan_meier_tool_set_graph_cb (G_GNUC_UNUSED GtkWidget *dummy,
316 KaplanMeierToolState *state)
318 gtk_toggle_button_set_active (GTK_TOGGLE_BUTTON (state->graph_button), TRUE);
319 kaplan_meier_tool_update_sensitivity_cb (NULL, state);
320 return FALSE;
324 * kaplan_meier_tool_set_censorship:
325 * @widget:
326 * @event:
327 * @state:
330 static gboolean
331 kaplan_meier_tool_set_censorship_cb (G_GNUC_UNUSED GtkWidget *widget,
332 G_GNUC_UNUSED GdkEventFocus *event,
333 KaplanMeierToolState *state)
335 gtk_toggle_button_set_active (GTK_TOGGLE_BUTTON (state->censorship_button), TRUE);
336 return FALSE;
339 static gboolean
340 kaplan_meier_tool_set_groups_cb (G_GNUC_UNUSED GtkWidget *widget,
341 G_GNUC_UNUSED GdkEventFocus *event,
342 KaplanMeierToolState *state)
344 gtk_toggle_button_set_active (GTK_TOGGLE_BUTTON (state->groups_check), TRUE);
345 return FALSE;
349 static gboolean
350 kaplan_meier_tool_set_censor_from_cb (G_GNUC_UNUSED GtkWidget *dummy,
351 KaplanMeierToolState *state)
353 gtk_spin_button_set_range (GTK_SPIN_BUTTON (state->censor_spin_to),
354 gtk_spin_button_get_value (GTK_SPIN_BUTTON (state->censor_spin_from)),G_MAXSHORT);
355 gtk_toggle_button_set_active (GTK_TOGGLE_BUTTON (state->censorship_button), TRUE);
357 return FALSE;
359 static gboolean
360 kaplan_meier_tool_set_censor_cb (G_GNUC_UNUSED GtkWidget *dummy,
361 KaplanMeierToolState *state)
363 gtk_toggle_button_set_active (GTK_TOGGLE_BUTTON (state->censorship_button), TRUE);
365 return FALSE;
368 static void
369 cb_group_name_edited (GtkCellRendererText *cell,
370 gchar *path_string,
371 gchar *new_text,
372 KaplanMeierToolState *state)
374 GtkTreeIter iter;
375 GtkTreePath *path;
377 if (cell != NULL) {
378 path = gtk_tree_path_new_from_string (path_string);
379 if (gtk_tree_model_get_iter (GTK_TREE_MODEL (state->groups_list),
380 &iter, path))
381 gtk_list_store_set (state->groups_list, &iter,
382 GROUP_NAME, new_text, -1);
383 else
384 g_warning ("Did not get a valid iterator");
385 gtk_tree_path_free (path);
389 static void
390 cb_change_to (GtkCellRendererText *cell,
391 gchar *path_string,
392 gchar *new_text,
393 KaplanMeierToolState *state)
395 GtkTreeIter iter;
396 GtkTreePath *path;
397 guint val = (guint) (atoi (new_text));
399 if (cell != NULL) {
400 path = gtk_tree_path_new_from_string (path_string);
401 if (gtk_tree_model_get_iter (GTK_TREE_MODEL (state->groups_list),
402 &iter, path))
403 gtk_list_store_set (state->groups_list, &iter,
404 GROUP_TO, val, -1);
405 else
406 g_warning ("Did not get a valid iterator");
407 gtk_tree_path_free (path);
411 static void
412 cb_change_from (GtkCellRendererText *cell,
413 gchar *path_string,
414 gchar *new_text,
415 KaplanMeierToolState *state)
417 if (cell != NULL) {
418 GtkTreeIter iter;
419 GtkTreePath *path;
420 guint val = (guint) (atoi (new_text));
421 guint old_to;
422 GObject *adjustment_to;
425 path = gtk_tree_path_new_from_string (path_string);
426 if (gtk_tree_model_get_iter (GTK_TREE_MODEL (state->groups_list),
427 &iter, path))
428 gtk_list_store_set (state->groups_list, &iter,
429 GROUP_FROM, val,
430 -1);
431 else
432 g_warning ("Did not get a valid iterator");
433 gtk_tree_path_free (path);
435 gtk_tree_model_get (GTK_TREE_MODEL (state->groups_list), &iter,
436 GROUP_TO, &old_to,
437 GROUP_ADJUSTMENT_TO, &adjustment_to,
438 -1);
440 if (old_to < val)
441 gtk_list_store_set (state->groups_list, &iter,
442 GROUP_TO, val,
443 -1);
444 g_object_set (adjustment_to, "lower", (gdouble) val, NULL);
449 static void
450 cb_selection_changed (GtkTreeSelection *selection,
451 KaplanMeierToolState *state)
453 gtk_widget_set_sensitive (state->remove_group_button,
454 gtk_tree_selection_get_selected (selection, NULL, NULL));
457 static void
458 kaplan_meier_tool_update_groups_sensitivity_cb (G_GNUC_UNUSED GtkWidget *dummy,
459 KaplanMeierToolState *state)
461 gboolean groups = gtk_toggle_button_get_active (
462 GTK_TOGGLE_BUTTON (state->groups_check));
463 GtkTreeSelection *selection = gtk_tree_view_get_selection (state->groups_treeview);
465 gtk_widget_set_sensitive (state->add_group_button, groups);
466 gtk_widget_set_sensitive (GTK_WIDGET (state->groups_treeview), groups);
468 if (groups) {
469 cb_selection_changed (selection, state);
470 gtk_widget_set_sensitive (state->logrank_button, TRUE);
471 } else {
472 gtk_tree_selection_unselect_all (selection);
473 gtk_widget_set_sensitive (state->remove_group_button, FALSE);
474 gtk_widget_set_sensitive (state->logrank_button, FALSE);
478 static void
479 dialog_kaplan_meier_tool_treeview_add_item (KaplanMeierToolState *state, guint i)
481 GtkTreeIter iter;
482 char * name = g_strdup_printf (_("Group %d"), i);
483 GObject *adjustment_to =
484 G_OBJECT (gtk_adjustment_new (0, 0, G_MAXUSHORT, 1, 1, 1));
485 GObject *adjustment_from =
486 G_OBJECT (gtk_adjustment_new (0, 0, G_MAXUSHORT, 1, 1, 1));
487 gtk_list_store_append (state->groups_list, &iter);
488 gtk_list_store_set (state->groups_list, &iter,
489 GROUP_NAME, name,
490 GROUP_FROM, (guint) i,
491 GROUP_TO, (guint) i,
492 GROUP_ADJUSTMENT_FROM, adjustment_from,
493 GROUP_ADJUSTMENT_TO, adjustment_to,
494 -1);
495 g_free (name);
498 static void
499 dialog_kaplan_meier_tool_setup_treeview (KaplanMeierToolState *state)
501 guint i;
502 GtkCellRenderer *renderer;
503 GtkWidget *scrolled = go_gtk_builder_get_widget (state->base.gui, "groups-scrolled");
504 GtkTreeSelection *selection;
506 state->groups_treeview = GTK_TREE_VIEW (go_gtk_builder_get_widget
507 (state->base.gui,
508 "groups-tree"));
509 state->groups_list = gtk_list_store_new (GROUP_COLUMNS,
510 G_TYPE_STRING, G_TYPE_UINT, G_TYPE_UINT, G_TYPE_OBJECT, G_TYPE_OBJECT);
511 state->groups_treeview = GTK_TREE_VIEW (gtk_tree_view_new_with_model
512 (GTK_TREE_MODEL (state->groups_list)));
513 g_object_unref (state->groups_list);
514 selection = gtk_tree_view_get_selection (state->groups_treeview);
515 gtk_tree_selection_set_mode (selection, GTK_SELECTION_SINGLE);
517 for (i = 0; i<2; i++)
518 dialog_kaplan_meier_tool_treeview_add_item (state, i);
520 g_signal_connect (selection,
521 "changed",
522 G_CALLBACK (cb_selection_changed), state);
524 renderer = gtk_cell_renderer_text_new ();
525 g_object_set (G_OBJECT (renderer),
526 "editable", TRUE,
527 NULL);
528 gtk_tree_view_insert_column_with_attributes (state->groups_treeview,
529 -1, _("Group"),
530 renderer,
531 "text", GROUP_NAME,
532 NULL);
533 g_signal_connect (G_OBJECT (renderer), "edited",
534 G_CALLBACK (cb_group_name_edited), state);
536 renderer = gtk_cell_renderer_spin_new ();
538 g_object_set (G_OBJECT (renderer), "editable", TRUE, "xalign", 1.0,
539 "digits", 0, NULL);
540 g_signal_connect (G_OBJECT (renderer), "edited",
541 G_CALLBACK (cb_change_from), state);
542 gtk_tree_view_insert_column_with_attributes (state->groups_treeview,
543 -1, _("From"),
544 renderer,
545 "text", GROUP_FROM,
546 "adjustment", GROUP_ADJUSTMENT_FROM,
547 NULL);
549 renderer = gtk_cell_renderer_spin_new ();
550 g_object_set (G_OBJECT (renderer), "editable", TRUE, "xalign", 1.0,
551 "digits", 0, NULL);
552 g_signal_connect (G_OBJECT (renderer), "edited",
553 G_CALLBACK (cb_change_to), state);
554 gtk_tree_view_insert_column_with_attributes (state->groups_treeview,
555 -1, _("To"),
556 renderer,
557 "text", GROUP_TO,
558 "adjustment", GROUP_ADJUSTMENT_TO,
559 NULL);
561 gtk_container_add (GTK_CONTAINER (scrolled), GTK_WIDGET (state->groups_treeview));
563 cb_selection_changed (selection, state);
566 static gboolean
567 kaplan_meier_tool_add_group_cb (G_GNUC_UNUSED GtkWidget *dummy,
568 KaplanMeierToolState *state)
570 dialog_kaplan_meier_tool_treeview_add_item
571 (state, gtk_tree_model_iter_n_children (GTK_TREE_MODEL (state->groups_list),
572 NULL));
573 return FALSE;
576 static gboolean
577 kaplan_meier_tool_remove_group_cb (G_GNUC_UNUSED GtkWidget *dummy,
578 KaplanMeierToolState *state)
580 GtkTreeSelection *selection;
581 GtkTreeIter iter;
583 selection = gtk_tree_view_get_selection (state->groups_treeview);
585 if (gtk_tree_selection_get_selected (selection, NULL, &iter)) {
586 gtk_list_store_remove ( state->groups_list, &iter);
589 return FALSE;
594 * dialog_kaplan_meier_tool:
595 * @wbcg:
596 * @sheet:
598 * Show the dialog (guru).
602 dialog_kaplan_meier_tool (WBCGtk *wbcg, Sheet *sheet)
604 KaplanMeierToolState *state;
605 GtkWidget *widget;
606 char const * plugins[] = { "Gnumeric_fnstat",
607 "Gnumeric_fnlookup",
608 "Gnumeric_fnmath",
609 "Gnumeric_fninfo",
610 "Gnumeric_fnlogical",
611 NULL};
613 if ((wbcg == NULL) ||
614 gnm_check_for_plugins_missing (plugins, wbcg_toplevel (wbcg)))
615 return 1;
617 /* Only pop up one copy per workbook */
618 if (gnm_dialog_raise_if_exists (wbcg, KAPLAN_MEIER_KEY))
619 return 0;
621 state = g_new0 (KaplanMeierToolState, 1);
623 if (dialog_tool_init (&state->base, wbcg, sheet,
624 GNUMERIC_HELP_LINK_KAPLAN_MEIER,
625 "res:ui/kaplan-meier.ui", "KaplanMeier",
626 _("Could not create the Kaplan Meier Tool dialog."),
627 KAPLAN_MEIER_KEY,
628 G_CALLBACK (kaplan_meier_tool_ok_clicked_cb), NULL,
629 G_CALLBACK (kaplan_meier_tool_update_sensitivity_cb),
632 g_free(state);
633 return 0;
638 state->censorship_button = GTK_WIDGET (go_gtk_builder_get_widget
639 (state->base.gui,
640 "censor-button"));
641 state->censor_spin_from = GTK_WIDGET (go_gtk_builder_get_widget
642 (state->base.gui,
643 "censored-spinbutton1"));
644 gtk_spin_button_set_range (GTK_SPIN_BUTTON (state->censor_spin_from), 0.,G_MAXSHORT);
645 state->censor_spin_to = GTK_WIDGET (go_gtk_builder_get_widget
646 (state->base.gui,
647 "censored-spinbutton2"));
648 gtk_spin_button_set_range (GTK_SPIN_BUTTON (state->censor_spin_to), 0.,G_MAXSHORT);
649 state->graph_button = GTK_WIDGET (go_gtk_builder_get_widget
650 (state->base.gui,
651 "graph-button"));
652 state->tick_button = GTK_WIDGET (go_gtk_builder_get_widget
653 (state->base.gui,
654 "tick-button"));
655 state->add_group_button = GTK_WIDGET (go_gtk_builder_get_widget
656 (state->base.gui,
657 "add-button"));
658 state->remove_group_button = GTK_WIDGET (go_gtk_builder_get_widget
659 (state->base.gui,
660 "remove-button"));
661 state->std_error_button = GTK_WIDGET (go_gtk_builder_get_widget
662 (state->base.gui,
663 "std-error-button"));
664 state->logrank_button = GTK_WIDGET (go_gtk_builder_get_widget
665 (state->base.gui,
666 "logrank-button"));
668 state->groups_check = GTK_WIDGET (go_gtk_builder_get_widget
669 (state->base.gui,
670 "groups-check"));
671 state->groups_grid = GTK_WIDGET (go_gtk_builder_get_widget
672 (state->base.gui,
673 "groups-grid"));
674 state->groups_input = gnm_expr_entry_new (state->base.wbcg, TRUE);
675 gnm_expr_entry_set_flags (state->groups_input, GNM_EE_FORCE_ABS_REF,
676 GNM_EE_MASK);
677 gtk_grid_attach (GTK_GRID (state->groups_grid),
678 GTK_WIDGET (state->groups_input), 1, 1, 2, 1);
680 dialog_kaplan_meier_tool_setup_treeview (state);
682 g_signal_connect_after (G_OBJECT (state->groups_check),
683 "toggled",
684 G_CALLBACK (kaplan_meier_tool_update_sensitivity_cb), state);
685 g_signal_connect_after (G_OBJECT (state->censorship_button),
686 "toggled",
687 G_CALLBACK (kaplan_meier_tool_update_sensitivity_cb), state);
688 g_signal_connect_after (G_OBJECT (state->graph_button),
689 "toggled",
690 G_CALLBACK (kaplan_meier_tool_update_sensitivity_cb), state);
691 g_signal_connect_after (G_OBJECT (state->std_error_button),
692 "toggled",
693 G_CALLBACK (kaplan_meier_tool_update_sensitivity_cb), state);
694 g_signal_connect_after (G_OBJECT (state->groups_input),
695 "changed",
696 G_CALLBACK (kaplan_meier_tool_update_sensitivity_cb),
697 state);
699 g_signal_connect_after (G_OBJECT (state->groups_check),
700 "toggled",
701 G_CALLBACK (kaplan_meier_tool_update_groups_sensitivity_cb), state);
702 g_signal_connect_after (G_OBJECT (state->tick_button),
703 "toggled",
704 G_CALLBACK (kaplan_meier_tool_set_graph_cb), state);
705 g_signal_connect_after (G_OBJECT (state->add_group_button),
706 "clicked",
707 G_CALLBACK (kaplan_meier_tool_add_group_cb), state);
708 g_signal_connect_after (G_OBJECT (state->remove_group_button),
709 "clicked",
710 G_CALLBACK (kaplan_meier_tool_remove_group_cb), state);
711 g_signal_connect_after (G_OBJECT (state->censor_spin_from),
712 "value-changed",
713 G_CALLBACK (kaplan_meier_tool_set_censor_from_cb), state);
714 g_signal_connect_after (G_OBJECT (state->censor_spin_to),
715 "value-changed",
716 G_CALLBACK (kaplan_meier_tool_set_censor_cb), state);
717 g_signal_connect (G_OBJECT
718 (gnm_expr_entry_get_entry (
719 GNM_EXPR_ENTRY (state->base.input_entry_2))),
720 "focus-in-event",
721 G_CALLBACK (kaplan_meier_tool_set_censorship_cb), state);
722 g_signal_connect (G_OBJECT
723 (gnm_expr_entry_get_entry (
724 GNM_EXPR_ENTRY (state->groups_input))),
725 "focus-in-event",
726 G_CALLBACK (kaplan_meier_tool_set_groups_cb), state);
728 gnm_editable_enters (GTK_WINDOW (state->base.dialog),
729 GTK_WIDGET (state->groups_input));
731 widget = go_gtk_builder_get_widget (state->base.gui, "groups-label");
732 gtk_label_set_mnemonic_widget (GTK_LABEL (widget),
733 GTK_WIDGET (state->groups_input));
734 go_atk_setup_label (widget, GTK_WIDGET (state->groups_input));
736 gnm_dao_set_put (GNM_DAO (state->base.gdao), TRUE, TRUE);
737 kaplan_meier_tool_update_sensitivity_cb (NULL, state);
738 kaplan_meier_tool_update_groups_sensitivity_cb (NULL, state);
739 tool_load_selection ((GnmGenericToolState *)state, TRUE);
741 gtk_widget_show_all (GTK_WIDGET (state->base.dialog));
742 /* And to hide the in-place button again */
743 gnm_dao_set_inplace ( GNM_DAO (state->base.gdao), NULL);
745 return 0;