为什么这个GeoTool片段不能生成可查看的shapefile?

时间:2013-09-13 07:18:38

标签: java geotools

我正在创建一个简单的程序,它从csv文件读取值并根据这些值创建一个shp文件。这是对this example

的轻微修改

形状文件似乎已创建,但是当我查看shapefile with a another snippet时,我什么都看不到。我可以使用此程序查看其他示例shapefile。

我的代码中缺少什么?

我的数据:

LAT1, LON1, LAT2, LON2, LAT3, LON3, LAT3, LON3, CITY, NUMBER
10, 10, 20, 20, 30, 30, 10, 10, Trento, 140

我的代码:

public class ShapeReaderWriter {

    public static void main(String[] args) throws Exception {

        //read the xml file
        File file = FileUtils.getFile("D:\\workspaces\\Routeguard\\Xml2Shape\\src\\com\\meteogroup\\conversion\\locations.csv");

        List<String> lines = FileUtils.readLines(file, "utf-8");

        final SimpleFeatureType TYPE = createFeatureType();

        List<SimpleFeature> features = new ArrayList<SimpleFeature>();        

        GeometryFactory geometryFactory = JTSFactoryFinder.getGeometryFactory(null);
        SimpleFeatureBuilder featureBuilder = new SimpleFeatureBuilder(TYPE);

        int i = 0;
        for(String line : lines){
            if (i > 0 && line.trim().length() > 0) { // skip blank lines + header
                String tokens[] = line.split("\\,");

                Coordinate[] coordinates = createPolygonDescription(tokens, 8); //the number of values the polygon has

                String name = tokens[8].trim();
                int number = Integer.parseInt(tokens[9].trim());

                /* Longitude (= x coord) first ! */
                Polygon polygon = geometryFactory.createPolygon(coordinates);
                featureBuilder.add(polygon);
                featureBuilder.add(name);
                featureBuilder.add(number);
                SimpleFeature feature = featureBuilder.buildFeature(null);
                features.add(feature);
            }
            i++;
        }

        /*
         * Get an output file name and create the new shapefile
         */
        File newFile = getNewShapeFile(file);

        ShapefileDataStoreFactory dataStoreFactory = new ShapefileDataStoreFactory();

        Map<String, Serializable> params = new HashMap<String, Serializable>();
        params.put("url", newFile.toURI().toURL());
        params.put("create spatial index", Boolean.TRUE);

        ShapefileDataStore newDataStore = (ShapefileDataStore) dataStoreFactory.createNewDataStore(params);
        newDataStore.createSchema(TYPE);

        /*
         * You can comment out this line if you are using the createFeatureType method (at end of
         * class file) rather than DataUtilities.createType
         */
        //newDataStore.forceSchemaCRS(DefaultGeographicCRS.WGS84);

        /*
         * Write the features to the shapefile
         */
        Transaction transaction = new DefaultTransaction("create");

        String typeName = newDataStore.getTypeNames()[0];
        SimpleFeatureSource featureSource = newDataStore.getFeatureSource(typeName);

        if (featureSource instanceof SimpleFeatureStore) {
            SimpleFeatureStore featureStore = (SimpleFeatureStore) featureSource;

            /*
             * SimpleFeatureStore has a method to add features from a
             * SimpleFeatureCollection object, so we use the ListFeatureCollection
             * class to wrap our list of features.
             */
            SimpleFeatureCollection collection = new ListFeatureCollection(TYPE, features);
            featureStore.setTransaction(transaction);
            try {
                featureStore.addFeatures(collection);
                transaction.commit();

            } catch (Exception problem) {
                problem.printStackTrace();
                transaction.rollback();

            } finally {
                transaction.close();
            }
            System.exit(0); // success!
        } else {
            System.out.println(typeName + " does not support read/write access");
            System.exit(1);
        }

    }

    private static Coordinate[] createPolygonDescription(String[] tokens, int max) {
        Coordinate[] coords = new Coordinate[max / 2];
        int j = 0;
        for(int i = 0 ; i < max; i = i+2){
            Coordinate c = new Coordinate(Double.parseDouble(tokens[i + 1]), Double.parseDouble(tokens[i])); // seems weird but isn't  -> lon is the x value, lat is the y
            coords[j] = c;
            j++;
        }
        return coords;
    }

    private static SimpleFeatureType createFeatureType() {

        SimpleFeatureTypeBuilder builder = new SimpleFeatureTypeBuilder();
        builder.setName("Location");
        builder.setCRS(DefaultGeographicCRS.WGS84); // <- Coordinate reference system

        // add attributes in order
        builder.add("Polygon", Polygon.class);
        builder.length(15).add("Name", String.class); // <- 15 chars width for name field
        builder.add("Number", Integer.class);

        // build the type
        final SimpleFeatureType LOCATION = builder.buildFeatureType();

        return LOCATION;
    }

    private static File getNewShapeFile(File csvFile) {
        String path = csvFile.getAbsolutePath();
        String newPath = path.substring(0, path.length() - 4) + ".shp";

        JFileChooser chooser = new JFileChooser("shp");
        chooser.setDialogTitle("Save shapefile");
        chooser.setSelectedFile(new File(newPath));

        int returnVal = chooser.showSaveDialog(null);

        if (returnVal != JFileChooser.APPROVE_OPTION) {
            // the user cancelled the dialog
            System.exit(0);
        }

        File newFile = chooser.getSelectedFile();
        if (newFile.equals(csvFile)) {
            System.out.println("Error: cannot replace " + csvFile);
            System.exit(0);
        }

        return newFile;
    }

}

我的观众:

public class Quickstart {

/**
 * GeoTools Quickstart demo application. Prompts the user for a shapefile and displays its
 * contents on the screen in a map frame
 */
public static void main(String[] args) throws Exception {
    // display a data store file chooser dialog for shapefiles
    File file = JFileDataStoreChooser.showOpenFile("shp", null);
    if (file == null) {
        return;
    }

    FileDataStore store = FileDataStoreFinder.getDataStore(file);
    SimpleFeatureSource featureSource = store.getFeatureSource();

    // Create a map content and add our shapefile to it
    MapContent map = new MapContent();
    map.setTitle("Quickstart");

    Style style = SLD.createSimpleStyle(featureSource.getSchema());
    Layer layer = new FeatureLayer(featureSource, style);
    map.addLayer(layer);

    // Now display the map
    JMapFrame.showMap(map);
}

}

谢谢你,并为这段长片而烦恼!

2 个答案:

答案 0 :(得分:4)

看起来geotools几何名称在内部硬编码为“the_geom”。

我遇到了同样的错误,并且通过替换此行来修复:

builder.add("Polygon", Polygon.class);

这一个:

builder.add("the_geom", Polygon.class);

答案 1 :(得分:0)

稳定分支按预期工作,对于任何寻找解决方案的人来说,这是我到目前为止所发现的:

  • 10-SNAPSHOT:不工作
  • 11-SNAPSHOT:不工作
  • 2.7.5:工作

不是你想要的答案,但对我来说,不要再被卡住了!