1010
1111namespace MapResourceOverlay
1212{
13- [ KSPAddon ( KSPAddon . Startup . Flight , false ) ]
13+ [ KSPAddon ( KSPAddon . Startup . Flight , true ) ]
1414 public class MapOverlay : MonoBehaviour
1515 {
1616 private CelestialBody _body ;
1717 private Mesh _mesh ;
18- private readonly List < string > _resources = new List < string > { "Karbonite" , "Minerals" , "Ore" , "Substrate" , "Water" } ;
18+
19+ private readonly List < string > _resources = new List < string >
20+ {
21+ "Karbonite" ,
22+ "Minerals" ,
23+ "Ore" ,
24+ "Substrate" ,
25+ "Water"
26+ } ;
27+
1928 private readonly IButton _mapOverlayButton ;
2029 private MapOverlayGui _gui ;
2130 private bool _changed ;
2231 private string _selectedResourceName ;
32+ private Coordinates _mouseCoords ;
33+ private CelestialBody targetBody ;
34+
35+ [ KSPField ( isPersistant = true ) ] private bool _show ;
36+
37+ private Vector2 mouse ;
2338
2439
2540 public MapOverlay ( )
@@ -29,28 +44,49 @@ public MapOverlay()
2944 _mapOverlayButton . ToolTip = "Map Resource Overlay" ;
3045 _mapOverlayButton . Visibility = new GameScenesVisibility ( GameScenes . FLIGHT ) ;
3146 _mapOverlayButton . OnClick += e => ToggleGui ( ) ;
47+ DontDestroyOnLoad ( this ) ;
3248 }
3349
3450 public void ToggleGui ( )
3551 {
52+ if ( _gui != null )
53+ {
54+ _gui . SetVisible ( false ) ;
55+ }
3656 _gui = new MapOverlayGui ( this ) ;
3757 _gui . SetVisible ( true ) ;
3858 }
59+
60+ public void OnDestroy ( )
61+ {
62+ Debug . Log ( "destroying MapResourceOverlay" ) ;
63+ _mapOverlayButton . Destroy ( ) ;
64+ if ( _gui != null )
65+ {
66+ _gui . Model = null ;
67+ _gui . SetVisible ( false ) ;
68+ }
69+ gameObject . renderer . enabled = false ;
70+ }
71+
3972 public void Awake ( )
4073 {
74+
4175 }
4276 public void Start ( )
4377 {
44- Show = false ;
78+ Debug . Log ( "MapResourceOverlay starting" ) ;
4579 gameObject . layer = 10 ;
4680 gameObject . AddComponent < MeshRenderer > ( ) ;
4781 _mesh = gameObject . AddComponent < MeshFilter > ( ) . mesh ;
4882 SelectedResourceName = Resources [ 0 ] ;
83+ var overlays = FindObjectsOfType < MapOverlay > ( ) . ToList ( ) ;
84+ Debug . Log ( "MapResourceOverlay left: " + overlays . Count ( x => x != this ) ) ;
4985 }
5086
5187 public void Update ( )
5288 {
53- if ( HighLogic . LoadedScene != GameScenes . FLIGHT && HighLogic . LoadedScene != GameScenes . TRACKSTATION )
89+ if ( HighLogic . LoadedScene != GameScenes . FLIGHT )
5490 {
5591 gameObject . renderer . enabled = ( false ) ;
5692 }
@@ -63,17 +99,19 @@ private void updateMapView()
6399 if ( ! Show || MapView . MapCamera == null )
64100 {
65101 gameObject . renderer . enabled = false ;
102+ _mouseCoords = null ;
66103 }
67104 else
68105 {
69106 gameObject . renderer . enabled = true ;
70- var targetBody = GetTargetBody ( MapView . MapCamera . target ) ;
107+ targetBody = GetTargetBody ( MapView . MapCamera . target ) ;
71108
72- if ( targetBody != null && targetBody != _body || _changed )
109+ if ( targetBody != null && targetBody != _body || targetBody != null && _changed )
73110 {
74111 _changed = false ;
112+ Debug . Log ( "new target: " + targetBody . GetName ( ) ) ;
75113 var dir = System . IO . Path . GetDirectoryName ( Assembly . GetExecutingAssembly ( ) . Location ) ;
76- var radii = System . IO . File . ReadAllLines ( dir + "/Assets/Radii.cfg" ) ;
114+ var radii = System . IO . File . ReadAllLines ( dir + "/Assets/Radii.cfg" ) ;
77115 var radius = float . Parse ( radii . First ( x => x . StartsWith ( targetBody . GetName ( ) ) ) . Split ( '=' ) [ 1 ] ) ;
78116 _body = targetBody ;
79117 evilmesh ( targetBody , SelectedResourceName ) ;
@@ -85,10 +123,93 @@ private void updateMapView()
85123 gameObject . transform . localScale = Vector3 . one * 1000f * radius ;
86124 gameObject . transform . localPosition = ( Vector3 . zero ) ;
87125 gameObject . transform . localRotation = ( Quaternion . identity ) ;
126+
127+ }
128+
129+ }
130+
131+ }
132+
133+ public void OnGUI ( )
134+ {
135+ if ( Show && targetBody != null )
136+ {
137+ if ( Event . current . type == EventType . Layout )
138+ {
139+ _mouseCoords = GetMouseCoordinates ( targetBody ) ;
140+ mouse = Event . current . mousePosition ;
141+ }
142+ if ( _mouseCoords != null )
143+ {
144+
145+ var id = new System . Random ( ) . Next ( 65536 ) + Assembly . GetExecutingAssembly ( ) . GetName ( ) . Name . GetHashCode ( ) + "tooltip" . GetHashCode ( ) ;
146+ var abundance = ORSPlanetaryResourceMapData . getResourceAvailabilityByRealResourceName (
147+ targetBody . flightGlobalsIndex , _selectedResourceName , _mouseCoords . Latitude , _mouseCoords . Longitude )
148+ . getAmount ( ) ;
149+ string abundanceString ;
150+ if ( abundance > 0.001 )
151+ {
152+ abundanceString = ( abundance * 100.0 ) . ToString ( "0.00" ) + "%" ;
153+ }
154+ else
155+ {
156+ abundanceString = ( abundance * 1000000.0 ) . ToString ( "0.0" ) + "ppm" ;
157+ }
158+ GUI . Window ( id , new Rect ( mouse . x + 10 , mouse . y + 10 , 200f , 55f ) , i =>
159+ {
160+ GUI . Label ( new Rect ( 5 , 10 , 190 , 20 ) , "Long: " + _mouseCoords . Longitude . ToString ( "###.##" ) + " Lat: " + _mouseCoords . Latitude . ToString ( "####.##" ) ) ;
161+ GUI . Label ( new Rect ( 5 , 30 , 190 , 20 ) , "Amount: " + abundanceString ) ;
162+
163+ } ,
164+ _selectedResourceName ) ;
165+ }
166+ }
167+ }
168+ public static Coordinates GetMouseCoordinates ( CelestialBody targetBody )
169+ {
170+ Ray mouseRay = PlanetariumCamera . Camera . ScreenPointToRay ( Input . mousePosition ) ;
171+ mouseRay . origin = ScaledSpace . ScaledToLocalSpace ( mouseRay . origin ) ;
172+ var bodyToOrigin = mouseRay . origin - targetBody . position ;
173+ double curRadius = targetBody . pqsController . radiusMax ;
174+ double lastRadius = 0 ;
175+ int loops = 0 ;
176+ while ( loops < 50 )
177+ {
178+ Vector3d relSurfacePosition ;
179+ if ( PQS . LineSphereIntersection ( bodyToOrigin , mouseRay . direction , curRadius , out relSurfacePosition ) )
180+ {
181+ var surfacePoint = targetBody . position + relSurfacePosition ;
182+ double alt = targetBody . pqsController . GetSurfaceHeight (
183+ QuaternionD . AngleAxis ( targetBody . GetLongitude ( surfacePoint ) , Vector3d . down ) * QuaternionD . AngleAxis ( targetBody . GetLatitude ( surfacePoint ) , Vector3d . forward ) * Vector3d . right ) ;
184+ double error = Math . Abs ( curRadius - alt ) ;
185+ if ( error < ( targetBody . pqsController . radiusMax - targetBody . pqsController . radiusMin ) / 100 )
186+ {
187+ return new Coordinates ( targetBody . GetLatitude ( surfacePoint ) , Utilities . ClampDegrees ( targetBody . GetLongitude ( surfacePoint ) ) ) ;
188+ }
189+ else
190+ {
191+ lastRadius = curRadius ;
192+ curRadius = alt ;
193+ loops ++ ;
194+ }
195+ }
196+ else
197+ {
198+ if ( loops == 0 )
199+ {
200+ break ;
201+ }
202+ else
203+ { // Went too low, needs to try higher
204+ curRadius = ( lastRadius * 9 + curRadius ) / 10 ;
205+ loops ++ ;
206+ }
88207 }
89208 }
209+ return null ;
90210 }
91211
212+
92213 private void evilmesh ( CelestialBody targetBody , string resourceName )
93214 {
94215 int bodyIndex = FlightGlobals . Bodies . IndexOf ( targetBody ) ;
@@ -125,8 +246,14 @@ private void evilmesh(CelestialBody targetBody, string resourceName)
125246 var avail = ORSPlanetaryResourceMapData . getResourceAvailabilityByRealResourceName ( bodyIndex , resourceName , 90 - lat , lon ) ;
126247 var amount = avail . getAmount ( ) ;
127248 amount = Mathf . Clamp ( ( float ) amount * 500000f , 0f , 255f ) ;
128-
129- colors [ lon + lat * ( nbLong + 1 ) + 1 ] = new Color32 ( Convert . ToByte ( amount ) , byte . MinValue , byte . MinValue , 100 ) ;
249+ if ( amount > 0.0 )
250+ {
251+ colors [ lon + lat * ( nbLong + 1 ) + 1 ] = new Color32 ( Convert . ToByte ( amount ) , byte . MinValue , byte . MinValue , 70 ) ;
252+ }
253+ else
254+ {
255+ colors [ lon + lat * ( nbLong + 1 ) + 1 ] = new Color32 ( byte . MinValue , byte . MinValue , byte . MinValue , 0 ) ;
256+ }
130257 }
131258 }
132259 vertices [ vertices . Length - 1 ] = Vector3 . up * - radius ;
@@ -171,13 +298,13 @@ private void evilmesh(CelestialBody targetBody, string resourceName)
171298 int current = lon + lat * ( nbLong + 1 ) + 1 ;
172299 int next = current + nbLong + 1 ;
173300
174- triangles [ i ++ ] = current ;
175- triangles [ i ++ ] = current + 1 ;
176301 triangles [ i ++ ] = next + 1 ;
177-
302+ triangles [ i ++ ] = current + 1 ;
178303 triangles [ i ++ ] = current ;
179- triangles [ i ++ ] = next + 1 ;
304+
180305 triangles [ i ++ ] = next ;
306+ triangles [ i ++ ] = next + 1 ;
307+ triangles [ i ++ ] = current ;
181308 }
182309 }
183310
@@ -209,7 +336,12 @@ private static CelestialBody GetTargetBody(MapObject target)
209336 return target . vessel . mainBody ;
210337 return null ;
211338 }
212- public bool Show { get ; set ; }
339+
340+ public bool Show
341+ {
342+ get { return _show ; }
343+ set { _show = value ; }
344+ }
213345
214346 public List < string > Resources
215347 {
@@ -219,40 +351,66 @@ public List<string> Resources
219351 public string SelectedResourceName
220352 {
221353 get { return _selectedResourceName ; }
222- set
223- {
354+ set
355+ {
224356 _selectedResourceName = value ;
225357 _changed = true ;
226358 }
227359 }
360+
361+
228362 }
229363
230364 public class MapOverlayGui : Window < MapOverlayGui >
231365 {
232- private readonly MapOverlay _model ;
366+ public MapOverlay Model ;
233367
234- public MapOverlayGui ( MapOverlay model ) : base ( "Map Overlay" , 300 , 200 )
368+ public MapOverlayGui ( MapOverlay model )
369+ : base ( "Map Overlay" , 300 , 200 )
235370 {
236- _model = model ;
371+ Model = model ;
372+
237373 }
238374
239375 protected override void DrawWindowContents ( int windowId )
240376 {
241377 if ( GUILayout . Button ( "Toggle Overlay" ) )
242378 {
243- _model . Show = ! _model . Show ;
379+ Model . Show = ! Model . Show ;
244380 }
245381 GUILayout . Box ( "" ) ;
246382 GUILayout . BeginVertical ( ) ;
247- foreach ( var res in _model . Resources )
248- {
383+ foreach ( var res in Model . Resources )
384+ {
249385 if ( GUILayout . Button ( res ) )
250386 {
251- _model . SelectedResourceName = res ;
387+ Model . SelectedResourceName = res ;
252388 }
253389 }
254390 GUILayout . EndVertical ( ) ;
255391 }
256392 }
257393
394+ public class Coordinates
395+ {
396+ private readonly double _latitude ;
397+ private readonly double _longitude ;
398+
399+ public Coordinates ( double latitude , double longitude )
400+ {
401+ _latitude = latitude ;
402+ _longitude = longitude ;
403+ }
404+
405+ public double Latitude
406+ {
407+ get { return _latitude ; }
408+ }
409+
410+ public double Longitude
411+ {
412+ get { return _longitude ; }
413+ }
414+ }
415+
258416}
0 commit comments