arcgissamples\geometry\ClipShapefileByEnvelope.java
/* Copyright 2010 ESRI * * All rights reserved under the copyright laws of the United States * and applicable international laws, treaties, and conventions. * * You may freely redistribute and use this sample code, with or * without modification, provided you include the original copyright * notice and use restrictions. * * See the use restrictions. * */ package arcgissamples.geometry; import java.io.File; import java.io.IOException; import com.esri.arcgis.datasourcesfile.ShapefileWorkspaceFactory; import com.esri.arcgis.geodatabase.IFeature; import com.esri.arcgis.geodatabase.IFeatureBuffer; import com.esri.arcgis.geodatabase.IFeatureClass; import com.esri.arcgis.geodatabase.IFeatureCursor; import com.esri.arcgis.geodatabase.IField; import com.esri.arcgis.geodatabase.IFields; import com.esri.arcgis.geodatabase.SpatialFilter; import com.esri.arcgis.geodatabase.Workspace; import com.esri.arcgis.geodatabase.esriFieldType; import com.esri.arcgis.geodatabase.esriSpatialRelEnum; import com.esri.arcgis.geometry.Envelope; import com.esri.arcgis.geometry.IGeometry; import com.esri.arcgis.geometry.ITopologicalOperator; import com.esri.arcgis.system.AoInitialize; import com.esri.arcgis.system.EngineInitializer; import com.esri.arcgis.system.esriLicenseProductCode; import com.esri.arcgis.system.esriLicenseStatus; /** * Description: This sample takes a source shapefile and the name of a target shapefile, along with the extents of a * clipping envelope. These are used to export the features inside the clipping envelope to the newly created target * shapefile. Any feature crossing the clipping envelope is clipped. Inputs: Shapefile - input shapefile dataset. * Outputs: Shapefile - a new shapefile representing the new clip extent. */ public class ClipShapefileByEnvelope { public ClipShapefileByEnvelope() { } public static void main(String[] args) { System.out.println("Starting ClipShapefileByEnvelope - An ArcObjects Java SDK Developer Sample"); try { // Initialize the engine and licenses. EngineInitializer.initializeEngine(); AoInitialize aoInit = new AoInitialize(); initializeArcGISLicenses(aoInit); //Get DEVKITHOME Home String devKitHome = System.getenv("AGSDEVKITJAVA"); if (!(new File(devKitHome).exists())) { System.out.println(devKitHome + " does not exist.\nExiting..."); System.exit(-1); } final String srcShapefilePath = devKitHome + "java" + File.separator + "samples" + File.separator + "data" + File.separator + "usa"; final String srcShapefileName = "states.shp"; final String clippedShapefilePath = getOutputDir() + File.separator + "clipbyenvelope"; final String clippedShapefileName = "clipped.shp"; final double llLng = -115.216; final double llLat = 44.3; final double urLng = -92.45; final double urLat = 35.67; File clippedShapefileFile = new File(clippedShapefilePath, clippedShapefileName); if (clippedShapefileFile.exists()) { System.out.println("Output shapefile already exists: " + clippedShapefileFile.getAbsolutePath()); System.out.println("Delete it (plus related files) and rerun"); System.exit(0); } File clippedDir = new File(clippedShapefilePath); clippedDir.mkdir(); IFeatureClass clippedFeatureClass = clip(srcShapefilePath, srcShapefileName, clippedShapefilePath, clippedShapefileName, llLng, llLat, urLng, urLat); System.out.println("Created " + clippedShapefileFile.getAbsolutePath()); System.out.println("It contains " + clippedFeatureClass.featureCount(null) + " feature(s)."); aoInit.shutdown(); } catch (IOException e) { e.printStackTrace(); System.out.println(e.getMessage()); System.out.println("Sample failed. Exiting..."); System.exit(-1); } } /** * Clips shapefile * @param srcShapefilePath * @param srcShapefileName * @param clippedShapefilePath * @param clippedShapefileName * @param llLng * @param llLat * @param urLng * @param urLat * @return * @throws IOException */ public static IFeatureClass clip(String srcShapefilePath, String srcShapefileName, String clippedShapefilePath, String clippedShapefileName, double llLng, double llLat, double urLng, double urLat) throws IOException { // open source shapefile ShapefileWorkspaceFactory shapefileWorkspaceFactory = new ShapefileWorkspaceFactory(); Workspace srcWorkspace = new Workspace(shapefileWorkspaceFactory.openFromFile(srcShapefilePath, 0)); IFeatureClass srcFeatureClass = srcWorkspace.openFeatureClass(srcShapefileName); // create clip envelope to clip against the source features Envelope theClipEnvelope = new Envelope(); theClipEnvelope.putCoords(llLng, llLat, urLng, urLat); // define a spatial query filter SpatialFilter spatialFilter = new SpatialFilter(); spatialFilter.setGeometryByRef(theClipEnvelope); spatialFilter.setGeometryField(srcFeatureClass.getShapeFieldName()); spatialFilter.setSpatialRel(esriSpatialRelEnum.esriSpatialRelIntersects); // get a cursor based on the spatial query for the source features IFeatureCursor srcFeatureCursor = srcFeatureClass.search(spatialFilter, true); // create target clip shapefile with same fields as source shapefile Workspace clippedWorkspace = new Workspace(shapefileWorkspaceFactory.openFromFile(clippedShapefilePath, 0)); IFeatureClass clippedFeatureClass = clippedWorkspace.createFeatureClass(clippedShapefileName, srcFeatureClass .getFields(), srcFeatureClass.getCLSID(), srcFeatureClass.getEXTCLSID(), srcFeatureClass .getFeatureType(), srcFeatureClass.getShapeFieldName(), ""); // create a cursor and buffer for the clipped features IFeatureCursor clippedFeaturesCursor = clippedFeatureClass.IFeatureClass_insert(true); IFeatureBuffer clippedFeaturesBuffer = clippedFeatureClass.createFeatureBuffer(); // // Loop through the source features and copy them to the clipped shapefile. // IFeature srcIFeature = srcFeatureCursor.nextFeature(); System.out.print("working: "); while (srcIFeature != null) { System.out.print(" . "); // get the source shape to clip. It may be a polygon, point, polyline, etc. IGeometry srcShapeGeometry = srcIFeature.getShapeCopy(); // // Only an object that implements IToplogicalOperator can clip and // call buffer() on itself, so we check and then cast the geometry/shape to it, // If we knew we would always be dealing with a polygon, or polyline // or point or multipoint, etc, we could cast to it instead. // if (!(srcShapeGeometry instanceof ITopologicalOperator)) { continue; } ITopologicalOperator srcShapeTopoGeom = (ITopologicalOperator) srcShapeGeometry; srcShapeTopoGeom.clip(theClipEnvelope); clippedFeaturesBuffer.setShapeByRef(srcShapeTopoGeom.buffer(0)); // // Copy fields too, except the ID and geometry/shape fields // IFields srcFields = srcIFeature.getFields(); IFields clippedFields = clippedFeaturesBuffer.getFields(); int srcNFields = srcFields.getFieldCount(); for (int i = 0; i < srcNFields; i++) { IField srcField = srcFields.getField(i); if (srcField.getType() == esriFieldType.esriFieldTypeOID || srcField.getType() == esriFieldType.esriFieldTypeGeometry) { continue; } String srcFieldName = srcField.getName(); int srcFieldNameIndex = srcFields.findField(srcFieldName); Object srcFeatureNameValue = srcIFeature.getValue(srcFieldNameIndex); int clippedFieldNameIndex = clippedFields.findField(srcFieldName); clippedFeaturesBuffer.setValue(clippedFieldNameIndex, srcFeatureNameValue); } clippedFeaturesCursor.insertFeature(clippedFeaturesBuffer); srcIFeature = srcFeatureCursor.nextFeature(); } System.out.println(); clippedFeaturesCursor.flush(); return clippedFeatureClass; } /** * Initializes the lowest available ArcGIS License */ private static void initializeArcGISLicenses(AoInitialize aoInit) { try { if (aoInit.isProductCodeAvailable(esriLicenseProductCode.esriLicenseProductCodeEngine) == esriLicenseStatus.esriLicenseAvailable) { aoInit.initialize(esriLicenseProductCode.esriLicenseProductCodeEngine); } else if (aoInit.isProductCodeAvailable(esriLicenseProductCode.esriLicenseProductCodeArcView) == esriLicenseStatus.esriLicenseAvailable) { aoInit.initialize(esriLicenseProductCode.esriLicenseProductCodeArcView); } else { System.err.println("Could not initialize an Engine or ArcView license. Exiting application."); System.exit(-1); } } catch (Exception e) { e.printStackTrace(); } } /** * Returns output directory * @return */ private static String getOutputDir() { String userDir; if (System.getProperty("os.name").toLowerCase().indexOf("win") > -1) userDir = System.getenv("UserProfile"); else userDir = System.getenv("HOME"); String outputDir = userDir + File.separator + "arcgis_sample_output"; System.out.println("Creating output directory - " + outputDir); new File(outputDir).mkdir(); return outputDir; } }