shire 发表于 2015-2-2 11:52:56

新人求助 galileo PWM脉冲输出与代码不一致

想用arduino驱动舵机,用digitalWrite函数写PWM脉冲,怎么也动不了。然后用示波器观察对应pin的波形,发现与程序不一致。用如下代码进行测试:
int pin=8;
int angle;
int pulsewidth;
int val;
void servopulse(int servopin,int angle)
{
pulsewidth=(angle*11)+500;
digitalWrite(servopin,HIGH);
delayMicroseconds(pulsewidth);
digitalWrite(servopin,LOW);
delayMicroseconds(20000-pulsewidth);
}
void setup()
{
pinMode(pin,OUTPUT);
digitalWrite(pin,LOW);
delay(1000);
val=500;
}

void loop()
{
digitalWrite(pin,HIGH);
delayMicroseconds(val);
digitalWrite(pin,LOW);
delayMicroseconds(20000-val);
}
理论上应该输出脉宽为0.5ms,周期为20ms的脉冲,用示波器测试显示实际脉宽为2.3ms。这样val只能在0-600时舵机会转动,实际相应脉宽为2.2-2.5ms,则舵机只能旋转某一个很小的角度,求大神指点。

shire 发表于 2015-2-2 14:05:33

没有人知道为什么吗
:'(:'(

Super169 发表于 2015-2-2 14:12:43

本帖最后由 Super169 于 2015-2-2 14:20 编辑

delaymicroseconds 大於 16385 好像有問題....


嘗試執行以下程式看看, 不知是否我的板子有問題, 在官網上看不到有關 delayMicroseconds 上限的資料

void setup() {

unsigned long s1, s2;
Serial.begin(57600);

s1 = micros();
delayMicroseconds(16385);
s2 = micros();
Serial.println(s1);
Serial.println(s2);

s1 = micros();
delayMicroseconds(16386);
s2 = micros();
Serial.println(s1);
Serial.println(s2);
}

void loop() {
// put your main code here, to run repeatedly:

}

shire 发表于 2015-2-2 14:19:51

Super169 发表于 2015-2-2 14:12 static/image/common/back.gif
delaymicroseconds 大於 16385 好像有問題....

不明白,感觉是系统时钟的问题

Super169 发表于 2015-2-2 14:21:06

shire 发表于 2015-2-2 14:19 static/image/common/back.gif
不明白,感觉是系统时钟的问题

剛補上了程式, 不知是否我的板子有問題, 你嘗試執行那個程式看看吧.

Super169 发表于 2015-2-2 14:27:30

本想測試用 delayMicroseconds 會否有 overhead 影響, 因為一般要精確的時間做法不同 (可參考 官方的 server.cpp).

但當我計算你的程式時, 時間太不合理, 再三研究, 發覺我的板子的 delayMicroseconds 在數值超過 16485 (對, 是 16385 而非 16384) 時, 會很古怪.但 unsigned int 應該可以接受 65535 的.

這可能不是你的問題, 只是我的板子有問題, 所以提議你試試.

Super169 发表于 2015-2-2 14:38:43

原來官網上已有說明了:

Currently, the largest value that will produce an accurate delay is 16383. This could change in future Arduino releases. For delays longer than a few thousand microseconds, you should use delay() instead.

你的程式中:delayMicroseconds(20000-val);
結果會超出 16383, 不可以使用 delayMicroseconds.

shire 发表于 2015-2-2 14:42:51

Super169 发表于 2015-2-2 14:27 static/image/common/back.gif
本想測試用 delayMicroseconds 會否有 overhead 影響, 因為一般要精確的時間做法不同 (可參考 官方的 serve ...

不明白为什么超过16384会有问题,那舵机控制代码该怎么写呢?用example里的sweep也不能用

Super169 发表于 2015-2-2 15:19:34

本帖最后由 Super169 于 2015-2-2 15:20 编辑

奇怪, 我之前明明 post 了官網的資料, 但那個 回覆 突然失蹤了.
官網上有說明的:

Currently, the largest value that will produce an accurate delay is 16383. This could change in future Arduino releases. For delays longer than a few thousand microseconds, you should use delay() instead.

你的程式中, 20000 - val 的值會超出 16383, 所以不應該用.

Super169 发表于 2015-2-2 15:21:55

shire 发表于 2015-2-2 14:42 static/image/common/back.gif
不明白为什么超过16384会有问题,那舵机控制代码该怎么写呢?用example里的sweep也不能用

你看看 server.cpp 吧, 一般不是用 delaymicroseconds 的, 而是用內部的 timer 處理.

shire 发表于 2015-2-2 15:34:45

Super169 发表于 2015-2-2 15:21 static/image/common/back.gif
你看看 server.cpp 吧, 一般不是用 delaymicroseconds 的, 而是用內部的 timer 處理.

用delay()试了一下还是不行,感觉像digitalWrite就要执行超过0.5ms,所以出来的脉冲根本达不到0.5-2.5ms的要求。

shire 发表于 2015-2-2 15:55:49

Super169 发表于 2015-2-2 15:21 static/image/common/back.gif
你看看 server.cpp 吧, 一般不是用 delaymicroseconds 的, 而是用內部的 timer 處理.

用了example里面的servo的例程也不行

Super169 发表于 2015-2-2 16:45:05

高階的程式總會有 overhead 的, 只是一般應用都可以接受, 不容易察覺, 但對於要求達 us 的就不太好了.
但 pinMode 也不會要 0.5ms 這麼慢, 簡單測試了大約要 8us 就可以了.

Super169 发表于 2015-2-2 16:46:32

我現在只有 UNO 及 Nano 在手, 今晚回家用 Galileo 試試吧.

Super169 发表于 2015-2-2 19:41:48

看來不是 delayMicroseconds 的問題, 剛用 Galileo 測試了, 16384 以上很正常 (當然,少少誤差是必然的).
晚飯後再試試 servo 庫是否可用.
页: [1] 2
查看完整版本: 新人求助 galileo PWM脉冲输出与代码不一致