# X plane 模擬環境 ###### tags: `飛控` | 月份 | 週次(日期) | 內容 | | ---- | --------------------- | ------------------------------------------------------ | | Oct | I (Oct.10~OctOct.16) | 建立Xplane的環境 | | | II (Oct.17~Oct.23) | 使用UDP連結Xplane,傳輸數據至matlab| | | III (Oct.24~Oct.30) | 連結外部搖桿數據至matlab | | Nov | IV (Oct.31~Nov.6) |建立PID控制器控制姿態 | | | V (Nov.7~Nov.13) |debug | | | VI (Nov.14~Nov.20) |debug | | | VII (Nov.21~Nov.27) |先基於Cessna172調整PID參數使姿態 | | Dec | VIII (Nov.28~Dec.4) |定義新飛機氣動外型(TUNA T) | | | IX (Dec.5~Dec.11) |對自訂飛機調整PID控制器 | | | X (Dec.12~Dec.18) |收集飛行動態資料 | | | XI (Dec.19~Dec.26) |debug | | | XII (Dec.26~Jan.1) |debug | >[name=紀中威] >[name=蕭凡棋] ## 安裝Xplane 去到UAV雲端中-工具程式-Xplane10將所有相關東西下載並依序1~9執行一遍 ### 使用軟體 #### Xplane 10 #### Matlab 2022b ## 使用UDP連結Matlab ![](https://i.imgur.com/riZD1wb.png) 我們將使用 MATLAB 中 Simullink 透過UDP發送及接收Xplane模擬出來的飛行數據,也可以使用外接控制器去發送控制訊號 本次模擬皆是模擬定翼機,如果要試其他類型可以去 http://www.nuclearprojects.com/xplane/info.shtml ## Sending UDP datagrams ![](https://i.imgur.com/mXGRMfs.png) --- ### Input ![](https://i.imgur.com/riHZFQs.png) 輸入訊號可以使用各種的RC控制器,我是使用Logitech 3D extreme pro 透過UDP訊號輸入直接覆蓋在Xplane10中的操縱輸入 如果要使用Logitech 3D extreme pro 去以下網址下載驅動程式 https://support.logi.com/hc/zh-tw/articles/360024843033--%E4%B8%8B%E8%BC%89-Extreme-3D-Pro ![](https://i.imgur.com/bI9WkNg.png) 可以創建一個scope來監測操縱桿的訊號輸入是否正確 使用過程中怕訊號有出錯,所以我們需要創建一個calibrate block 來設定上下限 roll, pitch, yaw : -1 ~ 1 thrust : 0 ~ 1 --- ### Encoding and sending ![](https://i.imgur.com/5c5eQJV.png) 再來我們需要將訊號打包成Xplane 看得懂的訊號,來自控制桿的訊號為 double ,需要先使用Data Type Conversion 轉換成 single 在 轉成 8位無符號整數(uint8)。 ![](https://i.imgur.com/pr8T0Lw.png) 將Data Type Conversion block 中的 Output data type : [Inherit: Inherit via back propagation] 改成 Output data type : [single] 使用Byte pack 將單精度訊號打包成unit8 ![](https://i.imgur.com/0XKQlLU.png) --- #### UDP_encode ![](https://i.imgur.com/GGNgPPT.png) ![](https://i.imgur.com/ahmYyje.png) 可以勾選不同的頻道數量來決定我們需要進行人為控制的參數選項,調整右下的UDP rate 越大發送訊號的頻率會越高,下面11 25的部分就是我們介入pitch, roll, yaw, throttle的部分。Xplane10_Settings_Data inputs and outputs 中可以查看對應數字的控制參數頻道,但隨著版本不一樣可能有所不同 ``` function UDP = UDP_encode(roll_single, pitch_single, yaw_single, throttle_single) DATA = [68 65 84 65 48]; NULL = [0 192 121 196]; UDP_flightcon = [11 0 0 0 pitch_single' roll_single' yaw_single' NULL NULL NULL NULL NULL]; UDP_throttle = [25 0 0 0 throttle_single' NULL NULL NULL NULL NULL NULL NULL]; UDP = [DATA UDP_flightcon UDP_throttle]'; end ``` 傳送信號的最後一步,就是將訊號傳到Xplane10裡面,我們需要設定相同的IP address 和對應的port 確保有正確接收,在UDP Send Block 設定address & port ,如果是在同一台電腦上使用的話,可以打127.0.0.1就好,意思就是本台主機,X-Plane 默認接收端口是 49000 ,可以去Xplane 10_Net Connection_Data 中下面查看使用的UDP ports 如果使用不同台電腦,可以去cmd 中打ipconfig 中的IPV4 address 即是電腦IP位址 ![](https://i.imgur.com/gRllilp.png) ![](https://i.imgur.com/9KvzjEo.png) 發送成功的話會顯示,表示Xplane 10 成功接收來自simulink 中UDP 發送的訊號 ![](https://i.imgur.com/CaRstkM.png) --- ## Receiving UDP datagrams ![](https://i.imgur.com/Kr1W8el.png) 由於Xplane10 中49000 49001 49002 已經被定義使用我們可以將發送端口設置成 49003, --- ### UDP recieve ![](https://i.imgur.com/w549Kx5.png) ![](https://i.imgur.com/nz0ATc5.png) 將UDP Recieve Block 接收IP和address 改成 在Xplane10上面設定的一樣(0.0001改成0.1) #### **發現** 可以更改UDP recieve block 中的maximum length for message 來更改輸出數據的多寡, heading data = 5 bytes 資料長度所選 group of 4 bytes each 8 fields ![](https://i.imgur.com/cwnhDQ9.png) 已這張圖為例 maximum length for message = 8 * 9 * 4 + 5 = 293 --- ### UDP decode UDP decode 接收來自Recieve 的資料加以整理,輸出我們想要觀測的數據 每個頻道有 36bytes ,每個頻道編號分配 4bytes ``` % X-Plane: Channels 11, 17, 20 %-------------------------------------------------------------------------- % flight_con = [elev ailrn ruddr]; % flight controls % attitude = [pitch roll hding_true hding_mag]; % pitch, roll, yaw % location = [lat lon alt_msl alt_agl]; % latitude, longitude, altitude [deg],[ftmsl],[ftagl] (mean sea level, actual ground level) %-------------------------------------------------------------------------- function [elev, ailrn, ruddr, pitch, roll, hding_true, hding_mag, lat, lon, alt_msl, alt_agl] = UDP_decode(UDP) % We don't need the DATA header, which are the first 5 bytes UDP = UDP(6:end); % We cut the datagram in channels, each containing 36 bytes, 4 for the channel number, and 4 for each of the 8 entries. CH11 = UDP(1:36); CH17 = UDP(37:72); CH20 = UDP(73:108); %------------------------- % At last we extract each entry from their channel and output them. elev = Channel_to_single(CH11,1); ailrn = Channel_to_single(CH11,2); ruddr = Channel_to_single(CH11,3); pitch = Channel_to_single(CH17,1); roll = Channel_to_single(CH17,2); hding_true = Channel_to_single(CH17,3); hding_mag = Channel_to_single(CH17,4); lat = Channel_to_single(CH20,1); lon = Channel_to_single(CH20,2); alt_msl = Channel_to_single(CH20,3); alt_agl = Channel_to_single(CH20,4); %--------------------------------- end function [single] = Channel_to_single(CH, data_pos) start_byte = 1 + 4*data_pos; stop_byte = start_byte + 3; single = CH(start_byte:stop_byte); end ``` 傳出的訊號需要拆封成simulink可以讀取的訊號,加上Byte Unpack 並根據UDP decode 訊號輸出訊號調整數量及訊號型態,輸出的訊號可以用scope 來隨時監測 ![](https://i.imgur.com/ilCMSgV.png) ![](https://i.imgur.com/5T3uCZk.jpg) --- ### 將機型換成Cessna 172P 並對輸出數值做調整 **輸出訊號名稱** 1. speed 2. elevator 3. aileron 4. rudder 5. latitude 6. longitude 7. altitude {%youtube 6dRcyO_HCW4 %}