rome
Offline
Sr. Member
Karma: 13
Posts: 342
|
 |
« Reply #105 on: July 19, 2012, 10:07:03 am » |
Yeah. Someone could also ask for 2.5 buttons ... Be sure you've got the latest version of menwiz as freeRam *must* compile ... Until the first version 1.0 (soon to be delivered if I get positive feedback) I'm touching the lib and sometime I've got some regression error. Currently I'm struggling with raspi/arduino integration and I've not time enough to finalize this lib.
|
|
|
|
« Last Edit: July 19, 2012, 10:09:17 am by brunialti »
|
Logged
|
|
|
|
|
Offline
Full Member
Karma: 0
Posts: 120
|
 |
« Reply #106 on: July 19, 2012, 02:18:45 pm » |
just got my raspi today as it goes I'll look at the freeRam, after some raspi fiddling of course
|
|
|
|
|
Logged
|
|
|
|
|
rome
Offline
Sr. Member
Karma: 13
Posts: 342
|
 |
« Reply #107 on: July 20, 2012, 12:14:27 pm » |
Please find the new lib version at https://github.com/brunialti/MENWIZ/downloads . There are the new following methods: void menwiz::writeEeprom(); //write all MENWIZ binded variables to eeprom void menwiz::readEeprom(); //read from eeprom the previously saved variable values void _menu::setBehaviour(byte behaviour, boolean value); //toggle action confirmation, horizontal/vertical scrolling of list In order to let you have a better idea of the changes, please read the updated quick tour pdf doc here attached. Due to the eeprom support it is now necessary to include EEPROM.h file in the user sketch. This introduce a small backward compatibility break. Feedbacks are welcome
|
|
|
|
« Last Edit: July 21, 2012, 10:59:56 am by brunialti »
|
Logged
|
|
|
|
|
Offline
Full Member
Karma: 0
Posts: 120
|
 |
« Reply #108 on: July 26, 2012, 11:24:10 am » |
Hi, do you have an example of the setBehaviour? I'm not sure how it should be declared and against what object? tree. _menu etc?
I'm getting errors like "MW_ACTION_IMMEDIATE is not defined"
|
|
|
|
|
Logged
|
|
|
|
|
Offline
Full Member
Karma: 0
Posts: 120
|
 |
