별건 아니지만, 예전 프로그램을 조합+개조하여 만들어 본 녀석인데..
흐음.. 엔터를 두번이나 눌러야 하다니 이걸 어떻게 개선을 해야 하려나..

아무튼 이녀석의 목적은
- 서보모터를 시리얼 포트를 통해 값을 입력받아 제어한다.

일단 약간의 버그로 인해
- 숫자 입력후 엔터를 두번 눌러야 각도가 변경되고
- 엔터만 눌러대거나, 이상한 각도를 입력하면 서보가 길길댄다.

입력가능한 숫자 범위는 서보마다 다르겠지만
ES-311 엘레파츠의 저렴한 모터로는
32~112 값으로 0도에서 180도까지 이동이 가능하다(정확하게는 한 160도 정도 되는듯?)

소스코드

신고
Posted by 구차니

댓글을 달아 주세요

  1. 앗이거... 제가 찾고있었던건데 ㅎㅎ.. 근데 어떻게 사용해야될련지는 모르겠네요... 원격컴퓨터에서 RC 비행기를 조종하는 솔루션개발중인데 어떻게 시작할지 막막하네요 ㅠㅠ

    2010.06.26 17:04 신고 [ ADDR : EDIT/ DEL : REPLY ]
    • 헐 솔루션이라니 ㅠ.ㅠ
      너무 고도의 것을 하시려는거 아닌가요? ^^;

      저도 백수모드라서 한번 해볼까 해요
      굳이 RC가 아니더라도 여러가지 방법으로 말이죠 ^^

      2010.06.26 22:55 신고 [ ADDR : EDIT/ DEL ]
    • ㅎㅎ.. 구상도는 생각했는데 역시 너무 어렵겠죠 ?

      2010.06.27 16:02 신고 [ ADDR : EDIT/ DEL ]
    • 일단 컴퓨터로 오면은 실시간성에 문제가 생기니 추락해도 책임안진다고 하시면 될꺼 같기도 해요 ㅋㅋ

      2010.06.27 19:18 신고 [ ADDR : EDIT/ DEL ]

How to control analog servo using Atmega128 timer0 (8bit timer)

서보모터는, 재미난 녀석이다. 근데 다루기 쉽지는 않다 ㅠ.ㅠ
예전에 구매한 녀석으로 이렇게 생겨먹었다.

특이하게도 색이 흰색/빨강/검정이 아니라 주황/빨강/갈색이다.
빨강은 Vcc
갈색은 GND
주황은 Signal 이다.


서보 스펙
아날로그 신호를 받아들이며(아날로그 서보)
4.8V에 0.19sec/60' 대략 180도 전체 이동에 0.6sec 정도 걸린다.(생각보다 빠른거 같은데 막상보면 느리다.)

AVR 스펙
us-technology 사의 제품으로 16Mhz로 작동하며
PORTC 는 디버깅용 LED
PORTF 는 PWM 출력용으로 사용하였다.

Timer0(8bit timer)를 이용하여, PWM 신호를 만들어낸다.(Timer만으로 제어함)
[링크 : http://www.us-technology.co.kr/product/product_main.asp?mode=101&smode=2]

소스코드는 AVR BIBLE (배성중/북두출판사) 를 참고하였으며
winavr 요즘 버전에 맞추고(ISR, outp 매크로, include 경로), 클럭이 맞지않아 변수들을 수정하여 타이밍을 조절하였다.

지루한 계산
16Mhz = 16,000,000 hz 이고
서보 모터는 20ms = 0.02sec 단위로 신호를 넣어준다.
그리고 PWM 신호는 0.5ms ~ 2ms 사이의 길이를 넣어주면 0 ~ 180도의 각도로 이동한다.
(책에는 1.5ms 에서 길거나 짧거나 라고 하는데 서보마다 다른듯.. 데이터 시트에도 없다 ㄱ-)

일단 8bit timer를 사용함으로 256 clock 마다 overflow를 발생시키며
    16,000,000(clock/sec) / 256 = 62,500 times
1초에 62,500 번의 overflow가 발생하게 된다.
    1/62500 = 0.000016 sec 이며
    62500/50 = 1250 이다.(20ms 는 1초에 50회)
즉, 256번씩의 overflow를 1250번 반복하게 되면 0.02sec = 20msec 간격을 잡을수 있다.
그리고 1msec는 62.5 인터럽트가 모이면 되고,
실험적으로 서보에서 사용하는 PWM의 width를 얻어내면 된다.

엘레파츠 ES-311 서보에서
     0도는 0.512ms = 32 overflows
    90도는 1.216ms = 76 overflows
    180도 1.792ms = 112 overflows

아무튼 위의 값은 정확한건 아니지만.. (ㄱ-) 대략적으로 맞아들어가며
0도와 180도의 하한/상한을 찾은뒤 평균내면 90도가 잡아진다.(레드썬!)
(위의 값으로는 180도 쪽이 약간 5도 정도 부족해 보이나,
끽끽대며 더이상 가지 못하는 문제가 있어 실질적으로 90도를 약간 좌측으로 수정해야 하지 않을까 싶다.)

대충의 계산방식이 들어있는 스프레드시트 파일.
클럭과 timer overflow 에 필요한 clock을 입력하면 된다.


소스코드 & 동영상


신고
Posted by 구차니

댓글을 달아 주세요

  1. 게르드

    오오~ 서보도 잘 움직이네요..^^ +_+

    2010.01.20 14:27 신고 [ ADDR : EDIT/ DEL : REPLY ]
    • 이거 버전 1 이고
      파워분리하고 쇼해서 기판이 좀 달라졌어 ㅋㅋ

      2010.01.20 14:36 신고 [ ADDR : EDIT/ DEL ]
  2. 비밀댓글입니다

    2011.03.04 11:01 [ ADDR : EDIT/ DEL : REPLY ]
    • 회로도 까지 만들어 가면서 만든 녀석이 아니라서요 ^^;
      그냥 단순하게 pin 하나를 서보의 signal에 연결하고
      전원 / gnd 는 따로 연결을 해주고
      ATMEGA의 PWM 기능을 사용하지 않고, 딜레이를 사용하여 PWM 신호를 생성하는 식으로 구현했었습니다.

      2011.03.04 11:11 신고 [ ADDR : EDIT/ DEL ]
  3. 비밀댓글입니다

    2014.11.08 16:28 [ ADDR : EDIT/ DEL : REPLY ]
    • for(;;) 안에 딜레이나 일정 시간에 한번씩만 값을 바꾸는 루틴이 필요 합니다.
      while(sec < 49)
      61
      {
      62
      PORTC = Bout;
      63
      }
      제 코드에서는 이런식으로 #if 1 별로
      값을 한번만 바꾸도록 해서 필요한 주기 동안은 값이 hi/low로 설정되어 있도록 되어있습니다.

      2014.11.09 15:46 신고 [ ADDR : EDIT/ DEL ]