// final program for Rachelle DeCoste Wheaton Fab Lab Final Project June 2022 #include #include "RTClib.h" #include #include LiquidCrystal_I2C lcd(0x27, 16, 2); //what is the 0x27? will that have to change when I have my own board? RTC_PCF8523 rtc; byte customChar[8] = { //define the custom leaf character 0b00100, 0b01110, 0b11111, 0b11111, 0b11111, 0b01110, 0b00100, 0b00100 }; // Which pin on the board is connected to the NeoPixels? on my board 10,11,12,13 used 5-8 on Arduino Uno #define PINstrip1 10 #define PINstrip2 11 #define PINstrip3 12 #define PINstrip4 13 #define NUMPIXELS 13 // tinyNeoPixel strip1(NUMPIXELS, PINstrip1, NEO_GRB + NEO_KHZ800); tinyNeoPixel strip2(NUMPIXELS, PINstrip2, NEO_GRB + NEO_KHZ800); tinyNeoPixel strip3(NUMPIXELS, PINstrip3, NEO_GRB + NEO_KHZ800); tinyNeoPixel strip4(NUMPIXELS, PINstrip4, NEO_GRB + NEO_KHZ800); //declare the pins for the buttons - digital pins on ATTiny are 14,15,16 on Arduino 2,3,4 const int buttonPin_LOW = 14; const int buttonPin_MED = 15; const int buttonPin_HIGH = 16; //const int ledPin = 13; //this is for diagnosis purposes - it's the built in arduino pin int buttonState_LOW = 0; // variable for reading the LOW pushbutton status int buttonState_MED = 0; // variable for reading the MED pushbutton status int buttonState_HIGH = 0; // variable for reading the HIGH pushbutton status //define level of light for each plant int PlantOneChoice=0; // this is the variable I will use when inputting from the button. Values will be 1, 2 or 3 int PlantTwoChoice=0; int PlantThreeChoice=0; int PlantFourChoice=0; //define moisture sensor pins - these are analog pins so I can read level from 0 to 1223 int moistsens1 = 0; //these are pin numbers 0,1,2,3 on my board, but A0,A1,A2,A3 on uno int moistsens2 = 1; int moistsens3 = 2; int moistsens4 = 3; // you can adjust the threshold value - we determined 400 is reasonable with the ATTiny1616 int thresholdValue = 400; void setup() { // put your setup code here, to run once: strip1.begin(); // INITIALIZE NeoPixel strip object (REQUIRED) strip2.begin(); // INITIALIZE NeoPixel strip object (REQUIRED) strip3.begin(); // INITIALIZE NeoPixel strip object (REQUIRED) strip4.begin(); // INITIALIZE NeoPixel strip object (REQUIRED) lcd.init(); // initialize the lcd lcd.backlight(); lcd.createChar(0,customChar); lcd.clear(); lcd.setCursor(0, 0); // Go to position column 1 & row 1 lcd.write((byte)0); //make leaf character lcd.setCursor(3, 0); // Go to position column 4 & row 1 lcd.print("Welcome to "); // Print "...!" lcd.setCursor(15, 0); // Go to position column 16 & row 1 lcd.write((byte)0); //make leaf character lcd.setCursor(0, 1); // Go to position column 1 & row 2 lcd.print("Demeter's Garden"); // Print "..." delay(2000); //This leaves the welcome message for the first 2 seconds lcd.clear(); pinMode(buttonPin_LOW, INPUT); pinMode(buttonPin_MED, INPUT); pinMode(buttonPin_HIGH, INPUT); Askquestion(); } void loop() { // put main code here, to run repeatedly: DateTime now = rtc.now(); //read in the time from the RTC and set it to "now" if (PlantOneChoice==1 && now.hour()>9 && now.hour()<16) //for selection of low light, turn light on from 10am and turn off at 4pm, so this is less than hour 16 { LightsOn(); } else if (PlantOneChoice==2 && now.hour()>9 && now.hour()<19)//for selection of med light, turn light on from 10am and turn off at 7pm, so this is less than hour 19 { LightsOn(); } else if (PlantOneChoice==3 && now.hour()>9 && now.hour()<22)//for selection of med light, turn light on from 10am and turn off at 10pm, so this is less than hour 22 { LightsOn(); } else { //this will turn off all pixels outside of 10am until end time as above strip1.clear(); // Set all pixel colors to 'off' strip2.clear(); // Set all pixel colors to 'off' strip3.clear(); // Set all pixel colors to 'off' strip4.clear(); // Set all pixel colors to 'off' } //end else //add moisture sensor part strip1.show(); // Send the updated pixel colors to the hardware. strip2.show(); // Send the updated pixel colors to the hardware. strip3.show(); // Send the updated pixel colors to the hardware. strip4.show(); // Send the updated pixel colors to the hardware. }// end loop() void Askquestion() { //this is the function where the question of how much light for each plant is asked lcd.clear(); lcd.print("For plant One"); lcd.setCursor(0, 1); lcd.print("what light level?"); delay(1000); lcd.clear(); lcd.print("L=6 hours, M=9"); lcd.setCursor(0, 1); lcd.print("H=12. Choose now"); delay(1000); PlantOneChoice=getInput(); // repeat the same code for next plant. probably could use index to make this nicer, but going to just copy and paste for now to get it done lcd.clear(); lcd.print("For plant Two"); lcd.setCursor(0, 1); lcd.print("what light level?"); delay(1000); lcd.clear(); lcd.print("L=6 hours, M=9"); lcd.setCursor(0, 1); lcd.print("H=12. Choose now"); delay(1000); PlantTwoChoice=getInput(); // repeat the same code for next plant. probably could use index to make this nicer, but going to just copy and paste for now to get it done lcd.clear(); lcd.print("For plant Three"); lcd.setCursor(0, 1); lcd.print("what light level?"); delay(1000); lcd.clear(); lcd.print("L=6 hours, M=9"); lcd.setCursor(0, 1); lcd.print("H=12. Choose now"); delay(1000); PlantThreeChoice=getInput(); // repeat the same code for next plant. probably could use index to make this nicer, but going to just copy and paste for now to get it done lcd.clear(); lcd.print("For plant Four"); lcd.setCursor(0, 1); lcd.print("what light level?"); delay(1000); lcd.clear(); lcd.print("L=6 hours, M=9"); lcd.setCursor(0, 1); lcd.print("H=12. Choose now"); delay(1000); PlantFourChoice=getInput(); } //end Askquestion function void LightsOn() { // The first NeoPixel in a strand is #0, second is 1, all the way up // to the count of pixels minus one. for(int i=0; i<(NUMPIXELS-1); i++) { // For each pixel... if((i%4)==0) { strip1.setPixelColor(i, strip1.Color(0, 0, 150)); strip2.setPixelColor(i, strip2.Color(0, 0, 150)); strip3.setPixelColor(i, strip3.Color(0, 0, 150)); strip4.setPixelColor(i, strip4.Color(0, 0, 150)); } else { strip1.setPixelColor(i, strip1.Color(150, 0, 0)); strip2.setPixelColor(i, strip2.Color(150, 0, 0)); strip3.setPixelColor(i, strip1.Color(150, 0, 0)); strip4.setPixelColor(i, strip2.Color(150, 0, 0)); } } }//end of LightsOn int getInput() { int gotchoice=0; while(gotchoice==0){ //these read the button states within the loop. i had them before the loop and that doesn't work. of course. buttonState_LOW = digitalRead(buttonPin_LOW); buttonState_MED = digitalRead(buttonPin_MED); buttonState_HIGH = digitalRead(buttonPin_HIGH); if(buttonState_LOW==HIGH){ delay(500); lcd.clear(); lcd.print("Lights on 10am"); lcd.setCursor(0, 1); lcd.print("Lights off 4pm"); // digitalWrite(ledPin, HIGH);//just to see if button presses are getting here delay(1000); //gotchoice=true; gotchoice=1; } else if(buttonState_MED==HIGH){ delay(500); lcd.clear(); lcd.print("Lights on 10am"); lcd.setCursor(0, 1); lcd.print("Lights off 7pm"); // digitalWrite(ledPin, HIGH); delay(1000); gotchoice=2; } else if(buttonState_HIGH==HIGH){ delay(500); lcd.clear(); lcd.print("Lights on 10am"); lcd.setCursor(0, 1); lcd.print("Lights off 10pm"); // digitalWrite(ledPin, HIGH); delay(1000); gotchoice=3; } } //end while return gotchoice; } //end getInput function void needwater() {//this function will run repeatedly and check moisture levels to turn light facing up red if plant needs water int sensorValue1 = analogRead(moistsens1); int sensorValue2 = analogRead(moistsens2); int sensorValue3 = analogRead(moistsens3); int sensorValue4 = analogRead(moistsens4); //note: serial printlines are only going to work when plugged into computer and are there for assessing thresholds. Leaving in for future use but will not do anything while plant is not plugged into computer if(sensorValue1 < thresholdValue){ Serial.println(" - Plant 1 doesn't need watering"); strip1.setPixelColor(12, strip1.Color(0, 150, 0)); } else { Serial.println(" - Time to water plant 1!"); strip1.setPixelColor(12, strip1.Color(150, 0, 0)); } Serial.print(sensorValue2); Serial.println("=Sensor 2 value"); if(sensorValue2 < thresholdValue){ Serial.println(" - Plant 2 doesn't need watering"); strip2.setPixelColor(12, strip2.Color(0, 150, 0)); } else { Serial.println(" - Time to water plant 2!"); strip2.setPixelColor(12, strip2.Color(150, 0, 0)); } Serial.print(sensorValue3); Serial.println("=Sensor 3 value"); if(sensorValue3 < thresholdValue){ Serial.println(" - Plant 3 doesn't need watering"); strip3.setPixelColor(12, strip1.Color(0, 150, 0)); } else { Serial.println(" - Time to water plant 3!"); strip3.setPixelColor(12, strip1.Color(150, 0, 0)); } Serial.print(sensorValue4); Serial.println("=Sensor 4 value"); if(sensorValue4 < thresholdValue){ Serial.println("Plant 4 doesn't need watering"); strip4.setPixelColor(12, strip2.Color(0, 150, 0)); } else { Serial.println("Time to water plant 4!"); strip4.setPixelColor(12, strip2.Color(150, 0, 0)); } }//end needwater