X-Git-Url: https://pintos-os.org/cgi-bin/gitweb.cgi?a=blobdiff_plain;f=src%2Fui%2Fgui%2Fpsppire-output-view.c;h=6c19434b1bb9c45548b571634b55ea49860d2631;hb=e85b9209febb65cb4a59635507fba948325607cd;hp=4a9a666cef6dd4c149425cdb6da69053fbb80285;hpb=21f20b8cb6460fd5ac9db7fde038bc00cfa80831;p=pspp diff --git a/src/ui/gui/psppire-output-view.c b/src/ui/gui/psppire-output-view.c index 4a9a666cef..6c19434b1b 100644 --- a/src/ui/gui/psppire-output-view.c +++ b/src/ui/gui/psppire-output-view.c @@ -28,14 +28,8 @@ #include "output/cairo-pager.h" #include "output/driver-provider.h" #include "output/driver.h" -#include "output/chart-item.h" -#include "output/group-item.h" -#include "output/message-item.h" #include "output/output-item.h" -#include "output/output-item-provider.h" #include "output/pivot-table.h" -#include "output/table-item.h" -#include "output/text-item.h" #include "gl/c-xvasprintf.h" #include "gl/minmax.h" @@ -49,6 +43,8 @@ struct output_view_item { struct output_item *item; GtkWidget *drawing_area; + int width, height; + int nesting_depth; }; struct psppire_output_view @@ -62,7 +58,6 @@ struct psppire_output_view glong y; GtkTreeView *overview; - GtkTreePath *cur_group; GtkWidget *toplevel; @@ -331,7 +326,7 @@ rerender (struct psppire_output_view *view) if (view->y > 0) view->y += view->object_spacing; - if (is_group_open_item (item->item)) + if (item->item->type == OUTPUT_ITEM_GROUP) continue; r = xr_fsm_create_for_scrolling (item->item, view->style, cr); @@ -358,11 +353,9 @@ rerender (struct psppire_output_view *view) gtk_layout_move (view->output, item->drawing_area, xpos, view->y); } - if (is_table_item (item->item)) - { - const struct table_item *ti = to_table_item (item->item); - gtk_widget_set_tooltip_text (item->drawing_area, ti->pt->notes); - } + if (item->item->type == OUTPUT_ITEM_TABLE) + gtk_widget_set_tooltip_text (item->drawing_area, + item->item->table->notes); { gint minw; @@ -395,49 +388,20 @@ rerender (struct psppire_output_view *view) cairo_region_destroy (region); } - -void -psppire_output_view_put (struct psppire_output_view *view, - const struct output_item *item) +static bool +init_output_view_item (struct output_view_item *view_item, + struct psppire_output_view *view, + const struct output_item *item, + int nesting_depth) { - struct output_view_item *view_item; - GtkWidget *drawing_area; - int tw, th; - - if (is_group_close_item (item)) - { - if (view->cur_group) - { - if (!gtk_tree_path_up (view->cur_group)) - { - gtk_tree_path_free (view->cur_group); - view->cur_group = NULL; - } - } - return; - } - else if (is_text_item (item)) - { - const struct text_item *text_item = to_text_item (item); - const char *text = text_item_get_text (text_item); - if (text[0] == '\0') - return; - } - - if (view->n_items >= view->allocated_items) - view->items = x2nrealloc (view->items, &view->allocated_items, - sizeof *view->items); - view_item = &view->items[view->n_items++]; - view_item->item = output_item_ref (item); - view_item->drawing_area = NULL; + *view_item = (struct output_view_item) { + .item = output_item_ref (item), + .nesting_depth = nesting_depth + }; GdkWindow *win = gtk_widget_get_window (GTK_WIDGET (view->output)); - if (is_group_open_item (item)) - tw = th = 0; - else if (win) + if (win && item->type != OUTPUT_ITEM_GROUP) { - view_item->drawing_area = drawing_area = gtk_drawing_area_new (); - if (!view->style) view->style = get_xr_fsm_style (view); @@ -453,17 +417,46 @@ psppire_output_view_put (struct psppire_output_view *view, { gdk_window_end_draw_frame (win, ctx); cairo_region_destroy (region); - return; + + output_item_unref (view_item->item); + return false; } - xr_fsm_measure (r, cr, &tw, &th); - create_drawing_area (view, drawing_area, r, tw, th, item); + xr_fsm_measure (r, cr, &view_item->width, &view_item->height); + view_item->drawing_area = gtk_drawing_area_new (); + create_drawing_area (view, view_item->drawing_area, r, view_item->width, + view_item->height, item); gdk_window_end_draw_frame (win, ctx); cairo_region_destroy (region); } - else - tw = th = 0; + return true; +} + +static void +psppire_output_view_put__ (struct psppire_output_view *view, + const struct output_item *item, + GtkTreePath *parent_path) +{ + if (item->type == OUTPUT_ITEM_TEXT) + { + char *text = text_item_get_plain_text (item); + bool text_is_empty = text[0] == '\0'; + free (text); + if (text_is_empty) + return; + } + + if (view->n_items >= view->allocated_items) + view->items = x2nrealloc (view->items, &view->allocated_items, + sizeof *view->items); + struct output_view_item *view_item = &view->items[view->n_items]; + if (!init_output_view_item (view_item, view, item, + parent_path ? gtk_tree_path_get_depth (parent_path) : 0)) + return; + view->n_items++; + + GtkTreePath *path = NULL; if (view->overview) { GtkTreeStore *store = GTK_TREE_STORE ( @@ -472,38 +465,44 @@ psppire_output_view_put (struct psppire_output_view *view, /* Create a new node in the tree and puts a reference to it in 'iter'. */ GtkTreeIter iter; GtkTreeIter parent; - if (view->cur_group - && gtk_tree_path_get_depth (view->cur_group) > 0 + if (parent_path + && gtk_tree_path_get_depth (parent_path) > 0 && gtk_tree_model_get_iter (GTK_TREE_MODEL (store), - &parent, view->cur_group)) + &parent, parent_path)) gtk_tree_store_append (store, &iter, &parent); else gtk_tree_store_append (store, &iter, NULL); - if (is_group_open_item (item)) - { - gtk_tree_path_free (view->cur_group); - view->cur_group = gtk_tree_model_get_path (GTK_TREE_MODEL (store), - &iter); - } - gtk_tree_store_set (store, &iter, COL_LABEL, output_item_get_label (item), COL_ADDR, item, COL_Y, view->y, -1); - GtkTreePath *path = gtk_tree_model_get_path ( + /* Get the path of the new row. */ + path = gtk_tree_model_get_path ( GTK_TREE_MODEL (store), &iter); gtk_tree_view_expand_row (view->overview, path, TRUE); - gtk_tree_path_free (path); } - if (view->max_width < tw) - view->max_width = tw; - view->y += th; + if (view->max_width < view_item->width) + view->max_width = view_item->width; + view->y += view_item->height; gtk_layout_set_size (view->output, view->max_width, view->y); + + if (item->type == OUTPUT_ITEM_GROUP) + for (size_t i = 0; i < item->group.n_children; i++) + psppire_output_view_put__ (view, item->group.children[i], path); + + gtk_tree_path_free (path); +} + +void +psppire_output_view_put (struct psppire_output_view *view, + const struct output_item *item) +{ + psppire_output_view_put__ (view, item, NULL); } static void @@ -743,8 +742,7 @@ build_target_list (const struct output_item *item) { GtkTargetList *tl = gtk_target_list_new (targets, G_N_ELEMENTS (targets)); g_return_val_if_fail (tl, NULL); - if (is_table_item (item) || - is_chart_item (item)) + if (item->type == OUTPUT_ITEM_TABLE || item->type == OUTPUT_ITEM_CHART) gtk_target_list_add_image_targets (tl, SELECT_FMT_IMG, TRUE); return tl; } @@ -805,10 +803,6 @@ struct psppire_output_view * psppire_output_view_new (GtkLayout *output, GtkTreeView *overview) { struct psppire_output_view *view; - GtkTreeViewColumn *column; - GtkCellRenderer *renderer; - - GtkTreeModel *model; view = xmalloc (sizeof *view); *view = (struct psppire_output_view) { @@ -835,7 +829,7 @@ psppire_output_view_new (GtkLayout *output, GtkTreeView *overview) { g_signal_connect (overview, "realize", G_CALLBACK (on_realize), view); - model = GTK_TREE_MODEL (gtk_tree_store_new ( + GtkTreeModel *model = GTK_TREE_MODEL (gtk_tree_store_new ( N_COLS, G_TYPE_STRING, /* COL_LABEL */ G_TYPE_POINTER, /* COL_ADDR */ @@ -843,9 +837,9 @@ psppire_output_view_new (GtkLayout *output, GtkTreeView *overview) gtk_tree_view_set_model (overview, model); g_object_unref (model); - column = gtk_tree_view_column_new (); + GtkTreeViewColumn *column = gtk_tree_view_column_new (); gtk_tree_view_append_column (GTK_TREE_VIEW (overview), column); - renderer = gtk_cell_renderer_text_new (); + GtkCellRenderer * renderer = gtk_cell_renderer_text_new (); gtk_tree_view_column_pack_start (column, renderer, TRUE); gtk_tree_view_column_add_attribute (column, renderer, "text", COL_LABEL); @@ -878,31 +872,9 @@ psppire_output_view_destroy (struct psppire_output_view *view) if (view->print_settings != NULL) g_object_unref (view->print_settings); - if (view->cur_group) - gtk_tree_path_free (view->cur_group); - free (view); } -void -psppire_output_view_clear (struct psppire_output_view *view) -{ - size_t i; - - view->max_width = 0; - view->y = 0; - - for (i = 0; i < view->n_items; i++) - { - gtk_container_remove (GTK_CONTAINER (view->output), - view->items[i].drawing_area); - output_item_unref (view->items[i].item); - } - free (view->items); - view->items = NULL; - view->n_items = view->allocated_items = 0; -} - /* Export. */ void @@ -917,7 +889,8 @@ psppire_output_view_export (struct psppire_output_view *view, size_t i; for (i = 0; i < view->n_items; i++) - driver->class->submit (driver, view->items[i].item); + if (view->items[i].nesting_depth == 0) + driver->class->submit (driver, view->items[i].item); output_driver_destroy (driver); } } @@ -993,29 +966,32 @@ paginate (GtkPrintOperation *operation, complete. Don't let that screw up printing. */ return TRUE; } - else if (view->print_item < view->n_items) + + while (view->print_item < view->n_items) { - xr_pager_add_item (view->pager, view->items[view->print_item++].item); - while (xr_pager_needs_new_page (view->pager)) - { - xr_pager_add_page (view->pager, - get_cairo_context_from_print_context (context)); - view->print_n_pages ++; - } - return FALSE; + const struct output_view_item *item = &view->items[view->print_item++]; + if (item->nesting_depth == 0) + { + xr_pager_add_item (view->pager, item->item); + while (xr_pager_needs_new_page (view->pager)) + { + xr_pager_add_page (view->pager, + get_cairo_context_from_print_context (context)); + view->print_n_pages ++; + } + return FALSE; + } } - else - { - gtk_print_operation_set_n_pages (operation, MAX (1, view->print_n_pages)); - /* Re-create the driver to do the real printing. */ - xr_pager_destroy (view->pager); - view->pager = xr_pager_create (view->page_style, view->fsm_style); - view->print_item = 0; - view->paginated = TRUE; + gtk_print_operation_set_n_pages (operation, MAX (1, view->print_n_pages)); - return TRUE; - } + /* Re-create the driver to do the real printing. */ + xr_pager_destroy (view->pager); + view->pager = xr_pager_create (view->page_style, view->fsm_style); + view->print_item = 0; + view->paginated = TRUE; + + return TRUE; } static void @@ -1050,7 +1026,11 @@ draw_page (GtkPrintOperation *operation, get_cairo_context_from_print_context (context)); while (!xr_pager_needs_new_page (view->pager) && view->print_item < view->n_items) - xr_pager_add_item (view->pager, view->items [view->print_item++].item); + { + const struct output_view_item *item = &view->items [view->print_item++]; + if (item->nesting_depth == 0) + xr_pager_add_item (view->pager, item->item); + } } @@ -1085,47 +1065,3 @@ psppire_output_view_print (struct psppire_output_view *view, g_object_unref (print); } - -struct psppire_output_view_driver - { - struct output_driver driver; - struct psppire_output_view *view; - }; - -static struct psppire_output_view_driver * -psppire_output_view_driver_cast (struct output_driver *driver) -{ - return UP_CAST (driver, struct psppire_output_view_driver, driver); -} - -static void -psppire_output_view_submit (struct output_driver *this, - const struct output_item *item) -{ - struct psppire_output_view_driver *povd = psppire_output_view_driver_cast (this); - - if (is_table_item (item)) - psppire_output_view_put (povd->view, item); -} - -static struct output_driver_class psppire_output_view_driver_class = - { - "PSPPIRE Output View", /* name */ - NULL, /* destroy */ - psppire_output_view_submit, /* submit */ - NULL, /* flush */ - }; - -void -psppire_output_view_register_driver (struct psppire_output_view *view) -{ - struct psppire_output_view_driver *povd; - struct output_driver *d; - - povd = xzalloc (sizeof *povd); - povd->view = view; - d = &povd->driver; - output_driver_init (d, &psppire_output_view_driver_class, "PSPPIRE Output View", - SETTINGS_DEVICE_UNFILTERED); - output_driver_register (d); -}