diff options
author | Steven Rostedt <srostedt@redhat.com> | 2009-12-02 21:23:17 -0500 |
---|---|---|
committer | Steven Rostedt <rostedt@goodmis.org> | 2009-12-17 21:43:47 -0500 |
commit | 064e10948d40840c8521f7f94cc3275eb8075b07 (patch) | |
tree | d4029da9e8ba72e7eefdab569014a6744aabe02e | |
parent | ac9d350897a5a6fec7b0e10cc421dc9a0aa995eb (diff) |
Add paging of large data files
Loading a large (100,000+ entry) data file can take a very long
time, and is quite annoying to wait for. This patch breaks the
data up into pages (10,000 rows per page). Then it lets the user
move about the pages with a scroll button.
Signed-off-by: Steven Rostedt <rostedt@goodmis.org>
-rw-r--r-- | Makefile | 2 | ||||
-rw-r--r-- | trace-filter.c | 1 | ||||
-rw-r--r-- | trace-view-store.c | 103 | ||||
-rw-r--r-- | trace-view-store.h | 59 | ||||
-rw-r--r-- | trace-view.c | 72 |
5 files changed, 205 insertions, 32 deletions
@@ -22,7 +22,7 @@ all: $(TARGETS) | |||
22 | 22 | ||
23 | LIB_FILE = libtracecmd.a | 23 | LIB_FILE = libtracecmd.a |
24 | 24 | ||
25 | HEADERS = parse-events.h trace-cmd.h trace-local.h | 25 | HEADERS = parse-events.h trace-cmd.h trace-local.h trace-view-store.h |
26 | 26 | ||
27 | trace-read.o:: $(HEADERS) | 27 | trace-read.o:: $(HEADERS) |
28 | trace-cmd.o:: $(HEADERS) $(LIB_FILE) | 28 | trace-cmd.o:: $(HEADERS) $(LIB_FILE) |
diff --git a/trace-filter.c b/trace-filter.c index 8d6fced..b7d8176 100644 --- a/trace-filter.c +++ b/trace-filter.c | |||
@@ -347,6 +347,7 @@ void trace_filter_cpu_dialog(void *trace_tree) | |||
347 | 347 | ||
348 | cpu_helper->allcpus = allset; | 348 | cpu_helper->allcpus = allset; |
349 | cpu_helper->cpu_mask = g_new0(guint64, (cpus >> 6) + 1); | 349 | cpu_helper->cpu_mask = g_new0(guint64, (cpus >> 6) + 1); |
350 | g_assert(cpu_helper->cpu_mask != NULL); | ||
350 | 351 | ||
351 | gtk_widget_show(check); | 352 | gtk_widget_show(check); |
352 | 353 | ||
diff --git a/trace-view-store.c b/trace-view-store.c index b65e6a3..3192b2b 100644 --- a/trace-view-store.c +++ b/trace-view-store.c | |||
@@ -177,6 +177,15 @@ trace_view_store_init (TraceViewStore *trace_view_store) | |||
177 | trace_view_store->num_rows = 0; | 177 | trace_view_store->num_rows = 0; |
178 | trace_view_store->rows = NULL; | 178 | trace_view_store->rows = NULL; |
179 | 179 | ||
180 | trace_view_store->spin = NULL; | ||
181 | trace_view_store->page = 1; | ||
182 | trace_view_store->pages = 1; | ||
183 | trace_view_store->rows_per_page = TRACE_VIEW_DEFAULT_MAX_ROWS; | ||
184 | trace_view_store->num_rows = 0; | ||
185 | trace_view_store->start_row = 0; | ||
186 | trace_view_store->visible_rows = 0; | ||
187 | trace_view_store->actual_rows = 0; | ||
188 | |||
180 | /* Set all columns visible */ | 189 | /* Set all columns visible */ |
181 | trace_view_store->visible_column_mask = (1 << TRACE_VIEW_STORE_N_COLUMNS) - 1; | 190 | trace_view_store->visible_column_mask = (1 << TRACE_VIEW_STORE_N_COLUMNS) - 1; |
182 | 191 | ||
@@ -195,11 +204,14 @@ trace_view_store_init (TraceViewStore *trace_view_store) | |||
195 | static void | 204 | static void |
196 | trace_view_store_finalize (GObject *object) | 205 | trace_view_store_finalize (GObject *object) |
197 | { | 206 | { |
198 | /* TraceViewStore *trace_view_store = TRACE_VIEW_STORE(object); */ | 207 | TraceViewStore *store = TRACE_VIEW_STORE(object); |
199 | 208 | ||
200 | /* free all records and free all memory used by the list */ | 209 | /* free all records and free all memory used by the list */ |
201 | #warning IMPLEMENT | 210 | #warning IMPLEMENT |
202 | 211 | ||
212 | if (store->spin) | ||
213 | g_object_unref(store->spin); | ||
214 | |||
203 | /* must chain up - finalize parent */ | 215 | /* must chain up - finalize parent */ |
204 | (* parent_class->finalize) (object); | 216 | (* parent_class->finalize) (object); |
205 | } | 217 | } |
@@ -303,7 +315,7 @@ trace_view_store_get_iter (GtkTreeModel *tree_model, | |||
303 | { | 315 | { |
304 | TraceViewStore *trace_view_store; | 316 | TraceViewStore *trace_view_store; |
305 | TraceViewRecord *record; | 317 | TraceViewRecord *record; |
306 | gint *indices, n, depth; | 318 | gint *indices, n, depth, pos; |
307 | 319 | ||
308 | g_assert(TRACE_VIEW_IS_LIST(tree_model)); | 320 | g_assert(TRACE_VIEW_IS_LIST(tree_model)); |
309 | g_assert(path!=NULL); | 321 | g_assert(path!=NULL); |
@@ -321,10 +333,13 @@ trace_view_store_get_iter (GtkTreeModel *tree_model, | |||
321 | if ( n >= trace_view_store->num_rows || n < 0 ) | 333 | if ( n >= trace_view_store->num_rows || n < 0 ) |
322 | return FALSE; | 334 | return FALSE; |
323 | 335 | ||
324 | record = trace_view_store->rows[n]; | 336 | record = trace_view_store->rows[trace_view_store->start_row + n]; |
325 | 337 | ||
326 | g_assert(record != NULL); | 338 | g_assert(record != NULL); |
327 | g_assert(record->pos == n); | 339 | |
340 | pos = record->pos - trace_view_store->start_row; | ||
341 | |||
342 | g_assert(pos == n); | ||
328 | 343 | ||
329 | /* We simply store a pointer to our custom record in the iter */ | 344 | /* We simply store a pointer to our custom record in the iter */ |
330 | iter->stamp = trace_view_store->stamp; | 345 | iter->stamp = trace_view_store->stamp; |
@@ -388,7 +403,7 @@ trace_view_store_get_value (GtkTreeModel *tree_model, | |||
388 | const gchar *comm; | 403 | const gchar *comm; |
389 | gchar *str; | 404 | gchar *str; |
390 | guint64 secs, usecs; | 405 | guint64 secs, usecs; |
391 | gint val; | 406 | gint val, pos; |
392 | int cpu; | 407 | int cpu; |
393 | 408 | ||
394 | g_return_if_fail (TRACE_VIEW_IS_LIST (tree_model)); | 409 | g_return_if_fail (TRACE_VIEW_IS_LIST (tree_model)); |
@@ -405,7 +420,9 @@ trace_view_store_get_value (GtkTreeModel *tree_model, | |||
405 | 420 | ||
406 | g_return_if_fail ( record != NULL ); | 421 | g_return_if_fail ( record != NULL ); |
407 | 422 | ||
408 | if(record->pos >= trace_view_store->num_rows) | 423 | pos = record->pos - trace_view_store->start_row; |
424 | |||
425 | if(pos >= trace_view_store->num_rows) | ||
409 | g_return_if_reached(); | 426 | g_return_if_reached(); |
410 | 427 | ||
411 | column = get_visible_column(TRACE_VIEW_STORE(tree_model), column); | 428 | column = get_visible_column(TRACE_VIEW_STORE(tree_model), column); |
@@ -433,6 +450,7 @@ trace_view_store_get_value (GtkTreeModel *tree_model, | |||
433 | case TRACE_VIEW_STORE_COL_INFO: | 450 | case TRACE_VIEW_STORE_COL_INFO: |
434 | 451 | ||
435 | data = tracecmd_read_at(trace_view_store->handle, record->offset, &cpu); | 452 | data = tracecmd_read_at(trace_view_store->handle, record->offset, &cpu); |
453 | g_assert(data != NULL); | ||
436 | if (cpu != record->cpu) { | 454 | if (cpu != record->cpu) { |
437 | free(data); | 455 | free(data); |
438 | return; | 456 | return; |
@@ -490,6 +508,7 @@ trace_view_store_iter_next (GtkTreeModel *tree_model, | |||
490 | { | 508 | { |
491 | TraceViewRecord *record, *nextrecord; | 509 | TraceViewRecord *record, *nextrecord; |
492 | TraceViewStore *trace_view_store; | 510 | TraceViewStore *trace_view_store; |
511 | gint pos; | ||
493 | 512 | ||
494 | g_return_val_if_fail (TRACE_VIEW_IS_LIST (tree_model), FALSE); | 513 | g_return_val_if_fail (TRACE_VIEW_IS_LIST (tree_model), FALSE); |
495 | 514 | ||
@@ -500,8 +519,10 @@ trace_view_store_iter_next (GtkTreeModel *tree_model, | |||
500 | 519 | ||
501 | record = (TraceViewRecord *) iter->user_data; | 520 | record = (TraceViewRecord *) iter->user_data; |
502 | 521 | ||
522 | pos = record->pos - trace_view_store->start_row; | ||
523 | |||
503 | /* Is this the last record in the list? */ | 524 | /* Is this the last record in the list? */ |
504 | if ((record->pos + 1) >= trace_view_store->num_rows) | 525 | if ((pos + 1) >= trace_view_store->num_rows) |
505 | return FALSE; | 526 | return FALSE; |
506 | 527 | ||
507 | nextrecord = trace_view_store->rows[(record->pos + 1)]; | 528 | nextrecord = trace_view_store->rows[(record->pos + 1)]; |
@@ -638,10 +659,10 @@ trace_view_store_iter_nth_child (GtkTreeModel *tree_model, | |||
638 | if( n >= trace_view_store->num_rows ) | 659 | if( n >= trace_view_store->num_rows ) |
639 | return FALSE; | 660 | return FALSE; |
640 | 661 | ||
641 | record = trace_view_store->rows[n]; | 662 | record = trace_view_store->rows[trace_view_store->start_row + n]; |
642 | 663 | ||
643 | g_assert( record != NULL ); | 664 | g_assert( record != NULL ); |
644 | g_assert( record->pos == n ); | 665 | g_assert( record->pos - trace_view_store->start_row == n ); |
645 | 666 | ||
646 | iter->stamp = trace_view_store->stamp; | 667 | iter->stamp = trace_view_store->stamp; |
647 | iter->user_data = record; | 668 | iter->user_data = record; |
@@ -702,6 +723,15 @@ static void mask_set_cpus(TraceViewStore *store, gint cpus) | |||
702 | *(store->cpu_mask) = (1ULL << (cpus & ((1ULL << 6) - 1))) - 1; | 723 | *(store->cpu_mask) = (1ULL << (cpus & ((1ULL << 6) - 1))) - 1; |
703 | } | 724 | } |
704 | 725 | ||
726 | static void update_page(TraceViewStore *store) | ||
727 | { | ||
728 | if (!store->spin) | ||
729 | return; | ||
730 | |||
731 | gtk_spin_button_set_range(GTK_SPIN_BUTTON(store->spin), | ||
732 | 1, store->pages); | ||
733 | } | ||
734 | |||
705 | /***************************************************************************** | 735 | /***************************************************************************** |
706 | * | 736 | * |
707 | * merge_sort_rows_ts: Merge sort the data by time stamp. | 737 | * merge_sort_rows_ts: Merge sort the data by time stamp. |
@@ -752,7 +782,27 @@ static void merge_sort_rows_ts(TraceViewStore *store) | |||
752 | } | 782 | } |
753 | } while (next >= 0); | 783 | } while (next >= 0); |
754 | 784 | ||
755 | store->num_rows = count; | 785 | store->visible_rows = count; |
786 | store->start_row = 0; | ||
787 | store->pages = (count / store->rows_per_page) + 1; | ||
788 | |||
789 | if (store->page > 1) { | ||
790 | if (count < store->page * store->rows_per_page) | ||
791 | store->page = store->pages; | ||
792 | |||
793 | /* still greater? */ | ||
794 | if (store->page > 1) { | ||
795 | store->start_row = | ||
796 | (store->page - 1) * store->rows_per_page; | ||
797 | g_assert(store->start_row < count); | ||
798 | } | ||
799 | } | ||
800 | |||
801 | store->num_rows = count > (store->start_row + store->rows_per_page) ? | ||
802 | store->rows_per_page : | ||
803 | count - store->start_row; | ||
804 | |||
805 | update_page(store); | ||
756 | 806 | ||
757 | g_free(indexes); | 807 | g_free(indexes); |
758 | } | 808 | } |
@@ -826,6 +876,8 @@ trace_view_store_new (struct tracecmd_input *handle) | |||
826 | rec = list; | 876 | rec = list; |
827 | 877 | ||
828 | trec = g_new(TraceViewRecord, count); | 878 | trec = g_new(TraceViewRecord, count); |
879 | g_assert(trec != NULL); | ||
880 | |||
829 | for (i = 0; i < count; i++) { | 881 | for (i = 0; i < count; i++) { |
830 | g_assert(rec != NULL); | 882 | g_assert(rec != NULL); |
831 | trec[i].cpu = cpu; | 883 | trec[i].cpu = cpu; |
@@ -848,13 +900,29 @@ trace_view_store_new (struct tracecmd_input *handle) | |||
848 | total += count; | 900 | total += count; |
849 | } | 901 | } |
850 | 902 | ||
851 | newstore->rows = g_malloc(sizeof(*newstore->rows) * total); | 903 | newstore->actual_rows = total; |
904 | newstore->rows = g_malloc(sizeof(*newstore->rows) * total + 1); | ||
852 | 905 | ||
853 | merge_sort_rows_ts(newstore); | 906 | merge_sort_rows_ts(newstore); |
854 | 907 | ||
855 | return newstore; | 908 | return newstore; |
856 | } | 909 | } |
857 | 910 | ||
911 | void trace_view_store_set_spin_button(TraceViewStore *store, GtkWidget *spin) | ||
912 | { | ||
913 | g_return_if_fail (TRACE_VIEW_IS_LIST (store)); | ||
914 | g_return_if_fail (GTK_IS_SPIN_BUTTON (spin)); | ||
915 | |||
916 | store->spin = spin; | ||
917 | |||
918 | gtk_spin_button_set_increments(GTK_SPIN_BUTTON(store->spin), | ||
919 | 1.0, 5.0); | ||
920 | |||
921 | update_page(store); | ||
922 | |||
923 | g_object_ref(spin); | ||
924 | } | ||
925 | |||
858 | /* --- helper functions --- */ | 926 | /* --- helper functions --- */ |
859 | 927 | ||
860 | gboolean trace_view_store_cpu_isset(TraceViewStore *store, gint cpu) | 928 | gboolean trace_view_store_cpu_isset(TraceViewStore *store, gint cpu) |
@@ -907,6 +975,19 @@ void trace_view_store_clear_cpu(TraceViewStore *store, gint cpu) | |||
907 | merge_sort_rows_ts(store); | 975 | merge_sort_rows_ts(store); |
908 | } | 976 | } |
909 | 977 | ||
978 | void trace_view_store_set_page(TraceViewStore *store, gint page) | ||
979 | { | ||
980 | g_return_if_fail (TRACE_VIEW_IS_LIST (store)); | ||
981 | g_return_if_fail (page >= 0 || page < store->pages); | ||
982 | |||
983 | store->page = page; | ||
984 | store->start_row = (page - 1) * store->rows_per_page; | ||
985 | g_assert(store->start_row < store->visible_rows); | ||
986 | store->num_rows = store->start_row + store->rows_per_page < | ||
987 | store->visible_rows ? store->rows_per_page : | ||
988 | store->visible_rows - store->start_row; | ||
989 | } | ||
990 | |||
910 | 991 | ||
911 | /***************************************************************************** | 992 | /***************************************************************************** |
912 | * | 993 | * |
diff --git a/trace-view-store.h b/trace-view-store.h index 8440888..9dbbb5a 100644 --- a/trace-view-store.h +++ b/trace-view-store.h | |||
@@ -62,7 +62,10 @@ struct _TraceViewStore | |||
62 | { | 62 | { |
63 | GObject parent; /* this MUST be the first member */ | 63 | GObject parent; /* this MUST be the first member */ |
64 | 64 | ||
65 | guint num_rows; /* number of rows that we have */ | 65 | guint start_row; /* row to start at */ |
66 | guint num_rows; /* number of rows that we have showing */ | ||
67 | guint visible_rows; /* number of rows defined */ | ||
68 | guint actual_rows; /* size of rows array */ | ||
66 | TraceViewRecord **rows; /* a dynamically allocated array of pointers to | 69 | TraceViewRecord **rows; /* a dynamically allocated array of pointers to |
67 | * the TraceViewRecord structure for each row */ | 70 | * the TraceViewRecord structure for each row */ |
68 | 71 | ||
@@ -78,6 +81,11 @@ struct _TraceViewStore | |||
78 | TraceViewRecord **cpu_list; | 81 | TraceViewRecord **cpu_list; |
79 | gint *cpu_items; | 82 | gint *cpu_items; |
80 | 83 | ||
84 | gint page; | ||
85 | gint pages; | ||
86 | gint rows_per_page; | ||
87 | GtkWidget *spin; | ||
88 | |||
81 | /* filters */ | 89 | /* filters */ |
82 | gint all_events; /* set 1 when all events are enabled */ | 90 | gint all_events; /* set 1 when all events are enabled */ |
83 | /* else */ | 91 | /* else */ |
@@ -91,29 +99,15 @@ struct _TraceViewStore | |||
91 | gint stamp; /* Random integer to check whether an iter belongs to our model */ | 99 | gint stamp; /* Random integer to check whether an iter belongs to our model */ |
92 | }; | 100 | }; |
93 | 101 | ||
94 | /* helper functions */ | ||
95 | |||
96 | static inline gint trace_view_store_get_cpus(TraceViewStore *store) | ||
97 | { | ||
98 | return store->cpus; | ||
99 | } | ||
100 | |||
101 | static inline guint64 *trace_view_store_get_cpu_mask(TraceViewStore *store) | ||
102 | { | ||
103 | return store->cpu_mask; | ||
104 | } | ||
105 | |||
106 | static inline gint trace_view_store_get_all_cpus(TraceViewStore *store) | ||
107 | { | ||
108 | return store->all_cpus; | ||
109 | } | ||
110 | |||
111 | gboolean trace_view_store_cpu_isset(TraceViewStore *store, gint cpu); | 102 | gboolean trace_view_store_cpu_isset(TraceViewStore *store, gint cpu); |
112 | 103 | ||
113 | void trace_view_store_set_all_cpus(TraceViewStore *store); | 104 | void trace_view_store_set_all_cpus(TraceViewStore *store); |
114 | void trace_view_store_set_cpu(TraceViewStore *store, gint cpu); | 105 | void trace_view_store_set_cpu(TraceViewStore *store, gint cpu); |
115 | void trace_view_store_clear_cpu(TraceViewStore *store, gint cpu); | 106 | void trace_view_store_clear_cpu(TraceViewStore *store, gint cpu); |
116 | 107 | ||
108 | void trace_view_store_set_spin_button(TraceViewStore *store, GtkWidget *spin); | ||
109 | |||
110 | void trace_view_store_set_page(TraceViewStore *store, gint page); | ||
117 | 111 | ||
118 | /* TraceViewStoreClass: more boilerplate GObject stuff */ | 112 | /* TraceViewStoreClass: more boilerplate GObject stuff */ |
119 | 113 | ||
@@ -127,10 +121,39 @@ GType trace_view_store_get_type (void); | |||
127 | 121 | ||
128 | TraceViewStore *trace_view_store_new (struct tracecmd_input *handle); | 122 | TraceViewStore *trace_view_store_new (struct tracecmd_input *handle); |
129 | 123 | ||
124 | #define TRACE_VIEW_DEFAULT_MAX_ROWS 10000 | ||
125 | |||
130 | #if 0 | 126 | #if 0 |
131 | void trace_view_store_append_record (TraceViewStore *trace_view_store, | 127 | void trace_view_store_append_record (TraceViewStore *trace_view_store, |
132 | const gchar *name, | 128 | const gchar *name, |
133 | guint year_born); | 129 | guint year_born); |
134 | #endif | 130 | #endif |
135 | 131 | ||
132 | |||
133 | /* helper functions */ | ||
134 | |||
135 | static inline gint trace_view_store_get_cpus(TraceViewStore *store) | ||
136 | { | ||
137 | g_return_val_if_fail (TRACE_VIEW_IS_LIST (store), -1); | ||
138 | return store->cpus; | ||
139 | } | ||
140 | |||
141 | static inline guint64 *trace_view_store_get_cpu_mask(TraceViewStore *store) | ||
142 | { | ||
143 | g_return_val_if_fail (TRACE_VIEW_IS_LIST (store), NULL); | ||
144 | return store->cpu_mask; | ||
145 | } | ||
146 | |||
147 | static inline gint trace_view_store_get_all_cpus(TraceViewStore *store) | ||
148 | { | ||
149 | g_return_val_if_fail (TRACE_VIEW_IS_LIST (store), -1); | ||
150 | return store->all_cpus; | ||
151 | } | ||
152 | |||
153 | static inline gint trace_view_store_get_page(TraceViewStore *store) | ||
154 | { | ||
155 | g_return_val_if_fail (TRACE_VIEW_IS_LIST (store), -1); | ||
156 | return store->page; | ||
157 | } | ||
158 | |||
136 | #endif /* _trace_view_store_h_included_ */ | 159 | #endif /* _trace_view_store_h_included_ */ |
diff --git a/trace-view.c b/trace-view.c index ac71c7c..555f1aa 100644 --- a/trace-view.c +++ b/trace-view.c | |||
@@ -80,6 +80,44 @@ cpus_clicked (gpointer data) | |||
80 | trace_filter_cpu_dialog(trace_tree); | 80 | trace_filter_cpu_dialog(trace_tree); |
81 | } | 81 | } |
82 | 82 | ||
83 | #if 0 | ||
84 | static GtkTreeModel * | ||
85 | create_combo_box_model(void) | ||
86 | { | ||
87 | GtkListStore *store; | ||
88 | GtkTreeIter iter; | ||
89 | |||
90 | store = gtk_list_store_new(1, G_TYPE_STRING); | ||
91 | gtk_list_store_append(store, &iter); | ||
92 | gtk_list_store_set(store, &iter, 0, "1", -1); | ||
93 | |||
94 | return GTK_TREE_MODEL(store); | ||
95 | } | ||
96 | #endif | ||
97 | |||
98 | static void | ||
99 | spin_changed(gpointer data, GtkWidget *spin) | ||
100 | { | ||
101 | GtkTreeView *tree = data; | ||
102 | GtkTreeModel *model; | ||
103 | gint val, page; | ||
104 | |||
105 | val = gtk_spin_button_get_value_as_int(GTK_SPIN_BUTTON(spin)); | ||
106 | |||
107 | model = gtk_tree_view_get_model(tree); | ||
108 | page = trace_view_store_get_page(TRACE_VIEW_STORE(model)); | ||
109 | if (page == val) | ||
110 | return; | ||
111 | |||
112 | g_object_ref(model); | ||
113 | gtk_tree_view_set_model(tree, NULL); | ||
114 | |||
115 | trace_view_store_set_page(TRACE_VIEW_STORE(model), val); | ||
116 | |||
117 | gtk_tree_view_set_model(tree, model); | ||
118 | g_object_unref(model); | ||
119 | } | ||
120 | |||
83 | static GtkTreeModel * | 121 | static GtkTreeModel * |
84 | create_trace_view_model(struct tracecmd_input *handle) | 122 | create_trace_view_model(struct tracecmd_input *handle) |
85 | { | 123 | { |
@@ -91,7 +129,8 @@ create_trace_view_model(struct tracecmd_input *handle) | |||
91 | } | 129 | } |
92 | 130 | ||
93 | static void | 131 | static void |
94 | load_trace_view(GtkWidget *view, struct tracecmd_input *handle) | 132 | load_trace_view(GtkWidget *view, struct tracecmd_input *handle, |
133 | GtkWidget *spin) | ||
95 | { | 134 | { |
96 | GtkTreeViewColumn *col; | 135 | GtkTreeViewColumn *col; |
97 | GtkCellRenderer *renderer; | 136 | GtkCellRenderer *renderer; |
@@ -155,6 +194,9 @@ load_trace_view(GtkWidget *view, struct tracecmd_input *handle) | |||
155 | 194 | ||
156 | model = create_trace_view_model(handle); | 195 | model = create_trace_view_model(handle); |
157 | 196 | ||
197 | trace_view_store_set_spin_button(TRACE_VIEW_STORE(model), spin); | ||
198 | g_object_unref(spin); | ||
199 | |||
158 | gtk_tree_view_set_model(GTK_TREE_VIEW(view), model); | 200 | gtk_tree_view_set_model(GTK_TREE_VIEW(view), model); |
159 | 201 | ||
160 | g_object_unref(model); /* destroy model automatically with view */ | 202 | g_object_unref(model); /* destroy model automatically with view */ |
@@ -171,6 +213,8 @@ void trace_view(int argc, char **argv) | |||
171 | GtkWidget *menu_item; | 213 | GtkWidget *menu_item; |
172 | GtkWidget *sub_item; | 214 | GtkWidget *sub_item; |
173 | GtkWidget *scrollwin; | 215 | GtkWidget *scrollwin; |
216 | GtkWidget *label; | ||
217 | GtkWidget *spin; | ||
174 | 218 | ||
175 | handle = read_trace_header(); | 219 | handle = read_trace_header(); |
176 | if (!handle) | 220 | if (!handle) |
@@ -279,6 +323,29 @@ void trace_view(int argc, char **argv) | |||
279 | /* --- End Filter Options --- */ | 323 | /* --- End Filter Options --- */ |
280 | gtk_menu_item_set_submenu(GTK_MENU_ITEM (menu_item), menu); | 324 | gtk_menu_item_set_submenu(GTK_MENU_ITEM (menu_item), menu); |
281 | 325 | ||
326 | |||
327 | /* --- Paging Hbox --- */ | ||
328 | |||
329 | hbox = gtk_hbox_new(FALSE, 0); | ||
330 | gtk_box_pack_start(GTK_BOX(vbox), hbox, FALSE, FALSE, 0); | ||
331 | gtk_widget_show(hbox); | ||
332 | |||
333 | /* --- Page Spin Button --- */ | ||
334 | |||
335 | label = gtk_label_new("Page"); | ||
336 | gtk_box_pack_start(GTK_BOX(hbox), label, FALSE, FALSE, 0); | ||
337 | gtk_widget_show(label); | ||
338 | |||
339 | spin = gtk_spin_button_new(NULL, 1.0, 0); | ||
340 | gtk_spin_button_set_range(GTK_SPIN_BUTTON(spin), 1, 1); | ||
341 | gtk_box_pack_start(GTK_BOX(hbox), spin, FALSE, FALSE, 0); | ||
342 | gtk_widget_show(spin); | ||
343 | |||
344 | g_signal_connect_swapped (G_OBJECT (spin), "value-changed", | ||
345 | G_CALLBACK (spin_changed), | ||
346 | (gpointer) trace_tree); | ||
347 | |||
348 | |||
282 | /* --- Top Level Hbox --- */ | 349 | /* --- Top Level Hbox --- */ |
283 | 350 | ||
284 | hbox = gtk_hbox_new(FALSE, 0); | 351 | hbox = gtk_hbox_new(FALSE, 0); |
@@ -295,7 +362,8 @@ void trace_view(int argc, char **argv) | |||
295 | 362 | ||
296 | /* --- Set up Trace Tree --- */ | 363 | /* --- Set up Trace Tree --- */ |
297 | 364 | ||
298 | load_trace_view(trace_tree, handle); | 365 | load_trace_view(trace_tree, handle, spin); |
366 | |||
299 | gtk_scrolled_window_add_with_viewport(GTK_SCROLLED_WINDOW(scrollwin), | 367 | gtk_scrolled_window_add_with_viewport(GTK_SCROLLED_WINDOW(scrollwin), |
300 | trace_tree); | 368 | trace_tree); |
301 | gtk_widget_show(trace_tree); | 369 | gtk_widget_show(trace_tree); |