Thông báo

Collapse
No announcement yet.

Rắc rối giao tiếp với encoder

Collapse
X
 
  • Lọc
  • Giờ
  • Show
Clear All
new posts

  • Rắc rối giao tiếp với encoder

    Các pác cho đệ hỏi một vấn đề dễ nhưng vẫn đang hết sức đau đầu, đệ có 1 rotary encoder 2 channel sóng vuông lệch pha 90 độ, đệ cho channel 1 nối vào INT0 với thiết lập "rising edge", còn trong hàm interrupt thì poll channel còn lại:

    interrupt [EXT_INT0] void ext_int0_isr(void)
    {
    // Place your code here
    if(PIND.2==1) count++;
    else count--;
    }

    Điều quái gở là count lúc nào cũng nhận giá trị âm, bất chấp quay ngược quay xuôi. Chỉ đến khi đệ quay trục động cơ thật chậm bằng tay thì nó mới tăng lên nhưng cũng không đều, các pác cho hỏi vì sao vậy, encoder xem trên Oscilloscope thì bình thường, ko có vấn đề gì. Đệ cảm ơn trước.

  • #2
    Nếu A là sườn lên thì B thấp là tăng còn B cao là giảm.

    http://www.dientuvietnam.net/forums/...d.php?p=259138
    From MTA

    Comment


    • #3
      Nguyên văn bởi constfang Xem bài viết
      Các pác cho đệ hỏi một vấn đề dễ nhưng vẫn đang hết sức đau đầu, đệ có 1 rotary encoder 2 channel sóng vuông lệch pha 90 độ, đệ cho channel 1 nối vào INT0 với thiết lập "rising edge", còn trong hàm interrupt thì poll channel còn lại:

      interrupt [EXT_INT0] void ext_int0_isr(void)
      {
      // Place your code here
      if(PIND.2==1) count++;
      else count--;
      }

      Điều quái gở là count lúc nào cũng nhận giá trị âm, bất chấp quay ngược quay xuôi. Chỉ đến khi đệ quay trục động cơ thật chậm bằng tay thì nó mới tăng lên nhưng cũng không đều, các pác cho hỏi vì sao vậy, encoder xem trên Oscilloscope thì bình thường, ko có vấn đề gì. Đệ cảm ơn trước.
      Có thể là do đụng độ giữa các ngắt, ưu tiên ngắt ngoài thấp quá so với vài ngắt khác chăng? Đó chỉ là một suy đoán.
      The goal of power electronics is control the flow of energy from an electrical source to an electrical load with high efficiency, high availability, high reliability, light weight and low cost.

      Comment


      • #4
        Nó đã đếm khi bạn quay tức là hoạt động tốt. Khi bạn quay chậm mới được, như vậy là đã nhận đựoc tín hiệu đếm lên, còn khi quay nhanh thì do không nhận đựoc tín hiệu đếm lên, nên toàn đếm xuống thôi, bạn phải xử lý các mức ưu tiên ngắt thật hợp lý, tránh xung đột ngắt. Goodluck!
        Học đến bao giờ mới thành tài?

        Comment


        • #5
          Cảm ơn các pác, khốn nỗi đệ chưa viết gì hết, mới chỉ đang thử cái encoder nên ngoài cái ngắt ngoài kia gần như không còn cái ngắt nào khác, Có vẻ như thằng VXL ko đọc được PIND dương một cách chính xác mặc dù khi đệ thử cắm thẳng PD2 vào +5V thì count vẫn tăng như gió, còn khi để lại vào channel B thì quay thuận chiều 360 độ nó đọc đúng 1000counts nhưng đến khi quay ngược lại nó ko quay ngược về 0 mà lại tăng lên khoảng 1200counts. Đệ đang định chuyển sang cách mấy pác chỉ ở đây, dùng 2 ngắt một lúc: http://www.dientuvietnam.net/forums/...ad.php?t=32078 nhưng dù có làm được bằng cách khác thì chắc đệ sẽ ko bao giờ biết được thằng này bị sai chỗ nào quá...

          Comment


          • #6
            Nguyên văn bởi constfang Xem bài viết
            Cảm ơn các pác, khốn nỗi đệ chưa viết gì hết, mới chỉ đang thử cái encoder nên ngoài cái ngắt ngoài kia gần như không còn cái ngắt nào khác, Có vẻ như thằng VXL ko đọc được PIND dương một cách chính xác mặc dù khi đệ thử cắm thẳng PD2 vào +5V thì count vẫn tăng như gió, còn khi để lại vào channel B thì quay thuận chiều 360 độ nó đọc đúng 1000counts nhưng đến khi quay ngược lại nó ko quay ngược về 0 mà lại tăng lên khoảng 1200counts. Đệ đang định chuyển sang cách mấy pác chỉ ở đây, dùng 2 ngắt một lúc: http://www.dientuvietnam.net/forums/...ad.php?t=32078 nhưng dù có làm được bằng cách khác thì chắc đệ sẽ ko bao giờ biết được thằng này bị sai chỗ nào quá...
            Vậy vấn đề không phải do ngắt, vậy có lẽ bác cấu hình I/O chưa đúng, tốt nhất bác post cả đoạn code, và cho biết mình đang sài VDK nào?
            The goal of power electronics is control the flow of energy from an electrical source to an electrical load with high efficiency, high availability, high reliability, light weight and low cost.

            Comment


            • #7
              Đệ xài cái code generation của Codevision thì được, chỉ gắn thêm cái LCD để debug thôi chắc ko ảnh hưởng nhiều.
              /************************************************** ***
              Chip type : ATmega128
              Program type : Application
              AVR Core Clock frequency: 16.000000 MHz
              Memory model : Small
              External RAM size : 0
              Data Stack size : 1024
              ************************************************** ***/

              #include <mega128.h>
              #include <stdio.h>

              // Alphanumeric LCD Module functions
              #asm
              .equ __lcd_port=0x1B ;PORTA
              #endasm
              #include <lcd.h>

              int count=0;
              // External Interrupt 0 service routine
              interrupt [EXT_INT0] void ext_int0_isr(void)
              {
              // Place your code here
              if(PIND.2==0) count++;
              else count--;
              }


              // Declare your global variables here

              void main(void)
              {
              // Declare your local variables here
              char* a="fashfdskjfhsk";
              // Input/Output Ports initialization
              // Port A initialization
              // Func7=In Func6=In Func5=In Func4=In Func3=In Func2=In Func1=In Func0=In
              // State7=T State6=T State5=T State4=T State3=T State2=T State1=T State0=T
              PORTA=0x00;
              DDRA=0x00;

              // Port B initialization
              // Func7=In Func6=In Func5=In Func4=In Func3=In Func2=In Func1=In Func0=In
              // State7=T State6=T State5=T State4=T State3=T State2=T State1=T State0=T
              PORTB=0x00;
              DDRB=0x00;

              // Port C initialization
              // Func7=In Func6=In Func5=In Func4=In Func3=In Func2=In Func1=In Func0=In
              // State7=T State6=T State5=T State4=T State3=T State2=T State1=T State0=T
              PORTC=0x00;
              DDRC=0x00;

              // Port D initialization
              // Func7=In Func6=In Func5=In Func4=In Func3=In Func2=In Func1=In Func0=In
              // State7=T State6=T State5=T State4=T State3=T State2=T State1=T State0=T
              PORTD=0x00;
              DDRD=0x00;

              // Port E initialization
              // Func7=In Func6=In Func5=In Func4=In Func3=In Func2=In Func1=In Func0=In
              // State7=T State6=T State5=T State4=T State3=T State2=T State1=T State0=T
              PORTE=0x00;
              DDRE=0x00;

              // Port F initialization
              // Func7=In Func6=In Func5=In Func4=In Func3=In Func2=In Func1=In Func0=In
              // State7=T State6=T State5=T State4=T State3=T State2=T State1=T State0=T
              PORTF=0x00;
              DDRF=0x00;

              // Port G initialization
              // Func4=In Func3=In Func2=In Func1=In Func0=In
              // State4=T State3=T State2=T State1=T State0=T
              PORTG=0x00;
              DDRG=0x00;

              // Timer/Counter 0 initialization
              // Clock source: System Clock
              // Clock value: Timer 0 Stopped
              // Mode: Normal top=FFh
              // OC0 output: Disconnected
              ASSR=0x00;
              TCCR0=0x00;
              TCNT0=0x00;
              OCR0=0x00;

              // Timer/Counter 1 initialization
              // Clock source: System Clock
              // Clock value: Timer 1 Stopped
              // Mode: Ph. correct PWM top=00FFh
              // OC1A output: Discon.
              // OC1B output: Discon.
              // OC1C output: Discon.
              // Noise Canceler: Off
              // Input Capture on Falling Edge
              // Timer 1 Overflow Interrupt: Off
              // Input Capture Interrupt: Off
              // Compare A Match Interrupt: Off
              // Compare B Match Interrupt: Off
              // Compare C Match Interrupt: Off
              TCCR1A=0x01;
              TCCR1B=0x00;
              TCNT1H=0x00;
              TCNT1L=0x00;
              ICR1H=0x00;
              ICR1L=0x00;
              OCR1AH=0x00;
              OCR1AL=0x00;
              OCR1BH=0x00;
              OCR1BL=0x00;
              OCR1CH=0x00;
              OCR1CL=0x00;

              // Timer/Counter 2 initialization
              // Clock source: System Clock
              // Clock value: Timer 2 Stopped
              // Mode: Normal top=FFh
              // OC2 output: Disconnected
              TCCR2=0x00;
              TCNT2=0x00;
              OCR2=0x00;

              // Timer/Counter 3 initialization
              // Clock source: System Clock
              // Clock value: Timer 3 Stopped
              // Mode: Normal top=FFFFh
              // OC3A output: Discon.
              // OC3B output: Discon.
              // OC3C output: Discon.
              // Noise Canceler: Off
              // Input Capture on Falling Edge
              // Timer 3 Overflow Interrupt: Off
              // Input Capture Interrupt: Off
              // Compare A Match Interrupt: Off
              // Compare B Match Interrupt: Off
              // Compare C Match Interrupt: Off
              TCCR3A=0x00;
              TCCR3B=0x00;
              TCNT3H=0x00;
              TCNT3L=0x00;
              ICR3H=0x00;
              ICR3L=0x00;
              OCR3AH=0x00;
              OCR3AL=0x00;
              OCR3BH=0x00;
              OCR3BL=0x00;
              OCR3CH=0x00;
              OCR3CL=0x00;

              // External Interrupt(s) initialization
              // INT0: On
              // INT0 Mode: Rising Edge
              // INT1: Off
              // INT2: Off
              // INT3: Off
              // INT4: Off
              // INT5: Off
              // INT6: Off
              // INT7: Off
              EICRA=0x03;
              EICRB=0x00;
              EIMSK=0x01;
              EIFR=0x01;


              // Timer(s)/Counter(s) Interrupt(s) initialization
              TIMSK=0x00;
              ETIMSK=0x00;

              // Analog Comparator initialization
              // Analog Comparator: Off
              // Analog Comparator Input Capture by Timer/Counter 1: Off
              ACSR=0x80;
              SFIOR=0x00;

              // LCD module initialization
              lcd_init(16);

              // Global enable interrupts
              #asm("sei")

              while (1)
              {
              // Place your code here
              lcd_gotoxy(3,1);
              sprintf(a,"fsdfd %d",count);
              lcd_puts(a);

              };

              }

              Comment


              • #8
                Pó tay luôn, không nhìn ra bị sai chổ nào.
                The goal of power electronics is control the flow of energy from an electrical source to an electrical load with high efficiency, high availability, high reliability, light weight and low cost.

                Comment


                • #9
                  Có thể encoder của bạn là loại ngõ ra open collector, bạn cấu hình input lại không có trở kéo lên nên nó cho giá trị - là phải rồi.
                  Đặt PORTD =0xFF;
                  DDRD =0x00;
                  Hoặc dùng trở kéo lên cho chắc, chọn tầm 470-1k5.
                  Brs.

                  Comment


                  • #10
                    Nguyên văn bởi GA_CN Xem bài viết
                    Có thể encoder của bạn là loại ngõ ra open collector, bạn cấu hình input lại không có trở kéo lên nên nó cho giá trị - là phải rồi.
                    Đặt PORTD =0xFF;
                    DDRD =0x00;
                    Hoặc dùng trở kéo lên cho chắc, chọn tầm 470-1k5.
                    Brs.
                    Có thể đây là một problem chăng? Cái problem này mình đã từng gặp.
                    The goal of power electronics is control the flow of energy from an electrical source to an electrical load with high efficiency, high availability, high reliability, light weight and low cost.

                    Comment


                    • #11
                      Nguyên văn bởi GA_CN Xem bài viết
                      Có thể encoder của bạn là loại ngõ ra open collector, bạn cấu hình input lại không có trở kéo lên nên nó cho giá trị - là phải rồi.
                      Đặt PORTD =0xFF;
                      DDRD =0x00;
                      Hoặc dùng trở kéo lên cho chắc, chọn tầm 470-1k5.
                      Brs.
                      Chính là nó đấy pác, cảm ơn pác nhiều,
                      p/s: thú thực là đệ tìm ra rồi định lên đây khoe thì thấy pác đã chỉ ra từ... 10 ngày trước

                      Comment

                      Về tác giả

                      Collapse

                      constfang Tìm hiểu thêm về constfang

                      Bài viết mới nhất

                      Collapse

                      Đang tải...
                      X