« Reply #109 on: July 26, 2012, 11:48:56 am » |
Hi, to be clear I'm using version 0.6.1 I'd defined my own button press detection as before, and emulated an exit press by fireing a custom function. While it asked for confirm to run when pressing confirm it ran. Now it doesn't run, asks for confirm, i press confirm and it goes back to the menu list #include <Wire.h> #include <LCD.h> #include <LiquidCrystal_SR.h> #include <buttons.h> #include <EEPROM.h> #include <MENWIZ.h> #include <MemoryFree.h>
//INTERRUPT BUTTONS const int pin = 13; // test for interrupt const int buttonPin = A0; // buttons can be read here volatile byte buttonAct = 0; // flag, follow button press volatile int buttonValue = 0; // button pressed analogue value volatile int buttonPressed = 0; // which button was pressed volatile byte lastButtonPressed = 0; // prev button pressed volatile byte state = LOW; // state of led on pin13 volatile byte lastState = HIGH; // unused?
/* // DEFINE ARDUINO PINS FOR THE NAVIGATION BUTTONS #define UP_BOTTON_PIN 9 #define DOWN_BOTTON_PIN 5 #define LEFT_BOTTON_PIN 7 #define RIGHT_BOTTON_PIN 8 #define CONFIRM_BOTTON_PIN 3 #define ESCAPE_BOTTON_PIN 4 */ // #define MW_ACTION_IMMEDIATE menwiz tree; // create lcd obj using LiquidCrystal lib LiquidCrystal_SR lcd(10, 11, 12); //Data,Clk,Enable.
int list,sp=110;
void setup(){ Serial.begin(19200); Serial.println(F("STARTED")); pinMode(pin, OUTPUT); attachInterrupt(0, readButtons, RISING);
_menu *r,*s1,*s2;
tree.addUsrNav(navMenu); tree.begin(&lcd,20,4); //declare lcd object and screen size to menwiz lib //_menu::setBehaviour(byte MW_ACTION_IMMEDIATE, false); r=tree.addMenu(MW_ROOT,NULL,"Root"); s1=tree.addMenu(MW_SUBMENU,r,"SUBMENU"); s2=tree.addMenu(MW_VAR,s1,"Node3"); s2->addVar(MW_LIST,&list); s2->addItem(MW_LIST,"Option1"); s2->addItem(MW_LIST,"Option2"); s2->addItem(MW_LIST,"Option3"); s2=tree.addMenu(MW_VAR,s1,"Node4"); s2->addVar(MW_AUTO_INT,&sp,0,120,10); s2=tree.addMenu(MW_VAR,s1,"Exit"); s2->addVar(MW_ACTION,exitFunct);
// tree.navButtons(UP_BOTTON_PIN,DOWN_BOTTON_PIN,LEFT_BOTTON_PIN,RIGHT_BOTTON_PIN,ESCAPE_BOTTON_PIN,CONFIRM_BOTTON_PIN); } int i = 0; void loop(){ if(i > 1000){ Serial.print(F("freeMemory() reports ")); Serial.println( freeMemory() ); i = 0; }else{ i++; } tree.draw(); }
void myfunc(){ Serial.println("ACTION FIRED!"); }
void readButtons(){ state = !state; digitalWrite(pin, state); /* 511 : none | 614 : up | 768 : down | 1023 : select */ lastButtonPressed = buttonPressed;
buttonValue = analogRead(buttonPin); if(buttonValue >= 900) { buttonPressed = 3; // select
} else if(buttonValue >= 700){ buttonPressed = 2; // down
} else if(buttonValue >= 600){ buttonPressed = 1; // up
} buttonAct = 1; Serial.print(buttonPressed); Serial.print(" XX "); Serial.println(buttonValue);
}
void exitFunct(){ Serial.println("EXIT Called"); buttonAct = 1; buttonPressed = 4; }
int navMenu(){ //MenuItem currentMenu=menu.getCurrent(); if(buttonAct){ buttonAct = 0; switch (buttonPressed){ case 4: //simulated escape return MW_BTE; break; case 3: //select return MW_BTC; break; case 2: //down return MW_BTD; break; case 1: //up return MW_BTU; break; } } else{ return MW_BTNULL; } }
|
|
|
|
|
Logged
|
|
|
|
|
rome
Offline
Sr. Member
Karma: 13
Posts: 342
|
 |
« Reply #110 on: July 26, 2012, 11:53:28 am » |
there is a misalignment between the quick tour doc and the code. The syntax is
xxx.setBehaviour(MW_ACTION_CONFIRM,false);
Does the example compile and run ? Iin the example there is also this behaviour commented.
|
|
|
|
« Last Edit: July 26, 2012, 11:56:15 am by brunialti »
|
Logged
|
|
|
|
|
rome
Offline
Sr. Member
Karma: 13
Posts: 342
|
 |
« Reply #111 on: July 26, 2012, 12:00:12 pm » |
reading better your code, it is wrong. The setBehaviour is a menu method that must be called after the menu declarations and for each variable object you want to affect, not before This is a chunk of real code working s1=menu.addMenu(MW_VAR,r,F("TEST ACTION")); s1->addVar(MW_ACTION,act); s1->setBehaviour(MW_ACTION_CONFIRM,false);
|
|
|
|
|
Logged
|
|
|
|
|
Offline
Full Member
Karma: 0
Posts: 120
|
 |
« Reply #112 on: July 26, 2012, 12:10:28 pm » |
there is a misalignment between the quick tour doc and the code. The syntax is
xxx.setBehaviour(MW_ACTION_CONFIRM,false);
Does the example compile and run ? Iin the example there is also this behaviour commented.
Yep it was the CONFIRM vs IMMEDIATE. If set false works as expected. If not declared at all, asks for confirm to run but don't run when confirm is pressed (not an issue for me) If declared as true, asks for confirm to run but don't run when confirm is pressed. Regarding my mistake declaring referenced in your last reply. That was me trying to find a working way but using the none existent MW_ACTION_IMMEDIATE
|
|
|
|
|
Logged
|
|
|
|
|
rome
Offline
Sr. Member
Karma: 13
Posts: 342
|
 |
« Reply #113 on: July 26, 2012, 02:28:31 pm » |
I cannot replicate what you noticed. I downloaded the 0.6.1. version from git hub and modified the example as following //MENWIZ ESAMPLE #include <Wire.h> //INSERT ALL THE FOLLOWING 5 INCLUDES AFTER INCLUDING WIRE LIB #include <LCD.h> #include <LiquidCrystal_I2C.h> #include <buttons.h> #include <MENWIZ.h> #include <EEPROM.h>
// DEFINE ARDUINO PINS FOR THE NAVIGATION BUTTONS #define UP_BUTTON_PIN 9 #define DOWN_BUTTON_PIN 10 #define LEFT_BUTTON_PIN 7 #define RIGHT_BUTTON_PIN 8 #define CONFIRM_BUTTON_PIN 12 #define ESCAPE_BUTTON_PIN 11
//Create global object menu and lcd menwiz menu; LiquidCrystal_I2C lcd(0x27, 2, 1, 0, 4, 5, 6, 7, 3, POSITIVE); // Addr, En, Rw, Rs, d4, d5, d6, d7, backlighpin, polarity
//instantiate global variables to bind to menu int tp=0; float f=26.0; boolean bb=0; byte b=50;
void setup(){ _menu *r,*s1,*s2; _var *v; int mem;
Serial.begin(19200); // have a look on memory before menu creation Serial.println(sizeof(menwiz)); mem=menu.freeRam(); // inizialize the menu object (20 colums x 4 rows) menu.begin(&lcd,20,4);
//create the menu tree r=menu.addMenu(MW_ROOT,NULL,"MAIN MENU"); //create a root menu at first (required) s1=menu.addMenu(MW_SUBMENU,r,"MEASURE SUBMENU"); //add a child (submenu) node to the root menu s2=menu.addMenu(MW_VAR,s1,"Test list"); //add a terminal node (that is "variable"); s2->addVar(MW_LIST,&tp); //create a variable of type "option list".. s2->addItem(MW_LIST,"option 1"); //add option to the OPTION LIST s2->addItem(MW_LIST,"option 2"); //add option to the OPTION LIST s2->addItem(MW_LIST,"option 3"); //add option to the OPTION LIST // s2->setBehaviour(MW_SCROLL_HORIZONTAL,true); //...if you like horizontal scroll
s2=menu.addMenu(MW_VAR,s1,"Test float var"); //add a terminal node (that is "variable"); s2->addVar(MW_AUTO_FLOAT,&f,11.00,100.00,0.5); //create a variable of type "float number"... //...associated to the terminal node and bind it to the app variable "f" of type float s2=menu.addMenu(MW_VAR,s1,"Test byte var"); //add a terminal node (that is "variable"); s2->addVar(MW_AUTO_BYTE,&b,25,254,10); //create a variable of type "byte"... //...associated to the terminal node and bind it to the app variable "b" of typr byte s2=menu.addMenu(MW_VAR,s1,"Test boolean var"); //add a terminal node (that is "variable"); s2->addVar(MW_BOOLEAN,&bb); //create a variable of type "boolean"
s1=menu.addMenu(MW_VAR,r,"TEST ACTION1"); //add a terminal node (that is "variable") create an "action" associated to the terminal node... s1->addVar(MW_ACTION,act1); //the act function as default will be called when enter button is pushed //s1->setBehaviour(MW_ACTION_CONFIRM,false); //...if you don't need action confirmation
s1=menu.addMenu(MW_VAR,r,"TEST ACTION2"); //add a terminal node (that is "variable") create an "action" associated to the terminal node... s1->addVar(MW_ACTION,act2); //the act function as default will be called when enter button is pushed s1->setBehaviour(MW_ACTION_CONFIRM,false); //...if you don't need action confirmation
//declare navigation buttons (required) menu.navButtons(UP_BUTTON_PIN,DOWN_BUTTON_PIN,LEFT_BUTTON_PIN,RIGHT_BUTTON_PIN,ESCAPE_BUTTON_PIN,CONFIRM_BUTTON_PIN);
//(tip): use preallocated internal menu.sbuf buffer to save memory space! sprintf(menu.sbuf,"MENWIZ TEST V %s\n.Free mem. :%d\n.Used mem :%d\n.Lap secs :%d",menu.getVer(),menu.freeRam(),mem-menu.freeRam(),5); //(optional) create a splash screen (duration 5.000 millis)with some usefull infos the character \n marks end of LCD line menu.addSplash((char *) menu.sbuf, 5000); //(optional)create a user define screen callback to activate after 10 secs (10.000 millis) since last button push menu.addUsrScreen(msc,10000); }
void loop(){ menu.draw(); //PUT APPLICATION CODE HERE (if any) }
// user defined callbacks void msc(){ sprintf(menu.sbuf,"User screen\nUptime (s): %ld\nFree mem : %d\n\n",millis()/1000,(int)menu.freeRam()); menu.drawUsrScreen(menu.sbuf); } void act1(){ Serial.println("FIRED ACTION1"); }
void act2(){ Serial.println("FIRED ACTION2"); } void savevar(){ menu.writeEeprom(); } void loadvar(){ menu.readEeprom(); }
The above code works as expected: the first action ask for confirmation before to write to serial, and second action do'not (EDIT but write correctly to serial). I think something in the custom button management routine could bias the result. I'll check.
|
|
|
|
« Last Edit: July 26, 2012, 02:45:16 pm by brunialti »
|
Logged
|
|
|
|
|
Offline
Full Member
Karma: 0
Posts: 120
|
 |
« Reply #114 on: July 26, 2012, 03:30:43 pm » |
I can only assume it is something ot do with the custom button function given that's the only difference. The button pin defines are commented out, could that be a problem? Here is my full code if it helps: #include <Wire.h> #include <LCD.h> #include <LiquidCrystal_SR.h> #include <buttons.h> #include <EEPROM.h> #include <MENWIZ.h> //#include <MemoryFree.h>
//INTERRUPT BUTTONS const int pin = 13; // test for interrupt const int buttonPin = A0; // buttons can be read here volatile byte buttonAct = 0; // flag, follow button press volatile int buttonValue = 0; // button pressed analogue value volatile int buttonPressed = 0; // which button was pressed volatile byte lastButtonPressed = 0; // prev button pressed volatile byte state = LOW; // state of led on pin13 volatile byte lastState = HIGH; // unused?
/* // DEFINE ARDUINO PINS FOR THE NAVIGATION BUTTONS #define UP_BOTTON_PIN 9 #define DOWN_BOTTON_PIN 5 #define LEFT_BOTTON_PIN 7 #define RIGHT_BOTTON_PIN 8 #define CONFIRM_BOTTON_PIN 3 #define ESCAPE_BOTTON_PIN 4 */ #define MW_ACTION_IMMEDIATE menwiz tree; // create lcd obj using LiquidCrystal lib LiquidCrystal_SR lcd(10, 11, 12); //Data,Clk,Enable.
int list,sp=110;
void setup(){ Serial.begin(19200); Serial.println(F("STARTED")); pinMode(pin, OUTPUT); attachInterrupt(0, readButtons, RISING);
_menu *r,*s1,*s2;
tree.addUsrNav(navMenu); tree.begin(&lcd,20,4); //declare lcd object and screen size to menwiz lib r=tree.addMenu(MW_ROOT,NULL,"Root"); s1=tree.addMenu(MW_SUBMENU,r,"SUBMENU"); s2=tree.addMenu(MW_VAR,s1,"Node3"); s2->addVar(MW_LIST,&list); s2->addItem(MW_LIST,"Option1"); s2->addItem(MW_LIST,"Option2"); s2->addItem(MW_LIST,"Option3"); s2=tree.addMenu(MW_VAR,s1,"Node4"); s2->addVar(MW_AUTO_INT,&sp,0,120,10); s2=tree.addMenu(MW_VAR,s1,"Exit"); s2->addVar(MW_ACTION,exitFunct); s2->setBehaviour(MW_ACTION_CONFIRM,false);
// tree.navButtons(UP_BOTTON_PIN,DOWN_BOTTON_PIN,LEFT_BOTTON_PIN,RIGHT_BOTTON_PIN,ESCAPE_BOTTON_PIN,CONFIRM_BOTTON_PIN); } int i = 0; void loop(){ if(i > 1000){ Serial.print(F("freeRam() reports ")); Serial.println( tree.freeRam() ); i = 0; }else{ i++; } tree.draw(); }
void myfunc(){ Serial.println("ACTION FIRED!"); }
void readButtons(){ state = !state; digitalWrite(pin, state); /* 511 : none | 614 : up | 768 : down | 1023 : select */ lastButtonPressed = buttonPressed;
buttonValue = analogRead(buttonPin); if(buttonValue >= 900) { buttonPressed = 3; // select
} else if(buttonValue >= 700){ buttonPressed = 2; // down
} else if(buttonValue >= 600){ buttonPressed = 1; // up
} buttonAct = 1; Serial.print(buttonPressed); Serial.print(" XX "); Serial.println(buttonValue);
}
void exitFunct(){ Serial.println("EXIT Called"); buttonAct = 1; buttonPressed = 4; }
int navMenu(){ //MenuItem currentMenu=menu.getCurrent(); if(buttonAct){ buttonAct = 0; switch (buttonPressed){ case 4: //simulated escape return MW_BTE; break; case 3: //select return MW_BTC; break; case 2: //down return MW_BTD; break; case 1: //up return MW_BTU; break; } } else{ return MW_BTNULL; } }
|
|
|
|
|
Logged
|
|
|
|
|
rome
Offline
Sr. Member
Karma: 13
Posts: 342
|
 |
« Reply #115 on: July 26, 2012, 04:09:17 pm » |
The code seems to be ok. By the way it would be more polite to call addUsrNav after begin method. I cannot test the code as i would need to set up the same custom analog buttons. You can try the following on my behalf :-) Replace the actual method addUsrNav in MENWIZ.cpp with the following void menwiz::addUsrNav(int (*f)()){ ERROR(0); btx=(_nav*)malloc(sizeof(_nav));if(btx==NULL){ERROR(900); return;} usrNav.fl=true; usrNav.fi=f; }
Let me know
|
|
|
|
« Last Edit: July 28, 2012, 04:07:54 am by brunialti »
|
Logged
|
|
|
|
|
Offline
Full Member
Karma: 0
Posts: 120
|
 |
« Reply #116 on: July 27, 2012, 08:47:49 am » |
I'll give it a try tonight and let you know. I'm not near my Arduino at the moment. http://arduino.cc/forum/index.php?topic=109796.0 talks about the button setup if you did want to try the buttons.
|
|
|
|
|
Logged
|
|
|
|
|
rome
Offline
Sr. Member
Karma: 13
Posts: 342
|
 |
« Reply #117 on: July 29, 2012, 02:44:16 pm » |
Please find in https://github.com/brunialti/MENWIZ/downloads the latest version of MENWIZ. This version should be my final one (bug fixing apart). Starting fron this versione the addMenu and addItem (the two methods used to build menu structure) accepts string labels wrapped by F() operator. It saves quite a lot of flash memory (but requires little changes to the sketch code of the previous versions). Some more behaviours were added to option list object: now it is possible to display options in 2 or 3 columns. There is still the dannix issue to check, but it seems limited to custom input devices using the MW_ACTION_CONFIRM behaviour. Here attached the library guide.
|
|
|
|
|
Logged
|
|
|
|
|
Offline
Full Member
Karma: 0
Posts: 120
|
 |
« Reply #118 on: July 30, 2012, 04:51:13 am » |
Hi, sorry for the delay getting back to you. I've made the changes you suggested //void menwiz::addUsrNav(int (*f)()){ // usrNav.fl=true; // usrNav.fi=f; // } void menwiz::addUsrNav(int (*f)()){ ERROR(0); btx=(_nav*)malloc(sizeof(_nav));if(btx==NULL){ERROR(900); return;} usrNav.fl=true; usrNav.fi=f; } As before, setBehaviour false: no confirm and runs ("Exit Called in serial output") setBehaviour true: confirm msg shown but no exit function run ("button press registered but no serial outout for "Exit called"") no setBehaviour declaration: same as setBehaviour true I'm going to update the lib with what you posted above and retry.
|
|
|
|
|
Logged
|
|
|
|
|
Offline
Full Member
Karma: 0
Posts: 120
|
 |
« Reply #119 on: July 30, 2012, 05:14:30 am » |
Hi, with the latest library it's the same as above. If confirm msg shown, confirm does not run the custom function.
Additionally now if setBehaviour is false, it calls the exit function but when the menu is redrawn it leaves node4 under SUBMENU which shouldn't be there, it's not at prog startup neither can you select Node4
menus is setup like so:
SUBMENU Node3 Option 1 Option 3 Option 3 Node4 0 [110] 120 Exit
So node4 should always be the next level up. I didn't reapply the addUsrNav function changes to this library test.
|
|
|
|
|
Logged
|
|
|
|
|
|