From 8b2cfb515befa803ed86a5cc458717d2e2c240c0 Mon Sep 17 00:00:00 2001 From: david Date: Thu, 27 Nov 2003 23:41:00 +0000 Subject: [PATCH] Add a scrolling list widget for selecting airports. --- src/GUI/AirportList.cxx | 43 ++++++++++++++++ src/GUI/AirportList.hxx | 28 ++++++++++ src/GUI/Makefile.am | 4 +- src/GUI/dialog.cxx | 11 ++++ src/GUI/puList.cxx | 110 ++++++++++++++++++++++++++++++++++++++++ src/GUI/puList.hxx | 37 ++++++++++++++ 6 files changed, 232 insertions(+), 1 deletion(-) create mode 100644 src/GUI/AirportList.cxx create mode 100644 src/GUI/AirportList.hxx create mode 100644 src/GUI/puList.cxx create mode 100644 src/GUI/puList.hxx diff --git a/src/GUI/AirportList.cxx b/src/GUI/AirportList.cxx new file mode 100644 index 000000000..43cee70ab --- /dev/null +++ b/src/GUI/AirportList.cxx @@ -0,0 +1,43 @@ +#include
+#include + +#include "AirportList.hxx" + + +AirportList::AirportList (int x, int y, int width, int height) + : puList(x, y, width, height) +{ + char buf[1024]; + + _airports = globals->get_airports(); + _nAirports = _airports->size(); + + _content = new char *[_nAirports+1]; + for (int i = 0; i < _nAirports; i++) { + const FGAirport * airport = _airports->getAirport(i); + snprintf(buf, 1023, "%s %s\n", + airport->id.c_str(), + airport->name.c_str()); + _content[i] = strndup(buf, 1023); + } + _content[_nAirports] = 0; + newList(_content); +} + +AirportList::~AirportList () +{ + for (int i = 0; i < _nAirports; i++) { + delete _content[i]; + _content[i] = 0; + } + delete [] _content; +} + +char * +AirportList::getStringValue () +{ + return (char *)_airports->getAirport(getIntegerValue())->id.c_str(); +} + +// end of AirportList.cxx + diff --git a/src/GUI/AirportList.hxx b/src/GUI/AirportList.hxx new file mode 100644 index 000000000..97a1c7346 --- /dev/null +++ b/src/GUI/AirportList.hxx @@ -0,0 +1,28 @@ +// AirportList.hxx - scrolling list of airports. + +#ifndef __AIRPORTLIST_HXX + +#include + +#include "puList.hxx" + +class FGAirportList; + +class AirportList : public puList +{ + public: + AirportList (int x, int y, int width, int height); + virtual ~AirportList (); + + // FIXME: add other string value functions + virtual char * getStringValue (); + + private: + FGAirportList * _airports; + int _nAirports; + char ** _content; +}; + +#endif // __AIRPORTLIST_HXX + +// end of AirportList.hxx diff --git a/src/GUI/Makefile.am b/src/GUI/Makefile.am index 44bb278f2..267f5414f 100644 --- a/src/GUI/Makefile.am +++ b/src/GUI/Makefile.am @@ -10,6 +10,8 @@ libGUI_a_SOURCES = \ preset_dlg.cxx preset_dlg.hxx \ prop_picker.cxx prop_picker.hxx \ sgVec3Slider.cxx sgVec3Slider.hxx \ - trackball.c trackball.h + trackball.c trackball.h \ + puList.cxx puList.hxx \ + AirportList.cxx AirportList.hxx INCLUDES = -I$(top_srcdir) -I$(top_srcdir)/src diff --git a/src/GUI/dialog.cxx b/src/GUI/dialog.cxx index a2e2fb8e3..3750d8b86 100644 --- a/src/GUI/dialog.cxx +++ b/src/GUI/dialog.cxx @@ -5,6 +5,9 @@ #include "dialog.hxx" #include "new_gui.hxx" +#include "puList.hxx" +#include "AirportList.hxx" + //////////////////////////////////////////////////////////////////////// @@ -234,6 +237,14 @@ FGDialog::makeObject (SGPropertyNode * props, int parentWidth, int parentHeight) puGroup * group = new puGroup(x, y); setupGroup(group, props, width, height, false); return group; + } else if (type == "list") { + puList * list = new puList(x, y, x + width, y + height); + setupObject(list, props); + return list; + } else if (type == "airport-list") { + AirportList * list = new AirportList(x, y, x + width, y + height); + setupObject(list, props); + return list; } else if (type == "input") { puInput * input = new puInput(x, y, x + width, y + height); setupObject(input, props); diff --git a/src/GUI/puList.cxx b/src/GUI/puList.cxx new file mode 100644 index 000000000..17f654bfc --- /dev/null +++ b/src/GUI/puList.cxx @@ -0,0 +1,110 @@ +// puList.cxx - implementation of a scrolling list box. + +#include "puList.hxx" + + +/** + * Static function: handle slider movements. + */ +static void +handle_slider (puObject * slider) +{ + puListBox * box = (puListBox *)slider->getUserData(); + int index = int(box->getNumItems() * (1.0 - slider->getFloatValue())); + if (index >= box->getNumItems()) + index = box->getNumItems() - 1; + box->setTopItem(index); +} + + +/** + * Static function: handle arrow clicks. + */ +static void +handle_arrow (puObject * arrow) +{ + puSlider * slider = (puSlider *)arrow->getUserData(); + puListBox * list_box = (puListBox *)slider->getUserData(); + + int step; + switch (((puArrowButton *)arrow)->getArrowType()) { + case PUARROW_DOWN: + step = 1; + break; + case PUARROW_UP: + step = -1; + break; + default: + step = 0; + break; + } + + int index = list_box->getTopItem(); + index += step; + if (index < 0) + index = 0; + else if (index >= list_box->getNumItems()) + index = list_box->getNumItems() - 1; + list_box->setTopItem(index); + + slider->setValue(1.0f - float(index)/list_box->getNumItems()); +} + +puList::puList (int x, int y, int w, int h) + : puGroup(x, y) +{ + init(w, h); +} + +puList::puList (int x, int y, int w, int h, char ** contents) + : puGroup(x, y) +{ + init(w, h); + newList(contents); +} + +puList::~puList () +{ +} + +void +puList::newList (char ** contents) +{ + _list_box->newList(contents); + _contents = contents; +} + +char * +puList::getStringValue () +{ + return _contents[_list_box->getIntegerValue()]; +} + +void +puList::init (int w, int h) +{ + _frame = new puFrame(0, 0, w, h); + + _list_box = new puListBox(0, 0, w-30, h); + _list_box->setStyle(-PUSTYLE_SMALL_SHADED); + _list_box->setUserData(this); + _list_box->setValue(0); + + _slider = new puSlider(w-30, 30, h-60, true); + _slider->setValue(1.0f); + _slider->setUserData(_list_box); + _slider->setCallback(handle_slider); + _slider->setCBMode(PUSLIDER_ALWAYS); + + _down_arrow = new puArrowButton(w-30, 0, w, 30, PUARROW_DOWN) ; + _down_arrow->setUserData(_slider); + _down_arrow->setCallback(handle_arrow); + + _up_arrow = new puArrowButton(w-30, h-30, w, h, PUARROW_UP); + _up_arrow->setUserData(_slider); + _up_arrow->setCallback(handle_arrow); + + close(); +} + +// end of puList.cxx diff --git a/src/GUI/puList.hxx b/src/GUI/puList.hxx new file mode 100644 index 000000000..43ba4e242 --- /dev/null +++ b/src/GUI/puList.hxx @@ -0,0 +1,37 @@ +// puList.hxx - a scrolling PUI list box. + +#ifndef __PULIST_HXX +#define __PULIST_HXX 1 + +#include + + +/** + * A scrolling list for PUI. + * + * Believe it or not, PUI does not have one of these. + */ +class puList : public puGroup +{ + public: + puList (int x, int y, int w, int h); + puList (int x, int y, int w, int h, char ** contents); + virtual ~puList (); + + virtual void newList (char ** contents); + // TODO: other string value funcs + virtual char * getStringValue (); + + protected: + virtual void init (int w, int h); + + private: + char ** _contents; + puFrame * _frame; + puListBox * _list_box; + puSlider * _slider; + puArrowButton * _up_arrow; + puArrowButton * _down_arrow; +}; + +#endif // __PULIST_HXX -- 2.39.5