佳礼资讯网

 找回密码
 注册

ADVERTISEMENT

楼主: crazybear

要如何同时控制5个servo motor?? (全部解决了,谢谢大家的帮忙)

[复制链接]
发表于 5-3-2009 09:02 AM | 显示全部楼层
原帖由 crazybear 于 4-3-2009 02:49 PM 发表
我的PROGRAMMING LEVEL是入手级罢了。
这对我来说很难。

其实源码范例已经在#2楼给了, 你不会珍惜。
回复

使用道具 举报


ADVERTISEMENT

发表于 5-3-2009 03:37 PM | 显示全部楼层
各位大大,
请问下。

还有什么wedsite有得买servo controller和servo motor 吗???
除了以下(这是小弟知道的):
1)www.pololu.com
2)www.hobbycity.com
想要买来做control robot arm的。。。
希望有更多选着后才买
回复

使用道具 举报

发表于 9-3-2009 09:57 PM | 显示全部楼层
原帖由 电动舞ver1 于 5-3-2009 03:37 PM 发表
各位大大,
请问下。

还有什么wedsite有得买servo controller和servo motor 吗???
除了以下(这是小弟知道的):
1)www.pololu.com
2)www.hobbycity.com
想要买来做control robot arm的。。。
希望有更 ...


http://www.cytron.com.my/
这里有可能有你要的东西。
回复

使用道具 举报

发表于 9-3-2009 10:03 PM | 显示全部楼层
原帖由 crazybear 于 4-3-2009 02:49 PM 发表


我的PROGRAMMING LEVEL是入手级罢了。
这对我来说很难。


最近不得空。所以迟来了。
给你一个tips.我怎样generate precise的pwm给servo motor.
你想看要怎样做到这个。
再post上来。可以帮你看看。
回复

使用道具 举报

发表于 9-3-2009 10:27 PM | 显示全部楼层
原帖由 fritlizt 于 9-3-2009 10:03 PM 发表


最近不得空。所以迟来了。
给你一个tips.我怎样generate precise的pwm给servo motor.
你想看要怎样做到这个。
再post上来。可以帮你看看。
http://i5.photobucket.com/albums/y187/skywalker_1211/servo ...


这个方法,resolution 可以很高,但是最多只有10个 channel,对吗?而且当你换其中一个 channel 的 pulse width 时,后面的 channel 会有一个 cycle 的 period 跑掉。
回复

使用道具 举报

发表于 9-3-2009 10:34 PM | 显示全部楼层
原帖由 waiweng83 于 9-3-2009 10:27 PM 发表


这个方法,resolution 可以很高,但是最多只有10个 channel,对吗?而且当你换其中一个 channel 的 pulse width 时,后面的 channel 会有一个 cycle 的 period 跑掉。


没错这个是他的缺点。 当改变period的时候, 后面的一个cycle会跑掉。
这个方法我用18f2550可以到16 channel.还可以。
回复

使用道具 举报

Follow Us
发表于 9-3-2009 10:58 PM | 显示全部楼层
16 channel??? 那当每一个 channel 的 pulse width 都是 2mS 时,那 period 不是变成 32mS 了??
回复

使用道具 举报

发表于 9-3-2009 10:59 PM | 显示全部楼层
原帖由 waiweng83 于 9-3-2009 10:58 PM 发表
16 channel??? 那当每一个 channel 的 pulse width 都是 2mS 时,那 period 不是变成 32mS 了??


用timer interrupt就可以了。
回复

使用道具 举报


ADVERTISEMENT

发表于 9-3-2009 11:03 PM | 显示全部楼层
那你是不是同一时间会有两个或以上的 channel 是同时 on 的?
回复

使用道具 举报

发表于 9-3-2009 11:11 PM | 显示全部楼层
原帖由 waiweng83 于 9-3-2009 11:03 PM 发表
那你是不是同一时间会有两个或以上的 channel 是同时 on 的?


对。 呵呵。 高手就是高手。 一讲就猜到。
回复

使用道具 举报

发表于 9-3-2009 11:25 PM | 显示全部楼层
之前我有想过这样子作,但是有一个问题想不到解决方法

比如说你的 channel 1 和 9 是一起 on,然后是 2 和 10, 3 和 11。。。Resolution 是 0.5uS。

但是当你的 Channel 1 pulse width = 1mS, Channel 9 pulse width = 1.0005mS 时,你怎样作?一开始,会先把 Channel 1 和 9 set high,然后 1mS 后把 channel 1 clear 掉。问题来了。要怎样在 0.5uS 内,跳出 interrupt,然后再进回 interrupt 里把 channel 9 clear 掉呢?
回复

使用道具 举报

发表于 11-3-2009 09:57 AM | 显示全部楼层
原帖由 fritlizt 于 9-3-2009 09:57 PM 发表


http://www.cytron.com.my/
这里有可能有你要的东西。

不好意识。。
请问大大们,
那里有的买32-pin的servo controller..
如以下的:

找到了。对不起。。

