Arduino Forum

Using Arduino => Programming Questions => Topic started by: spencerkim on Nov 01, 2019, 11:04 pm

Title: Questions about Programming a Servo Motor [Solved]
Post by: spencerkim on Nov 01, 2019, 11:04 pm
Code: [Select]

#include <Servo.h> //include servo library
Servo myservo; //define servo as servo

byte waterSens[] = {A0, A1, A2};
const byte howManySensors = sizeof(waterSens) / sizeof(waterSens[0]);

int servoPos;
const byte servoDryPos = 60;  //
const byte servoWetPos = 50;  //
const int sensorWetThreshold = 450; //

void setup()
{
  Serial.begin(9600);
  Serial.println("https://forum.arduino.cc/index.php?topic=641224");
  myservo.attach(9);//attach servo to pin 9
  //also just going to use led13 as a signal
  pinMode(LED_BUILTIN, OUTPUT);
  Serial.print("Number of sensors "); Serial.println(howManySensors);
  Serial.println("setup() done");
  delay(1000);
}

void loop()
{
  setTheServo(readTheSensors());
  delay(500);
}

bool readTheSensors()
{
  int currentSensorVal;
  bool result = true; //start assuming all dry, if any one (or more) is wet then set false
  for (int i = 0; i < howManySensors; i++)
  {
    currentSensorVal = analogRead(waterSens[i]);
    Serial.print(currentSensorVal); Serial.print(" ");
    if (currentSensorVal > sensorWetThreshold)
    {
      result = false;
      break;}
  }

  if (result) {
  Serial.println("All dry");
  servoPos = 0
  
  else Serial.println("At least one sensor is wet"){
  servoPos = 90
  }
  return result;

}//readTheSensors()

void setTheServo(bool dry)
{
  if (dry)
  {
    myservo.write(servoDryPos);
    digitalWrite(LED_BUILTIN, LOW);
  }
  else
  {
    myservo.write(servoWetPos);
    digitalWrite(LED_BUILTIN, HIGH);
  }
}


I wrote this code and I tested to see if it will work and it didn't. I want the servo motor to turn 90 degrees whenever water is detected at one or more of the three water level sensors and the servo motor should come back to the starting position when water is not detected. Also, it said that setTheServo was not detected in the code. How am I suppose to fix these problems?
Title: Re: Questions about Programming a Servo Motor
Post by: UKHeliBob on Nov 01, 2019, 11:29 pm
Code: [Select]
  }//readTheSensors()Is that actually the end of the function ?
Title: Re: Questions about Programming a Servo Motor
Post by: groundFungus on Nov 01, 2019, 11:30 pm
You are missing a } to close the readTheSensors() function definition.

