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=6d03bf519dac51a4869f9cc3ef71fef5778f1eed;hp=d756af4f7abc6544a55b4937f9167a31e89f3c7b;hpb=991b87b671dfda11f4aaae78b059c1450f9c8df1;p=pspp diff --git a/src/ui/gui/psppire-output-view.c b/src/ui/gui/psppire-output-view.c index d756af4f7a..6c19434b1b 100644 --- a/src/ui/gui/psppire-output-view.c +++ b/src/ui/gui/psppire-output-view.c @@ -43,6 +43,8 @@ struct output_view_item { struct output_item *item; GtkWidget *drawing_area; + int width, height; + int nesting_depth; }; struct psppire_output_view @@ -56,7 +58,6 @@ struct psppire_output_view glong y; GtkTreeView *overview; - GtkTreePath *cur_group; GtkWidget *toplevel; @@ -387,39 +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 (item->type == OUTPUT_ITEM_GROUP) - return; - - 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); - 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 (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); @@ -435,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 ( @@ -454,32 +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); - /* XXX group? */ 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 @@ -780,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) { @@ -810,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 */ @@ -818,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); @@ -853,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 @@ -892,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); } } @@ -968,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 @@ -1025,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); + } }