Pages: [1]   Go Down
Author Topic: Help controlling 2 servos with joystick  (Read 1129 times)
0 Members and 1 Guest are viewing this topic.
Offline Offline
Newbie
*
Karma: 0
Posts: 3
View Profile
 Bigger Bigger  Smaller Smaller  Reset Reset

Hi,

I've done some research but still struggling trying to make the pan/tilt motion with servos. I've made one move as it should, played around and don't seem to be getting anywhere. Maybe my connections are off, maybe I've overcomplicated the code (is that possible?)

Materials:
Hextronik HX5010 Twin Bearing Servo
TowerPro MG995 DIGI HI-SPEED Servo
Arduino Duemilanove
Breadboard (Came with starter kit, I guess it's medium size as I've seen longer?)
Smaller breadboard that fits perfectly inside the Arduino (I got one servo moving perfectly with this, have struggled with 2)
9V Battery with adaptor to Arduino
Joystick: Keyes_SJoys (Ebay Search: Black Thumb Joystick Module w 5 Pin Replacement for Arduino High Quality)

I have the Joystick pins hooked up for Analog 3, 4 & 0 respectively.
The Servos hooked up to Digital 4 & 10.
(And Ground and 5V's)

Code:


#include <Servo.h>

//CONSTANTS
const int servo1 = 4;       // first servo
const int servo2 = 10;       // second servo

//VARIABLE
int VRx = 3;        // VRx Thumbstick
int VRy = 4;        // VRy Thumbstick
int SW = 0;       // SW Thumbstick
int VRxPos = 90;
int VRyPos = 90;
int SWPos = 90;
boolean logging = false;

Servo myservo1;  // create servo object to control a servo
Servo myservo2;  // create servo object to control a servo

void setup() {

  // Servo  
  myservo1.attach(servo1);  // attaches the servo
  myservo2.attach(servo2);  // attaches the servo
              

  // Inizialize Serial
  Serial.begin(9600);
}


void loop(){

    // Display Joystick values using the serial monitor
    outputJoystick();

    // Read the horizontal joystick value  (value between 0 and 1023)
    VRxPos = analogRead(VRx);          
    VRxPos = map(VRxPos, 0, 1023, 0, 180);     // scale it to use it with the servo (result  between 0 and 180)

    myservo2.write(VRxPos);                         // sets the servo position according to the scaled value    

    // Read the horizontal joystick value  (value between 0 and 1023)
    VRyPos = analogRead(VRy);          
    VRyPos = map(VRyPos, 0, 1023, 0, 180);     // scale it to use it with the servo (result between 70 and 180)

    myservo1.write(VRyPos);                           // sets the servo position according to the scaled value

    

    delay(50);                                       // waits for the servo to get there

}


/**
* Display joystick values
*/
void outputJoystick(){

    Serial.print(VRxPos);
    Serial.print ("---");
    Serial.print(VRyPos);
    Serial.println ("----------------");
    Serial.print(SWPos);    
    Serial.println("------------");

}

Only question about the code is about the SW... do you assign it to anything in the loop?

Any help at all would be appreciated.
« Last Edit: July 04, 2013, 07:53:44 pm by ThisGuy1 » Logged

Manchester (England England)
Offline Offline
Brattain Member
*****
Karma: 602
Posts: 33374
Solder is electric glue
View Profile
WWW
 Bigger Bigger  Smaller Smaller  Reset Reset

Read the how to use this forum sticky PLEASE and post the code correctly.

You are outputting numbers to the serial port that never change. They are just the pin numbers of the analogue port you are using.
Logged

Offline Offline
Edison Member
*
Karma: 64
Posts: 2488
The last thing you did is where you should start looking.
View Profile
 Bigger Bigger  Smaller Smaller  Reset Reset

How are you powering the motors?
Logged

Offline Offline
Newbie
*
Karma: 0
Posts: 3
View Profile
 Bigger Bigger  Smaller Smaller  Reset Reset

1st of all, very much appreciate the quick replies.

I appreciate it's probably a basic error but could you type a solution to the coding issue you mentioned? What should be in the serial port?

I'm powering the motors with an Energizer 9V Battery (2nd to last on the Materials list) with the little cord adaptor running to the Duemilanove

Thanks in advance
Logged

Offline Offline
Edison Member
*
Karma: 64
Posts: 2488
The last thing you did is where you should start looking.
View Profile
 Bigger Bigger  Smaller Smaller  Reset Reset

Quote
What should be in the serial port?
Quote
They are just the pin numbers of the analogue port you are using.
   Serial.print(VRxPos);
    Serial.print(VRyPos);
Quote
I'm powering the motors with an Energizer 9V Battery
Look up the voltage/current rating of your motors
« Last Edit: July 03, 2013, 10:37:38 pm by LarryD » Logged

Manchester (England England)
Offline Offline
Brattain Member
*****
Karma: 602
Posts: 33374
Solder is electric glue
View Profile
WWW
 Bigger Bigger  Smaller Smaller  Reset Reset

Quote
but could you type a solution to the coding issue you mentioned
No not until you do as requested and post the code correctly. There is a modify button on the post.

Quote
What should be in the serial port?
What do you want it to be. At the moment it just prints the same numbers over doesn't it.

Quote
I'm powering the motors with an Energizer 9V Battery
They don't last long.
Logged

Offline Offline
Newbie
*
Karma: 0
Posts: 3
View Profile
 Bigger Bigger  Smaller Smaller  Reset Reset

Thanks for putting up with my stupidity thus far.

Is it modified correctly? To tell it to turn 180 I feel like I need to change the int VRxPos = 90 (originally wanted it turning 90) to something like VRxPos = (0, 180);, which would theoretically tell the serial port what to do, but then isn't that the point of VRxPos = map(VRxPos, 0, 1023, 0, 180); in the loop?

Am I getting any closer or going way off-road with this?
Logged

0
Offline Offline
Tesla Member
***
Karma: 141
Posts: 9470
Arduino rocks
View Profile
 Bigger Bigger  Smaller Smaller  Reset Reset

Below is some simple code I made to tinker with pots and servos. It is set up to view the output in the serial monitor.

Code:
//zoomkat dual pot/servo test 12-29-12
//view output using the serial monitor

#include <Servo.h>
Servo myservo1;
Servo myservo2;

int potpin1 = 0;  //analog input pin A0
int potpin2 = 1;

int newval1, oldval1;
int newval2, oldval2;

void setup()
{
  Serial.begin(9600); 
  myservo1.attach(2); 
  myservo2.attach(3);
  Serial.println("testing dual pot servo"); 
}

void loop()
{
  newval1 = analogRead(potpin1);           
  newval1 = map(newval1, 0, 1023, 0, 179);
  if (newval1 < (oldval1-2) || newval1 > (oldval1+2)){ 
    myservo1.write(newval1);
    Serial.print("1- ");
    Serial.println(newval1);
    oldval1=newval1;
  }

  newval2 = analogRead(potpin2);
  newval2 = map(newval2, 0, 1023, 0, 179);
  if (newval2 < (oldval2-2) || newval2 > (oldval2+2)){ 
    myservo2.write(newval2);
    Serial.print("2- ");   
    Serial.println(newval2);
    oldval2=newval2;
  }
  delay(50);
}

Logged

Consider the daffodil. And while you're doing that, I'll be over here, looking through your stuff.   smiley-cool

Offline Offline
Newbie
*
Karma: 0
Posts: 1
View Profile
 Bigger Bigger  Smaller Smaller  Reset Reset

I see you are using the Keyes_SJoys PS2 Joystick Game Controller Breakout Module For Arduino from ebay. If yours are anything like mine, then they are of no use for fine control. Attaching this to my multimeter (between GND and VRx or VRy) gives very non-linear results:

At rest in the middle gives approximately 3.5kohm. Pressed to one extreme gives a value of 100-130 ohms (depending on which pot I am reading). This value does not appreciably change as you relax the stick towards rest for a good third of its travel. Then the resistance actually goes DOWN to between 50-100ohms and then rapidly climbs back up to 3.5kohm in the last third of its travel. It is also not reproducable in the change region. i.e. if I reverse direction to a previous position, I do not get very reproducable results.

Going the other direction is much the same. At its extreme, I get about 4.6kohms, then UP to 5kohm as I relax it towards the rest (middle point) and then down again to 3.5 kohm at its central rest position.

The results are not reproducable, do not change appreciably for a good third of travel at the extremes and in the middle are completely counter-intuitive (reversing resistance direction for some of its travel). At best, these devices will only be usable as a detection for extreme up, left, right, down and middle. Also, they can be used for 45 degree angles of up and left, bottom and right, etc. The advertised momentary button (SW) also only works in the rest position (middle).  I would not use them for detecting any form of graduated change in direction.

Even for the detection of the extremes, there is a potential for false detection if a user simply bumps the stick slightly into the resistance reversing region while making a change in another intended direction. They are truly not great products, but then you often get what you pay for ...

I bought these as a very cheap system of getting a simple input for menu selection and basic navigation because I can still use them with just 3 pins on my AVR as low pincount is an issue in my design, so they kind of work. Effectively, they permit a total of 8 detectable positions plus the central rest position together with the momentary button, which is not too shabby for the use of just 3 pins.

Unfortunately, the quirks of these devices will cost me a lot of time and code in programming to detect whether we are truly at an extreme or whether we are just passing fleetingly through the resistance reversing direction. I think I might just require multiple consitent ADC (with a given tolerance) as an indicator that we are not fleetingly in the reversing area.

I am not unique in having these issues with these types of devices. See the comments on the sparkfun website (https://www.sparkfun.com/products/9032) for their similar item.

Also note that the momentary button has no resistance associated with it. This might be an issue for you depending on what you are trying to drive with it as use of any appreciable amount of current through this switch is reported to burn out these joysticks.

Given the other issues you have had with your code, these issues with this device are likely to make your project very difficult for you.

Regards
Mark
Logged

Pages: [1]   Go Up
Jump to: