kksou
Joined: 06 Sep 2006 Posts: 25
|
Posted: Thu Oct 19, 2006 3:50 am Post subject: Re: TreeModelFilter |
|
|
| stefan wrote: | i'm trying to use treemodelfilter within my application.
does anyone has an example of how to instantiate and use this widget??
|
Note: for those who have not used GtkTreeModelFilter before, this is a useful widget which allows one to selectively show or hide rows based on some criteria.
Here's a sample code to produce the following:
Sample code:
| Code: | <?php
$window = new GtkWindow();
$window->set_size_request(400, 320);
$window->connect_simple('destroy', array('Gtk','main_quit'));
$window->add($vbox = new GtkVBox());
$accel_group = new GtkAccelGroup();
$window->add_accel_group($accel_group);
// define menu definition
$menu_definition = array(
'_File' => array('_Quit|Q'),
'_Test' => array('Show All Rows|1', 'Show Rows where Qty > 10|2', 'Show Rows where Price < $10|3')
);
setup_menu($vbox, $menu_definition);
// display title
$title = new GtkLabel("Use of GtkTreeModelFilter");
$title->modify_font(new PangoFontDescription("Times New Roman Italic 10"));
$title->modify_fg(Gtk::STATE_NORMAL, GdkColor::parse("#0000ff"));
$title->set_size_request(-1, 40);
$vbox->pack_start($title, 0, 0);
$vbox->pack_start(new GtkLabel("Press Ctrl-1 to show all rows\nCtrl-2 to show qty > 10\nCtrl-3 to show price < \$10"), 0, 0);
$vbox->pack_start(new GtkLabel(), 0, 0); // add a small gap
// Set up a scroll window
$scrolled_win = &new GtkScrolledWindow();
$scrolled_win->set_policy( Gtk::POLICY_AUTOMATIC, Gtk::POLICY_AUTOMATIC);
$vbox->pack_start($scrolled_win);
// the 2D table
$data = array(
array('row0', 'item 19', 2, 3.1, 1),
array('row1', 'item 16', 20, 6.21, 1),
array('row2', 'item 13', 8, 9.36, 1),
array('row3', 'item 10', 11, 12.4, 1),
array('row4', 'item 7', 5, 15.5, 1),
array('row5', 'item 4', 17, 18.6, 1),
array('row6', 'item 3', 20, 21.73, 1));
display_table ($scrolled_win, $data);
function display_table($scrolled_win, $data) {
// Creates the list store
global $model;
$model = new GtkListStore(Gtk::TYPE_STRING, Gtk::TYPE_STRING,
Gtk::TYPE_LONG, Gtk::TYPE_DOUBLE, Gtk::TYPE_BOOLEAN); // note 1
$field_header = array('Row #', 'Description', 'Qty', 'Price');
$field_justification = array(0, 0, 0.5, 1);
// setup GtkTreeModelFilter - note 2
$modelfilter = $model->filter_new();
$modelfilter->set_visible_column(4);
// Creates the view to display the list store
$view = new GtkTreeView($modelfilter);
$scrolled_win->add($view);
// Creates the columns
for ($col=0; $col<count($field_header); ++$col) {
$cell_renderer = new GtkCellRendererText();
$cell_renderer->set_property("xalign", $field_justification[$col]);
$column = new GtkTreeViewColumn($field_header[$col], $cell_renderer, 'text', $col);
$column->set_alignment($field_justification[$col]);
$column->set_sort_column_id($col);
// set the header font and color
$label = new GtkLabel($field_header[$col]);
$label->modify_font(new PangoFontDescription("Arial Bold"));
$label->modify_fg(Gtk::STATE_NORMAL, GdkColor::parse("#0000FF"));
$column->set_widget($label);
$label->show();
// setup self-defined function to display alternate row color
$column->set_cell_data_func($cell_renderer, "format_col", $col);
$view->append_column($column);
}
// pupulates the data
for ($row=0; $row<count($data); ++$row) {
$values = array();
for ($col=0; $col<count($data[$row]); ++$col) {
$values[] = $data[$row][$col];
}
$model->append($values);
}
// setup selection
$selection = $view->get_selection(); // get the selection associated with the view
$selection->connect('changed', 'on_selection');
}
// self-defined function to format the price column
function format_col($column, $cell, $model, $iter, $col_num) {
$path = $model->get_path($iter); // get the current path
$row_num = $path[0]; // get the row number
if ($col_num==3) {
$amt = $model->get_value($iter, 3);
$cell->set_property('text', '$'.number_format($amt,2));
}
$row_color = ($row_num%2==1) ? '#dddddd' : '#ffffff'; // sets the row color for odd and even rows
$cell->set_property('cell-background', $row_color); // sets the background color
}
// the function that is called when user selects a row
function on_selection($selection) {
list($model, $iter) = $selection->get_selected();
if ($iter==NULL) return;
$desc = $model->get_value($iter, 1);
$qty = $model->get_value($iter, 2);
$price = $model->get_value($iter, 3);
print "You have selected $desc: $qty ($price)\n";
}
// setup menu
function setup_menu($vbox, $menus) {
global $accel_group;
$menubar = new GtkMenuBar();
$vbox->pack_start($menubar, 0, 0);
foreach($menus as $toplevel => $sublevels) {
$menubar->append($top_menu = new GtkMenuItem($toplevel));
$menu = new GtkMenu();
$top_menu->set_submenu($menu);
foreach($sublevels as $submenu) {
if (strpos("$submenu", '|') === false) {
$accel_key = '';
} else {
list($submenu, $accel_key) = explode('|', $submenu);
}
if (is_array($submenu)) { // set up radio menus
$i=0;
$radio[0] = null;
foreach($submenu as $radio_item) {
$radio[$i] = new GtkRadioMenuItem($radio[0], $radio_item);
$radio[$i]->connect('toggled', "on_toggle");
$menu->append($radio[$i]);
++$i;
}
$radio[0]->set_active(1); // select the first item
} else {
if ($submenu=='<hr>') {
$menu->append(new GtkSeparatorMenuItem());
} else {
$submenu2 = str_replace('_', '', $submenu);
$submenu2 = str_replace(' ', '_', $submenu2);
$stock_image_name = 'Gtk::STOCK_'.strtoupper($submenu2);
if (defined($stock_image_name)) {
$menu_item = new GtkImageMenuItem(constant($stock_image_name));
} else {
$menu_item = new GtkMenuItem($submenu);
}
if ($accel_key!='') {
$menu_item->add_accelerator("activate", $accel_group, ord($accel_key), Gdk::CONTROL_MASK, 1);
}
$menu->append($menu_item);
$menu_item->connect('activate', 'on_menu_select');
}
}
}
}
}
// process menu item selection
function on_menu_select($menu_item) {
global $model;
$item = $menu_item->child->get_label();
echo "menu selected: $item\n";
if ($item=='_Quit') {
Gtk::main_quit();
} elseif ($item=='Show All Rows') { // note 3
$n = $model->iter_n_children(NULL);
for($i=0; $i<$n; ++$i) {
$iter = $model->get_iter($i);
$model->set($iter, 4, 1);
}
} elseif ($item=='Show Rows where Qty > 10') { // note 4
$n = $model->iter_n_children(NULL);
for($i=0; $i<$n; ++$i) {
$iter = $model->get_iter($i);
$qty = $model->get_value($iter, 2);
if ($qty>10) {
$model->set($iter, 4, 1);
} else {
$model->set($iter, 4, 0);
}
}
} elseif ($item=='Show Rows where Price < $10') { // note 5
$n = $model->iter_n_children(NULL);
for($i=0; $i<$n; ++$i) {
$iter = $model->get_iter($i);
$price = $model->get_value($iter, 3);
$model->set($iter, 4, 1);
if ($price<10) {
$model->set($iter, 4, 1);
} else {
$model->set($iter, 4, 0);
}
}
}
}
$window->show_all();
Gtk::main();
?>
|
More explanation at:
http://www.kksou.com/php-gtk2/articles/selectively-display-rows-in-GtkTreeView-with-GtkTreeModelFilter---Part-1.php
Regards,
/kksou |
|