Microservo turning with no input

Helllo, for my halloween project, I am making a locked box. The final intention is for the microservo to turn (and open the box) when push buttons are pressed in a specified order.

For this project, I am using an Arduino Uno board and a Miuzei Micro Servo 9g SG90 (4.8 - 6V, so I am using the 5V from the arduino).

As seen in the attachment, I have attached the microservo to the board and nothing else...but the motor moves on its own! It is not supposed to move until a signal goes into pin 9, but there is no wire going in there, so I am very confused now. I though it might be a hardware issue so I swapped both the board and the microservo but the results are the same.

Any help will be greatly appreciated!

#include <Servo.h>

Servo myservo;  // create servo object to control a servo
// twelve servo objects can be created on most boards

int pos = 0;    // variable to store the servo position

enum SwitchStates {IS_LOCKED, IS_OPEN};
SwitchStates switchState = IS_LOCKED;   
int switchPin = 9;

void switchMachine() {
  int pinIs = digitalRead(switchPin);
    switch (switchState) {                        
      case IS_LOCKED: {                                
         if (pinIs == HIGH) {                           
            switchState = IS_OPEN;
         }
         else switchState = IS_LOCKED;
         break;                                       
      }
      case IS_OPEN: {                              
        switchState = IS_OPEN;
        for (pos = 0; pos <= 100; pos += 1) { // goes from 0 degrees to 100 degrees
            myservo.write(pos);              // tell servo to go to position in variable 'pos'
            delay(15);  
            }
        break;                                        
      }  
    }
  }

void setup() {
  myservo.attach(2);  // attaches the servo on pin 2 to the servo object
  pinMode(switchPin, INPUT);
}

void loop() {
    switchMachine();
}

Arduino with MicroServo.png

Arduino with MicroServo.png

How is the input wired ?
Have you got a resistor in place to keep the pin at a known state (HIGH or LOW) when it is not activated or is it floating at aun unknown state, sometimes HIGH. sometimes LOW ?

Consider using INPUT_PULLUP in pinMode() to avoid the need for an external resistor

Hi,
Welcome to the forum.
Thanks for using code tags on your sketch.

When you declare a pin an input, that pin is floating.
It needs 5v or 0V applied, not open circuit.

As you seem to have your switch between the input and 5v, you need to add a 10k resistor between the input and gnd.

Or put your switch between input and gnd and declare.

pinMode(switchPin, INPUT_PULLUP);

You will then have to invert your code logic but that is easily done.

Tom... :slight_smile:

If nothing else helps, two suggestions:
Initially (in setup) move the servo to the locked position.
Use some power supply for the servo.

Thank you all! Very useful. I changed my code to add the pullup resistor, and connected the switch from the signal to the push button to the ground.

Tested one button, when button is pushed, servo turns. Good!
Tested two buttons. When first button, then second button, servo turns. Good!
Tested three buttons. Sometimes the servo turns when the buttons are pressed in the correct order. Sometimes they do not.

Is there a limit to the number of digital inputs I can have with the pullup resistor active? I am not sure why 2 buttons work but 3 buttons do not.

In the schematic, all the push buttons are omron b3f. I checked with the multimeter and the diagonals are connected only if the button is pushed, so only the diagonals are connected.

#include <Servo.h>

Servo myservo;  // create servo object to control a servo
// twelve servo objects can be created on most boards

int pos = 0;    // variable to store the servo position

enum SwitchStates {FIRST_STATE, SECOND_STATE, THIRD_STATE, FOURTH_STATE, FIFTH_STATE, IS_OPEN};
SwitchStates switchState = THIRD_STATE;
int thirdPin = 11;
int fourthPin = 10;
int lastPin = 9;

 