[ 本帖最后由 电动舞ver1 于 11-3-2009 10:05 AM 编辑 ]
回复

使用道具 举报

发表于 17-3-2009 08:35 AM | 显示全部楼层
原帖由 waiweng83 于 9-3-2009 11:25 PM 发表
之前我有想过这样子作,但是有一个问题想不到解决方法

比如说你的 channel 1 和 9 是一起 on,然后是 2 和 10, 3 和 11。。。Resolution 是 0.5uS。

但是当你的 Channel 1 pulse width = 1mS, Channel  ...


用多过一个timer就会有这种问题。 哈。我暂时还没想到解决方法。如果遇到这种问题。 mcu 够快就可以了。 只怕不够快。 就要另想办法,
不过给搂主的case够用的了。
不过5个channal就不会有这个问题。

[ 本帖最后由 fritlizt 于 17-3-2009 08:37 AM 编辑 ]
回复

使用道具 举报

 楼主| 发表于 3-4-2009 10:59 AM | 显示全部楼层

回复 33# fritlizt 的帖子

我照着你要我做的方式来做,现写1Hz的blinking LED。
我用DELAY就可以,但是用TIMER INTERRUPT就出现怪怪的RESULT。
我不懂问题出在哪里,我没用过TIMER INTERRUPT。
  1. #include <16F877A.h>                           
  2. #use delay(clock=20000000)
  3. #fuses HS,NOWDT,NOPROTECT,NOLVP

  4. int count1=0;

  5. void main()
  6. {
  7.    setup_timer_1 (T1_INTERNAL);
  8.    enable_interrupts(GLOBAL);
  9.    enable_interrupts(INT_TIMER1);
  10.    set_timer1(60536);         //interrupt at 1ms
  11.    
  12.    while(1);     
  13. }

  14. #INT_TIMER1
  15. void timer1_interrupt ()
  16. {
  17.    count1++;
  18.    
  19.    if(count1==500)
  20.    {
  21.    output_low(PIN_A0);
  22.    }
  23.    if(count1==1000)
  24.    {
  25.    count1=0;
  26.    output_high(PIN_A0);
  27.    }
  28. }
复制代码
回复

使用道具 举报

发表于 3-4-2009 11:28 AM | 显示全部楼层
原帖由 crazybear 于 3-4-2009 10:59 AM 发表
我照着你要我做的方式来做,现写1Hz的blinking LED。
我用DELAY就可以,但是用TIMER INTERRUPT就出现怪怪的RESULT。
我不懂问题出在哪里,我没用过TIMER INTERRUPT。
#include                           
#use ...


int count1-->unsigned int16 count1.
你要算到1000,用16bit variable.

timer1 interrupt 没有reload timer1 value.

setup timer1 prescaler?用1 也好也写下去。 以后容易读。
回复

使用道具 举报

 楼主| 发表于 3-4-2009 12:17 PM | 显示全部楼层
原帖由 fritlizt 于 3-4-2009 11:28 AM 发表


int count1-->unsigned int16 count1.
你要算到1000,用16bit variable.

timer1 interrupt 没有reload timer1 value.

setup timer1 prescaler?用1 也好也写下去。 以后容易读。


要谢谢fritlizt兄指导,终於可以走了。
以下是修改后的CODE跟PROTEUS的RESULT。
  1. #include <16F877A.h>                           
  2. #use delay(clock=20000000)
  3. #fuses HS,NOWDT,NOPROTECT,NOLVP

  4. unsigned int16 count1=0;

  5. void main()
  6. {
  7.    setup_timer_1 (T1_INTERNAL|T1_DIV_BY_1);
  8.    enable_interrupts(GLOBAL);
  9.    enable_interrupts(INT_TIMER1);
  10.    set_timer1(60536);         //interrupt at 1ms
  11.    output_high(PIN_A0);
  12.    
  13.    while(1);     
  14. }

  15. #INT_TIMER1
  16. void timer1_interrupt ()
  17. {
  18.    set_timer1(60536);
  19.    count1++;
  20.    
  21.    if(count1==500)
  22.    {
  23.    output_low(PIN_A0);
  24.    }
  25.    if(count1==1000)
  26.    {
  27.    count1=0;
  28.    output_high(PIN_A0);
  29.    }
  30. }
复制代码


PROTEUS的RESULT,可能是太慢的关系,所以不能拿到FULL CYCLE的WAVEFORM。

评分

参与人数 1积分 +5 收起 理由
fritlizt + 5

查看全部评分

回复

使用道具 举报


ADVERTISEMENT

发表于 3-4-2009 07:48 PM | 显示全部楼层
接下来你要做的就是
void main()
{
   setup_timer_1 (T1_INTERNAL|T1_DIV_BY_1);
   enable_interrupts(GLOBAL);
   enable_interrupts(INT_TIMER1);
   set_timer1(60536);         //interrupt at 1ms
   output_high(PIN_A0);
   
    led 闪1hz;
    delay 1s;
    led 闪2hz
    delay 1s;
    led 闪4hz;
   while(1);     
}

