mirror of https://github.com/ArduPilot/ardupilot
179 lines
5.1 KiB
Lua
179 lines
5.1 KiB
Lua
--[[ Upon Arming , creates a four item mission consisting of: NAV_TAKEOFF, DO_LAND_START,Final Approach WP opposite bearing from HOME of heading used during takeoff, at TKOFF_ALT or SCR_USER3 above home, SCR_USER2 or 2X TKOFF_DIST, and a LAND waypoint at HOME and stops until next disarm/boot. SCR_USER1 is used to enable or disable it.
|
|
--]]
|
|
local MAV_SEVERITY = {EMERGENCY=0, ALERT=1, CRITICAL=2, ERROR=3, WARNING=4, NOTICE=5, INFO=6, DEBUG=7}
|
|
|
|
local PARAM_TABLE_KEY = 80
|
|
local PARAM_TABLE_PREFIX = "AUTOLAND_"
|
|
assert(param:add_table(PARAM_TABLE_KEY, PARAM_TABLE_PREFIX, 4), 'could not add param table')
|
|
|
|
-- add a parameter and bind it to a variable
|
|
function bind_add_param(name, idx, default_value)
|
|
assert(param:add_param(PARAM_TABLE_KEY, idx, name, default_value), string.format('could not add param %s', name))
|
|
return Parameter(PARAM_TABLE_PREFIX .. name)
|
|
end
|
|
|
|
--[[
|
|
// @Param: AUTOLAND_ENABLE
|
|
// @DisplayName: AUTOLAND ENABLE
|
|
// @Description: enable AUTOLAND script action
|
|
// @Values: 0:Disabled,1:Enabled
|
|
// @User: Standard
|
|
--]]
|
|
local AULND_ENABLE = bind_add_param('ENABLE', 1, 1)
|
|
local enable = AULND_ENABLE:get()
|
|
|
|
--[[
|
|
// @Param: AUTOLAND_WP_ALT
|
|
// @DisplayName: Final approach waypoint alt
|
|
// @Description: Altitude of final approach waypoint created by script
|
|
// @Range: 1 100
|
|
// @Units: m
|
|
// @User: Standard
|
|
--]]
|
|
local AULND_ALT = bind_add_param('WP_ALT', 2, 0)
|
|
local final_wp_alt = AULND_ALT:get()
|
|
--[[
|
|
// @Param: AUTOLAND_WP_DIST
|
|
// @DisplayName: Final approach waypoint distance
|
|
// @Description: Distance from landng point (HOME) to final approach waypoint created by script in the opposite direction of initial takeoff
|
|
// @Range: 0 1000
|
|
// @Units: m
|
|
// @User: Standard
|
|
--]]
|
|
local AULND_DIST = bind_add_param('WP_DIST', 3, 0)
|
|
local final_wp_dist = AULND_DIST:get()
|
|
|
|
FRAME_GLOBAL = 3
|
|
NAV_WAYPOINT = 16
|
|
NAV_TAKEOFF = 22
|
|
NAV_LAND = 21
|
|
DO_LAND_START = 189
|
|
|
|
TAKEOFF_PITCH = 15
|
|
|
|
local function wrap_360(angle)
|
|
local res = math.fmod(angle, 360.0)
|
|
if res < 0 then
|
|
res = res + 360.0
|
|
end
|
|
return res
|
|
end
|
|
|
|
local function wrap_180(angle)
|
|
local res = wrap_360(angle)
|
|
if res > 180 then
|
|
res = res - 360
|
|
end
|
|
return res
|
|
end
|
|
|
|
function create_final_approach_WP(i,bearing,dist,alt) --index,degs,m,m
|
|
local item = mavlink_mission_item_int_t()
|
|
local loc = ahrs:get_home()
|
|
loc:offset_bearing(bearing,dist) ---degs and meters
|
|
|
|
item:seq(i)
|
|
item:frame(FRAME_GLOBAL)
|
|
item:command(NAV_WAYPOINT)
|
|
item:param1(0)
|
|
item:param2(0)
|
|
item:param3(0)
|
|
item:param4(0)
|
|
item:x(loc:lat())
|
|
item:y(loc:lng())
|
|
item:z(alt)
|
|
return item
|
|
end
|
|
|
|
function create_takeoff_WP(alt)
|
|
local item = mavlink_mission_item_int_t()
|
|
local loc = ahrs:get_home()
|
|
|
|
item:seq(1)
|
|
item:frame(FRAME_GLOBAL)
|
|
item:command(NAV_TAKEOFF)
|
|
item:param1(TAKEOFF_PITCH)
|
|
item:param2(0)
|
|
item:param3(0)
|
|
item:param4(0)
|
|
item:x(loc:lat())
|
|
item:y(loc:lng())
|
|
item:z(alt)
|
|
return item
|
|
end
|
|
|
|
function create_land_WP()
|
|
local item = mavlink_mission_item_int_t()
|
|
local loc = ahrs:get_home()
|
|
|
|
item:seq(4)
|
|
item:frame(FRAME_GLOBAL)
|
|
item:command(NAV_LAND)
|
|
item:param1(15)
|
|
item:param2(0)
|
|
item:param3(0)
|
|
item:param4(0)
|
|
item:x(loc:lat())
|
|
item:y(loc:lng())
|
|
item:z(0)
|
|
return item
|
|
end
|
|
|
|
function create_do_land_start_WP()
|
|
local item = mavlink_mission_item_int_t()
|
|
|
|
item:seq(2)
|
|
item:frame(FRAME_GLOBAL)
|
|
item:command(DO_LAND_START)
|
|
item:param1(0)
|
|
item:param2(0)
|
|
item:param3(0)
|
|
item:param4(0)
|
|
item:x(0)
|
|
item:y(0)
|
|
item:z(0)
|
|
return item
|
|
end
|
|
|
|
function update()
|
|
if not arming:is_armed() then --if disarmed, wait until armed
|
|
mission_loaded = false
|
|
return update,1000
|
|
end
|
|
|
|
if not mission_loaded then --if first time after arm and enabled is valid then create mission
|
|
local home = ahrs:get_home()
|
|
local location = ahrs:get_location()
|
|
local speed = gps:ground_speed(0)
|
|
local alt = baro:get_altitude()
|
|
if location and home and speed > (0.5 * param:get("AIRSPEED_MIN")) then
|
|
local yaw = gps:ground_course(0)
|
|
mission:set_item(3,create_final_approach_WP(3,wrap_180(yaw+180),final_wp_dist,final_wp_alt))
|
|
mission:set_item(4,create_land_WP())
|
|
mission_loaded = true
|
|
gcs:send_text(MAV_SEVERITY.NOTICE, string.format("Captured initial takeoff direction = %.1f at %.1f m and %.1f m/s",yaw, alt, speed))
|
|
end
|
|
end
|
|
return update, 200
|
|
end
|
|
|
|
gcs:send_text(MAV_SEVERITY.INFO,"Loaded UniversalAutoLand.lua")
|
|
if enable == 1 then
|
|
if final_wp_dist == 0 or final_wp_alt ==0 then
|
|
gcs:send_text(MAV_SEVERITY.CRITICAL, string.format("Must set Final Waypoint alt and dist values!"))
|
|
return
|
|
end
|
|
mission:clear()
|
|
local item = mavlink_mission_item_int_t()
|
|
item:command(NAV_WAYPOINT)
|
|
mission:set_item(0,item)
|
|
mission:set_item(1,create_takeoff_WP(param:get("TKOFF_ALT")))
|
|
mission:set_item(2,create_do_land_start_WP())
|
|
gcs:send_text(MAV_SEVERITY.CRITICAL, string.format("Set Final Waypoint alt and dist values!"))
|
|
return update, 1000
|
|
else
|
|
gcs:send_text(MAV_SEVERITY.CRITICAL, string.format("Script disabled by AUTOLAND_ENABLE"))
|
|
return
|
|
end
|
|
|