a szervó motor és a potméter beillesztve, állító és visszajelző kar a helyén, van kerete már és előlapja.
a szervó motor és a potméter beillesztve, állító és visszajelző kar a helyén, van kerete már és előlapja.
FSX-ből sikerült kinyerni a fékszárny állapojelző értékét, ezt eljuttatni egy arduinóra, ahol a szervó motor ennek megfelelő állapotba fordul.
Ahhoz, hogy a repszimből valahogy kinyerjük az adatokat szükségünk van valamiféle API-ra, amin keresztül hozzáférünk lehetőleg mindenhez. Az FSUIPC ad nekünk egy SDK-t is, amivel tudunk Microsoft Flight Simulator verzióihoz (nekem konkrétan FSX SE van felrakva) és Prepar3d-hez kapcsolódni, onnan adatot kinyerni, módosítani .
Az SDK-ban jópár programozási nyelvhez találunk APIt. Pl VisualBasic, C, C#, .NET, Delphi, Python, Java.
A C és a Java API-kat néztem meg, a többiről nem nagyon tudok nyilatkozni. Mivel Java fejlesztésben van sok tapasztalatom, megpróbálok ezzel megvalósítani mindent. Azért azt meg kell említenem, hogy rengeteg időt fordítottam a C-re is. Van egy nagyon nagy előnye a C API-nak a Java-hoz képest. Ez pedig nem más, hogyha Arduinóra akarunk adatot küldeni, akkor a C típusok gyakorlatilag megegyeznek az Arduino típusokkal. Ez nagyon leegyszerűsíti azt a folyamatot, amikor egy integer-t, byte-ot vagy long adatot akarunk az Arduinóra küldeni vagy onnan fogadni. Java esetében kicsit ügyeskedni kell, hogy megfelelően értelmezze mind a két oldal.
Na de nézzük a Java API-t. A build path-ra rátesszük az fsuipc.jar-t és beállítjuk a native libraryt is hozzá (fsuipc_java.dll). A native library beállítása az alábbi képen, ez a project settings / Java Build path / Libraries fülön lesz. Itt a dll-t tartalmazó könyvtárat kell megadni.
Ezek után nincs más dolgunk, mint a com.flightsim.fsuipc.fsuipc_wrapper osztályt importálni és ennek a statikus függvényeivel tudunk is dolgozni. Az összedobott kis programomban két függvényt használok.
public static synchronized native int Open(int arg0);
Kapcsolódás a szimulátorhoz. Egy paramétere van, amivel a szimulátor típusát adhatjuk meg. Használjuk az fsuipc_wrapper.SIM_ANY konstanst és akkor bármihez tud csatlakozni, ami épp fut. Visszatérési értéke 0, ha sikertelen a csatlakozás.
void ReadData(int arg0, int arg1, byte[] arg2);
Ezzel lehet kiolvasni egy adott címről valamit. A címet az arg0 helyén adjuk meg, arg1 lesz, hogy hány byte-ot akarunk, arg2 pedig a byte tömb, ahova bepakolja.
FSUIPC4 Offsets Status.pdf
A legjobb, ha már a legelején elkezdünk barátkozni az offset status doksival. Ez voltaképp egy jó nagy táblázat, ahol fel van sorolva minden cím, ott milyen adat található, milyen hosszon, és hogy mit csinálhatunk vele (olvashatjuk/írhatjuk). A programomban a flaps állapotjelzőjének az állását olvasom ki, ez a sor így néz ki a pdf-ben:
Offset | Size | Use | FSX Read | FSX Write |
0BE0 | 4 | Flaps position indicator (left). This gives the proportional amount, with 16383=full deflection. It doesn’t correspond to the equally spaced notches used for the control lever. If you know the maximum deflection angle you can derive the current angle by ((max * position indicator) / 16383). This only gives the (inboard?) trailing edge flaps. Please see offsets 30E0–30FF for greater details where needed. | Ok-SimC* (see note) |
No |
Ebből látjuk, hogy ez egy 4 byte-os adat, értékkészlete 0-16383. Voltaképp 2 byte elég lenne a tárolásához, nem igazán értem miért van mégis 4-en. Mindenesetre ezen gyorsan túllépve a következő kérdés az, hogyan csináljak ebből egy használható számot. Erre tökéletes a java.nio.ByteBuffer, valahogy így:
ByteBuffer wrapped = ByteBuffer.wrap(inputData);
int tmpi = wrapped.getInt();
Egy érdekesség még van itt: ahhoz hogy a ByteBuffert használni tudjam az int készítéshez, meg kell fordítanom a szimulátortól kapott byte tömböt.
A teljes java kódot innen tudod letölteni.
A működésről egy rövid videó:
Néhány gondolat a villanymotorokról. Három alapvető típusát említeném meg
DC Motor
Ez talán a legegyszerűbb, egy sima egyenáramú avagy DC motor.
Két lába van, feszültséget kapcsolunk rá, a polaritástól függően óramutató járásával megegyező vagy ellentétes irányba forogni kezd. A feszültség nagyságával szabályozhatjuk a sebességét.
A DC motor akkor hasznos, ha (meglepő módon) azt szeretnénk, hogy valami forogjon. Addig elég egyszerű dolgunk van, amíg nem akarjuk a sebességét vagy az irányát szabályozni, hanem valamilyen módon előre beállítva csak forgatni. Ezt egy arduino egyetlen digitális lábával vezérelhetjük. A dolog bonyolódik, ha az irányát és a sebességét is akarjuk változtatni. Ebben az esetben már mindenképp szükségünk lesz egy motorvezérlő áramkörre. Építhetünk ilyet, vagy veszünk egy IC-t, mint pl az L293D - Dual Full Bridge MotorDriver. Ezzel meghatározhatjuk a forgás irányt és a forgás sebességét is. Az irányhoz két digitális lábra van szükség, a sebességhez pedig egy harmadikra, ami PWM képes.
A PWM a pulse-width modulation, azaz impulzusszélesség moduláció rövidítése. Ha nem akarsz belemélyedni, annyit kell tudnod, hogy minden arduinónak van néhány digitális lába, amiken képes ezt a jelet összeállítani, neked csak annyi dolgod van, hogy a megfelelő lábakat használd. Ezen a lábon így nem csak 0 és 1 értéket tudsz küldeni, hanem az analogWrite() segítségével 0-255 közötti értéket, ami 0-5V-nak felel meg. Az arduino oldalán találsz egy részletesebb leírást erről.
Szervó motor
Egy szervó motornak 3 kivezetése van. Kettő szolgál a tápellátásra (+5V és GND), a harmadikkal pedig azt adjuk meg, hogy milyen állapotba mozduljon a motor. Ez nem arra való, hogy körbe-körbe forgassunk vele dolgokat, hisz jellemzően 180 fok körül van a maximális elfordulása. Az SG90-es mikro szervó motor pl 5V-os. Ha 5 voltot adunk a jel lábára, akkor maximális kitérésre áll az egyik irányban, 0-nál a másik irányban. Értelemszerűen köztes modulált feszültségeknél százalékosan a megfelelő köztes állapotba. Arduinóval egyszerű vezérelni, van külön Servo könyvtár hozzá, aminek segítségével egyetlen utasítással a kívánt állapotba lehet állítani (itt arra kell figyelni, hogy PWM képes lábát kell használni a boardnak a modulált jel küldéséhez).
Amit még jó tudni róla, hogy ha megkapja a tápfeszültséget, akkor beáll a motor a jel lábon érkező állapotba, ha onnan külső erővel kimozdítod, ellenáll (fékez), illetve visszamozdul azonnal. Ha nem kap tápot, akkor viszont szabadon forgatható (a saját 180fokos elfordulásán belül).
Egy ilyen szervó motor kiválóan alkalmas lehet a fékszárny visszajelző mozgatásához. Ott nagyjából csak 90fokos elfordulásra lesz szükség, és csak egy lábat visz el a vezérléshez.
Stepper vagy léptetőmotor
Ez a motor tud körbe-körbe forogni, igazából mégsem arra lett kitalálva, hogy pörgessünk vele bármit is. Sokkal inkább arra, ha valamit precíziósan akarunk mozgatni. A vezérléséhez célszerű az adott léptetőmotorhoz való motorvezérlőt megvenni, általában ezt a motorral együtt csomagban is rendelheted. Én is így tettem.
Na de hogy is működik? Ami nekem van, az egy unipoláris léptetőmotor. 4 elektromágnes van benne 90 fokonként elhelyezve. A vezérlés abból áll, hogy megmondom melyik mágnes legyen áram alatt, azaz melyik húzzon. Ekkor a motor tengelye, abba az irányba fordul be. Ha azt szeretném, hogy forogjon a motor, akkor ennek megfelelően rövid időközönként sorba kell bekapcsolnom a következő mágnest, kikapcsolni az előzőt. Ez nagyon jó, amikor pontos elmozdulásokat szeretnék elérni anélkül, hogy valami külső eszközzel mérnénk, hogy épp hogy áll a tengely. Ezek a léptetőmotorok a teljesítményhatárukon belül biztosan lépnek egyet. Nyilván, ha sikerül fizikailag megakadályozni a tengely elfordulását, akkor a motor nem biztos, hogy abban az állapotban lesz, ahol azt a vezérlés oldalról gondoljuk. Ezt azért mérlegelni kell mikor egy ilyen vezérlést összerakunk. Ilyen motorokat használnak amúgy 3D nyomtatókban is, hisz ott is a precizitás a fontos. A szimulátorban még nem látom hol lesz ez jó. Ha a forgó mechanikus műszereket le akarnám gyártani ahelyett, hogy monitoron megjelenítem, valószínű ott ez lenne a befutó.
Vezérlése amúgy 4 lábat visz el az arduinóról, a 4 elektromágnesnek megfelelően.
Röviden ennyi a motorok összehasonlításáról. A fékszárnyak állapotjelzéséhez szervó motort fogok használni, az tűnik a leghatékonyabbnak és legegyszerűbbnek erre a feladatra.
10 percben videóban összefoglalva mindez: