]> git.tdb.fi Git - libs/gltk.git/blobdiff - source/dropdown.cpp
Implement keyboard navigation for most widgets
[libs/gltk.git] / source / dropdown.cpp
index 7dc0d3550bcaf7d8953ec2a8b5d1013355ad69fd..ef0fa22f97c8f150009988b3487c716b1e576cf2 100644 (file)
@@ -25,11 +25,15 @@ Dropdown::Dropdown(ListData &d):
 
 void Dropdown::init()
 {
+       input_type = INPUT_NAVIGATION;
+
        dropped = false;
 
        add(list);
+       list.set_visible(false);
        list.set_view_all();
        list.signal_item_selected.connect(sigc::mem_fun(this, &Dropdown::list_item_selected));
+       list.signal_selection_cleared.connect(sigc::mem_fun(this, &Dropdown::list_selection_cleared));
        list.signal_autosize_changed.connect(sigc::mem_fun(this, &Dropdown::list_autosize_changed));
 }
 
@@ -61,13 +65,6 @@ void Dropdown::autosize_special(const Part &part, Geometry &ageom) const
        }
 }
 
-void Dropdown::set_selected_index(int index)
-{
-       list.set_selected_index(index);
-       if(index<0)
-               text.set(string());
-}
-
 void Dropdown::rebuild_special(const Part &part)
 {
        if(part.get_name()=="text")
@@ -88,35 +85,64 @@ void Dropdown::button_press(int x, int y, unsigned btn)
        {
                Container::button_press(x, y, btn);
                if(!click_focus)
-               {
-                       dropped = false;
-                       clear_state(ACTIVE);
-                       signal_ungrab_pointer.emit();
-               }
+                       close_list();
        }
        else if(btn==1)
+               open_list();
+}
+
+bool Dropdown::navigate(Navigation nav)
+{
+       if(dropped)
        {
-               dropped = true;
-               resize_list();
-               set_state(ACTIVE);
-               signal_grab_pointer.emit();
+               if(nav==NAV_CANCEL)
+                       close_list();
+               else
+                       list.navigate(nav);
        }
+       else if(nav==NAV_ACTIVATE)
+               open_list();
+       else
+               return false;
+
+       return true;
 }
 
 void Dropdown::on_geometry_change()
 {
-       resize_list();
+       if(dropped)
+               resize_list();
 }
 
 void Dropdown::on_style_change()
 {
        text.set_style(style);
+       if(dropped)
+               resize_list();
+}
+
+void Dropdown::open_list()
+{
+       dropped = true;
+       list.set_visible(true);
        resize_list();
+       set_state(ACTIVE);
+       set_input_focus(&list);
+       signal_grab_pointer.emit();
+}
+
+void Dropdown::close_list()
+{
+       dropped = false;
+       list.set_visible(false);
+       clear_state(ACTIVE);
+       signal_ungrab_pointer.emit();
 }
 
 void Dropdown::list_autosize_changed()
 {
-       resize_list();
+       if(dropped)
+               resize_list();
        signal_autosize_changed.emit();
 }
 
@@ -168,6 +194,11 @@ void Dropdown::list_item_selected(unsigned index)
        rebuild();
 }
 
+void Dropdown::list_selection_cleared()
+{
+       text.set(string());
+}
+
 
 Dropdown::Loader::Loader(Dropdown &d):
        DataFile::DerivedObjectLoader<Dropdown, Widget::Loader>(d)