GeoPackage Plugin

Supports direct access to a GeoPackage database.

GeoPackage is an open, standards-based, platform-independent, portable, self-describing, compact format for transferring geospatial information.

The module supports both vector data, as GeoPackage features, and raster data, as GeoPackage tiles. Access to a GeoPackage can be performed either low level, using the GeoPackage class, or high level, using the GeoPackage JDBC data store for vector data, and the GeoPackageReader for raster data.

References:

Maven

<dependency>
   <groupId>org.geotools</groupId>
   <artifactId>gt-geopkg</artifactId>
   <version>${geotools.version}</version>
 </dependency>

DataStore Connection Parameters

Parameter Description
“dbtype” Must be the string “geopkg”
“database” The database to connect to
“user” User name (optional)

Access

Example use:

Map params = new HashMap();
params.put("dbtype", "geopkg");
params.put("database", "test.gkpg");

DataStore datastore = DataStoreFinder.getDataStore(params);

High level coverage reader

The high level coverage reader can access all tile entries found in the package, exposing each one as a separate coverage.

GeoPackageReader reader = new GeoPackageReader(getClass().getResource("world_lakes.gpkg"), null);
System.out.println(Arrays.asList(reader.getGridCoverageNames()));
GeneralParameterValue[] parameters = new GeneralParameterValue[1];
GridGeometry2D gg = new GridGeometry2D(new GridEnvelope2D(new Rectangle(500,500)), new ReferencedEnvelope(0,180.0,-85.0,0,WGS_84));
parameters[0] = new Parameter<GridGeometry2D>(AbstractGridFormat.READ_GRIDGEOMETRY2D, gg);
GridCoverage2D gc = reader.read("World_Lakes", parameters);

Adding a feature entry using the low level API

A GeoPackage with a feature entry can be created using the following low level code:

GeoPackage geopkg = new GeoPackage(File.createTempFile("geopkg", "db", new File("target")));
geopkg.init();

ShapefileDataStore shp = ...

FeatureEntry entry = new FeatureEntry();
geopkg.add(entry, shp.getFeatureSource(), null);

Once created, the features in the entry can be read using a SimpleFeatureReader:

try(SimpleFeatureReader r = geopkg.reader(entry, null, null)) {
  while(r.hasNext()) {
      SimpleFeature sf = r.next());
  }
}

The parallel writer method can be used to grab a SimpleFeatureWriter to modify existing features.

Adding a tile entry using the low level API

A GeoPackage with a tile entry can be created using the following low level code:

GeoPackage geopkg = new GeoPackage(File.createTempFile("geopkg", "db", new File("target")));
geopkg.init();

TileEntry e = new TileEntry();
e.setTableName("foo");
e.setBounds(new ReferencedEnvelope(-180,180,-90,90,DefaultGeographicCRS.WGS84));
e.getTileMatricies().add(new TileMatrix(0, 1, 1, 256, 256, 0.1, 0.1));
e.getTileMatricies().add(new TileMatrix(1, 2, 2, 256, 256, 0.1, 0.1));

geopkg.create(e);
assertTileEntry(e);

List<Tile> tiles = new ArrayList();
tiles.add(new Tile(0,0,0,new byte[]{...}));
tiles.add(new Tile(1,0,0,new byte[]{...}));
tiles.add(new Tile(1,0,1,new byte[]{...}));
tiles.add(new Tile(1,1,0,new byte[]{...}));
tiles.add(new Tile(1,1,1,new byte[]{...}));

for (Tile t : tiles) {
    geopkg.add(e, t);
}

Tile can then be read back using a TileReader, as follows (the zoom and row/col limits can be set to null to read everything):

try(TileReader r = geopkg.reader(e, lowZoom, highZoom, lowCol, highCol, lowRow, highRow)) {
    while(r.hasNext()) {
      Tile a = r.next();
      // do something with the tile
    }
}