Robofun 機器人論壇
標題:
伺服馬達Futaba S3003
[打印本頁]
作者:
森涼
時間:
2007-8-28 20:26
標題:
伺服馬達Futaba S3003
我想問點先可以令到個Futaba S3003向後郁嫁??????
作者:
yyy
時間:
2007-8-29 22:09
原帖由
森涼
於 2007-8-28 20:26 發表
我想問點先可以令到個Futaba S3003向後郁嫁??????
大大,看不懂您的意思喔。
作者:
森涼
時間:
2007-8-30 15:44
姐係咁
我用緊ATmega8 control隻Futaba S3003
佢而+就逆時針咁轉
但係我想佢順時針咁轉
想睇下各位大大識唔識點寫個果programme
作者:
nadeshiko
時間:
2007-8-31 18:03
你的意思是說你的SCM只能逆時針轉
不能順時針轉動嗎???
所以你希望我門幫你想程式???
基本上你如果能讓他逆時針轉的話
那你順時針轉動只要改變你逆時針的脈波就行了
試試看吧
看你的SCM要多少脈波竟能順時針轉動
作者:
TroyLee
時間:
2007-8-31 18:49
這是我以前用 Attiny2313 的程式
用 WinAVR (GCC-4.1) 去寫的, 程式應該很容易移植,
因為只要調整晶體振盪器的數值跟暫存器名稱應該就可以用了!
#include "avr/io.h"
#include "avr/interrupt.h"
#define SERVO_MIDDLE 1350
#define SERVO(x) (SERVO_MIDDLE + (x))*2
#define SERVO_MIDDLE2 1520
#define SERVO2(x) (SERVO_MIDDLE2 + (x))*2
#define FORWARD 0
#define BACKWARD 1
long servoCommand=0, servoCommand2=0;
unsigned int dcCommandSpeed=0, dcCommandDir=0, dcStop = 0;
void port_init(void)
{
PORTA = 0x00;
DDRA = 0x00;
PORTB = 0x00;
DDRB = 0xFF;
PORTD = 0x00;
DDRD = _BV(PD5);
// 啟動外部中斷
MCUCR |= _BV(ISC10);
GIMSK |= _BV(INT1);
}
void timer0_init(void)
{
TCCR0B = 0x00;
TCNT0 = 256-100;
OCR0A = 256-100;
OCR0B = 256-100;
TCCR0A = 0x03;
TCCR0B = 0x05;
TIMSK |= _BV(TOIE0);
}
void timer1_init(void)
{
TCCR1B = 0x00;
TCNT1H = 0x00;
TCNT1L = 0x00;
ICR1 = (unsigned long)20000*2-1;
OCR1A = SERVO(0);
OCR1B = SERVO(0);
TCCR1A = 0xA2;
TCCR1B = 0x1A;
TIMSK |= _BV(TOIE1);
}
//UART0 initialize
// desired baud rate: 9600
// actual: baud rate:9615 (0.2%)
void UartInit(void)
{
UCSRB = 0x00;
UBRRH = 0x00;
UBRRL = 0x67;
UCSRA = 0x00;
UCSRC = 0x06;
UCSRB = _BV(RXCIE)|_BV(RXEN);
}
void AVRInit(void)
{
cli();
port_init();
timer0_init();
timer1_init();
UartInit();
sei();
}
SIGNAL(SIG_OVERFLOW1)
{
// Servo Load New Position
OCR1A = SERVO(servoCommand);
OCR1B = SERVO2(servoCommand2);
if ( dcStop ) {
OCR1B = SERVO2(0);
}
}
SIGNAL(SIG_OVERFLOW0)
{
TCNT0 = 256 - 100;
// Servo Load New Position
PORTD &= ~_BV(PD5);
PORTB &= ~_BV(PB2);
if ( !dcCommandSpeed || dcStop) {
TCCR0A &= ~(0xF0);
TCCR0A |= 0xA0;
} else if ( !dcCommandDir && dcCommandSpeed/* == FORWARD*/ ) {
PORTB |= _BV(PB2);
OCR0A = (256-100) + dcCommandSpeed;
TCCR0A &= ~(0xF0);
TCCR0A |= 0x80;
} else if ( dcCommandDir && dcCommandSpeed/*== BACKWARD*/ ) {
PORTD |= _BV(PD5);
OCR0B = (256-100) + dcCommandSpeed;
TCCR0A &= ~(0xF0);
TCCR0A |= 0x20;
}
}
SIGNAL( SIG_USART0_RX )
{
char ch = UDR;
if ( ch == 'S' ) {
// 初始化或重置控制板
// 將伺服馬達設為中心
servoCommand = 0;
servoCommand2= 0;
// DutyCycle = 0 %
dcCommandSpeed = 0;
dcCommandDir = FORWARD;
} else if ( ch >= 'A' && ch <= 'G' ) {
// 控制轉向, 將 Ascii 'A' ~ 'G' 轉為數字 n = 2 ~ 8
// (n+15)*50uS = 伺服馬達方向
ch = ch - 'D';
servoCommand = ch*50;
} else if ( ch >= '1' && ch <= '9' ) {
ch = ch - '5';
servoCommand2 = ch*50;
if( ch == 4 )
servoCommand2 = ch * 100;
// 控制 DutyCycle, 將 Ascii '0' ~ '9' 轉為數字 0 ~ 9
//ch = ch - '0';
//dcCommandSpeed = ch*10;
// 設定行徑方向向前
//dcCommandDir = FORWARD;
} else {
// 接收到錯誤命令
// 避免 Compiler 產生警告
}
}
SIGNAL( SIG_INT1 )
{
// 車體前方停止鍵被按下
// 將直流馬達控制關閉
dcStop = !dcStop;
}
int main(void)
{
AVRInit();
while(1);
return 0;
}
複製代碼
[
本帖最後由 TroyLee 於 2007-8-31 18:56 編輯
]
作者:
TroyLee
時間:
2007-8-31 18:55
抱歉剛剛仔細看了這是比較舊版的程式碼...
新版的跑不見了......
我大概跟你說一下, 程式是靠 Timer1 (16bit) 的 Output Compare 去產生 Servo Pulse
總共會有兩組, 分別輸出在 OC1A 和 OC1B 接腳,
硬體的設定大概是 16MHz 的振盪器,
UART 跑 9600 bps
#define SERVO_MIDDLE 1350
這個用來設定第一個 Servo 開機之後的中立點
#define SERVO(x)
用來計算位置的,
那程式要改的大概就是這邊跟 UART RX 的 ISR
可以自己定傳輸的方式...
應該不難理解吧@@
歡迎光臨 Robofun 機器人論壇 (https://robofun.net/forum/)
Powered by Discuz! X3.2