10
10
import gov .nasa .worldwind .WorldWindow ;
11
11
import gov .nasa .worldwind .geom .Camera ;
12
12
import gov .nasa .worldwind .geom .Location ;
13
+ import gov .nasa .worldwind .geom .Position ;
13
14
import gov .nasa .worldwind .gesture .GestureRecognizer ;
14
15
import gov .nasa .worldwind .gesture .PinchRecognizer ;
15
16
import gov .nasa .worldwind .gesture .RotationRecognizer ;
16
17
import gov .nasa .worldwind .util .WWMath ;
17
18
18
19
public class CameraControlFragment extends BasicGlobeFragment {
19
20
21
+ private static final double COLLISION_THRESHOLD = 20.0 ; // 20m above surface
22
+
20
23
/**
21
24
* Creates a new WorldWindow object with a custom WorldWindowController.
22
25
*/
@@ -42,7 +45,7 @@ public WorldWindow createWorldWindow() {
42
45
* A custom WorldWindController that uses gestures to control the camera directly via the setAsCamera interface
43
46
* instead of the default setAsLookAt interface.
44
47
*/
45
- private class CameraController extends BasicWorldWindowController {
48
+ private static class CameraController extends BasicWorldWindowController {
46
49
47
50
protected double beginHeading ;
48
51
@@ -189,15 +192,22 @@ protected void gestureDidBegin() {
189
192
}
190
193
191
194
protected void applyLimits (Camera camera ) {
192
- double distanceToExtents = this . wwd . distanceToViewGlobeExtents () ;
195
+ Position position = camera . position ;
193
196
194
197
double minAltitude = 100 ;
195
- double maxAltitude = distanceToExtents ;
196
- camera .position .altitude = WWMath .clamp (camera .position .altitude , minAltitude , maxAltitude );
198
+ double maxAltitude = this .wwd .distanceToViewGlobeExtents ();
199
+ position .altitude = WWMath .clamp (position .altitude , minAltitude , maxAltitude );
200
+
201
+ // Check if camera altitude is not under the surface
202
+ double elevation = this .wwd .getGlobe ().getElevationAtLocation (position .latitude , position .longitude )
203
+ * wwd .getVerticalExaggeration () + COLLISION_THRESHOLD ;
204
+ if (elevation > position .altitude ) {
205
+ position .altitude = elevation ;
206
+ }
197
207
198
208
// Limit the tilt to between nadir and the horizon (roughly)
199
- double r = wwd .getGlobe ().getRadiusAt (camera . position .latitude , camera . position .latitude );
200
- double maxTilt = Math .toDegrees (Math .asin (r / (r + camera . position .altitude )));
209
+ double r = wwd .getGlobe ().getRadiusAt (position .latitude , position .latitude );
210
+ double maxTilt = Math .toDegrees (Math .asin (r / (r + position .altitude )));
201
211
double minTilt = 0 ;
202
212
camera .tilt = WWMath .clamp (camera .tilt , minTilt , maxTilt );
203
213
}
0 commit comments