void switchMachine() {
    int pinIs = digitalRead(thirdPin);
    switch (switchState) { 
      case FIRST_STATE: {                                
        if (pinIs == LOW) {
          switchState = FIRST_STATE;
        }
        break;                                       
      }
      case SECOND_STATE: {                                
        if (pinIs == LOW) {
          switchState = FIRST_STATE;
        }
        break;                                       
      }
      case THIRD_STATE: {                                
        if (pinIs == LOW) {
          switchState = FOURTH_STATE;
        }
        break;                                       
      }
      case FOURTH_STATE: {                                
        if (pinIs == LOW) {
          switchState = THIRD_STATE;
        }
        break;  
      }
      case FIFTH_STATE: {                                
        if (pinIs == LOW) {
          switchState = THIRD_STATE;
        }
        break;                                       
      }
      case IS_OPEN: {
        if (pinIs == LOW) {
          switchState = THIRD_STATE;
          for (pos = 100; pos >= 0; pos -= 1) { // goes from 100 degrees to 0 degrees
            myservo.write(pos);              // tell servo to go to position in variable 'pos'
            delay(15);
          }
        }
        break;      
      }
    }
  
  pinIs = digitalRead(fourthPin);
    switch (switchState) { 
      case FIRST_STATE: {                                
        if (pinIs == LOW) {
          switchState = FIRST_STATE;
        }
        break;                                       
      }
      case SECOND_STATE: {                                
        if (pinIs == LOW) {
          switchState = FIRST_STATE;
        }
        break;                                       
      }
      case THIRD_STATE: {                                
        if (pinIs == LOW) {
          switchState = THIRD_STATE;
        }
        break;                                       
      }
      case FOURTH_STATE: {                                
        if (pinIs == LOW) {
          switchState = FIFTH_STATE;
        }
        break;  
      }
      case FIFTH_STATE: {                                
        if (pinIs == LOW) {
          switchState = THIRD_STATE;
        }
        break;                                       
      }
      case IS_OPEN: {
        if (pinIs == LOW) {
          switchState = THIRD_STATE;
          for (pos = 100; pos >= 0; pos -= 1) { // goes from 100 degrees to 0 degrees
            myservo.write(pos);              // tell servo to go to position in variable 'pos'
            delay(15);
          }
        }
        break;      
      }
    }    
  
  pinIs = digitalRead(lastPin);
    switch (switchState) {
      case FIRST_STATE: {                                
        if (pinIs == LOW) {
          switchState = FIRST_STATE;
        }
        break;                                       
      }
      case SECOND_STATE: {                                
        if (pinIs == LOW) {
          switchState = FIRST_STATE;
        }
        break;                                       
      }
      case THIRD_STATE: {                                
        if (pinIs == LOW) {
          switchState = THIRD_STATE;
        }
        break;                                       
      }
      case FOURTH_STATE: {                                
        if (pinIs == LOW) {
          switchState = THIRD_STATE;
        }
        break;  
      }
      case FIFTH_STATE: {                                
        if (pinIs == LOW) {
          for (pos = 0; pos <= 100; pos += 1) { // goes from 00 degrees to 100 degrees
          myservo.write(pos);              // tell servo to go to position in variable 'pos'
          delay(15);                       // waits 15ms for the servo to reach the position
          }
          switchState = IS_OPEN;
        }
        break;                                       
      }
      case IS_OPEN: {
        if (pinIs == LOW) {
          switchState = THIRD_STATE;
          for (pos = 100; pos >= 0; pos -= 1) { // goes from 100 degrees to 0 degrees
            myservo.write(pos);              // tell servo to go to position in variable 'pos'
            delay(15);
          }
        }
        break;      
      }                                        
  }  
}


void setup() {
  myservo.attach(2);  // attaches the servo on pin 12 to the servo object
  pinMode(thirdPin, INPUT_PULLUP);
  pinMode(fourthPin, INPUT_PULLUP);
  pinMode(lastPin, INPUT_PULLUP);
  for (pos = 100; pos >= 0; pos -= 1) { // goes from 100 degrees to 0 degrees
  myservo.write(pos);              // tell servo to go to position in variable 'pos'
  delay(15);  
  }
}

void loop() {
    switchMachine();
}

You'll only get bogus from buttons without debouncing :frowning:

Thank you! The debouncing was the final thing needed to solve the problem. The project now works! Thanks all!

When you get a solution, please post your final code so that new users with a similar issue in future years may benefit.