想想看要怎样做吧。
回复

使用道具 举报

 楼主| 发表于 5-4-2009 05:47 PM | 显示全部楼层
原帖由 fritlizt 于 3-4-2009 07:48 PM 发表
接下来你要做的就是
void main()
{
   setup_timer_1 (T1_INTERNAL|T1_DIV_BY_1);
   enable_interrupts(GLOBAL);
   enable_interrupts(INT_TIMER1);
   set_timer1(60536);         //interrupt at 1ms
    ...


做到了!
  1. #include <16F877A.h>                           
  2. #use delay(clock=20000000)
  3. #fuses HS,NOWDT,NOPROTECT,NOLVP

  4. unsigned int16 count1=0, value1;

  5. void main()
  6. {
  7.    setup_timer_1 (T1_INTERNAL|T1_DIV_BY_1);
  8.    enable_interrupts(GLOBAL);
  9.    enable_interrupts(INT_TIMER1);
  10.    set_timer1(60536);         //interrupt at 1ms
  11.    output_high(PIN_A0);
  12.    
  13. for(;;)
  14.     {
  15.    value1=(60536);
  16.    delay_ms(2000);
  17.    value1=(63036);
  18.    delay_ms(2000);
  19.    value1=(64286);
  20.    delay_ms(2000);
  21.    }

  22.    
  23.    while(1);
  24. }


  25. #INT_TIMER1
  26. void timer1_interrupt ()
  27. {
  28.    set_timer1(value1);
  29.    count1++;
  30.    
  31.    if(count1==500)
  32.    {
  33.    output_low(PIN_A0);
  34.    }
  35.    
  36.    if(count1==1000)
  37.    {
  38.    count1=0;
  39.    output_high(PIN_A0);
  40.    }
  41. }
复制代码
1Hz的Risetime n falltime



2Hz


4Hz


[ 本帖最后由 crazybear 于 5-4-2009 05:56 PM 编辑 ]

评分

参与人数 1积分 +5 收起 理由
fritlizt + 5

查看全部评分

回复

使用道具 举报

发表于 5-4-2009 06:57 PM | 显示全部楼层
原帖由 crazybear 于 5-4-2009 05:47 PM 发表


做到了!#include                           
#use delay(clock=20000000)
#fuses HS,NOWDT,NOPROTECT,NOLVP

unsigned int16 count1=0, value1;

void main()
{
   setup_timer_1 (T1_INTERNAL|T1_D ...


嗯。。。。大概是这样。 你的simulation看不到东西。
可能是interval太长了。

接下来。 做换duty cycle.
1ms on, 3ms off.
有两种方法, 一种是counter, fix interrupt。
另一种是直接换interrupt time.1ms interrupt, 3ms interrupt. etc.
用第二种方法。
回复

使用道具 举报

 楼主| 发表于 5-4-2009 07:56 PM | 显示全部楼层
原帖由 fritlizt 于 5-4-2009 06:57 PM 发表


嗯。。。。大概是这样。 你的simulation看不到东西。
可能是interval太长了。

接下来。 做换duty cycle.
1ms on, 3ms off.
有两种方法, 一种是counter, fix interrupt。
另一种是直接换interrupt time.1 ...


我想应该是这样吧!
但是那input_state() function好像没有做用这样的。
那OUTPUT ALWAYS HIGH

  1. #include <16F877A.h>                           
  2. #use delay(clock=20000000)
  3. #fuses HS,NOWDT,NOPROTECT,NOLVP


  4. void main()
  5. {   setup_timer_1 (T1_INTERNAL|T1_DIV_BY_1);
  6.    enable_interrupts(GLOBAL);
  7.    enable_interrupts(INT_TIMER1);
  8.    set_timer1(60536);         //interrupt at 1ms
  9.    output_high(PIN_A0);
  10.    
  11.    while(1);
  12. }


  13. #INT_TIMER1
  14. void timer1_interrupt ()
  15. {
  16.    if(input_state(PIN_A0))
  17.    {
  18.    output_low(PIN_A0);
  19.    set_timer1(50536);
  20.    }
  21.    else
  22.    {
  23.    output_high(PIN_A0);
  24.    set_timer1(60536);
  25.    }
  26.    clear_interrupt(INT_TIMER1);
  27. }
复制代码
回复

使用道具 举报

您需要登录后才可以回帖 登录 | 注册

本版积分规则

 

ADVERTISEMENT



ADVERTISEMENT



ADVERTISEMENT

ADVERTISEMENT


版权所有 © 1996-2023 Cari Internet Sdn Bhd (483575-W)|IPSERVERONE 提供云主机|广告刊登|关于我们|私隐权|免控|投诉|联络|脸书|佳礼资讯网

GMT+8, 20-4-2024 02:42 AM , Processed in 0.078215 second(s), 26 queries , Gzip On.

Powered by Discuz! X3.4

Copyright © 2001-2021, Tencent Cloud.

快速回复 返回顶部 返回列表