|
|
View previous topic :: View next topic |
Author |
Message |
Jent
Joined: 04 Feb 2012 Posts: 20
|
Problem in coding of servo motor+digital compass module |
Posted: Fri Mar 02, 2012 11:52 am |
|
|
Hi, I am trying to control the servo motor turning base on the heading degree from compass module. Now I did for testing purpose first, but it did not work on my servo motor. Below is my coding:
Code: |
#include <18f4550.h>
#fuses HS, NOWDT, NOPROTECT, BROWNOUT, PUT, NOLVP
#use delay(clock=20M, crystal)
#include <flex_lcd.c>
#use i2c(master, sda=PIN_B0, scl=PIN_B1, FORCE_HW)
#define HMC6352_I2C_WRITE_ADDRESS 0x42
#define HMC6352_I2C_READ_ADDRESS 0x43
#define HMC6352_GET_DATA_COMMAND 0X41 //Transmit "A" to compass for heading
// Read the compass heading. This is in unit of 1/10 of a degree
// from 0 to 3599
#define SERVO_CONTROL PIN_B3
int16 HMC6352_read_heading(void)
{
int8 lsb;
int8 msb;
i2c_start();
i2c_write(HMC6352_I2C_WRITE_ADDRESS); //0x42 is the address that we need to communicate with to write information to the device
i2c_write(HMC6352_GET_DATA_COMMAND); //"A" or 0x41 is sent to magnetometer to get a response that pertains to what direction it is facing
i2c_stop();
delay_ms(10);
i2c_start();
i2c_write(HMC6352_I2C_READ_ADDRESS); //0x43 is the address that to communicate with to read information from compass
msb=i2c_read(); //Response 1 for MSb data after reading the data from compass
lsb=i2c_read(0); //Response 2 for LSb data after reading the data from compass
i2c_stop();
return((int16)lsb | (int16)msb << 8);
}
void main()
{
unsigned int a;
Int16 heading;
set_tris_b(0b00000011);
output_low(PIN_B3);
while(true)
{
heading=(HMC6352_read_heading())/10;
lcd_init();
printf(lcd_putc, "\fHeading degree:");
printf(lcd_putc, "\n %LuDE", heading); //display the heading degree from digital compass
delay_ms(1000);
if(90<=heading<=180)
{
for(a=0; a<100; a++)
{
output_high(SERVO_CONTROL);
delay_us(1000); //send 1ms to servo motor to turn anticlockwise
output_low(SERVO_CONTROL);
delay_us(19000);
}
}
else if(181<=heading<=270)
{
for(a=0; a<100; a++)
{
output_high(SERVO_CONTROL);
delay_us(2000); //send 2ms to servo motor to turn clockwise
output_low(SERVO_CONTROL);
delay_us(18000);
}
}
else
{
for(a=0; a<100; a++)
{
output_high(SERVO_CONTROL);
delay_us(1500); //send 1.5ms to servo motor in neutral position
output_low(SERVO_CONTROL);
delay_us(18500);
}
}
}
}
|
I intend to set a certain degree getting from compass to control the servo motor turning, but the servo motor just turn right and left for a short time, then didn't work anymore,even i rotate the compass from 000degree to 359degree.
Probably my coding having problem although it didn't come out with error in my ccs compiler. Hope obtain the experts guiding me to edit my problem..this is urgent...thanks your kindly help.. |
|
|
Mike Walne
Joined: 19 Feb 2004 Posts: 1785 Location: Boston Spa UK
|
Problem solving |
Posted: Fri Mar 02, 2012 12:01 pm |
|
|
Add some diagnostics so that you can 'see' what's happening.
You're the one with the kit in front of you.
Mike |
|
|
Jent
Joined: 04 Feb 2012 Posts: 20
|
|
Posted: Fri Mar 02, 2012 12:08 pm |
|
|
I really cant find out the problems, before this, I have try to test the servo motor by using the simple coding below, but it seemed to be working...
Code: |
#include <18F4550.h>
#fuses HS, NOWDT, NOPROTECT, BROWNOUT, PUT, NOLVP
#use delay(clock = 20M, crystal)
#define SERVO_CONTROL PIN_B3
void main()
{
unsigned int a;
set_tris_b(0b00000111); //set port b of pin7-3 as output and input, pin2-0 as input
output_b(0);
while(true)
{
for(a=0; a<100; a++)
{
output_high(SERVO_CONTROL); //high with pulse of +5V
delay_us(1500); //delay 1.5ms for move the servo to cetre
output_low(SERVO_CONTROL); //low pulse of 0V
delay_us(18500); //delay low pulse with 18.5ms, plus
// 1.5ms total 20ms for one pulse period
}
}
}
|
is that possible if I i used IF(..) may effect the servo motor turning? or either it is totally wrong? |
|
|
temtronic
Joined: 01 Jul 2010 Posts: 9229 Location: Greensville,Ontario
|
|
Posted: Fri Mar 02, 2012 12:34 pm |
|
|
Mike's right, we (you) need more info...
simple stuff like..
does the compass work right ?
does 'heading' seem OK.....?
how about displaying 'a' on the LCD,though fast, you should see it...
maybe change 'a' to 'cw',ccw','home' so you can see what is changing. |
|
|
Mike Walne
Joined: 19 Feb 2004 Posts: 1785 Location: Boston Spa UK
|
diagnostics |
Posted: Fri Mar 02, 2012 3:47 pm |
|
|
Thanks temtronic, we sing from the same hymn sheet again, but different time zones. Is that out of phase?.
To Jent,
Could you use one or more 8 bit ports effectively as LED bar graph(s)? Monitor heading and / or compass reading.
I had this dispute in the 70's / 80's about analogue / digital meters. At that time EVERYTHING had to go digital.
My view is, use what's most appropriate, NOT fashion.
I suggest that bar graphs may be easier to use in your situation, to tell you what's going on, from speed & observability points of view.
Suppose you want to represent values 0 - 255 on 8 LEDs. The simplest is to light no LEDs from 0 to 15, LED1 from 16 to 47, LED0 and LED1 from 48 to 79 etc. However you could PWM LED0 as value increases from 0 to 15, have LED0 on and PWM LED1 from 16 to 48 etc, all the way up to 255. The PWMing approach give better resolution at slower speeds.
Just my opinion, take it for what it's worth.
Mike |
|
|
SherpaDoug
Joined: 07 Sep 2003 Posts: 1640 Location: Cape Cod Mass USA
|
|
Posted: Fri Mar 02, 2012 5:52 pm |
|
|
Is there any chance the servo is creating a magnetic effect that alters the compass reading independent of actual motion? If you assume the compass output is always the actual direction, you may have problems. _________________ The search for better is endless. Instead simply find very good and get the job done. |
|
|
Jent
Joined: 04 Feb 2012 Posts: 20
|
|
Posted: Fri Mar 02, 2012 8:02 pm |
|
|
Thanks so much for guiding me...
to temtronic,
Before this, I have ever tried to test the compass solely, it worked ok..
but when I added up with servo motor coding, the heading degree shown in LCD become lagging and slow.
To Mike,
Actually this is my project in university, it is requirement for me to do so, I am not to play with the fashion stuff...anyway, thanks guiding me too. ^.^
To SherpaDoug,
Magnetic effect? This one I never realized that. But I had tried to separate the servo more than 30cm.
If I am not assuming the degree getting from compass, then what should I refer to? Since my robot need to accord to the compass then set the set-point direction for example to set as 000 degree, then my robot veering until get the set-point then go straight for it... Headache on it...>.< |
|
|
Jent
Joined: 04 Feb 2012 Posts: 20
|
|
Posted: Fri Mar 02, 2012 11:02 pm |
|
|
Now my main problem is, no matter how i set the range for the heading degree...for example: if(000<=heading<=180), then follow by if(181<=heading<=359)...
It may just read the data in "if(000<=heading<=180".... why this may happen? not supposing it may choose the correct condition when it met the current heading degree?...
I'm sure my coding existing problems...So confusing...please help ....>.< |
|
|
Mike Walne
Joined: 19 Feb 2004 Posts: 1785 Location: Boston Spa UK
|
Testing testing testing |
Posted: Sat Mar 03, 2012 3:06 am |
|
|
Quote: |
Before this, I have ever tried to test the compass solely, it worked ok..
but when I added up with servo motor coding, the heading degree shown in LCD become lagging and slow.
|
Of course it's slow with the motor coding in there. Your wasting 2 seconds in delay loops alone.
Possible magnetic interaction:-
(1) Separate the servo motor from the compass.
(2) Suspend the compass above your test area.
(3) Run compass code only.
(4) Operate the servos manually.
(5) Make the servos pass under the compass in different directions.
(6) Observe (or log) compass readings
This should tell you if the compass is being affected by the motors.
If your compass can't be made to work with the motors, could you consider a Gyro?
Quote: |
Now my main problem is, no matter how i set the range for the heading degree...for example: if(000<=heading<=180), then follow by if(181<=heading<=359)...
It may just read the data in "if(000<=heading<=180".... why this may happen? not supposing it may choose the correct condition when it met the current heading degree?...
I'm sure my coding existing problems...So confusing...please help ....>.< |
Sorry, but I simply don't understand how you are trying to control the direction in which the robot is supposed to go. Maybe you need to test the servos separately from the compass. Could you send the heading value to the servos either from a potentiometer or a PC, then see how the servos respond to that.
Mike |
|
|
|
|
You cannot post new topics in this forum You cannot reply to topics in this forum You cannot edit your posts in this forum You cannot delete your posts in this forum You cannot vote in polls in this forum
|
Powered by phpBB © 2001, 2005 phpBB Group
|