Hello there good people of Arduino land!
This is my first post and I would firstly like to say hello to everyone, and wish you all well, and also I hope you're all keeping safe what with the current situation re. that corona thing!
Secondly, I should apologise for my lack of knowledge and my use of incorrect nomenclature.
I've been tinkering with Arduinos for only a short while, so if I appear a complete rookie, then that's because I am!
The project:
I wish to build a water drop controller which will dispense three timed drops, each from three independently controlled valves, and trigger a camera to capture the collision event.
I have already built two successful devices, which were much, much simpler:
- A single valve/double drop controller
- A double valve/single drop (each) controller
My plan is to use an Arduino Nano as an I2C master since it has 8 analog pins, to gather the necessary timing data.
I will need 6 analog pins to obtain the required timing data:
- pot1 - Flash delay (valve one) / initial delay (valve two and three)
- pot2 - Drop One size (All three valves)
- pot3 - Drop One delay (All three valves)
- pot4 - Drop Two size (All three valves)
- pot5 - Drop Two delay (All three valves)
- pot6 - Drop Three size (All three valves)
(The first entry above - pot1 - will have two operations - for valve one it will be the flash delay for the camera trigger, and for valves two and three it will be a delay before the first drop - since I may wish to drop a single drop from each valve using different coloured water, and therefore will need a pause between the drops)
Pins A4 and A5 will be for the usual SDA and SCL I2C bus to connect to 3 AtMega328P-PU chips as slaves which will control the individual valves with the data sent from the master.
The selected valve will be chosen via a simple button, one corresponding to each valve.
Each valve will have its own 'select' button - which will be marked with a '<' on the lcd.
All the data will be displayed on a single 20X4 lcd screen.
I realise that I will have to keep each time value to under 99 milliseconds in order to get all the data to fit on the 20X4 lcd.
Hopefully it will look something like this:
I will then trigger the event by sending a single pulse from the master to the same digital pin on each of the slaves.
The master (Nano) will then fire the flash at the pre-determined time, by calculating the longest elapsed time (for the complete drop event) from whichever valve that may be.
The problem:
The test circuit I have built to test the potentiometer array readings seems to work, but it only updates the time data when the button is pressed, and of course due to the 'mechanical memory' of the pot, the same value is 'carried' over to the next pot value.
(This may not be a big problem however, and I've thought about rotary encoders, but I would need six of them, and I haven't yet found a reliable way to use them without interrupts, so I'm stuck with pots...which is fine - I will be using precision 10-turn pots for the final build)
It is a very simple circuit, so I didn't post a schematic, but simply put:
- Arduino Nano clone (Elegoo with UNO bootloader)
- 3 momentary push buttons (pins D2, D3, D4)
- single 10K potentiometer (pin A7)
- 16x2 lcd screen
I have tried to find out how to address this problem by searching the internet and indeed these forums, but I haven't been able to find an answer which I understand!
I know this is probably a very well known issue, but I'm still a beginner!
What I would like is for each value to be able to be adjusted 'live' so to speak, so that I can see what value is being set.
At the moment, I can turn the pot, and then when I press the button, it updates....so I have to guess what the value might be....which is no good clearly!
I plan to simply duplicate the (working) sketch six times, to have the correct number of parameters...which is maybe easier said than done naturally!
Here is the test sketch:
#include <digitalIOPerformance.h> //----Old library which is supposed to enable faster performance.
#include <Wire.h>
#include <LiquidCrystal.h> //----Open LiquidCrystal library.
LiquidCrystal lcd(12, 11, 10, 9, 8, 7); //----Create the lcd instance.
//----Define button and pot pins
#define button1 2
#define button2 3
#define button3 4
#define pot A7
//----Start an array with 3 fields, one for each time value.
int potValues[3];
//----set button states to HIGH.
int button1state = HIGH;
int button2state = HIGH;
int button3state = HIGH;
void setup() {
//----start serial comms.
Serial.begin(9600);
//----set pinModes.
pinMode(button1, INPUT_PULLUP);
pinMode(button2, INPUT_PULLUP);
pinMode(button3, INPUT_PULLUP);
pinMode(pot, INPUT);
//----initialize the lcd and print static info.
lcd.begin(16, 2);
lcd.clear();
lcd.setCursor(1, 0);
lcd.print("Val1");
lcd.setCursor(6, 0);
lcd.print("Val2");
lcd.setCursor(11, 0);
lcd.print("Val3");
}
void loop() {
button1state = digitalRead(button1); //----Read button1.
if (button1state == LOW) { //----if button1 is pressed...
//----Read pot and map the first time value to field '0'
potValues[0] = map(analogRead(pot), 0, 1023, 1, 5);
//----Set lcd to print time value.
lcd.setCursor(1, 1);
lcd.print(" ");
lcd.setCursor(1, 1);
lcd.print(potValues[0]);
delay(10);
//----Set lcd position markers, and overwrite the previous ones.
lcd.setCursor(0, 0);
lcd.print(">");
lcd.setCursor(5, 0);
lcd.print("<");
lcd.setCursor(10, 0);
lcd.print(" ");
lcd.setCursor(15, 0);
lcd.print(" ");
}
//----Duplicate of 'button1' but changed button#, array field and cursor positions etc.
button2state = digitalRead(button2);
if (button2state == LOW) {
potValues[1] = map(analogRead(pot), 0, 1023, 1, 5);
lcd.setCursor(6, 1);
lcd.print(" ");
lcd.setCursor(6, 1);
lcd.print(potValues[1]);
delay(10);
lcd.setCursor(5, 0);
lcd.print(">");
lcd.setCursor(10, 0);
lcd.print("<");
lcd.setCursor(0, 0);
lcd.print(" ");
lcd.setCursor(15, 0);
lcd.print(" ");
}
//----Duplicate of 'button1' but changed button#, array field and cursor positions etc.
button3state = digitalRead(button3);
if (button3state == LOW) {
potValues[2] = map(analogRead(pot), 0, 1023, 1, 5);
lcd.setCursor(12, 1);
lcd.print(" ");
lcd.setCursor(12, 1);
lcd.print(potValues[2]);
delay(10);
lcd.setCursor(10, 0);
lcd.print(">");
lcd.setCursor(15, 0);
lcd.print("<");
lcd.setCursor(0, 0);
lcd.print(" ");
lcd.setCursor(5, 0);
lcd.print(" ");
}
}
I've been testing some I2C master/slave stuff, so I think I've got a good handle on that when the time comes, but this issue is really holding things up!
I will be eternally grateful if someone would kindly nudge me in the right direction.
And sorry I've rambled on a bit! :-[
Thank you!