From b2a270aa108a4ea3314621527c24531b54ec1b9f Mon Sep 17 00:00:00 2001 From: Christopher James Lahey Date: Thu, 9 Aug 2001 10:16:52 +0000 Subject: Added a "header" argument to these structures which just gets passed 2001-08-09 Christopher James Lahey * e-table-field-chooser-dialog.c, e-table-field-chooser-dialog.h, e-table-field-chooser.c, e-table-field-chooser.h: Added a "header" argument to these structures which just gets passed downwards. * e-table-field-chooser-item.c, e-table-field-chooser-item.h: Added a "header" argument here. Made it so that only rows that aren't already in the header are shown. * e-table-header-item.c: Set the "header" argument on our e-table-field-chooser-dialog. Fixes Ximian bug #2654. svn path=/trunk/; revision=11828 --- widgets/table/e-table-field-chooser-dialog.c | 24 ++++ widgets/table/e-table-field-chooser-dialog.h | 1 + widgets/table/e-table-field-chooser-item.c | 157 ++++++++++++++++++++++----- widgets/table/e-table-field-chooser-item.h | 5 +- widgets/table/e-table-field-chooser.c | 23 ++++ widgets/table/e-table-field-chooser.h | 1 + widgets/table/e-table-header-item.c | 1 + 7 files changed, 186 insertions(+), 26 deletions(-) diff --git a/widgets/table/e-table-field-chooser-dialog.c b/widgets/table/e-table-field-chooser-dialog.c index 2e1525b7c0..85b62fc349 100644 --- a/widgets/table/e-table-field-chooser-dialog.c +++ b/widgets/table/e-table-field-chooser-dialog.c @@ -39,6 +39,7 @@ enum { ARG_0, ARG_DND_CODE, ARG_FULL_HEADER, + ARG_HEADER, }; GtkType @@ -88,6 +89,8 @@ e_table_field_chooser_dialog_class_init (ETableFieldChooserDialogClass *klass) GTK_ARG_READWRITE, ARG_DND_CODE); gtk_object_add_arg_type ("ETableFieldChooserDialog::full_header", GTK_TYPE_OBJECT, GTK_ARG_READWRITE, ARG_FULL_HEADER); + gtk_object_add_arg_type ("ETableFieldChooserDialog::header", GTK_TYPE_OBJECT, + GTK_ARG_READWRITE, ARG_HEADER); } static void @@ -98,6 +101,7 @@ e_table_field_chooser_dialog_init (ETableFieldChooserDialog *e_table_field_choos e_table_field_chooser_dialog->etfc = NULL; e_table_field_chooser_dialog->dnd_code = g_strdup(""); e_table_field_chooser_dialog->full_header = NULL; + e_table_field_chooser_dialog->header = NULL; gnome_dialog_append_buttons(GNOME_DIALOG(e_table_field_chooser_dialog), GNOME_STOCK_BUTTON_CLOSE, @@ -111,6 +115,7 @@ e_table_field_chooser_dialog_init (ETableFieldChooserDialog *e_table_field_choos gtk_object_set(GTK_OBJECT(widget), "dnd_code", e_table_field_chooser_dialog->dnd_code, "full_header", e_table_field_chooser_dialog->full_header, + "header", e_table_field_chooser_dialog->header, NULL); gtk_box_pack_start(GTK_BOX(GNOME_DIALOG(e_table_field_chooser_dialog)->vbox), @@ -135,6 +140,8 @@ e_table_field_chooser_dialog_destroy (GtkObject *object) g_free(etfcd->dnd_code); if (etfcd->full_header) gtk_object_unref(GTK_OBJECT(etfcd->full_header)); + if (etfcd->header) + gtk_object_unref(GTK_OBJECT(etfcd->header)); } static void @@ -164,6 +171,20 @@ e_table_field_chooser_dialog_set_arg (GtkObject *object, GtkArg *arg, guint arg_ "full_header", etfcd->full_header, NULL); break; + case ARG_HEADER: + if (etfcd->header) + gtk_object_unref(GTK_OBJECT(etfcd->header)); + if (GTK_VALUE_OBJECT(*arg)) + etfcd->header = E_TABLE_HEADER(GTK_VALUE_OBJECT(*arg)); + else + etfcd->header = NULL; + if (etfcd->header) + gtk_object_ref(GTK_OBJECT(etfcd->header)); + if (etfcd->etfc) + gtk_object_set(GTK_OBJECT(etfcd->etfc), + "header", etfcd->header, + NULL); + break; default: break; } @@ -180,6 +201,9 @@ e_table_field_chooser_dialog_get_arg (GtkObject *object, GtkArg *arg, guint arg_ case ARG_FULL_HEADER: GTK_VALUE_OBJECT (*arg) = GTK_OBJECT(etfcd->full_header); break; + case ARG_HEADER: + GTK_VALUE_OBJECT (*arg) = GTK_OBJECT(etfcd->header); + break; default: arg->type = GTK_TYPE_INVALID; break; diff --git a/widgets/table/e-table-field-chooser-dialog.h b/widgets/table/e-table-field-chooser-dialog.h index 4e8992f54a..cdc8fd3218 100644 --- a/widgets/table/e-table-field-chooser-dialog.h +++ b/widgets/table/e-table-field-chooser-dialog.h @@ -56,6 +56,7 @@ struct _ETableFieldChooserDialog ETableFieldChooser *etfc; gchar *dnd_code; ETableHeader *full_header; + ETableHeader *header; }; struct _ETableFieldChooserDialogClass diff --git a/widgets/table/e-table-field-chooser-item.c b/widgets/table/e-table-field-chooser-item.c index a551f75c6a..3084d9e758 100644 --- a/widgets/table/e-table-field-chooser-item.c +++ b/widgets/table/e-table-field-chooser-item.c @@ -43,10 +43,12 @@ static guint etfci_signals [LAST_SIGNAL] = { 0, }; static GnomeCanvasItemClass *etfci_parent_class; static void etfci_drop_table_header (ETableFieldChooserItem *etfci); +static void etfci_drop_full_header (ETableFieldChooserItem *etfci); enum { ARG_0, ARG_FULL_HEADER, + ARG_HEADER, ARG_DND_CODE, ARG_WIDTH, ARG_HEIGHT, @@ -57,6 +59,9 @@ etfci_destroy (GtkObject *object){ ETableFieldChooserItem *etfci = E_TABLE_FIELD_CHOOSER_ITEM (object); etfci_drop_table_header (etfci); + etfci_drop_full_header (etfci); + if (etfci->combined_header != NULL) + gtk_object_unref (GTK_OBJECT (etfci->combined_header)); gdk_font_unref(etfci->font); @@ -74,11 +79,11 @@ etfci_find_button (ETableFieldChooserItem *etfci, double loc) style = GTK_WIDGET (GNOME_CANVAS_ITEM (etfci)->canvas)->style; - count = e_table_header_count(etfci->full_header); + count = e_table_header_count(etfci->combined_header); for (i = 0; i < count; i++) { ETableCol *ecol; - ecol = e_table_header_get_column (etfci->full_header, i); + ecol = e_table_header_get_column (etfci->combined_header, i); height += e_table_header_compute_height (ecol, style, etfci->font); if (height > loc) return i; @@ -86,6 +91,36 @@ etfci_find_button (ETableFieldChooserItem *etfci, double loc) return MAX(0, count - 1); } +static void +etfci_rebuild_combined (ETableFieldChooserItem *etfci) +{ + int count; + GHashTable *hash; + int i; + + if (etfci->combined_header != NULL) + gtk_object_unref (GTK_OBJECT (etfci->combined_header)); + + etfci->combined_header = e_table_header_new (); + + hash = g_hash_table_new (NULL, NULL); + + count = e_table_header_count (etfci->header); + for (i = 0; i < count; i++) { + ETableCol *ecol = e_table_header_get_column (etfci->header, i); + g_hash_table_insert (hash, GINT_TO_POINTER (ecol->col_idx), GINT_TO_POINTER (1)); + } + + count = e_table_header_count (etfci->full_header); + for (i = 0; i < count; i++) { + ETableCol *ecol = e_table_header_get_column (etfci->full_header, i); + if (! (GPOINTER_TO_INT (g_hash_table_lookup (hash, GINT_TO_POINTER (ecol->col_idx))))) + e_table_header_add_column (etfci->combined_header, ecol, -1); + } + + g_hash_table_destroy (hash); +} + static void etfci_reflow (GnomeCanvasItem *item, gint flags) { @@ -96,15 +131,17 @@ etfci_reflow (GnomeCanvasItem *item, gint flags) double height = 0; GtkStyle *style; + etfci_rebuild_combined (etfci); + style = GTK_WIDGET (GNOME_CANVAS_ITEM (etfci)->canvas)->style; old_height = etfci->height; - count = e_table_header_count(etfci->full_header); + count = e_table_header_count(etfci->combined_header); for (i = 0; i < count; i++) { ETableCol *ecol; - ecol = e_table_header_get_column (etfci->full_header, i); + ecol = e_table_header_get_column (etfci->combined_header, i); height += e_table_header_compute_height (ecol, style, etfci->font); } @@ -167,7 +204,7 @@ etfci_font_load (ETableFieldChooserItem *etfci, char *font) } static void -etfci_drop_table_header (ETableFieldChooserItem *etfci) +etfci_drop_full_header (ETableFieldChooserItem *etfci) { GtkObject *header; @@ -175,12 +212,12 @@ etfci_drop_table_header (ETableFieldChooserItem *etfci) return; header = GTK_OBJECT (etfci->full_header); - if (etfci->structure_change_id) - gtk_signal_disconnect (header, etfci->structure_change_id); - if (etfci->dimension_change_id) - gtk_signal_disconnect (header, etfci->dimension_change_id); - etfci->structure_change_id = 0; - etfci->dimension_change_id = 0; + if (etfci->full_header_structure_change_id) + gtk_signal_disconnect (header, etfci->full_header_structure_change_id); + if (etfci->full_header_dimension_change_id) + gtk_signal_disconnect (header, etfci->full_header_dimension_change_id); + etfci->full_header_structure_change_id = 0; + etfci->full_header_dimension_change_id = 0; if (header) gtk_object_unref (header); @@ -190,29 +227,79 @@ etfci_drop_table_header (ETableFieldChooserItem *etfci) } static void -structure_changed (ETableHeader *header, ETableFieldChooserItem *etfci) +full_header_structure_changed (ETableHeader *header, ETableFieldChooserItem *etfci) { e_canvas_item_request_reflow(GNOME_CANVAS_ITEM(etfci)); } static void -dimension_changed (ETableHeader *header, int col, ETableFieldChooserItem *etfci) +full_header_dimension_changed (ETableHeader *header, int col, ETableFieldChooserItem *etfci) { e_canvas_item_request_reflow(GNOME_CANVAS_ITEM(etfci)); } static void -etfci_add_table_header (ETableFieldChooserItem *etfci, ETableHeader *header) +etfci_add_full_header (ETableFieldChooserItem *etfci, ETableHeader *header) { etfci->full_header = header; gtk_object_ref (GTK_OBJECT (etfci->full_header)); - etfci->structure_change_id = gtk_signal_connect ( + etfci->full_header_structure_change_id = gtk_signal_connect ( + GTK_OBJECT (header), "structure_change", + GTK_SIGNAL_FUNC(full_header_structure_changed), etfci); + etfci->full_header_dimension_change_id = gtk_signal_connect ( + GTK_OBJECT (header), "dimension_change", + GTK_SIGNAL_FUNC(full_header_dimension_changed), etfci); + e_canvas_item_request_reflow(GNOME_CANVAS_ITEM(etfci)); +} + +static void +etfci_drop_table_header (ETableFieldChooserItem *etfci) +{ + GtkObject *header; + + if (!etfci->header) + return; + + header = GTK_OBJECT (etfci->header); + if (etfci->table_header_structure_change_id) + gtk_signal_disconnect (header, etfci->table_header_structure_change_id); + if (etfci->table_header_dimension_change_id) + gtk_signal_disconnect (header, etfci->table_header_dimension_change_id); + etfci->table_header_structure_change_id = 0; + etfci->table_header_dimension_change_id = 0; + + if (header) + gtk_object_unref (header); + etfci->header = NULL; + etfci->height = 0; + e_canvas_item_request_reflow(GNOME_CANVAS_ITEM(etfci)); +} + +static void +table_header_structure_changed (ETableHeader *header, ETableFieldChooserItem *etfci) +{ + e_canvas_item_request_reflow(GNOME_CANVAS_ITEM(etfci)); +} + +static void +table_header_dimension_changed (ETableHeader *header, int col, ETableFieldChooserItem *etfci) +{ + e_canvas_item_request_reflow(GNOME_CANVAS_ITEM(etfci)); +} + +static void +etfci_add_table_header (ETableFieldChooserItem *etfci, ETableHeader *header) +{ + etfci->header = header; + gtk_object_ref (GTK_OBJECT (etfci->header)); + + etfci->table_header_structure_change_id = gtk_signal_connect ( GTK_OBJECT (header), "structure_change", - GTK_SIGNAL_FUNC(structure_changed), etfci); - etfci->dimension_change_id = gtk_signal_connect ( + GTK_SIGNAL_FUNC(table_header_structure_changed), etfci); + etfci->table_header_dimension_change_id = gtk_signal_connect ( GTK_OBJECT (header), "dimension_change", - GTK_SIGNAL_FUNC(dimension_changed), etfci); + GTK_SIGNAL_FUNC(table_header_dimension_changed), etfci); e_canvas_item_request_reflow(GNOME_CANVAS_ITEM(etfci)); } @@ -227,6 +314,12 @@ etfci_set_arg (GtkObject *o, GtkArg *arg, guint arg_id) switch (arg_id){ case ARG_FULL_HEADER: + etfci_drop_full_header (etfci); + if (GTK_VALUE_OBJECT (*arg)) + etfci_add_full_header (etfci, E_TABLE_HEADER(GTK_VALUE_OBJECT (*arg))); + break; + + case ARG_HEADER: etfci_drop_table_header (etfci); if (GTK_VALUE_OBJECT (*arg)) etfci_add_table_header (etfci, E_TABLE_HEADER(GTK_VALUE_OBJECT (*arg))); @@ -343,12 +436,17 @@ etfci_draw (GnomeCanvasItem *item, GdkDrawable *drawable, int x, int y, int widt { ETableFieldChooserItem *etfci = E_TABLE_FIELD_CHOOSER_ITEM (item); GnomeCanvas *canvas = item->canvas; - const int rows = e_table_header_count (etfci->full_header); + int rows; int y1, y2; int row; GtkStyle *style; GtkStateType state; + if (etfci->combined_header == NULL) + return; + + rows = e_table_header_count (etfci->combined_header); + style = GTK_WIDGET (canvas)->style; state = GTK_WIDGET_STATE (canvas); @@ -356,7 +454,7 @@ etfci_draw (GnomeCanvasItem *item, GdkDrawable *drawable, int x, int y, int widt for (row = 0; row < rows; row++, y1 = y2){ ETableCol *ecol; - ecol = e_table_header_get_column (etfci->full_header, row); + ecol = e_table_header_get_column (etfci->combined_header, row); y2 += e_table_header_compute_height (ecol, style, etfci->font); @@ -412,12 +510,15 @@ etfci_start_drag (ETableFieldChooserItem *etfci, GdkEvent *event, double x, doub { TARGET_ETABLE_COL_TYPE, 0, TARGET_ETABLE_COL_HEADER }, }; + if (etfci->combined_header == NULL) + return; + drag_col = etfci_find_button(etfci, y); - if (drag_col < 0 || drag_col > e_table_header_count(etfci->full_header)) + if (drag_col < 0 || drag_col > e_table_header_count(etfci->combined_header)) return; - ecol = e_table_header_get_column (etfci->full_header, drag_col); + ecol = e_table_header_get_column (etfci->combined_header, drag_col); etfci->drag_col = ecol->col_idx; @@ -429,7 +530,7 @@ etfci_start_drag (ETableFieldChooserItem *etfci, GdkEvent *event, double x, doub button_height = e_table_header_compute_height (ecol, widget->style, etfci->font); pixmap = gdk_pixmap_new (widget->window, etfci->width, button_height, -1); - e_table_header_draw_button (pixmap, e_table_header_get_column (etfci->full_header, drag_col), + e_table_header_draw_button (pixmap, e_table_header_get_column (etfci->combined_header, drag_col), widget->style, etfci->font, GTK_WIDGET_STATE (widget), widget, widget->style->fg_gc[GTK_STATE_NORMAL], 0, 0, @@ -508,6 +609,8 @@ etfci_class_init (GtkObjectClass *object_class) GTK_ARG_READWRITE, ARG_DND_CODE); gtk_object_add_arg_type ("ETableFieldChooserItem::full_header", GTK_TYPE_OBJECT, GTK_ARG_WRITABLE, ARG_FULL_HEADER); + gtk_object_add_arg_type ("ETableFieldChooserItem::header", GTK_TYPE_OBJECT, + GTK_ARG_WRITABLE, ARG_HEADER); gtk_object_add_arg_type ("ETableFieldChooserItem::width", GTK_TYPE_DOUBLE, GTK_ARG_READWRITE, ARG_WIDTH); gtk_object_add_arg_type ("ETableFieldChooserItem::height", GTK_TYPE_DOUBLE, @@ -520,13 +623,17 @@ etfci_init (GnomeCanvasItem *item) ETableFieldChooserItem *etfci = E_TABLE_FIELD_CHOOSER_ITEM (item); etfci->full_header = NULL; + etfci->header = NULL; + etfci->combined_header = NULL; etfci->height = etfci->width = 0; etfci->font = NULL; - etfci->structure_change_id = 0; - etfci->dimension_change_id = 0; + etfci->full_header_structure_change_id = 0; + etfci->full_header_dimension_change_id = 0; + etfci->table_header_structure_change_id = 0; + etfci->table_header_dimension_change_id = 0; etfci->dnd_code = NULL; diff --git a/widgets/table/e-table-field-chooser-item.h b/widgets/table/e-table-field-chooser-item.h index d91c36d52b..c6b41f9f8c 100644 --- a/widgets/table/e-table-field-chooser-item.h +++ b/widgets/table/e-table-field-chooser-item.h @@ -17,6 +17,8 @@ BEGIN_GNOME_DECLS typedef struct { GnomeCanvasItem parent; ETableHeader *full_header; + ETableHeader *header; + ETableHeader *combined_header; double height, width; @@ -25,7 +27,8 @@ typedef struct { /* * Ids */ - int structure_change_id, dimension_change_id; + int full_header_structure_change_id, full_header_dimension_change_id; + int table_header_structure_change_id, table_header_dimension_change_id; gchar *dnd_code; diff --git a/widgets/table/e-table-field-chooser.c b/widgets/table/e-table-field-chooser.c index 2f3562a8f3..4d5854b3cb 100644 --- a/widgets/table/e-table-field-chooser.c +++ b/widgets/table/e-table-field-chooser.c @@ -37,6 +37,7 @@ static GtkVBoxClass *parent_class = NULL; enum { ARG_0, ARG_FULL_HEADER, + ARG_HEADER, ARG_DND_CODE, }; @@ -85,6 +86,8 @@ e_table_field_chooser_class_init (ETableFieldChooserClass *klass) GTK_ARG_READWRITE, ARG_DND_CODE); gtk_object_add_arg_type ("ETableFieldChooser::full_header", GTK_TYPE_OBJECT, GTK_ARG_READWRITE, ARG_FULL_HEADER); + gtk_object_add_arg_type ("ETableFieldChooser::header", GTK_TYPE_OBJECT, + GTK_ARG_READWRITE, ARG_HEADER); } static void allocate_callback(GtkWidget *canvas, GtkAllocation *allocation, ETableFieldChooser *etfc) @@ -155,6 +158,7 @@ e_table_field_chooser_init (ETableFieldChooser *etfc) e_table_field_chooser_item_get_type(), "width", (double) 100, "full_header", etfc->full_header, + "header", etfc->header, "dnd_code", etfc->dnd_code, NULL ); @@ -184,6 +188,8 @@ e_table_field_chooser_destroy (GtkObject *object) g_free(etfc->dnd_code); if (etfc->full_header) gtk_object_unref(GTK_OBJECT(etfc->full_header)); + if (etfc->header) + gtk_object_unref(GTK_OBJECT(etfc->header)); if (etfc->gui) gtk_object_unref(GTK_OBJECT(etfc->gui)); @@ -227,6 +233,20 @@ e_table_field_chooser_set_arg (GtkObject *object, GtkArg *arg, guint arg_id) "full_header", etfc->full_header, NULL); break; + case ARG_HEADER: + if (etfc->header) + gtk_object_unref(GTK_OBJECT(etfc->header)); + if (GTK_VALUE_OBJECT(*arg)) + etfc->header = E_TABLE_HEADER(GTK_VALUE_OBJECT(*arg)); + else + etfc->header = NULL; + if (etfc->header) + gtk_object_ref(GTK_OBJECT(etfc->header)); + if (etfc->item) + gtk_object_set(GTK_OBJECT(etfc->item), + "header", etfc->header, + NULL); + break; default: break; } @@ -244,6 +264,9 @@ e_table_field_chooser_get_arg (GtkObject *object, GtkArg *arg, guint arg_id) case ARG_FULL_HEADER: GTK_VALUE_OBJECT (*arg) = GTK_OBJECT(etfc->full_header); break; + case ARG_HEADER: + GTK_VALUE_OBJECT (*arg) = GTK_OBJECT(etfc->header); + break; default: arg->type = GTK_TYPE_INVALID; break; diff --git a/widgets/table/e-table-field-chooser.h b/widgets/table/e-table-field-chooser.h index ff24ebbab4..6531472c62 100644 --- a/widgets/table/e-table-field-chooser.h +++ b/widgets/table/e-table-field-chooser.h @@ -61,6 +61,7 @@ struct _ETableFieldChooser gchar *dnd_code; ETableHeader *full_header; + ETableHeader *header; }; struct _ETableFieldChooserClass diff --git a/widgets/table/e-table-header-item.c b/widgets/table/e-table-header-item.c index acaa1c1510..d3a28c8f69 100644 --- a/widgets/table/e-table-header-item.c +++ b/widgets/table/e-table-header-item.c @@ -1199,6 +1199,7 @@ ethi_popup_field_chooser(GtkWidget *widget, EthiHeaderInfo *info) GtkWidget *etfcd = e_table_field_chooser_dialog_new(); gtk_object_set(GTK_OBJECT(etfcd), "full_header", info->ethi->full_header, + "header", info->ethi->eth, "dnd_code", info->ethi->dnd_code, NULL); gtk_widget_show(etfcd); -- cgit v1.2.3