PWM servosignál - Arduino - převod na STEP/DIR

Dneska se procesory objevují všude, pokud máte nějaký nápad, či udělát, tak se neváhejte pochlubit.
Zpráva
Autor
guchar
Příspěvky: 8243
Registrován: čtv 07.05.2015 16:24
Bydliště: ČR

Re: PWM servosignál - Arduino - převod na STEP/DIR

#16 Příspěvek od guchar »

@jyrry V počátku čtení jsem toho hodně přeskočil. Se zpožděním se zač. "rozkoukávám". A mini-Orientovat.
V záhlaví máš psáno
" // AVR Timer CTC Interrupts Calculator
// v. 8 "
Plyne z toho že používáš: (Changelog) // v. 8 - ATtiny84 ?
" ATtiny84
ATtiny24, ATtiny44.
Timer0 - 8-bit
Timer1 - 16-bit"
! Stránka neskáče sama přímo na OKÉNKO "About" . Na volbu (OKÉNKO) "About" nutno kliknout !
http://www.arduinoslovakia.eu/application/timer-calculator#tab_about
Uživatelský avatar
jyrry
Příspěvky: 22016
Registrován: pon 28.02.2005 0:00
Bydliště: Rakovník
Kontaktovat uživatele:

Re: PWM servosignál - Arduino - převod na STEP/DIR

#17 Příspěvek od jyrry »

guchar píše:...

Používám destičku "Arduino nano" nebo "Arduino Pro mini" s ATmega328P.
jyrry.webnode.cz
Uživatelský avatar
jyrry
Příspěvky: 22016
Registrován: pon 28.02.2005 0:00
Bydliště: Rakovník
Kontaktovat uživatele:

Re: PWM servosignál - Arduino - převod na STEP/DIR

#18 Příspěvek od jyrry »

ellet píše:... Ta se ale nesmí potkat a nevidím tam žádný ošetření...

No, to mě taky napadlo, že se to nějak potkává a ošetřit to (snad zatím) neumím :oops:
Otáčení krokáče tak nějak funguje, zlobí spíš tohle:

Kód: Vybrat vše

  #define input 2 // vstup PWM
  #define output  4 // vystup PWM
  #define led  13 // pin LED
  const int hystereze = 30;
  const int neutral_uS = 1500;
  const int min_uS = 900;
  const int max_uS = 2080;
  int out_uS = 1500;
  int cislo;
  long int new_uS;

void setupTimer1() {
  noInterrupts();
  // Clear registers
  TCCR1A = 0;
  TCCR1B = 0;
  TCNT1 = 0;
  TIMSK1 = 0;  // Clear the interrupt mask
 
  // Hz (16000000/((OCR1A + 1) * 256))
  OCR1A = 1249;
  // CTC
  TCCR1B |= (1 << WGM12);
  // Prescaler 256
  TCCR1B |= (1 << CS12);
  // Output Compare Match A Interrupt Enable
  TIMSK1 |= (1 << OCIE1A);
  interrupts();
}

void setup() {
  pinMode(led, OUTPUT); // LED
  pinMode(input, INPUT_PULLUP); // input PWM
  pinMode(output, OUTPUT);  // output servo
  setupTimer1();
  attachInterrupt(0, puls_start, RISING);
  delay(500);
  Serial.begin(115200);
}

void loop() {
    if (cislo > hystereze) {
    digitalWrite(led, HIGH);
    cislo = cislo / 40;
    if(new_uS < neutral_uS) {
      if(out_uS > min_uS) out_uS = out_uS - cislo;
    }
    if(new_uS > neutral_uS) {
      if(out_uS < max_uS) out_uS = out_uS + cislo ;
    }
  }
  else digitalWrite(led, LOW);
}

void puls_start() {
  new_uS = micros();
  attachInterrupt(0, puls_end, FALLING); 
  }

void puls_end() {
  new_uS = micros() - new_uS;
  new_uS = min(new_uS, max_uS);
  new_uS = max(new_uS, min_uS);
  cislo = abs(new_uS - neutral_uS);
  tisk();
  attachInterrupt(0, puls_start, RISING);
}

