aboutsummaryrefslogtreecommitdiff
path: root/src/FbTk/Menu.cc
diff options
context:
space:
mode:
Diffstat (limited to 'src/FbTk/Menu.cc')
-rw-r--r--src/FbTk/Menu.cc113
1 files changed, 50 insertions, 63 deletions
diff --git a/src/FbTk/Menu.cc b/src/FbTk/Menu.cc
index 451f620..1710db4 100644
--- a/src/FbTk/Menu.cc
+++ b/src/FbTk/Menu.cc
@@ -22,7 +22,7 @@
22// FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER 22// FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
23// DEALINGS IN THE SOFTWARE. 23// DEALINGS IN THE SOFTWARE.
24 24
25// $Id: Menu.cc,v 1.4 2003/01/10 00:47:59 fluxgen Exp $ 25// $Id: Menu.cc,v 1.5 2003/01/12 17:01:02 fluxgen Exp $
26 26
27//use GNU extensions 27//use GNU extensions
28#ifndef _GNU_SOURCE 28#ifndef _GNU_SOURCE
@@ -31,6 +31,7 @@
31 31
32#include "Menu.hh" 32#include "Menu.hh"
33 33
34#include "MenuItem.hh"
34#include "ImageControl.hh" 35#include "ImageControl.hh"
35#include "MenuTheme.hh" 36#include "MenuTheme.hh"
36#include "App.hh" 37#include "App.hh"
@@ -134,17 +135,16 @@ Menu::Menu(MenuTheme &tm, int screen_num, ImageControl &imgctrl):
134 evm.add(*this, menu.frame); 135 evm.add(*this, menu.frame);
135} 136}
136 137
137
138Menu::~Menu() { 138Menu::~Menu() {
139 menu.window.hide(); 139 menu.window.hide();
140 140
141 if (shown && shown->windowID() == windowID()) 141 if (shown && shown->windowID() == windowID())
142 shown = (Menu *) 0; 142 shown = (Menu *) 0;
143 143
144 //TODO: this looks kind of strange 144 while (!menuitems.empty()) {
145 int n = menuitems.size() - 1; 145 delete menuitems.back();
146 for (int i = 0; i < n; ++i) 146 menuitems.pop_back();
147 remove(0); 147 }
148 148
149 if (menu.title_pixmap) 149 if (menu.title_pixmap)
150 m_image_ctrl.removeImage(menu.title_pixmap); 150 m_image_ctrl.removeImage(menu.title_pixmap);
@@ -166,35 +166,25 @@ Menu::~Menu() {
166} 166}
167 167
168int Menu::insert(const char *label, RefCount<Command> &cmd, int pos) { 168int Menu::insert(const char *label, RefCount<Command> &cmd, int pos) {
169 MenuItem *item = new MenuItem(label, cmd); 169 return insert(new MenuItem(label, cmd), pos);
170 if (pos < 0)
171 menuitems.push_back(item);
172 else {
173 if ( pos > menuitems.size())
174 pos = menuitems.size();
175 menuitems.insert(menuitems.begin() + pos, item);
176 }
177} 170}
171
178int Menu::insert(const char *label, int pos) { 172int Menu::insert(const char *label, int pos) {
179 MenuItem *item = new MenuItem(label); 173 return insert(new MenuItem(label), pos);
180 if (pos == -1)
181 menuitems.push_back(item);
182 else
183 menuitems.insert(menuitems.begin() + pos, item);
184 return menuitems.size(); 174 return menuitems.size();
185} 175}
186 176
187int Menu::insert(const char *label, Menu *submenu, int pos) { 177int Menu::insert(const char *label, Menu *submenu, int pos) {
188 MenuItem *item = new MenuItem(label, submenu); 178 submenu->m_parent = this;
179 return insert(new MenuItem(label, submenu), pos);
180}
181
182int Menu::insert(MenuItem *item, int pos) {
189 if (pos == -1) { 183 if (pos == -1) {
190 menuitems.push_back(item); 184 menuitems.push_back(item);
191 } else { 185 } else {
192 menuitems.insert(menuitems.begin() + pos, item); 186 menuitems.insert(menuitems.begin() + pos, item);
193 } 187 }
194
195 submenu->m_parent = this;
196
197 return menuitems.size();
198} 188}
199 189
200int Menu::remove(unsigned int index) { 190int Menu::remove(unsigned int index) {
@@ -213,7 +203,7 @@ int Menu::remove(unsigned int index) {
213 if (item) { 203 if (item) {
214 menuitems.erase(it); 204 menuitems.erase(it);
215 if ((! internal_menu) && (item->submenu())) { 205 if ((! internal_menu) && (item->submenu())) {
216 Menu *tmp = (Menu *) item->submenu(); 206 Menu *tmp = item->submenu();
217 207
218 if (! tmp->internal_menu) { 208 if (! tmp->internal_menu) {
219 delete tmp; 209 delete tmp;
@@ -289,7 +279,7 @@ void Menu::update() {
289 menu.sublevels = 1; 279 menu.sublevels = 1;
290 280
291 while (menu.item_h * (menuitems.size() + 1) / menu.sublevels + 281 while (menu.item_h * (menuitems.size() + 1) / menu.sublevels +
292 menu.title_h + m_border_width > m_screen_height) 282 menu.title_h + m_border_width > m_screen_height)
293 menu.sublevels++; 283 menu.sublevels++;
294 284
295 if (menu.sublevels < menu.minsub) 285 if (menu.sublevels < menu.minsub)
@@ -543,8 +533,10 @@ void Menu::drawSubmenu(unsigned int index) {
543 if (! moving) 533 if (! moving)
544 drawItem(index, True); 534 drawItem(index, True);
545 535
546 if (! item->submenu()->isVisible()) 536 if (! item->submenu()->isVisible()) {
547 item->submenu()->show(); 537 item->submenu()->show();
538 item->submenu()->raise();
539 }
548 540
549 item->submenu()->moving = moving; 541 item->submenu()->moving = moving;
550 which_sub = index; 542 which_sub = index;
@@ -568,18 +560,16 @@ bool Menu::hasSubmenu(unsigned int index) const {
568void Menu::drawItem(unsigned int index, bool highlight, bool clear, 560void Menu::drawItem(unsigned int index, bool highlight, bool clear,
569 int x, int y, unsigned int w, unsigned int h) 561 int x, int y, unsigned int w, unsigned int h)
570{ 562{
571 if (index >= menuitems.size() || menuitems.size() == 0) 563 if (index >= menuitems.size() || menuitems.size() == 0 ||
564 menu.persub == 0)
572 return; 565 return;
573 566
574 MenuItem *item = menuitems[index]; 567 MenuItem *item = menuitems[index];
575 if (! item) return; 568 if (! item) return;
576 569
577 bool dotext = true, dohilite = true, dosel = true; 570 bool dotext = true, dohilite = true, dosel = true;
578 const char *text = item->label().c_str(); 571 const char *text = item->label().c_str();
579 int sbl = 0, i = index - (sbl * menu.persub); 572 int sbl = index / menu.persub, i = index - (sbl * menu.persub);
580 if (menu.persub != 0)
581 sbl = index / menu.persub;
582
583 int item_x = (sbl * menu.item_w), item_y = (i * menu.item_h); 573 int item_x = (sbl * menu.item_w), item_y = (i * menu.item_h);
584 int hilite_x = item_x, hilite_y = item_y, hoff_x = 0, hoff_y = 0; 574 int hilite_x = item_x, hilite_y = item_y, hoff_x = 0, hoff_y = 0;
585 int text_x = 0, text_y = 0, len = strlen(text), sel_x = 0, sel_y = 0; 575 int text_x = 0, text_y = 0, len = strlen(text), sel_x = 0, sel_y = 0;
@@ -621,7 +611,7 @@ void Menu::drawItem(unsigned int index, bool highlight, bool clear,
621 611
622 sel_x += quarter_w; 612 sel_x += quarter_w;
623 sel_y = item_y + quarter_w; 613 sel_y = item_y + quarter_w;
624 614
625 if (clear) { 615 if (clear) {
626 XClearArea(m_display, menu.frame.window(), item_x, item_y, menu.item_w, menu.item_h, 616 XClearArea(m_display, menu.frame.window(), item_x, item_y, menu.item_w, menu.item_h,
627 False); 617 False);
@@ -829,30 +819,29 @@ void Menu::buttonReleaseEvent(XButtonEvent &re) {
829 re.x >= 0 && re.x < (signed) menu.width && 819 re.x >= 0 && re.x < (signed) menu.width &&
830 re.y >= 0 && re.y < (signed) menu.frame_h) { 820 re.y >= 0 && re.y < (signed) menu.frame_h) {
831 821
832 if (re.button == 3) { 822
833 hide(); 823
834 } else { 824 int sbl = (re.x / menu.item_w), i = (re.y / menu.item_h),
835 int sbl = (re.x / menu.item_w), i = (re.y / menu.item_h), 825 ix = sbl * menu.item_w, iy = i * menu.item_h,
836 ix = sbl * menu.item_w, iy = i * menu.item_h, 826 w = (sbl * menu.persub) + i,
837 w = (sbl * menu.persub) + i, 827 p = (which_sbl * menu.persub) + which_press;
838 p = (which_sbl * menu.persub) + which_press; 828
839 829 if (w < static_cast<int>(menuitems.size()) && w >= 0) {
840 if (w < static_cast<int>(menuitems.size()) && w >= 0) { 830 drawItem(p, (p == which_sub), True);
841 drawItem(p, (p == which_sub), True); 831
842 832 if (p == w && isItemEnabled(w)) {
843 if (p == w && isItemEnabled(w)) { 833 if (re.x > ix && re.x < (signed) (ix + menu.item_w) &&
844 if (re.x > ix && re.x < (signed) (ix + menu.item_w) && 834 re.y > iy && re.y < (signed) (iy + menu.item_h)) {
845 re.y > iy && re.y < (signed) (iy + menu.item_h)) { 835 menuitems[w]->click(re.button, re.time);
846 if (*menuitems[w]->command() != 0) 836 itemSelected(re.button, w);
847 menuitems[w]->command()->execute(); 837
848 else 838 update(); // update any changed item
849 itemSelected(re.button, w);
850 }
851 } 839 }
852 } else 840 }
853 drawItem(p, false, true); 841 } else
842 drawItem(p, false, true);
854 843
855 } 844
856 } 845 }
857} 846}
858 847
@@ -924,25 +913,23 @@ void Menu::exposeEvent(XExposeEvent &ee) {
924 // first... we see in which sub level the expose starts... and how many 913 // first... we see in which sub level the expose starts... and how many
925 // items down in that sublevel 914 // items down in that sublevel
926 915
927 int sbl = (ee.x / menu.item_w), id = (ee.y / menu.item_h), 916 unsigned int sbl = (ee.x / menu.item_w), id = (ee.y / menu.item_h),
928 // next... figure out how many sublevels over the redraw spans 917 // next... figure out how many sublevels over the redraw spans
929 sbl_d = ((ee.x + ee.width) / menu.item_w), 918 sbl_d = ((ee.x + ee.width) / menu.item_w),
930 // then we see how many items down to redraw 919 // then we see how many items down to redraw
931 id_d = ((ee.y + ee.height) / menu.item_h); 920 id_d = ((ee.y + ee.height) / menu.item_h);
932
933 if (id_d > menu.persub) id_d = menu.persub; 921 if (id_d > menu.persub) id_d = menu.persub;
934 922
935 // draw the sublevels and the number of items the exposure spans 923 // draw the sublevels and the number of items the exposure spans
936 int i, ii; 924 unsigned int i, ii;
937 for (i = sbl; i <= sbl_d; i++) { 925 for (i = sbl; i <= sbl_d; i++) {
938 // set the iterator to the first item in the sublevel needing redrawing 926 // set the iterator to the first item in the sublevel needing redrawing
939 int index = id + i * menu.persub; 927 unsigned int index = id + i * menu.persub;
940 if (index < static_cast<int>(menuitems.size()) && index >= 0) { 928 if (index < static_cast<int>(menuitems.size()) && index >= 0) {
941 Menuitems::iterator it = menuitems.begin() + index; 929 Menuitems::iterator it = menuitems.begin() + index;
942 Menuitems::iterator it_end = menuitems.end(); 930 Menuitems::iterator it_end = menuitems.end();
943 for (ii = id; ii <= id_d && it != it_end; ++it, ii++) { 931 for (ii = id; ii <= id_d && it != it_end; ++it, ii++) {
944 int index = ii + (i * menu.persub); 932 unsigned int index = ii + (i * menu.persub);
945 // redraw the item
946 drawItem(index, (which_sub == index), true, 933 drawItem(index, (which_sub == index), true,
947 ee.x, ee.y, ee.width, ee.height); 934 ee.x, ee.y, ee.width, ee.height);
948 } 935 }