Code: [Select]
if (result) {
  Serial.println("All dry");
  servoPos = 0
 
  else Serial.println("At least one sensor is wet"){
  servoPos = 90
  }

Take a look at the syntax in that statement.  It is not right.

Should be?

Code: [Select]
if (result)
   {
      Serial.println("All dry");
      servoPos = 0
   }
   else
   {
      Serial.println("At least one sensor is wet");
      servoPos = 90
   }


Use the autoformat tool to indent your code.  Mistakes like that will often show up.  If you put every { and every } on their own lines it is easier to see if one is missing or misplaced.
Title: Re: Questions about Programming a Servo Motor
Post by: spencerkim on Nov 02, 2019, 12:20 am
Yes, I had some problems after that point on setting the servo motor.
Title: Re: Questions about Programming a Servo Motor
Post by: spencerkim on Nov 02, 2019, 04:35 pm
Code: [Select]

#include <Servo.h> //include servo library
Servo myservo; //define servo as servo

byte waterSens[] = {A1, A3};
const byte howManySensors = sizeof(waterSens) / sizeof(waterSens[0]);

int servoPos;
const byte servoDryPos = 90;  //
const byte servoWetPos = 180;  //
const int sensorWetThreshold = 600; //

void setup()
{
  Serial.begin(9600);
  Serial.println("https://forum.arduino.cc/index.php?topic=641224");
  myservo.attach(2);//attach servo to pin 9
  //also just going to use led13 as a signal
  pinMode(LED_BUILTIN, OUTPUT);
  Serial.print("Number of sensors "); Serial.println(howManySensors);
  Serial.println("setup() done");
  delay(1000);
}

void loop()
{
  setTheServo(readTheSensors());
  delay(500);
}

bool readTheSensors()
{
  int currentSensorVal;
  bool result = true; //start assuming all dry, if any one (or more) is wet then set false
  for (int i = 0; i < howManySensors; i++)
  {
    currentSensorVal = analogRead(waterSens[i]);
    Serial.print(currentSensorVal); Serial.print(" ");
    if (currentSensorVal > sensorWetThreshold)
    {
      result = false;
      break;}
  }

  if (result)
  {
    Serial.println("All dry");
    servoPos = 90;
  }
  else
  {
    Serial.println("At least one sensor is wet");
    servoPos = 180;
  }
  return result;

}//readTheSensors()

void setTheServo(bool dry)
{
  if (dry)
  {
    myservo.write(servoDryPos);
    digitalWrite(LED_BUILTIN, LOW);
  }
  else
  {
    myservo.write(servoWetPos);
    digitalWrite(LED_BUILTIN, HIGH);
  }
}


I updated my code to this, but it still doesn't work. What should I change so that the servo motor turns 90 degrees and remain at that position if one of the two water sensors sense the water and come back to the original position when the water is gone
Title: Re: Questions about Programming a Servo Motor
Post by: groundFungus on Nov 02, 2019, 04:40 pm
Quote
doesn't work
Provides no useful information.   What does the code do?  How does that differ from what you want?
Title: Re: Questions about Programming a Servo Motor
Post by: spencerkim on Nov 02, 2019, 04:46 pm
The code does not make the servo motor turn. If I plug in the battery(9V), the servo motor just starts to move by itself for 5 seconds and stops. However, I have to make it move 90 degrees only when water is sensed on the water sensor
Title: Re: Questions about Programming a Servo Motor
Post by: hammy on Nov 02, 2019, 06:38 pm
You can't run this stuff off a small 9v battery - it can't supply the current .
Title: Re: Questions about Programming a Servo Motor
Post by: lastchancename on Nov 02, 2019, 07:44 pm
Do you have a SERVO, or servo MOTOR ?
Big difference... one needs the servo library or similar, the other uses an h-bridge or driver to provide the control voltage.
Servos have all the goods in a single box, usually for RC hobby applications.
Servo motors are usually seen in larger automation / industrial control projects.
Title: Re: Questions about Programming a Servo Motor
Post by: spencerkim on Nov 02, 2019, 10:12 pm
I have servos. Not servo motors. However, they are both called servo motors, but one is RC servo motors, and the other is industrial servo motors
Title: Re: Questions about Programming a Servo Motor
Post by: lastchancename on Nov 02, 2019, 10:20 pm
incorrect.   a servomotor is a type of (usually) dc motor.
Title: Re: Questions about Programming a Servo Motor
Post by: Blackfin on Nov 02, 2019, 10:24 pm
Do you Serial.prints produce the expected results?
Title: Re: Questions about Programming a Servo Motor
Post by: spencerkim on Nov 03, 2019, 12:51 am
No, it does not
Title: Re: Questions about Programming a Servo Motor
Post by: Blackfin on Nov 03, 2019, 02:03 am
No, it does not

Well, what do you see?

You know, the more detail you offer, the quicker the debug process will be.
Title: Re: Questions about Programming a Servo Motor
Post by: Blackfin on Nov 03, 2019, 02:10 am
Also:

Code: [Select]
myservo.attach(2);        //attach servo to pin 9

Why does your comment say pin 9 but your call to attach references pin 2?

The Servo library only supports pins 9 or 10.


Edit: N/M, misread library reference...
Title: Re: Questions about Programming a Servo Motor
Post by: groundFungus on Nov 03, 2019, 02:24 am
Quote
The Servo library only supports pins 9 or 10.
Where did you get that information? 

Servo library reference. (https://www.arduino.cc/en/Reference/Servo)

AnalogWrite on pins 9 and 10 are disabled by the Servo library.
Title: Re: Questions about Programming a Servo Motor
Post by: Blackfin on Nov 03, 2019, 02:35 am
Where did you get that information? 

Servo library reference. (https://www.arduino.cc/en/Reference/Servo)

AnalogWrite on pins 9 and 10 are disabled by the Servo library.
Apologies, my mistake: I read this:

https://www.arduino.cc/en/Reference/ServoAttach

but only just noticed that applied to "...Arduino 0016 and earlier...".

Title: Re: Questions about Programming a Servo Motor
Post by: spencerkim on Nov 03, 2019, 03:31 am
I got that information from my friend. I see the light coming on the water sensor and the servo motor not turning on. Where am I suppose to connect the servo motor?
Title: Re: Questions about Programming a Servo Motor
Post by: lastchancename on Nov 03, 2019, 04:38 am
Well, that depends on whether it's an RC servo or a servo motor,
Please post a link to the product or datasheet
Title: Re: Questions about Programming a Servo Motor
Post by: spencerkim on Nov 03, 2019, 01:46 pm
https://www.amazon.com/SunFounder-Digital-Helicopter-Airplane-Controls/dp/B01M5LIKLQ/ref=sr_1_5?keywords=servo+motor+rc+2+count&qid=1572785105&sr=8-5 (https://www.amazon.com/SunFounder-Digital-Helicopter-Airplane-Controls/dp/B01M5LIKLQ/ref=sr_1_5?keywords=servo+motor+rc+2+count&qid=1572785105&sr=8-5)
Title: Re: Questions about Programming a Servo Motor
Post by: UKHeliBob on Nov 03, 2019, 01:55 pm
I suggest that you split
Code: [Select]
  setTheServo(readTheSensors());
so that you can print the value returned by readTheSensors() to see whether it matches your expectations

What do you see when you print currentSensorVal ?
Title: Re: Questions about Programming a Servo Motor
Post by: Danois90 on Nov 03, 2019, 02:20 pm
You might want to supply a diagram of your wiring. There is not enough current available on the 5V pin on the arduino to power a servo and I guess that is your problem.
Title: Re: Questions about Programming a Servo Motor
Post by: spencerkim on Nov 06, 2019, 02:17 am
Diagram of my wiring
Title: Re: Questions about Programming a Servo Motor
Post by: lastchancename on Nov 06, 2019, 02:51 am
OPS IMAGE

(https://forum.arduino.cc/index.php?action=dlattach;topic=644044.0;attach=331748)
Title: Re: Questions about Programming a Servo Motor
Post by: Danois90 on Nov 06, 2019, 12:26 pm
The diagram fails to illustrate if the power supply is a 9V battery wired directly to the breadboard?
Title: Re: Questions about Programming a Servo Motor
Post by: spencerkim on Nov 06, 2019, 10:17 pm
The 9V power supply is connected to the Arduino Uno board.
Title: Re: Questions about Programming a Servo Motor
Post by: groundFungus on Nov 06, 2019, 10:37 pm
Quote
The 9V power supply is connected to the Arduino Uno board.
Is the servo powered by the Uno 5V (see reply #21)? Or is the servo powered by 9V?  Is the servo rated for 9V, if so?
Title: Re: Questions about Programming a Servo Motor
Post by: spencerkim on Nov 06, 2019, 11:21 pm
The servo is powered by the Uno 5V not the 9V battery itself
Title: Re: Questions about Programming a Servo Motor
Post by: UKHeliBob on Nov 06, 2019, 11:46 pm
Is the 9V battery the type that I know as a PP3 with terminals on the top ?

If so then it will not power the Arduino for long, let alone the servo
Title: Re: Questions about Programming a Servo Motor
Post by: spencerkim on Nov 08, 2019, 12:20 am
Yes, it is the PP3 battery. How do I power the servo motor then?
Title: Re: Questions about Programming a Servo Motor
Post by: lastchancename on Nov 08, 2019, 12:42 am
With a power supply, or larger battery?

Keep you 0V lines common, and don't short anything!
Your servo datasheet will note the stall current requirement- that's the minimum you need.

If the servo stalls, it could drag the supply down, which might reset the arduino.
Title: Re: Questions about Programming a Servo Motor
Post by: spencerkim on Nov 08, 2019, 02:38 am
I want to know about both ways, so I could choose which one to use for my Arduino Uno servo motor connection.
Title: Re: Questions about Programming a Servo Motor
Post by: spencerkim on Nov 09, 2019, 05:54 pm
Should I use a 6V battery for my servo motor?
Title: Re: Questions about Programming a Servo Motor
Post by: UKHeliBob on Nov 09, 2019, 05:58 pm
4 AA batteries (not rechargeable ones) in series usually works OK
Title: Re: Questions about Programming a Servo Motor
Post by: spencerkim on Nov 09, 2019, 06:07 pm
Do I connect them to the Arduino or the actual 5V and breadboard?
Title: Re: Questions about Programming a Servo Motor
Post by: groundFungus on Nov 09, 2019, 06:12 pm
Connect the plus from the battery pack ONLY to the plus power wire of the servo.  Connect the minus from the battery pack to the minus power wire of the servo AND the ground of the Arduino.
Title: Re: Questions about Programming a Servo Motor
Post by: spencerkim on Nov 10, 2019, 05:31 pm
I tried connecting 4 AA batteries directly to the servo motor. However, it didn't work. Is there a problem with my coding? I am trying to make the servo motor turn 90 degrees when the water is sensed and come back to the original position when the water goes away.
Title: Re: Questions about Programming a Servo Motor
Post by: groundFungus on Nov 10, 2019, 05:34 pm
Did you connect the negative of the battery to the servo ground and the Arduino ground?
Title: Re: Questions about Programming a Servo Motor
Post by: spencerkim on Nov 10, 2019, 05:37 pm
There is only one wire connecting to the negative of the battery. Can you upload a diagram to explain what you mean by that?
Title: Re: Questions about Programming a Servo Motor
Post by: UKHeliBob on Nov 10, 2019, 05:55 pm
Connect the negative of the battery to the servo and also to a GND pin on the Arduino so that the 2 systems have a common point of reference
Title: Re: Questions about Programming a Servo Motor
Post by: groundFungus on Nov 10, 2019, 06:01 pm
Here is a diagram.

(https://forum.arduino.cc/index.php?action=dlattach;topic=644044.0;attach=332337)
Title: Re: Questions about Programming a Servo Motor
Post by: spencerkim on Nov 10, 2019, 08:55 pm
Thanks. I will try that.
Title: Re: Questions about Programming a Servo Motor
Post by: spencerkim on Nov 11, 2019, 10:19 pm
I tried doing that, but it still didn't work the way that I want it to. Is there a problem with my coding?
Title: Re: Questions about Programming a Servo Motor
Post by: DuffleBag on Nov 11, 2019, 11:03 pm
Edit: I stand corrected about PWM... but still, this board should be able to drive that servo (with risk)

I've connected similar micro servos to my Arduino directly and it's worked just fine.  

Yes, a separate power supply is safer, and smarter, but if you're getting confused (which it sounds like) it's added complication that makes troubleshooting harder.

One thing I am seeing is that you are trying to drive your servo from pin 2, which is not PWM for a standard uno.  Servos need to be plugged into a PMW pin to function correctly.

My suggestion:

Try picking a different signal pin, one that has a "~" in front of it on the board. 3, 9, 10, 11 maybe?  

And also power your servo (5v & gnd) from the board like you had originally, and see if it works.

If it does:

Dig out an old USB phone charger and hack apart an old USB cable to power that servo directly.  Don't forgot to connect the ground back to the board.  Or do nothing, and know you're taking a chance and might fry your board one day.
Title: Re: Questions about Programming a Servo Motor
Post by: UKHeliBob on Nov 11, 2019, 11:08 pm
Quote
Servos need to be plugged into a PMW pin to function correctly.
Not true
Title: Re: Questions about Programming a Servo Motor
Post by: spencerkim on Nov 11, 2019, 11:09 pm
Ok. I will try doing that
Title: Re: Questions about Programming a Servo Motor
Post by: DuffleBag on Nov 11, 2019, 11:19 pm
Not true
Really?? I learned something today then.... :smiley-zipper:
Title: Re: Questions about Programming a Servo Motor
Post by: UKHeliBob on Nov 11, 2019, 11:34 pm
See servo.attach() (https://www.arduino.cc/en/Reference/ServoAttach)
Title: Re: Questions about Programming a Servo Motor
Post by: spencerkim on Nov 12, 2019, 02:46 am
Code: [Select]
#include <Servo.h> //include servo library
Servo myservo; //define servo as servo

byte waterSens[] = {A1, A3};
const byte howManySensors = sizeof(waterSens) / sizeof(waterSens[0]);

int servoPos;
const byte servoDryPos = 90;  //
const byte servoWetPos = 180;  //
const int sensorWetThreshold = 600; //

void setup()
{
  Serial.begin(9600);
  Serial.println("https://forum.arduino.cc/index.php?topic=641224");
  myservo.attach(2);//attach servo to pin 2
  //also just going to use led13 as a signal
  pinMode(LED_BUILTIN, OUTPUT);
  Serial.print("Number of sensors "); Serial.println(howManySensors);
  Serial.println("setup() done");
  delay(1000);
}

void loop()
{
  setTheServo(readTheSensors());
  delay(500);
}

bool readTheSensors()
{
  int currentSensorVal;
  bool result = true; //start assuming all dry, if any one (or more) is wet then set false
  for (int i = 0; i < howManySensors; i++)
  {
    currentSensorVal = analogRead(waterSens[i]);
    Serial.print(currentSensorVal); Serial.print(" ");
    if (currentSensorVal > sensorWetThreshold)
    {
      result = false;
      break;}
  }

  if (result)
  {
    Serial.println("All dry");
    servoPos = 90;
  }
  else
  {
    Serial.println("At least one sensor is wet");
    servoPos = 180;
  }
  return result;

}//readTheSensors()

void setTheServo(bool dry)
{
  if (dry)
  {
    myservo.write(servoDryPos);
    digitalWrite(LED_BUILTIN, LOW);
  }
  else
  {
    myservo.write(servoWetPos);
    digitalWrite(LED_BUILTIN, HIGH);
  }
}


Would this coding make the servo motor turn 90 degrees when water sensed on the water sensor?
It is not working when the water is sensed? What are some corrections that I should make in my coding?
I used some information from here to get my help.https://forum.arduino.cc/index.php?topic=321984.0 (https://forum.arduino.cc/index.php?topic=321984.0)
Title: Re: Questions about Programming a Servo Motor
Post by: spencerkim on Nov 12, 2019, 03:01 am
Code: [Select]
#include <Servo.h> //include servo library
Servo myservo; //define servo as servo

byte waterSens[] = {A1, A3};
const byte howManySensors = sizeof(waterSens) / sizeof(waterSens[0]);

int servoPos;
const byte servoDryPos = 90;  //
const byte servoWetPos = 180;  //
const int sensorWetThreshold = 600; //

void setup()
{
  Serial.begin(9600);
  Serial.println("https://forum.arduino.cc/index.php?topic=641224");
  myservo.attach(2);//attach servo to pin 2
  //also just going to use led13 as a signal
  pinMode(LED_BUILTIN, OUTPUT);
  Serial.print("Number of sensors "); Serial.println(howManySensors);
  Serial.println("setup() done");
  delay(1000);
}

void loop()
{
  setTheServo(readTheSensors());
  delay(500);
}

bool readTheSensors()
{
  int SensorVal;
  bool result = true; //start assuming all dry, if any one (or more) is wet then set false
  for (int i = 0; i < howManySensors; i++);
  {
    int SensorVal = analogRead;{A1, A3;};
    Serial.print(SensorVal); Serial.print(" ");
    if (SensorVal > sensorWetThreshold);
    {
      result = false;
    }
  }

  if (result)
  {
    Serial.println("All dry");
    servoPos = 90;
  }
  else
  {
    Serial.println("At least one sensor is wet");
    servoPos = 180;
  }
  return result;

}//readTheSensors()

void setTheServo(bool dry)
{
  if (dry)
  {
    myservo.write(servoDryPos);
    digitalWrite(LED_BUILTIN, LOW);
  }
  else
  {
    myservo.write(servoWetPos);
    digitalWrite(LED_BUILTIN, HIGH);
  }
}


Or would this coding work better on making the servo motor turn 90 degrees when water is sensed on the water sensor?? I am new to coding, so I don't get this very well
Title: Re: Questions about Programming a Servo Motor
Post by: DuffleBag on Nov 12, 2019, 05:30 am
I'm still not clear as to what is working, and what isn't.  If you're new to coding, try commenting out pieces of your code and trying each thing by itself.

What happens if you change your loop to this?
Code: [Select]

void loop()
{
  //setTheServo(readTheSensors());
  setTheServo(true);
  delay(500);
  setTheServo(false);
  delay(500);
}


If it moves, then you know your servo setup is fine, and the problem is in your logic, or water sensors
Title: Re: Questions about Programming a Servo Motor
Post by: sayHovis on Nov 12, 2019, 05:42 am
What on Earth is this:

Code: [Select]
int SensorVal = analogRead;{A1, A3;};

Looks to me like that should refer to the sensor array, running through them in the "for", so probably:

Code: [Select]
int SensorVal = analogRead(waterSens[i]);


Title: Re: Questions about Programming a Servo Motor
Post by: sayHovis on Nov 12, 2019, 06:19 am
The way you structured that code is good practice, separating the reading of the sensors from the moving of the servo. That is, you send a bool from readTheSensors() to setTheServo(bool dry) with this line:

Code: [Select]
setTheServo(readTheSensors());

So why are you also attempting to position the servo inside readTheSensors():

Code: [Select]

Serial.println("All dry");
servoPos = 90; // ??????


That would defeat the object of the nice tidy way you already have it, so separate the input from the output.



Title: Re: Questions about Programming a Servo Motor
Post by: spencerkim on Nov 13, 2019, 12:28 am
The servo motor has to move when the water is sensed, so I thought that I had to read the sensor inside the set the servo. Also, for the second problem, should I put the input and the output on a different line
Title: Re: Questions about Programming a Servo Motor
Post by: spencerkim on Nov 14, 2019, 04:21 am
I tried doing everything to the servo that was related to the wiring of the circuit. However, it didn't work. I think there is a problem with my coding, but I can't figure it out. Help please!!!
Title: Re: Questions about Programming a Servo Motor
Post by: UKHeliBob on Nov 14, 2019, 07:14 am
Does the Servo Sweep example work ?
Title: Re: Questions about Programming a Servo Motor
Post by: spencerkim on Nov 14, 2019, 10:19 pm
Do you mean servo.attach ?
Title: Re: Questions about Programming a Servo Motor
Post by: UKHeliBob on Nov 14, 2019, 11:43 pm
Do you mean servo.attach ?

If that was a question about reply #55 then the answer is no
Title: Re: Questions about Programming a Servo Motor
Post by: spencerkim on Nov 15, 2019, 11:20 pm
Then, what do you mean by servo sweep
Title: Re: Questions about Programming a Servo Motor
Post by: UKHeliBob on Nov 15, 2019, 11:41 pm
Then, what do you mean by servo sweep

Look in the example programs for the Servo library.  One of them is named Sweep.  Does your servo move as expected when you upload the program ?
Title: Re: Questions about Programming a Servo Motor
Post by: spencerkim on Nov 17, 2019, 01:46 am
Yes, the sweep program in the servo library works. Should I try by making the servo motor loop at 89 and 90 degrees when the water is sensed in the water sensor? Would that work?
Title: Re: Questions about Programming a Servo Motor
Post by: spencerkim on Nov 17, 2019, 01:55 am
Code: [Select]
#include <Servo.h> //include servo library
Servo myservo; //define servo as servo

byte waterSens[] = {A1, A3};
const byte howManySensors = sizeof(waterSens) / sizeof(waterSens[0]);

int servoPos = 0;

void setup()
{
  Serial.begin(9600);
  Serial.println("https://forum.arduino.cc/index.php?topic=641224");
  myservo.attach(2);//attach servo to pin 2
  Serial.print("Number of sensors "); Serial.println(howManySensors);
  Serial.println("setup() done");
  delay(1000);
}

void loop() {
  int sensorValue = analogRead(waterSens);//read the water sensor value
         
  sensorValue = map(sensorValue, 0, 1023, 0, 90);
     if (sensorValue >= 1) {
        for (servoPos = 0; servoPos <= 90; servoPos += 1) { // goes from 0 degrees to 90 degrees
    // in steps of 1 degree
    myservo.write(servoPos);              // tell servo to go to position in variable 'pos'
    delay(15);                       // waits 15ms for the servo to reach the position
  }
  for (servoPos = 90; servoPos >= 89; servoPos -= 1) { // goes from 90 degrees to 89 degrees
    myservo.write(servoPos);              // tell servo to go to position in variable 'pos'
    delay(15);                       // waits 15ms for the servo to reach the position
  }
     
     }
     
  else{
    myservo.write(0);
  }
                   
 
 
  Serial.println(sensorValue);
  delay(20);       
}


Or, would this be a better code to make the servo motor to stay near 90 degrees?
Title: Re: Questions about Programming a Servo Motor
Post by: Blackfin on Nov 17, 2019, 02:13 am
Code: [Select]
#include <Servo.h> //include servo library
Servo myservo; //define servo as servo

byte waterSens[] = {A1, A3};
const byte howManySensors = sizeof(waterSens) / sizeof(waterSens[0]);

int servoPos = 0;

void setup()
{
  Serial.begin(9600);
  Serial.println("https://forum.arduino.cc/index.php?topic=641224");
  myservo.attach(2);//attach servo to pin 2
  Serial.print("Number of sensors "); Serial.println(howManySensors);
  Serial.println("setup() done");
  delay(1000);
}

void loop() {
  int sensorValue = analogRead(waterSens);//read the water sensor value
         
  sensorValue = map(sensorValue, 0, 1023, 0, 90);
     if (sensorValue >= 1) {
        for (servoPos = 0; servoPos <= 90; servoPos += 1) { // goes from 0 degrees to 90 degrees
    // in steps of 1 degree
    myservo.write(servoPos);              // tell servo to go to position in variable 'pos'
    delay(15);                       // waits 15ms for the servo to reach the position
  }
  for (servoPos = 90; servoPos >= 89; servoPos -= 1) { // goes from 90 degrees to 89 degrees
    myservo.write(servoPos);              // tell servo to go to position in variable 'pos'
    delay(15);                       // waits 15ms for the servo to reach the position
  }
     
     }
     
  else{
    myservo.write(0);
  }
                   
 
 
  Serial.println(sensorValue);
  delay(20);       
}


Or, would this be a better code to make the servo motor to stay near 90 degrees?
You have:

Code: [Select]
    byte waterSens[] = {A1, A3};
.
.
.

    int sensorValue = analogRead(waterSens);


waterSens is a pointer to an array of bytes. You need to access the element there with something like:

Code: [Select]
    int sensorValue = analogRead(waterSens[0]);

This will read the sensor on A1. If you want to interleave the sensors you need a variable as an index.
Title: Re: Questions about Programming a Servo Motor
Post by: spencerkim on Nov 17, 2019, 03:22 am
So, if I want to also do it for A3, I need to set the variable of the sensorvalue as an index?
Title: Re: Questions about Programming a Servo Motor
Post by: groundFungus on Nov 17, 2019, 03:40 am
To read A3:
Code: [Select]
int sensorValue = analogRead(waterSens[1]);
1 is the index in the [].   See the array reference (https://www.arduino.cc/reference/en/language/variables/data-types/array/).
Title: Re: Questions about Programming a Servo Motor
Post by: Blackfin on Nov 17, 2019, 05:04 am
Does this come close to what you want (compiles, not tested):

Code: [Select]
#include <Servo.h> //include servo library

#define MOISTURE_THRESH     450     //ADC counts    base moisture level (you fill in correct value)
#define HYST                20      //ADC counts    +/- from this value will switch
#define SAMPLE_INTERVAL     50      //mS            mS between sensor checks

#define WET_POS             90      //
#define DRY_POS             0       //

Servo myservo; //define servo as servo

byte
    waterSens[] = {A1, A3};
const byte
    howManySensors = sizeof(waterSens) / sizeof(waterSens[0]);
int
    grReadings[howManySensors];

void setup()
{
    Serial.begin( 9600 );
    Serial.println( "https://forum.arduino.cc/index.php?topic=641224" );
    myservo.attach( 2 );//attach servo to pin 2
    myservo.write( 0 );
    Serial.print( "Number of sensors " ); Serial.println( howManySensors );
    Serial.println( "setup() done" );
   
}//setup

void loop()
{
    unsigned long
        tNow;
    static unsigned long
        tSample = 0;
    static byte
        lastbWater = 0,
        bWater = 0;
       
    tNow = millis();
    if( tNow - tSample >= SAMPLE_INTERVAL )
    {   
        tSample = tNow;       
        for( int i=0; i<howManySensors; i++ )
        {
            int sensorValue = analogRead( waterSens[i] ); //read each twice twice due to channel change each pass
            delayMicroseconds( 20 );
            grReadings[i] = analogRead( waterSens[i] );
           
        }//for

        if( bWater == 0 )
        {
            for( int i=0; i<howManySensors; i++ )   
                bWater |= (grReadings[i] >= MOISTURE_THRESH+HYST) ? 1:0;
               
        }//if
        else
        {
            byte bDry = 0;           
            for( int i=0; i<howManySensors; i++ )
                bDry |= (grReadings[i] > MOISTURE_THRESH-HYST) ? 1:0;

            bWater = bDry;
               
        }//else 

        if( bWater != lastbWater )
        {
            lastbWater = bWater;
            myservo.write( (bWater) ? WET_POS : DRY_POS );
               
        }//if
           
    }//if     
   
}//loop
Title: Re: Questions about Programming a Servo Motor
Post by: sayHovis on Nov 17, 2019, 06:37 am
5 pages in, I decided to have a further look at the OPs original code from over 2 weeks ago.



I don't have the OP's sensors, but analog is analog, so with potentiometers on A0, A1 and A2, and a servo on pin 9, I tested the OP's code as fixed in my 2 bullets above, and it works. (At least according to my understanding of what's supposed to happen: all sensors dry servo goes one way, at least one sensor is wet, it goes the other?)



Here's OP's code from Nov 2, fixed as in the bullets above (all changes commented) and tested successfully with pots on A0, A1 and A2 and with a servo on 9.

Note the servo positions and threshold for my test:

Code: [Select]

const byte servoDryPos = 70; 
const byte servoWetPos = 110; 
const int sensorWetThreshold = 450;


Code: [Select]


#include <Servo.h> //include servo library
Servo myservo; //define servo as servo

byte waterSens[] = {A0, A1, A2};
const byte howManySensors = sizeof(waterSens) / sizeof(waterSens[0]);

int servoPos;
const byte servoDryPos = 70;  //
const byte servoWetPos = 110;  //
const int sensorWetThreshold = 450; //

void setup()
{
  Serial.begin(9600);
  Serial.println("https://forum.arduino.cc/index.php?topic=641224");
  myservo.attach(9);//attach servo to pin 9
  //also just going to use led13 as a signal
  pinMode(LED_BUILTIN, OUTPUT);
  Serial.print("Number of sensors "); Serial.println(howManySensors);
  Serial.println("setup() done");
  delay(1000);
}

void loop()
{
  setTheServo(readTheSensors());
  delay(500);
}

bool readTheSensors()
{
  int currentSensorVal;
  bool result = true; //start assuming all dry, if any one (or more) is wet then set false
  for (int i = 0; i < howManySensors; i++)
  {
    currentSensorVal = analogRead(waterSens[i]);
    Serial.print(currentSensorVal); Serial.print(" ");
    if (currentSensorVal > sensorWetThreshold)
    {
      result = false;
      break;
    }
  }

  if (result)
  {
    Serial.println("All dry");
    //servoPos = 0; // was missing ;
    // but have //'d out the above line anyway
    // no point having a setTheServo() function AND doing it here
  } //this was missing

  else
  { //new
    Serial.println("At least one sensor is wet"); //was missing ;
    //  { this { should be on the line before the serial print
    //servoPos = 90; // was missing ;
    // but have //'d out the above line anyway
    // no point having a setTheServo() function AND doing it here
  }
  return result;

}//readTheSensors()

void setTheServo(bool dry)
{
  if (dry)
  {
    myservo.write(servoDryPos);
    digitalWrite(LED_BUILTIN, LOW);
  }
  else
  {
    myservo.write(servoWetPos);
    digitalWrite(LED_BUILTIN, HIGH);
  }
}

Title: Re: Questions about Programming a Servo Motor
Post by: spencerkim on Nov 17, 2019, 02:32 pm
Yes, the two codes are close to the one that I want. For the second code, I have tried it already, but it didn't work very well. The servo motor didn't turn when at least one sensor was dry.
Title: Re: Questions about Programming a Servo Motor
Post by: sayHovis on Nov 17, 2019, 02:55 pm
The servo motor didn't turn when at least one sensor was dry.
The way I understood it (but I haven't read every single word in the thread, I must say) if ALL sensors are dry the servo is supposed to go one way, and if AT LEAST one is wet, it goes the other.

Where did "at least one sensor was dry" come from? (Maybe I missed that part...)


Your opening post says:

I want the servo motor to turn 90 degrees whenever water is detected at one or more of the three water level sensors and the servo motor should come back to the starting position when water is not detected.
... and that's what your code as fixed does, if dry is under the threshold and wet is over. (Although the servo positions I used were 70 and 110 I think.)





Title: Re: Questions about Programming a Servo Motor
Post by: spencerkim on Nov 17, 2019, 04:58 pm
The way I understood it (but I haven't read every single word in the thread, I must say) if ALL sensors are dry the servo is supposed to go one way, and if AT LEAST one is wet, it goes the other.

Where did "at least one sensor was dry" come from? (Maybe I missed that part...)







For that part, I meant to say when at least one sensor was wet
Title: Re: Questions about Programming a Servo Motor
Post by: sayHovis on Nov 17, 2019, 05:16 pm
For that part, I meant to say when at least one sensor was wet
Ok well that's what that code does for me, admittedly without your sensors but using a potentiometer on the basis that an analog signal from a pot is the same as one from an analog sensor, and just comparing to some threshold.

If I start with all 3 below the threshold, I get the message they're all dry, servo one side, led off. If one goes over, servo swings, led goes on, message says at least one is wet. If I make another one go over it obviously stays like that. Then only goes back to dry state when both go dry.

Sorry, can't help any more. On my system, it's doing as you ask.....

Title: Re: Questions about Programming a Servo Motor
Post by: spencerkim on Nov 17, 2019, 07:01 pm
Thanks for the help. I will try to do it on my system
Title: Re: Questions about Programming a Servo Motor
Post by: spencerkim on Nov 17, 2019, 07:51 pm
Did you actually pour water onto the sensor? My monitor is telling me that it is dry the whole time
Title: Re: Questions about Programming a Servo Motor
Post by: sayHovis on Nov 18, 2019, 12:58 pm
I told you I don't have your sensors: I used a potentiometer to mimic your sensors to just give a varying value for the analogRead().

... admittedly without your sensors but using a potentiometer on the basis that an analog signal from a pot is the same as one from an analog sensor, and just comparing to some threshold.
I certainly was not going to order some sensors that I will never use again, just to test your code.



Let's step back and check if any of your sensors work. Forget the servo stuff for a moment: do you have a simple sketch that reads one of your sensors and gives a different value between it being wet and dry?

Just this in loop() should do the trick:

Code: [Select]

void loop()
{
Serial.println(analogRead(A0));
delay(100);
}


What values do you get as you move a sensor in and out of a glass of water like this guy (https://www.youtube.com/watch?v=n7WRi5U5lQk) who going by your image in #22/23 has the same sensor.

If all you're doing is checking the presence or absence of water rather than the depth then perhaps the threshold needs to be set very low? Totally dry, out of the water, would be 0 maybe, but just touching the surface might be 1 or 2, I don't know.

You need to guarantee the sensors are working and that you know what threshold value you actually need.

Where did this 450 come from?

Code: [Select]
const int sensorWetThreshold = 450;

Since an analogRead() goes from 0-1023 that would presumably be the sensor about half-way in water? Did you test that value or just chose it randomly?



So do everyone a favour (not least yourself ;) ), forget the code you have so far, and just print out the values from the sensor as described.
Title: Re: Questions about Programming a Servo Motor
Post by: spencerkim on Nov 19, 2019, 02:09 am
I got the whole thing to work by setting the threshold to 10. Thanks for the help
Title: Re: Questions about Programming a Servo Motor
Post by: sayHovis on Nov 19, 2019, 04:34 am
I got the whole thing to work by setting the threshold to 10.
Excellent. Now it might be a good idea to go back to the opening post and edit the title there and add [solved] or similar. (Not that this question is about programming a servo ;) it's about reading an analog sensor and setting its go/no-go threshold.)

edit.. I just looked at your older threads from October, which are presumably on the same project. Back then you had this:

Code: [Select]
  if (sensorValue >= 50) {

It's a pity you didn't stick with a low value like that, since your code in this thread was basically ok all along, just a bad threshold. But all's well that ends well, I guess.

Thanks for the help
You're welcome.