ISR(TIMER1_COMPA_vect) {
  digitalWrite(output, HIGH);
  delayMicroseconds(out_uS);
  digitalWrite(output, LOW);
}

void tisk() {
  Serial.println(cislo); 
}

Je to hýbání servem "jako hydraulickým válcem"; pořešil jsem to tak že načte impulz a hned po něm vygeneruje impulz pro servo, není tedy třeba ten výstup časovat timerem:

Kód: Vybrat vše

  #define input 2 // vstup PWM
  #define output  4 // vystup PWM
  #define led  13 // pin LED
  const int hystereze = 30;
  const int neutral_uS = 1500;
  const int min_uS = 900;
  const int max_uS = 2080;
  int out_uS = 1500;
  int cislo;
  long int new_uS;

void setup() {
  pinMode(led, OUTPUT); // LED
  pinMode(input, INPUT_PULLUP); // input PWM
  pinMode(output, OUTPUT);  // output servo
  attachInterrupt(0, puls_start, RISING);
  delay(500);
  // Serial.begin(115200);
}

void loop() {
delay(10);   
}

void puls_start() {
  new_uS = micros();
  attachInterrupt(0, puls_end, FALLING); 
  }

void puls_end() {
  new_uS = micros() - new_uS;
  new_uS = min(new_uS, max_uS);
  new_uS = max(new_uS, min_uS);
  cislo = abs(new_uS - neutral_uS);
  vypocet();
  puls();
  // tisk();
  attachInterrupt(0, puls_start, RISING);
}

void vypocet() {
  if (cislo > hystereze) {
    digitalWrite(led, HIGH);
    cislo = cislo / 40;
    if(new_uS < neutral_uS) {
      if(out_uS > min_uS) out_uS = out_uS - cislo;
    }
    if(new_uS > neutral_uS) {
      if(out_uS < max_uS) out_uS = out_uS + cislo ;
    }
  }
  else {
    cislo = 0;
    digitalWrite(led, LOW);
  }
}

void puls() {
  digitalWrite(output, HIGH);
  delayMicroseconds(out_uS);
  digitalWrite(output, LOW);
}

void tisk() {
  Serial.println(cislo); 
}
jyrry.webnode.cz
guchar
Příspěvky: 8243
Registrován: čtv 07.05.2015 16:24
Bydliště: ČR

Re: PWM servosignál - Arduino - převod na STEP/DIR

#19 Příspěvek od guchar »

@jyrry Dík. Timer1 je u ATmega328P ten 16-bit (ty dva další Timers (0 a 2) jsou 8-bitové. Potom ale podle
" Microcontrollers -- ATmega328P
Arduino Uno, Arduino Pro Mini.
ATmega48A, ATmega48PA, ATmega88A, ATmega88PA, ATmega168A, ATmega168PA, ATmega328 "
- Tomuhle zatím nějak plně nerozumím. I když asi možná náhrada za ATmega328 je (picoPower) ATmega328P
(A common alternative to the ATmega328 is the "picoPower" ATmega328P.) https://en.wikipedia.org/wiki/ATmega328 )
Každopádně bych měl cukání sáhnout po
"Changelog: v. 3 - More ATmega328P microcontrollers + sorting"
- Nestačilo by k otáčení věže rozlišeni délky impulzu s krokem 10 ms <150, 200> ?
Uživatelský avatar
ellet
Příspěvky: 2401
Registrován: pát 12.02.2016 11:37
Bydliště: Vysočina, ČR

Re: PWM servosignál - Arduino - převod na STEP/DIR

#20 Příspěvek od ellet »

jyrry píše:..Otáčení krokáče tak nějak funguje, zlobí spíš tohle...
Asi proto, že vlivem přerušení může dojít ke změně proměnných při výpočtu v loop().
Ale to druhý by snad mělo chodit. Ještě ty proměnný volatile a vyhodil bych i delay(10) jen pro lepší pocit (na funkci se to asi neprojeví). Taky bych uvažoval o načtení středový polohy v setup() místo tvrdé konstanty ale to už je zase o něčem jiným.
Uživatelský avatar
ellet
Příspěvky: 2401
Registrován: pát 12.02.2016 11:37
Bydliště: Vysočina, ČR

Re: PWM servosignál - Arduino - převod na STEP/DIR

#21 Příspěvek od ellet »

No, tak jsi mě donutil :) , to testnout. Řekl bych, že sketch_2 je použitelný ale asi bych to řešil úplně bez přerušení. Jestli to má být ale trochu i cvičení, tak proč ne.
Uživatelský avatar
jyrry
Příspěvky: 22016
Registrován: pon 28.02.2005 0:00
Bydliště: Rakovník
Kontaktovat uživatele:

