Re: Treeview and on_cell_toggled()



Here's what I do:

First off, here's my Gtk::TreeModel::ColumnRecord derivation for my example:

/////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
class CashModelColumns : public Gtk::TreeModel::ColumnRecord { public:
       CashModelColumns()
{ add(m_check);
           add(m_storeid);
           add(m_date);
           add(m_termid);
           add(m_cashcode);
           add(m_reset);
           add(m_displaydate);
       }
Gtk::TreeModelColumn<Glib::ustring> m_date; Gtk::TreeModelColumn<Glib::ustring> m_displaydate; Gtk::TreeModelColumn<Glib::ustring> m_reset; Gtk::TreeModelColumn<Glib::ustring> m_cashcode;
       Gtk::TreeModelColumn<Glib::ustring> m_storeid;
       Gtk::TreeModelColumn<Glib::ustring> m_termid;
Gtk::TreeModelColumn<bool> m_check; }; CashModelColumns cash_columns; /////////////////////////////////////////////////////////////////////////////////////////////////////////////

Here is where the model and the  treeview are created:

//////////////////////////////////////////////////////////////////////////////////////////////////////////
   ecshlist = Gtk::TreeStore::create(cash_columns);
ecshtree = manage(new Gtk::TreeView()); ecshtree->set_model(ecshlist);
   ecshtree->append_column_editable(" Select ", cash_columns.m_check);
ecshtree->append_column(" Date ", cash_columns.m_displaydate); ecshtree->append_column(" Register # ", cash_columns.m_termid); ecshtree->append_column(" Reset # ", cash_columns.m_reset); ((Gtk::CellRendererToggle *)ecshtree->get_column_cell_renderer(0))->signal_toggled().connect(sigc::mem_fun(*this, &CashierReconciliation::on_child_toggled));
/////////////////////////////////////////////////////////////////////////////////////////////////////

Here is the function "on_child_toggled"

//////////////////////////////////////////////////////////////////////////////////////////////////
void CashierReconciliation::on_child_toggled(Glib::ustring str)
{
   Gtk::TreeModel::Path path(str.c_str());
   Gtk::TreeModel::Row row = *(ecshlist->get_iter(path));
   Gtk::TreeModel::Row parent = *(row.parent());
   Gtk::TreeModel::Children::iterator iter;
   Gtk::TreeModel::Children children = row.children();

///////////////////////////////////////////////////////////////////////////////////////
// here is where what you want to do is done.. but there is more.
   if(children)
       check_all_children(children,row[cash_columns.m_check]);
///////////////////////////////////////////////////////////////////////////////////////

///////////////////////////////////////////////////////////////////////////////////////
// this code goes back up the chain, either setting or clearing the checkbox if(row[cash_columns.m_check])
   {
       while(parent)
       {
           parent[cash_columns.m_check] = true;
           parent = *(parent.parent());
       }
   }
   else
   {
       while(parent)
       {
           Gtk::TreeModel::Children siblings = parent.children();
           for(iter = siblings.begin(); iter != siblings.end(); ++iter)
           {
               Gtk::TreeModel::Row child_row = *iter;
               if(child_row[cash_columns.m_check])
                   break;
           }
           parent[cash_columns.m_check] = (iter != siblings.end());
           parent = *(parent.parent());
       }
   }
/////////////////////////////////////////////////////////////////////////////////////////
}
////////////////////////////////////////////////////////////////////////////////////////

lastly, here is "check_all_children"

//////////////////////////////////////////////////////////////////////////////////////
void CashierReconciliation::check_all_children(Gtk::TreeModel::Children& children,bool condition)
{
for(Gtk::TreeModel::Children::iterator iter = children.begin(); iter != children.end(); ++iter)
   {
       Gtk::TreeModel::Row child_row = *iter;
       child_row[cash_columns.m_check] = condition;
       Gtk::TreeModel::Children next = child_row.children();
       if(next)
           check_all_children(next,condition);
} }
///////////////////////////////////////////////////////////////////////////////////

The foregoing not only checks the children of the top level parent, but if you expand the parent and check only one of the children, it will cause all parents up the chain to the top level one to
be checked as well.

This works great for me.

Cheers,

Bob Caryl


lmarcilly aressi fr wrote:

Hi all,

Here is an example of my treeview :

Group1 |-----------Elt1 |-----------Elt2 Group2 |------Group2_1 |----------Elt1 |----------Elt2 |-------Elt1
I have a second column which contain a boolean (false by default). For example, when user select Group1 (so that boolean change to true), i want that boolean value change also for Elt1 and Elt2. I think that i have to use CellRendererToggle and to connect it with signal but i can't made it work!! It won't compile, i try a lot of test but without success..

Could you help me? I have seen http://www.gtkmm.org/gtkmm2/docs/tutorial/html/apb.html and http://www.gtkmm.org/gtkmm2/docs/tutorial/html/ch08s02.html#id2519595 and particularly :


Gtk::CellRendererToggle* pRenderer = Gtk::manage( new Gtk::CellRendererToggle() );
pRenderer->signal_toggled().connect(
 SigC::bind( SigC::slot(*this, &Example_TreeView_TreeStore::on_cell_toggled), m_columns.dave)
);
Does anybody has an example which works perfectly?

Thanks in advance.

lm.


_______________________________________________
gtkmm-list mailing list
gtkmm-list gnome org
http://mail.gnome.org/mailman/listinfo/gtkmm-list





[Date Prev][Date Next]   [Thread Prev][Thread Next]   [Thread Index] [Date Index] [Author Index]