logo elektroda
logo elektroda
X
logo elektroda
Adblock/uBlockOrigin/AdGuard mogą powodować znikanie niektórych postów z powodu nowej reguły.

Program do ramienia z wykorzystanie 6 serwomechanizmów

Sukluk123 25 Lis 2017 01:23 1329 20
  • #1 16847315
    Sukluk123
    Poziom 7  
    Posty: 9
    Witam,
    Boryka się od miesiąca z problemem napisania programu do ramienia z wykorzystaniem pięciu serw(Redox L360 ; 4,8 V - 6,0 V). Chodzi mi oto aby program ( napisany w kompilatorze Arduino) mógł wykonać jeden prosty ruch np. Pierwsze serwo ma zmienić pozycje np. o 90°, drugie o 50 °, potem trzecie o 30° i czwarte o 10° i 5 serwa o 90° i wszystkie serwa mają odczekać np.10 sekund. Potem wszystkie serwa mają wrócić do pozycji sartowej. Chodzi mi głownie o szkic takiego przykładowego programu lub strony gdzie było by to wyjaśnione.
  • Pomocny post
    #2 16847411
    pitron
    Poziom 24  
    Posty: 811
    Pomógł: 51
    Ocena: 100
    Właściwie z czym masz problem?
    Użycie biblioteki <Servo.h> jest dosyć proste, kłopoty może sprawić obsługa czasu i wątków <timers.h> i <event.h>.
    Na początek próbuj z dealy.
    Pewnie poniższy kod już próbowałeś?
    Kod: C / C++
    Zaloguj się, aby zobaczyć kod
  • #3 16847864
    Sukluk123
    Poziom 7  
    Posty: 9
    A mógłbyś napisać program żeby jedno serwo obróciło się o 90 i zatrzymało się ? Wtedy bym już sobie poradził
  • #4 16848310
    pitron
    Poziom 24  
    Posty: 811
    Pomógł: 51
    Ocena: 100
    Może tak:

    Kod: C / C++
    Zaloguj się, aby zobaczyć kod


    Skompilował się bez błędów ale z braku czasu nie podłączałem serwa.
    Oczywiście bibliotekę servo.h masz w katalogi libraries.
  • #5 16848870
    Sukluk123
    Poziom 7  
    Posty: 9
    Wymyśliłem coś takiego:

    #include <Servo.h>

    Servo servo1;
    Servo servo2;
    Servo servo3;

    int i = 0;

    void setup() {
    servo1.attach(9);
    servo2.attach(3);
    servo3.attach(6);
    }
    //SERVO1

    void loop() {
    for (i = 0; i <= 90; i += 1) {
    servo1.write(i);
    delay(70);
    }

    for (i = 90; i >= 0; i -= 0) {
    servo1.write(i);
    }

    //SERVO2

    for (i = 0; i <= 100; i += 1) {
    servo2.write(i);
    delay(70);
    }

    for (i = 100; i >= 0; i -= 0) {
    servo2.write(i);
    }


    //SERVO3

    for (i = 0; i <= 180; i += 1) {
    servo3.write(i);
    delay(70);
    }

    for (i = 180; i >= 0; i -= 0) {
    servo3.write(i);
    }

    }

    Tylko mam taki problem że pętla for dla serwa1 ładnie działa i osiąga powoli swoją pozycje a kolejne pętle już tak jakby nie działają
  • #6 16848999
    krzysiek_krm
    Poziom 40  
    Posty: 4612
    Pomógł: 716
    Ocena: 599
    Czy ta pętla
    Sukluk123 napisał:
    for (i = 90; i >= 0; i -= 0) {
    servo1.write(i);
    }

    aby nie kręci się w kółko w nieskończoność ?
  • #7 16849135
    Sukluk123
    Poziom 7  
    Posty: 9
    To co zrobić żeby program wyszedł z tej petli? i w takim razie jak inaczej zrobić żeby serwa po kolei zmieniały swoją pozycje
  • Pomocny post
    #8 16849167
    BlueDraco
    Specjalista - Mikrokontrolery
    Posty: 6479
    Pomógł: 939
    Ocena: 421
    Przyjrzyj się tej pętli i popraw oczywisty błąd. Odejmowanie zera raczej nie spowoduje zmiany wartości zmiennej, na którą czekasz w tej pętli.
  • #9 16849176
    krzysiek_krm
    Poziom 40  
    Posty: 4612
    Pomógł: 716
    Ocena: 599
    Sukluk123 napisał:
    To co zrobić żeby program wyszedł z tej petli? i w takim razie jak inaczej zrobić żeby serwa po kolei zmieniały swoją pozycje

    Z opisu z pierwszego postu wynika, że pętle "cofania" serw w ogóle nie są potrzebne, serwa mają się cofnąć po zakończeniu całej sekwencji i upływie jakiegoś czasu.
  • #10 16849205
    Sukluk123
    Poziom 7  
    Posty: 9
    krzysiek_krm napisał:
    Sukluk123 napisał:
    To co zrobić żeby program wyszedł z tej petli? i w takim razie jak inaczej zrobić żeby serwa po kolei zmieniały swoją pozycje

    Z opisu z pierwszego postu wynika, że pętle "cofania" serw w ogóle nie są potrzebne, serwa mają się cofnąć po zakończeniu całej sekwencji i upływie jakiegoś czasu.


    //Ale jak usunę tą pętle cofania to serwa wracają do pozycji 0 i tak w kółko
    //Chodzi mi o to żeby te serwa pokolei powoli zaczeły sie zmieniać swoją pozycje, pierwsze servo o 90, drugie o 120, trzecie o 130 i czwarte o 10
    #include <Servo.h>

    Servo servo1;
    Servo servo2;
    Servo servo3;
    Servo servo4;

    void setup() {
    servo1.attach(9);
    servo2.attach(3);
    servo3.attach(5);
    servo4.attach(11);
    }
    void loop(){
    servo1.write (90);
    servo2.write(120);
    servo3.write(130);
    servo4.write(10);

    }

    //A następnie żeby wróciły do takich pozycji:
    servo1.write (180);
    servo2.write(50);
    servo3.write(50);
    servo4.write(10);
  • #11 16849219
    krzysiek_krm
    Poziom 40  
    Posty: 4612
    Pomógł: 716
    Ocena: 599
    Sukluk123 napisał:
    Ale jak usunę tą pętle cofania to serwa wracają do pozycji 0 i tak w kółko

    Niemożliwe, metoda "write" pamięta ostatnią nastawę, chyba że chodzi Ci o to, że po zakończeniu sekwencji tych serw, wszystko zaczyna się od początku, i tak w kółko.
    Wynika to z faktu, że "loop" kręci się w kółko w nieskończoność.
    Czy chcesz żeby sekwencja wykonała się dokładnie jeden raz po resecie, czy jakoś inaczej ?
  • #12 16849227
    Sukluk123
    Poziom 7  
    Posty: 9
    Ujmę to tak: Mam ramie i chcę zrobić program żeby to ramie wykonało jeden ruch i wrócił się z powrotem do pozycji ustalonej czyli:
    Po kolei
    1.Pierwsze serwo ma się obrócić o 90°
    2.Drugie servo o 120°
    3.Trzecie servo o 130°
    4.Czwarte servo o 10°
    5.Odczekać kilka sekund
    6.Następnie czwarte servo ma zmienić pozycje o 100°
    7.Trzecie o 50°
    8.Drugie o 50°
    9. Pierwsze o 60°
    10.I wszystko ma się zatrzymać
  • Pomocny post
    #13 16849244
    krzysiek_krm
    Poziom 40  
    Posty: 4612
    Pomógł: 716
    Ocena: 599
    Jeżeli ma się to wykonać tylko jeden raz możesz cały kod umieścić w "setup" (po wywołaniu wszystkich metod "attach") a "loop" zostawić puste, będzie się kręciła w nieskończoność nic nie robiąc.
    Wszystkie ruchy serw realizujesz za pomocą pierwszej pętli "for" z twojego postu #5, for (początek; koniec; zmiana), jeżeli "jedzie w górę" to zmiana jest i++ jeżeli "jedzie w dół" to zmiana jest i--.
    Opóźnienie to delay (tyle_ile_trzeba).
    Wykonując ruchy serw w drugiej fazie (po opóźnieniu) musisz zacząć ruch każdego serwa od miejsca, w którym skończyłeś jego ruch przed opóźnieniem a skończyć tam gdzie chcesz.
  • #14 16849964
    Sukluk123
    Poziom 7  
    Posty: 9
    OK, pomogło a jeszcze mam pytanie czy arduino ma funkcje zczytania aktualną pozycje serwa i dopiero od tej pozycji w której się znajduje wykonać ruch?
  • #15 16849968
    pitron
    Poziom 24  
    Posty: 811
    Pomógł: 51
    Ocena: 100
    Pętla loop jest po to żeby program cały czas działał.
    Jeżeli się jej pozbędziesz program pójdzie raz i koniec do następnego restartu całego układu.
    Możesz dodać warunek i przycisk którym będziesz aktywował kod wewnątrz loop na żądanie a loop niech sobie biega w kółko.
    Tak jak na początku pisałem zainteresuj się bibliotekami timers zamiast prostego delay.
  • #16 16849994
    Konto nie istnieje
    Konto nie istnieje  
  • #17 16850040
    Slawek K.
    Poziom 35  
    Posty: 3020
    Pomógł: 259
    Ocena: 1303
    Piotrus_999 napisał:
    Jedna zasadnicza uwaga: każde serwo jest inne. Mają inną szerokość impulsu dla punktu centalnego i punktów krańcowych. Bez kalibracji i ustalenia gdzie one są wszelkie wychylenia są mocno przybliżone.

    Jakie znaczenie ma to, gdzie jest neutrum w nie podłączonym do układu mechanicznego serwie ? żadne, zawsze jest w jakiejś pozycji, natomiast czym innym jest ustawienie pracy serwa w konkretnym układzie mechanicznym, robi się to łącznie, poprzez mechanikę (położenie orczyka na wieloklinie, długość i punkt mocowania cięgna itp.) oraz elektronicznie poprzez sztuczne tzw. przesunięcie neutrum oraz ograniczenia obu wychyleń.

    Pozdr
  • #18 16850142
    Sukluk123
    Poziom 7  
    Posty: 9
    Przechodząc do praktyki , to napisał by ktoś to przerwanie na timerze? lub napisał przykładowe komendy?
  • #19 16850189
    Konto nie istnieje
    Konto nie istnieje  
  • #20 16850655
    Sukluk123
    Poziom 7  
    Posty: 9
    No sporo, ale co to ma do timerów?
  • #21 16850741
    krzysiek_krm
    Poziom 40  
    Posty: 4612
    Pomógł: 716
    Ocena: 599
    Kilka kwestii, może trochę pobieżnie, nie jestem specjalistą od Arduino.
    Sukluk123 napisał:
    OK, pomogło a jeszcze mam pytanie czy arduino ma funkcje zczytania aktualną pozycje serwa i dopiero od tej pozycji w której się znajduje wykonać ruch?

    Jest to metoda "read":
    https://www.arduino.cc/en/Reference/ServoRead
    pitron napisał:
    Pętla loop jest po to żeby program cały czas działał.
    Jeżeli się jej pozbędziesz program pójdzie raz i koniec do następnego restartu całego układu.

    Dlatego otwartym tekstem zapytałem czy ma to się wykonać jeden raz, autor stwierdził, że tak więc "setup" się do tego w zupełności nadaje, to właśnie taki "run once".
    pitron napisał:
    Tak jak na początku pisałem zainteresuj się bibliotekami timers zamiast prostego delay.

    Jakkolwiek "delay" jest programowaniem metodą "łoma i siekiery", do tej aplikacji zupełnie dobrze się nadaje. Elegancko można odmierzać czas majstrując przy timerach, ewentualnie używając funkcji "millis" albo "micros" twórczo adaptując przykład z Arduino IDE pod tytułem "blink without delay", myślę że dla autora może to być nieco prostsze.
    Piotrus_999 napisał:
    Jedna zasadnicza uwaga: każde serwo jest inne. Mają inną szerokość impulsu dla punktu centalnego i punktów krańcowych. Bez kalibracji i ustalenia gdzie one są wszelkie wychylenia są mocno przybliżone.

    Z dokumentacji wynika, że metoda "attach":
    https://www.arduino.cc/en/Reference/ServoAttach
    ma możliwość podania parametrów kalibracyjnych, trzeba tę kalibrację wykonać doświadczalnie, co może być nieco niewygodne, ale możliwość jest.
    Można nawet realizować jakieś dziwaczne i nieliniowe charakterystyki za pomocą metody:
    https://www.arduino.cc/en/Reference/ServoWriteMicroseconds
    Zatem możliwości trochę jest.
    Sukluk123 napisał:
    Przechodząc do praktyki , to napisał by ktoś to przerwanie na timerze? lub napisał przykładowe komendy?

    Jak już wspomniałem, na początek możesz twórczo zmodyfikować przykład "blink without delay".

Podsumowanie tematu

✨ Użytkownik poszukuje pomocy w napisaniu programu do sterowania ramieniem robota z pięcioma serwomechanizmami (Redox L360) przy użyciu kompilatora Arduino. Program ma wykonywać sekwencję ruchów, w której każde serwo obraca się o określony kąt, a następnie wraca do pozycji początkowej po odczekaniu kilku sekund. W dyskusji poruszono kwestie dotyczące użycia biblioteki , obsługi czasu, oraz problemów z pętlami w kodzie. Uczestnicy sugerowali różne podejścia do realizacji sekwencji ruchów, w tym umieszczenie kodu w funkcji setup, aby wykonał się tylko raz, oraz wykorzystanie timerów zamiast prostego delay. Zwrócono również uwagę na konieczność kalibracji serwomechanizmów.
Podsumowanie AI na podstawie dyskusji. Może zawierać błędy.
REKLAMA