Re: PWM servosignál - Arduino - převod na STEP/DIR

#22 Příspěvek od jyrry »

ellet píše:... Řekl bych, že sketch_2 je použitelný ...

Slává :-D
Jo, mám to i s pulseIn ale to se mi nelíbí :-)
jyrry.webnode.cz
Uživatelský avatar
ellet
Příspěvky: 2401
Registrován: pát 12.02.2016 11:37
Bydliště: Vysočina, ČR

Re: PWM servosignál - Arduino - převod na STEP/DIR

#23 Příspěvek od ellet »

jyrry píše:... to se mi nelíbí :-)
To beru :D , já určitě souhlasím s přerušením při čtení pulzu, bude přesnější, jen někdy to není úplně potřeba (není jen pulseIn). Ale hlavně - ať to jde dál podle představ!
Uživatelský avatar
jyrry
Příspěvky: 22016
Registrován: pon 28.02.2005 0:00
Bydliště: Rakovník
Kontaktovat uživatele:

Re: PWM servosignál - Arduino - převod na STEP/DIR

#24 Příspěvek od jyrry »

ellet píše:... (není jen pulseIn). ...

Můžeš třeba jen naznačit? :-)
Měl jsem něco na věcech s PICy, možná to najdu... něco jako opakované čtení pinu a reakce na impulz...
jyrry.webnode.cz
Uživatelský avatar
ellet
Příspěvky: 2401
Registrován: pát 12.02.2016 11:37
Bydliště: Vysočina, ČR

Re: PWM servosignál - Arduino - převod na STEP/DIR

#25 Příspěvek od ellet »

Myslím to dřiv tak, že pokud ti funkce nevyhovuje, asi nebudeš první. Je proto dost reálný předpoklad, že něco v těch balících knihoven na netu, najdeš. Hodnota vrácená pulseIn se dá dál upravit (na př. přepočtem za cenu zpoždění, nebo zahodit nějaký nejnižší bit za cenu "hrubšího" rozlišení - bitshift ). Já osobně 1000 poloh na přejezd serva nikdy nepotřebuju (a chtěl bych vidět modeláře jak si říká - teď výškovku na 1652uS :) ). V řadě případů, při požadavku vlevo-stop-vpravo je, přesnost (a stabilita) hodnoty vrácené touto funkcí vlastně nadbytečná. Vlastní "tvorba", proč ne, taky používám někdy k zachycení hodnoty pinu assembler. Třeba realizace převodníku pwm na ppm vyjde celá v assembleru až školácky jednoduchá (ATtiny13, 4k. pro simulátor).
Cesta k měření délky pulsu s maximální přesností je jen přes přerušení, s obsluhou jen toho co je nutný, to je jasný
guchar
Příspěvky: 8243
Registrován: čtv 07.05.2015 16:24
Bydliště: ČR

Re: PWM servosignál - Arduino - převod na STEP/DIR

#26 Příspěvek od guchar »

Nějaký ten sketch, k inspiraci pro měření RC impulzů
PulseMeter - přípravek s výstupem 13 + 2 LED, AT89C2051
http://www.bezstarosti.cz/jungle/puls/puls.htm
http://www.bezstarosti.cz/jungle/puls/puls.asm
Reading PWM Signals From An RC Receiver With Arduino
http://www.camelsoftware.com/2015/12/25/reading-pwm-signals-from-an-rc-receiver-with-arduino/
How to Get an Arduino Micros() Function With 0.5us Precision
https://www.instructables.com/id/How-to-get-an-Arduino-micros-function-with-05us-pr/

