pub mod geojson_reader;
pub mod rasterize;
#[cfg(feature = "parquet")]
pub mod geoparquet;
#[cfg(feature = "geopackage")]
pub mod gpkg_reader;
#[cfg(feature = "shapefile")]
pub mod shapefile_reader;
use geo_types::Geometry;
use serde::{Deserialize, Serialize};
use std::collections::HashMap;
pub use geojson_reader::{parse_geojson, read_geojson};
pub use rasterize::{clip_raster, clip_raster_by_polygon, rasterize_polygons};
#[cfg(feature = "parquet")]
pub use geoparquet::{
Column, ColumnData, PointTable, read_geoparquet, read_geoparquet_points, write_geoparquet,
write_geoparquet_points,
};
#[cfg(feature = "geopackage")]
pub use gpkg_reader::{list_gpkg_layers, read_gpkg};
#[cfg(feature = "shapefile")]
pub use shapefile_reader::read_shapefile;
#[derive(Debug, Clone, Serialize, Deserialize)]
pub enum AttributeValue {
Null,
Bool(bool),
Int(i64),
Float(f64),
String(String),
}
#[derive(Debug, Clone)]
pub struct Feature {
pub geometry: Option<Geometry<f64>>,
pub properties: HashMap<String, AttributeValue>,
pub id: Option<String>,
}
impl Feature {
pub fn new(geometry: Geometry<f64>) -> Self {
Self {
geometry: Some(geometry),
properties: HashMap::new(),
id: None,
}
}
pub fn empty() -> Self {
Self {
geometry: None,
properties: HashMap::new(),
id: None,
}
}
pub fn set_property(&mut self, key: impl Into<String>, value: AttributeValue) {
self.properties.insert(key.into(), value);
}
pub fn get_property(&self, key: &str) -> Option<&AttributeValue> {
self.properties.get(key)
}
}
#[derive(Debug, Clone, Default)]
pub struct FeatureCollection {
pub features: Vec<Feature>,
}
impl FeatureCollection {
pub fn new() -> Self {
Self {
features: Vec::new(),
}
}
pub fn push(&mut self, feature: Feature) {
self.features.push(feature);
}
pub fn len(&self) -> usize {
self.features.len()
}
pub fn is_empty(&self) -> bool {
self.features.is_empty()
}
pub fn iter(&self) -> impl Iterator<Item = &Feature> {
self.features.iter()
}
}
impl IntoIterator for FeatureCollection {
type Item = Feature;
type IntoIter = std::vec::IntoIter<Feature>;
fn into_iter(self) -> Self::IntoIter {
self.features.into_iter()
}
}
pub fn read_vector(path: &std::path::Path) -> crate::error::Result<FeatureCollection> {
let ext = path
.extension()
.and_then(|e| e.to_str())
.unwrap_or("")
.to_lowercase();
match ext.as_str() {
"geojson" | "json" => geojson_reader::read_geojson(path),
#[cfg(feature = "shapefile")]
"shp" => shapefile_reader::read_shapefile(path),
#[cfg(feature = "geopackage")]
"gpkg" => gpkg_reader::read_gpkg(path, None),
_ => {
#[allow(unused_mut)]
let mut supported = vec![".geojson", ".json"];
#[cfg(feature = "shapefile")]
{
supported.push(".shp");
}
#[cfg(feature = "geopackage")]
{
supported.push(".gpkg");
}
Err(crate::error::Error::Other(format!(
"Unsupported vector format: '.{}'. Supported: {}",
ext,
supported.join(", ")
)))
}
}
}