KontrolSystem2
KontrolSystem2 copied to clipboard
Request for GeoCoordinates
Hi,
in KSP::Orbit::GeoCoordinates, is it possible to add the following please?
- I'd like to create my own GeoCoordinates knowing their latitude and longitude
- to fly planes, I'd like to know the bearing and the distance of my plane to a given point defined with GeoCoordinates.
Thanks :)
The first is already possible via the celestial body:
- Get the body either via
vessel.main_bodyorksp::orbit::find_body - Create GeoCoordinate via
body.geo_coordinate
As for bearing and distance: The GeoCoordinate already has information about the surface normal, terrain_height and functions to get the position at a given altitude (above sea-level ... I will improve the documentation a bit) ... so calculating the bearing and distance between to geo-coordinates should be simple:
- Distance: Either just the distance between the to positions (straight-line) or based on the the angle between the two surface normals
- Bearing: The bearing vector is just the difference between the two position with the surface normal at the current position removed (e.g. with
vec.exclude_from)- For plane control the bearing vector should already be good enough, if the bearing angle is need you could use
vessel.northor the up-vector of the body.
- For plane control the bearing vector should already be good enough, if the bearing angle is need you could use
Ok. I admit I check my scripts written with kOS for KSP1 and I saw I used bearing and distance. That's why I asked. Thanks for your answer.
I have what I want for the distance. For the bearing, I'm not sure I have understood how it works. The code below doesn't give me what I want. I'm testing this with a plane landed at runway 09L and I want the bearing to the runway 27R.
use { CONSOLE } from ksp::console
use { CONSOLE_WINDOW } from ksp::ui
use { Vessel } from ksp::vessel
use { Body, GeoCoordinates } from ksp::orbit
use { Vec3, vec2 } from ksp::math
use { yield } from ksp::game
use { format } from core::str
pub fn main_flight(vessel: Vessel) -> Unit = {
CONSOLE.clear()
CONSOLE_WINDOW.open()
CONSOLE_WINDOW.size = vec2(500,600)
const body = vessel.main_body
// runway 27R
const rw_coord = body.geo_coordinates(-0.62737558144645, -74.7654563642046)
while (true) {
let vessel_coord = vessel.geo_coordinates
let dist = distance_from_vessel(vessel, rw_coord)
let brg = bearing(vessel, rw_coord)
CONSOLE.print_at(0,0, format("Distance = {0:N2} m ", dist))
CONSOLE.print_at(1,0, format("Bearing = {0:N2}° ", brg))
yield()
}
}
fn distance_from_vessel(vessel: Vessel, geo_position: GeoCoordinates) -> float = {
const body = vessel.main_body
const vessel_vec = body.surface_position(vessel.geo_coordinates.latitude, vessel.geo_coordinates.longitude, vessel.geo_coordinates.terrain_height)
const geo_vec = body.surface_position(geo_position.latitude, geo_position.longitude, geo_position.terrain_height)
return vessel_vec.distance_to(geo_vec)
}
fn bearing(vessel: Vessel, target_position: GeoCoordinates) -> float = {
const vessel_geo = vessel.geo_coordinates
const vec_bearing = bearing_vec_between_geo(vessel_geo, target_position)
return vessel.north.angle_to(vec_bearing)
}
fn bearing_vec_between_geo(current_position: GeoCoordinates, target_position: GeoCoordinates) -> Vec3 = {
const body = current_position.body
const surfPosition1 = body.surface_position(current_position.latitude, current_position.longitude, current_position.terrain_height)
const surfNormal1 = current_position.surface_normal
const geo_vec = surfNormal1.exclude_from(surfPosition1)
const geovec2 = body.surface_position(target_position.latitude, target_position.longitude, target_position.terrain_height)
return (geo_vec - geovec2)
}
I just realized that there was a coordinate system mixup in body.surface_position which should be fixed in 0.5.4.1
Here is a little test program I used with a rover on the runway:
use { Vessel } from ksp::vessel
use { CONSOLE } from ksp::console
use { sleep } from ksp::game
use { atan2_deg, acos } from core::math
pub fn main_flight(vessel: Vessel) -> Result<Unit, string> = {
CONSOLE.clear()
while(true) {
const frame = vessel.main_body.celestial_frame
const target_geo = vessel.main_body.geo_coordinates(-0.6, -75)
const current_geo = vessel.geo_coordinates
const current_pos = current_geo.altitude_position(current_geo.terrain_height)
const target_pos = target_geo.altitude_position(target_geo.terrain_height)
const target_vector = target_pos - current_pos
const bearing_vector = current_geo.surface_normal.exclude_from(target_vector.normalized)
const forward = vessel.facing.vector
const right = vessel.facing.right_vector
const bearing = atan2_deg(bearing_vector * right, bearing_vector * forward)
const dist1 = target_vector.magnitude
const dist2 = vessel.main_body.radius * acos(current_geo.surface_normal * target_geo.surface_normal)
CONSOLE.print_at(4, 0, " " + current_geo.latitude.to_fixed(5) + " " + current_geo.longitude.to_fixed(5))
CONSOLE.print_at(5, 0, " " + bearing.to_fixed(2) + " " + dist1.to_fixed(2) + " " + dist2.to_fixed(2))
sleep(0.5)
}
}
Replacing .altitude_position with .global_altitude_position and .surface_normal with .global_surface_normal should now produce the same results
This issue is stale because it has been open for 60 days with no activity.
This issue was closed because it has been inactive for 14 days since being marked as stale.