GTK+ Forums

Discussion forum for GTK+ and Programming. Ask questions, troubleshoot problems, view and post example code, or express your opinions.
It is currently Sat Aug 23, 2014 3:33 am

All times are UTC




Post new topic Reply to topic  [ 1 post ] 
Author Message
 Post subject: Simplest way print treeview
PostPosted: Fri Mar 02, 2012 10:39 am 
Offline
GTK+ Geek

Joined: Mon Mar 30, 2009 12:40 pm
Posts: 69
Location: España
This is a very simple way to print a treeview.
Is based on the Foundations_of_GTK_Development book chapter 12.


Code:

#include <gtk/gtk.h>
#include <math.h>

#define HEADER_HEIGHT 20.0
#define HEADER_GAP 8.5
#define MAX_LIN 100


enum
{
COL_1,
COL_2,
COL_3,
COL_4,
COL_5,
COL_6,
COL_7,
COL_8,
COL_9,
N_COLS
};




typedef struct
{
  gdouble font_size;
  gint lines_per_page; 
  gint total_lines;
  gint total_pages;
 
  GtkTreeModel *model;
  GtkTreePath *path;
  GtkTreeIter iter;
  gint height;
} PrintData;

typedef struct
{
  GtkWidget *window, *chooser;
  GtkWidget *treeview;
  PrintData *data;
} Widgets;

GtkPrintSettings *settings;

static void print_treeview (GtkButton*, Widgets*);
static void begin_print (GtkPrintOperation*, GtkPrintContext*, Widgets*);
static void draw_page (GtkPrintOperation*, GtkPrintContext*, gint, Widgets*);
static void end_print (GtkPrintOperation*, GtkPrintContext*, Widgets*);

int main (int argc, char *argv[])
{
  GtkWidget *hbox, *print;
  Widgets *w;
  GtkWidget *scroll;
  GtkListStore         *store;
  GtkTreeIter           iter;
  GtkTreeViewColumn    *column;
  GtkCellRenderer      *renderer;
  gint i;

  gtk_init (&argc, &argv);

  w = g_slice_new (Widgets);
  w->window = gtk_window_new (GTK_WINDOW_TOPLEVEL);
  gtk_window_set_title (GTK_WINDOW (w->window), "Printing");
  gtk_container_set_border_width (GTK_CONTAINER (w->window), 10);
  gtk_widget_set_size_request (w->window, 200, -1);
  //gtk_window_maximize(GTK_WINDOW (w->window));

  g_signal_connect (G_OBJECT (w->window), "destroy",G_CALLBACK (gtk_main_quit), NULL);
 
  print = gtk_button_new_from_stock (GTK_STOCK_PRINT);
 
  g_signal_connect (G_OBJECT (print), "clicked",G_CALLBACK (print_treeview), (gpointer) w);
 
  scroll = gtk_scrolled_window_new (NULL, NULL);
  gtk_scrolled_window_set_policy(GTK_SCROLLED_WINDOW(scroll),GTK_POLICY_AUTOMATIC,GTK_POLICY_AUTOMATIC);                   
   
  w->treeview = gtk_tree_view_new();
   
  gtk_tree_view_set_grid_lines(GTK_TREE_VIEW(w->treeview),GTK_TREE_VIEW_GRID_LINES_BOTH);
  gtk_tree_view_set_rules_hint(GTK_TREE_VIEW(w->treeview),TRUE); //diferent colors in each line 
   
  store = gtk_list_store_new(N_COLS,G_TYPE_UINT,G_TYPE_STRING,G_TYPE_STRING,G_TYPE_STRING
                                     ,G_TYPE_STRING, G_TYPE_STRING,G_TYPE_STRING,G_TYPE_STRING,G_TYPE_STRING);
  for( i = 0; i < MAX_LIN; i++ )
    {
    gtk_list_store_append( store, &iter );
    gtk_list_store_set( store, &iter,
                            COL_1, i,
                            COL_2, g_strdup_printf( "Sample %d", i + 1),
                            COL_3, g_strdup_printf( "S3 %d", i + 1 ),
                            COL_4, g_strdup_printf( "S4 %d", i + 1),
                            COL_5, g_strdup_printf( "S5 %d", i + 1),
                            COL_6, g_strdup_printf( "S6 %d", i + 1 ),
                            COL_7, g_strdup_printf( "S7 %d", i + 1),
                            COL_8, g_strdup_printf( "S8 %d", i + 1 ),
                            COL_9, g_strdup_printf( "S9 %d", i + 1),
                            -1 );
    }

  gtk_tree_view_set_model( GTK_TREE_VIEW( w->treeview ),
                             GTK_TREE_MODEL( store ) );
  g_object_unref( G_OBJECT( store ) );
   
  for(i=0;i < 9;i++)
      {
      renderer = gtk_cell_renderer_text_new();
      column = gtk_tree_view_column_new();
      gtk_cell_layout_pack_start(GTK_CELL_LAYOUT(column), renderer, TRUE );
      gtk_tree_view_column_set_attributes(column, renderer,"text",i, NULL );
      gtk_tree_view_column_set_title(column,g_strdup_printf( "Column %d",i + 1));
      gtk_tree_view_column_set_resizable(column,TRUE);
      gtk_tree_view_column_set_sizing(column,GTK_TREE_VIEW_COLUMN_FIXED);
      gtk_tree_view_column_set_fixed_width(column,40);
      gtk_tree_view_append_column( GTK_TREE_VIEW(w->treeview),column);     
      }               
 
  gtk_container_add(GTK_CONTAINER(scroll),w->treeview);
 
  hbox = gtk_hbox_new (FALSE, 5);
  gtk_box_pack_start (GTK_BOX (hbox), print, FALSE, FALSE, 0);
 
  gtk_box_pack_start (GTK_BOX (hbox), scroll, TRUE, TRUE, 0);
 
  gtk_container_add (GTK_CONTAINER (w->window), hbox);
 
  gtk_widget_show_all (w->window);
 
  gtk_main ();
  return 0;
}