- měření otáček 0 až 166 Hz (9900 ot./min.), Arduino Nano 328P,
mimo další pozn.: " ... příkaz Pulse spolehlivě funguje do 1kHz ..."
http://www1.fs.cvut.cz/stretech/2017/sbornik_2017/pdf/46.pdf
Jaksi jsem tam neviděl (možná přehlédl) rozbor - ošetření možných zákmitů magnetického jazýčku.
Uživatelský avatar
ellet
Příspěvky: 2401
Registrován: pát 12.02.2016 11:37
Bydliště: Vysočina, ČR

Re: PWM servosignál - Arduino - převod na STEP/DIR

#27 Příspěvek od ellet »

"Příkaz Pulse", jak píše autor prezentace, ve Wiringu neznám, funkce pulseIn by měla pracovat od 10uS (viz stránky Arduino). Je možné, že má vlastní konstrukci Pulse na kterou se omezení vztahuje (třeba i z důvodu ošetření zákmitů).
guchar
Příspěvky: 8243
Registrován: čtv 07.05.2015 16:24
Bydliště: ČR

Re: PWM servosignál - Arduino - převod na STEP/DIR

#28 Příspěvek od guchar »

@ellet Vyjádření "Pulse" použil autor Ondřej Nevosad v kap. 6. Závěr. V 4.1 Měření otáček a 4.2 Měření napětí
už používá vyjádření-označení "pulseIn" jak v TEXTU tak v SKETCHs příkazech v souladu s
https://www.arduino.cc/en/Reference.PulseIn
https://www.arduino.cc/reference/en/language/functions/advanced-io/pulsein/
- Věta: "Metoda měření délky periody byla vybrána kvůli jednoduché programové realizaci
příkazem Pulse (pozn.: pulseIn(pin value), které spolehlivě funguje do 1kHz."
tedy platí pro jeho výrobek, aniž by rozváděl proč. Nebo uvedl zmínku o možných úpravách-změnách.
==edit02 Arduino PulseIn versus PulseInLong podrobný popis, včetně zdrojových kódů EN
https://www.best-microcontroller-projects.com/arduino-pulsein.html
Uživatelský avatar
ellet
Příspěvky: 2401
Registrován: pát 12.02.2016 11:37
Bydliště: Vysočina, ČR

Re: PWM servosignál - Arduino - převod na STEP/DIR

#29 Příspěvek od ellet »

guchar píše:... 4.2 Měření napětí už používá vyjádření-označení "pulseIn" ...
Autor má trochu nepořádek v nadpisech. Ten nadpis (4.2 Měření napětí), patří až pod sekvenci s pulseIn. Ne, že by nešlo ze střídy a špičkového napětí měřených pulsů nějaké napětí spočítat (efektivní nebo střední hodnotu toho signálu) ale tím se v této práci nezabývá. Dál bych to ani nerozebíral, je to práce studenta technického směru. Jen jsem považoval za důležité upozornit na originální dokumentaci pro studium vestavěných funkcí jazyka Wiring.
guchar
Příspěvky: 8243
Registrován: čtv 07.05.2015 16:24
Bydliště: ČR

Re: PWM servosignál - Arduino - převod na STEP/DIR

#30 Příspěvek od guchar »

Když vkládal SKETCH - obrázek, chtěl jej dát na konec 4.1 Místo je na začátku 4.2 To se stane i v lepších rodinách
- Šlo o prezentaci na workshopu. Přihlášení a výběr prací byl ponechán na uvážení vedení středních škol.
Neb jde o reprezentaci školy, mělo to jít přes připomínky spolu-studentů a vedení. Taky jim to uteklo. njn
https://aktualne.cvut.cz/tiskove-zpravy/20170606-prezentace-odbornych-projektu-stredoskolaku-to-je-strtech-2017-na-cvut-v
Odpovědět

Zpět na „Procesory a jiné vychytávky“