2 コミット 550dab4b69 ... 5278e70a95

作者 SHA1 メッセージ 日付
  grugly 5278e70a95 Updated README.md 7 年 前
  grugly 703bfc4b8e Animated the chicken, lots of cleaning up 7 年 前
2 ファイル変更131 行追加86 行削除
  1. 120 81
      Arduino_5_Button_16x2_LCD_Menu.ino
  2. 11 5
      README.md

+ 120 - 81
Arduino_5_Button_16x2_LCD_Menu.ino

@@ -30,75 +30,135 @@ extern "C" {
 #define BUTTON_UP	98
 #define BUTTON_RIGHT	0
 
-byte chicken[8] = { // Custom char for LCD in the shape of a chicken
-	B00000,
-	B00000,
-	B01100,
-	B11100,
-	B01111,
-	B01110,
-	B00100,
-	B00000
-};
-
-int backlight;		// Holds backlight status
-int brightness = 16;	// Brightnes of backlight
-int sleep_time = 4000;	// Time before screen turns off
-int refresh_delay = 1000;	// Info display refresh delay
-int cycle_delay = 1000;	// Work cycle refresh delay
+// Init LCD
+LiquidCrystal lcd(LCD_PIN_1, LCD_PIN_2, LCD_PIN_3,
+		  LCD_PIN_4, LCD_PIN_5, LCD_PIN_6);
 
-int menu_displayed = 0;	// Keep track of how deep into the menu we are
-int item = 0;		// Menu position
+// Defaults
+int backlight =0;	// Holds backlight status
+int brightness = 128;	// Brightnes of backlight
+int sleep_time = 5000;	// Time before screen turns off
+int refresh_delay = 500;// Info display refresh delay
+int cycle_delay = 500;	// Work cycle refresh delay
 
 // Timers
 unsigned long run_duration, wake_time, wake_duration,
 				last_refresh, last_cycle = 0;
 
-// Displayed text for each menu item
+// Displayed text for each menu item (16 char max)
 String menu_list[] = {
-      // 0123456789abcdef <-- 16 chars wide
 	"Brightness",
 	"Standby Delay",
-	"Refresh Delay",
-	"Work Cycle",
 	"Uptime"
 };
 
 // Count and store number of menu items
 int items = round((sizeof(menu_list) / sizeof(String) - 1));
+int item = 0;		// Menu position
+int menu_displayed = 0;	// Menu displayed if 1
 
-// Init LCD
-LiquidCrystal lcd(LCD_PIN_1, LCD_PIN_2, LCD_PIN_3,
-		  LCD_PIN_4, LCD_PIN_5, LCD_PIN_6);
+// Custom chars for LCD to animate a chicken bouncing across the screen
+byte chicken0[8] = { // High bounce
+	B00000,
+	B00000,
+	B01100,
+	B11100,
+	B01111,
+	B01110,
+	B00100,
+	B00000
+};
+byte chicken1[8] = { // Low bounce
+	B00000,
+	B00000,
+	B00000,
+	B01100,
+	B11100,
+	B01111,
+	B01110,
+	B00000
+};
+byte chicken2[8] = { // Squatting to lay
+	B00000,
+	B00000,
+	B00000,
+	B00000,
+	B01100,
+	B11100,
+	B01111,
+	B01110
+};
+byte chicken3[8] = { // Laying the egg
+	B00000,
+	B00000,
+	B01000,
+	B00001,
+	B01100,
+	B11100,
+	B01111,
+	B01110
+};
+byte egg[8] = { // The egg
+	B00000,
+	B00000,
+	B00000,
+	B00000,
+	B00100,
+	B01110,
+	B01110,
+	B00100
+};
+
+// Display statistics or, in this case, a chicken
+// bouncing across the screen and laying an egg
 
-// Display statistics or, in this case, a bunch of chickens..
+int anichar = 0; // Make chicken bounce
+int anipos = 15; // across the LCD
 void displayInfo() {
 	if ((run_duration - last_refresh) >= refresh_delay) {
-		lcd.clear();
-		// Show welcome msg (bunch of chickens)
-		lcd.write(byte(0));
-		lcd.print(" ");
-		lcd.write(byte(0));
-		lcd.print(" ");
-		lcd.write(byte(0));
-		lcd.print(" ");
-		lcd.write(byte(0));
-		lcd.print(" ");
-		lcd.write(byte(0));
-		lcd.print(" ");
-		lcd.write(byte(0));
-		lcd.print(" ");
-		lcd.write(byte(0));
-		lcd.print(" ");
-		lcd.write(byte(0));
-		lcd.print(" ");
+
+		// Animate a chicken to simulate actual data being displayed
+		if (anipos >= 0) {
+			if (anipos == 8) { // Lay egg at char 8
+				lcd.setCursor(anipos, 0);
+				lcd.write(2);
+				lcd.print(" ");
+				// Calls to delay() will block doWork() for
+				// their duration so don't use them if the
+				// work is critical
+				delay(refresh_delay);
+				lcd.setCursor(anipos, 0);
+				lcd.write(3);
+				delay(refresh_delay);
+				lcd.setCursor((anipos - 1), 0);
+				lcd.write(anichar);
+				lcd.write(4);
+				anipos -= 2;
+			} else { // Continue bouncing chicken
+				lcd.setCursor(anipos, 0);
+				lcd.write(anichar);
+				lcd.print(" ");
+				anipos--;
+			}
+		} else { // Clear the last chicken and the egg and start again
+			lcd.setCursor(0, 0);
+			lcd.print(" ");
+			lcd.setCursor(8, 0);
+			lcd.print(" ");
+			anipos = 15;
+		}
+		// Bounce chicken
+		if (anichar == 0) { anichar++; }
+		else { anichar--; }
+
+		// Reset timer
 		last_refresh = millis();
 	}
 }
 
-// Read sensors, flisk switches, etc..
+// Read sensors, flick switches, etc..
 void doWork() {
-	// Flash a dot in the bottom corner of the display to simulate work
+	// Flash a dot in the bottom corner of the LCD to simulate work
 	if ((run_duration - last_cycle) >= cycle_delay) {
 		lcd.setCursor(15, 1);
 		lcd.print(".");
@@ -154,7 +214,7 @@ int readButton() {
 
 // Display the menu item on the LCD
 void displayItem(int item) {
-	// clear the screen and print the item title
+	// Clear the screen and print the item title
 	lcd.clear();
 	lcd.print(String(menu_list[item]));
 
@@ -182,17 +242,7 @@ void displayItem(int item) {
 				lcd.print("OFF");
 			}
 			break;
-		case 2: // Display refresh delay in seconds
-			sec = refresh_delay / 1000;
-			lcd.setCursor(0, 1);
-			lcd.print(String(sec) + "sec");
-			break;
-		case 3: // Work cycle delay in seconds
-			sec = cycle_delay / 1000;
-			lcd.setCursor(0, 1);
-			lcd.print(String(sec) + "sec");
-			break;
-		case 4: // Display uptime
+		case 2: // Display uptime
 			s = (run_duration / 1000) % 60;
 			m = (run_duration / 60000) % 60;
 			h = (run_duration / 3600000) % 24;
@@ -204,7 +254,8 @@ void displayItem(int item) {
 }
 
 // Change values of menu items
-// action is 0 for decreasing (left button) and 1 for increasing (right button)
+// Action is 0 for decreasing (left button) and
+// 1 for increasing (right button)
 void updateItem(int item, int action) {
 	switch (item) {
 		case 0: // Brightness
@@ -229,28 +280,8 @@ void updateItem(int item, int action) {
 				sleep_time += 1000;
 			}
 			break;
-		case 2: // Refresh Delay
-			// Minimum delay is 1 seconds
-			if (action == 0 && refresh_delay > 1000) {
-				refresh_delay -= 1000;
-			}
-			// Max is 5 seconds
-			else if (action == 1 && refresh_delay < 5000) {
-				refresh_delay += 1000;
-			}
-			break;
-		case 3: // Cycle Delay
-			// Minimum delay is 1 seconds
-			if (action == 0 && cycle_delay > 1000) {
-				cycle_delay -= 1000;
-			}
-			// Max is 5 seconds
-			else if (action == 1 && cycle_delay < 5000) {
-				cycle_delay += 1000;
-			}
-			break;
 		// To display info, we don't need to modify the value
-		// so for item[4] (Uptime) we don't take any action.
+		// so for item[2] (Uptime) we don't take any action.
 	}
 	displayItem(item);
 }
@@ -259,7 +290,11 @@ void setup(void) {
 	// Setup LCD
 	lcd.begin(16, 2);
 	lcd.noCursor();
-	lcd.createChar(0, chicken);	// Create chicken char
+	lcd.createChar(0, chicken0);	// Create jumping chicken char
+	lcd.createChar(1, chicken1);	// Create landing chicken char
+	lcd.createChar(2, chicken2);	// Create squatting chicken char
+	lcd.createChar(3, chicken3);	// Create laying chicken char
+	lcd.createChar(4, egg);		// Create egg char
 
 	// Setup button and backlight pins
 	pinMode(BUTTON_PIN, INPUT);
@@ -282,6 +317,8 @@ void loop(void) {
 	if (backlight == 1 && wake_duration >= sleep_time) {
 		if (menu_displayed == 1) {
 			menu_displayed = 0;
+			item = 0;
+			lcd.clear();
 			wake_time = millis();
 		} else if (sleep_time != 11000) {
 			digitalWrite(BACKLIGHT_PIN, LOW);
@@ -314,6 +351,8 @@ void loop(void) {
 			case 1:	// Select button pushed
 				// Exit menu
 				menu_displayed = 0;
+				item = 0;
+				lcd.clear();
 				return;
 				break;
 			case 2:	// Left button pushed

+ 11 - 5
README.md

@@ -1,11 +1,11 @@
 # Arduino 5 Button 16x2 LCD Menu
 
-Basic menu for a 5 button, 16x2 LCD display shield for Arduino Uno
+Basic menu for a 5 button, 16x2 LCD display shield for Arduino Uno.
 
 ## Features
 
 * Adjustable backlight brightness
-* Adjustable LCD backlight stand-by for saving power
+* Adjustable LCD backlight stand-by for power saving
 * Loops through menu items (after the last, restarts on the first)
 
 ## Usage
@@ -19,13 +19,19 @@ Basic menu for a 5 button, 16x2 LCD display shield for Arduino Uno
 ## Implimentation
 
 1. Add your items to the menu_list[] array
-2. Add the code to display the values correctly for each item in displayItem() function
-3. Add the procedures and constraints to adjust the values in the updateItem() function
+2. Add the code to display the values correctly for each item in
+ the displayItem() function
+3. Add the procedures and constraints to adjust the values in the
+ updateItem() function
+
+You may also like to remove all the chicken animating code and the
+ contents of doWork() and displayInfo() and make it do something
+ more specific to your application.
 
 For compilation instructions, see http://playground.arduino.cc/OpenBSD/CLI
 
 ## TODO
 
-* Remove or animate the chicken
+* Save menu options to EEPROM
 * Remove C++ garbage and use ANSI C instead