static void print_treeview (GtkButton *button,Widgets *w)
{
  GtkPrintOperation *operation;
  GtkWidget *dialog;
  GError *error = NULL;
  gint res;

  operation = gtk_print_operation_new ();
  if (settings != NULL) gtk_print_operation_set_print_settings (operation, settings);
 
  w->data = g_slice_new (PrintData);
  w->data->font_size = 10.0;

  g_signal_connect (G_OBJECT (operation), "begin_print", G_CALLBACK (begin_print), (gpointer) w);
  g_signal_connect (G_OBJECT (operation), "draw_page", G_CALLBACK (draw_page), (gpointer) w);
  g_signal_connect (G_OBJECT (operation), "end_print", G_CALLBACK (end_print), (gpointer) w);

  res = gtk_print_operation_run (operation, GTK_PRINT_OPERATION_ACTION_PRINT_DIALOG, GTK_WINDOW (w->window), &error);
  //gtk_print_operation_run (operation, GTK_PRINT_OPERATION_ACTION_PREVIEW,GTK_WINDOW(w->window),NULL);
 
 
  if (res == GTK_PRINT_OPERATION_RESULT_APPLY)
  {
    if (settings != NULL) g_object_unref (settings);
    settings = g_object_ref (gtk_print_operation_get_print_settings (operation));
  }
  else if (error)
  {
    dialog = gtk_message_dialog_new (GTK_WINDOW (w->window),
                                     GTK_DIALOG_DESTROY_WITH_PARENT,
                                     GTK_MESSAGE_ERROR, GTK_BUTTONS_CLOSE,
                                         error->message);
   
    g_error_free (error);
    gtk_dialog_run (GTK_DIALOG (dialog));
    gtk_widget_destroy (dialog);     
  }
 
 
  g_object_unref (operation);
}


static void begin_print (GtkPrintOperation *operation,  GtkPrintContext *context, Widgets *w)
{
  gdouble height;
  GdkRectangle rect;

  w->data->total_lines = MAX_LIN;

  w->data->model = gtk_tree_view_get_model(GTK_TREE_VIEW(w->treeview));
  w->data->path = gtk_tree_path_new_first();
  gtk_tree_view_get_cell_area(GTK_TREE_VIEW(w->treeview),w->data->path,NULL,&rect);
  w->data->height = rect.height;

  height = gtk_print_context_get_height (context) - HEADER_HEIGHT - HEADER_GAP;
  w->data->lines_per_page = floor (height / w->data->height);
  w->data->total_pages = (w->data->total_lines - 1) / w->data->lines_per_page + 1;
  gtk_print_operation_set_n_pages (operation, w->data->total_pages);

}



