// lib_navball.ks - A library of functions to calculate navball-based directions. // Copyright © 2015,2017,2019,2023 KSLib team // Lic. MIT @lazyglobal off. @clobberbuiltins off. function east_for { parameter ves is ship. return vcrs(ves:up:vector, ves:north:vector). } function compass_for { parameter ves is ship,thing is "default". local pointing is ves:facing:forevector. if not thing:istype("string") { set pointing to type_to_vector(ves,thing). } local east is east_for(ves). local trig_x is vdot(ves:north:vector, pointing). local trig_y is vdot(east, pointing). local result is arctan2(trig_y, trig_x). if result < 0 { return 360 + result. } else { return result. } } function pitch_for { parameter ves is ship,thing is "default". local pointing is ves:facing:forevector. if not thing:istype("string") { set pointing to type_to_vector(ves,thing). } return 90 - vang(ves:up:vector, pointing). } function roll_for { parameter ves is ship,thing is "default". local pointing is ves:facing. if not thing:istype("string") { if thing:istype("vessel") or pointing:istype("part") { set pointing to thing:facing. } else if thing:istype("direction") { set pointing to thing. } else { print "type: " + thing:typename + " is not recognized by roll_for". } } if vang(pointing:topvector,ves:up:vector) < 0.2 {//this is the dead zone for roll when within 0.2 degrees of vertical return 0. } else { local trig_x is vdot(pointing:topvector,ves:up:vector). local vec_y is vcrs(ves:up:vector,ves:facing:forevector). local trig_y is vdot(pointing:topvector,vec_y). return arctan2(trig_y,trig_x). } } function compass_and_pitch_for { parameter ves is ship,thing is "default". local pointing is ves:facing:forevector. if not thing:istype("string") { set pointing to type_to_vector(ves,thing). } local east is east_for(ves). local trig_x is vdot(ves:north:vector, pointing). local trig_y is vdot(east, pointing). local trig_z is vdot(ves:up:vector, pointing). local compass is arctan2(trig_y, trig_x). if compass < 0 { set compass to 360 + compass. } local pitch is arctan2(trig_z, sqrt(trig_x^2 + trig_y^2)). return list(compass,pitch). } function bearing_between { parameter ves,thing_1,thing_2. local vec_1 is type_to_vector(ves,thing_1). local vec_2 is type_to_vector(ves,thing_2). local fake_north is vxcl(ves:up:vector, vec_1). local fake_east is vcrs(ves:up:vector, fake_north). local trig_x is vdot(fake_north, vec_2). local trig_y is vdot(fake_east, vec_2). return arctan2(trig_y, trig_x). } function type_to_vector { parameter ves,thing. if thing:istype("vector") { return thing:normalized. } else if thing:istype("direction") { return thing:forevector. } else if thing:istype("vessel") or thing:istype("part") { return thing:facing:forevector. } else if thing:istype("geoposition") or thing:istype("waypoint") { return (thing:position - ves:position):normalized. } else { print "type: " + thing:typename + " is not recognized by lib_navball". } }