This article explains how to zoom to the extent of selected features in one layer or multiple layers on a globe.
In this topic
ESRI.ArcGIS.GlobeCore.IGlobeDisplay globeDisplay = globe.GlobeDisplay; ESRI.ArcGIS.Analyst3D.IScene scene = globeDisplay.Scene; ESRI.ArcGIS.Carto.IEnumLayer enumLayer = scene.get_Layers(null , true );
ESRI.ArcGIS.Analyst3D.ISceneViewer sceneViewer = globeDisplay.ActiveViewer;
ESRI.ArcGIS.Analyst3D.ICamera camera = sceneViewer.Camera;
ESRI.ArcGIS.GlobeCore.IGlobeCamera globeCamera = (ESRI.ArcGIS.GlobeCore.IGlobeCamera)camera; // Explicit cast.
ESRI.ArcGIS.Geometry.IEnvelope envelopeCls = new EnvelopeClass(); envelopeCls.SetEmpty(); ESRI.ArcGIS.Geometry.IEnvelope layersExtentCls = new EnvelopeClass(); layersExtentCls.SetEmpty(); ESRI.ArcGIS.Geometry.IZAware ZAware = (ESRI.ArcGIS.Geometry.IZAware)envelopeCls; // Explicit cast. ZAware.ZAware = (true ); ESRI.ArcGIS.Geodatabase.ISpatialFilter spatialFilterCls = new ESRI.ArcGIS.Geodatabase.SpatialFilterClass(); ESRI.ArcGIS.Geometry.ISpatialReference spatialReference = scene.SpatialReference;
bool haveFeatures = false ; enumLayer.Reset();
ESRI.ArcGIS.Carto.ILayer layer; while ((layer = enumLayer.Next()) != null ) { if (layer == null ) break ;
The important thing to note is that you are trying to zoom to a number of selected features. If there are multiple features in the same feature class, keep updating the envelope of the extent by using the IEnvelope.Union method.
ESRI.ArcGIS.Carto.IFeatureLayer featureLayer = (ESRI.ArcGIS.Carto.IFeatureLayer)layer; // Explicit cast. ESRI.ArcGIS.Carto.IFeatureSelection featureSelection = (ESRI.ArcGIS.Carto.IFeatureSelection)layer; // Explicit Cast ESRI.ArcGIS.Geodatabase.ISelectionSet selectionSet = featureSelection.SelectionSet; ESRI.ArcGIS.Geodatabase.IFeatureClass featureClass = featureLayer.FeatureClass; string shapeField = featureClass.ShapeFieldName; spatialFilterCls.GeometryField = shapeField; spatialFilterCls.set_OutputSpatialReference(shapeField, spatialReference); ESRI.ArcGIS.Geodatabase.ICursor cursor; selectionSet.Search(spatialFilterCls, true , out cursor); ESRI.ArcGIS.Geodatabase.IFeatureCursor featureCursor = (ESRI.ArcGIS.Geodatabase.IFeatureCursor)cursor; // Explicit cast. bool getLayerExtent = true ; ESRI.ArcGIS.Geodatabase.IFeature feature; while ((feature = featureCursor.NextFeature()) != null ) { ESRI.ArcGIS.Geometry.IGeometry geometry = feature.Shape; ESRI.ArcGIS.Geometry.IEnvelope featureExtent = geometry.Envelope; envelopeCls.Union(featureExtent); haveFeatures = true ; if (getLayerExtent) { ESRI.ArcGIS.Geodatabase.IGeoDataset geoDataset = (ESRI.ArcGIS.Geodatabase.IGeoDataset)featureLayer; // Explicit cast. if (geoDataset != null ) { ESRI.ArcGIS.Geometry.IEnvelope layerExtent = geoDataset.Extent; layersExtentCls.Union(layerExtent); } getLayerExtent = false ; } } } In cases of point feature datasets—since the extent of a point is very small—use a special scenario so that you can zoom in closer to the point geometry. You can have the following special scenarios:
Scenario one —You can have the width and height of the envelope equal to zero. To do this, zoom to the layer extent and multiply it by a zoom factor (for example, 0.05) that reduces the extent of the zoom. Make sure that the zoom to envelope is centered at the point selected. See the following code example:
double width = envelopeCls.Width; double height = envelopeCls.Height; if (width == 0.0 && height == 0.0) { double dim = 1.0; bool bEmpty = layersExtentCls.IsEmpty; if (!bEmpty) { double layerWidth = layersExtentCls.Width; double layerHeight = layersExtentCls.Height; double layerDim = System.Math.Max(layerWidth, layerHeight) * 0.05; if (layerDim > 0.0) dim = System.Math.Min(1.0, layerDim); } double xMin = envelopeCls.XMin; double yMin = envelopeCls.YMin; ESRI.ArcGIS.Geometry.IPoint pointCls = new ESRI.ArcGIS.Geometry.PointClass(); pointCls.X = xMin; pointCls.Y = yMin; envelopeCls.Width = dim; envelopeCls.Height = dim; envelopeCls.CenterAt(pointCls); } Scenario two —You can have the width or height of the envelope equal to zero. To do this, set the width and height of the envelope's zoom equal to the greater of the width or height of the extent of the selected point feature. See the following code example:
else if (width == 0.0 || height == 0.0) { double maxDim = System.Math.Max(width, height); envelopeCls.Width = maxDim; envelopeCls.Height = maxDim; } Once you have the extent of all the selected features, use the IGlobeCamera.SetToZoomToExtents() method. Here, you can pass the extent and the active viewer as the parameters. See the following code example:
globeCamera.SetToZoomToExtents(envelopeCls, globe, sceneViewer);
sceneViewer.Redraw(true
); |
|
来自: 秋寒月 > 《arcglobe开发》