static void draw_page (GtkPrintOperation *operation,GtkPrintContext *context,gint page_nr,Widgets *w)
{
  cairo_t *cr;
  PangoLayout *layout;
  gdouble width, text_height;
  gint text_width, layout_height;
  PangoFontDescription *desc;
  gchar *page_str;
  GtkTreeViewColumn *column;
  gboolean visible;
  GValue value = {0};
  GString *text;
  gint col_num;
  GdkRectangle rect;
  gint i,x,y;

  text = g_string_new("");

  cr = gtk_print_context_get_cairo_context (context);
  width = gtk_print_context_get_width (context);
  layout = gtk_print_context_create_pango_layout (context);
  desc = pango_font_description_from_string ("Monospace");
  pango_font_description_set_size (desc, w->data->font_size * PANGO_SCALE);

  pango_layout_set_font_description (layout, desc);
  pango_layout_set_text (layout, "print tree view", -1);
  pango_layout_set_width (layout, -1);
  pango_layout_set_alignment (layout, PANGO_ALIGN_LEFT);
  pango_layout_get_size (layout, NULL, &layout_height);
  text_height = (gdouble) layout_height / PANGO_SCALE;

  cairo_move_to (cr, 0, (HEADER_HEIGHT - text_height) / 2);
  pango_cairo_show_layout (cr, layout);

  page_str = g_strdup_printf ("%d of %d", page_nr + 1, w->data->total_pages);
  pango_layout_set_text (layout, page_str, -1);
  pango_layout_get_size (layout, &text_width, NULL);
  pango_layout_set_alignment (layout, PANGO_ALIGN_RIGHT);

  cairo_move_to (cr, width - (text_width / PANGO_SCALE),
                 (HEADER_HEIGHT - text_height) / 2);
  pango_cairo_show_layout (cr, layout);
 
  cairo_move_to (cr, 0, HEADER_HEIGHT + HEADER_GAP);

  y = HEADER_HEIGHT;
  for (i = 0; i < w->data->lines_per_page && gtk_tree_model_get_iter(w->data->model,&w->data->iter,w->data->path); i++)
        {
        x = 0;
        for(col_num=0;col_num < gtk_tree_model_get_n_columns(w->data->model);col_num++)
           {
           column = gtk_tree_view_get_column(GTK_TREE_VIEW(w->treeview),col_num);
           visible = gtk_tree_view_column_get_visible(column);
           
           if(visible)
             {
             gtk_tree_model_get_value(w->data->model,&w->data->iter,col_num,&value);
       
             switch(G_VALUE_TYPE(&value))
                   {
                   case G_TYPE_STRING:
                        {
                        if(g_value_get_string(&value) != NULL) g_string_assign(text,g_value_get_string(&value));
                        } break;
                   case G_TYPE_UINT:
                        {
                        g_string_printf(text,"%d",g_value_get_uint(&value));
                        } break;
                   case G_TYPE_ULONG:
                        {
                        g_string_printf(text,"%lu",g_value_get_ulong(&value));
                        } break;
                   }
     
             g_value_unset(&value);
             
             }

           gtk_tree_view_get_background_area(GTK_TREE_VIEW(w->treeview),w->data->path,column,&rect);
           
           pango_layout_set_text(layout,text->str, -1);
           
           pango_layout_set_width(layout,rect.width * PANGO_SCALE);
           pango_layout_set_wrap(layout,PANGO_WRAP_CHAR);
           pango_layout_set_ellipsize(layout,PANGO_ELLIPSIZE_END);
           
           cairo_move_to (cr, x, y);
           pango_cairo_show_layout (cr, layout);
           
           x += (rect.width+3); 
             
           }
       
        y += w->data->height;
        gtk_tree_path_next(w->data->path);
        }

  g_string_free(text,TRUE);
  g_free (page_str);
  g_object_unref (layout);
  pango_font_description_free (desc);
}

static void end_print (GtkPrintOperation *operation, GtkPrintContext *context,Widgets *w)
{
  gtk_tree_path_free(w->data->path);     
  g_slice_free1 (sizeof (PrintData), w->data);
  w->data = NULL;
}



Top
 Profile  
 
Display posts from previous:  Sort by  
Post new topic Reply to topic  [ 1 post ] 

All times are UTC


Who is online

Users browsing this forum: Google [Bot] and 2 guests


You cannot post new topics in this forum
You cannot reply to topics in this forum
You cannot edit your posts in this forum
You cannot delete your posts in this forum
You cannot post attachments in this forum

Search for:
Jump to:  
Powered by phpBB © 2000, 2002, 2005, 2007 phpBB Group