Quick start
Use ordinary DataFrames with one or more columns of GeoInterface-compatible geometries.
julia
using GeoDataFrames
points = GeoInterface.Point.([(4.89, 52.37), (4.90, 52.38)]) # point geometry
df = DataFrame(geometry=points, name="test");2×2 DataFrame
| Row | geometry | name |
|---|---|---|
| Point… | String | |
| 1 | Point((4.89,52.37)) | test |
| 2 | Point((4.9,52.38)) | test |
Read and inspect
Read a vector file into a DataFrame by providing a filename or url:
julia
df = GeoDataFrames.read("https://github.com/yeesian/ArchGDALDatasets/raw/refs/heads/master/ospy/data1/sites.shp")
(rows=nrow(df), geometrycolumns=GeoInterface.geometrycolumns(df), crs=GeoInterface.crs(df))(rows = 42, geometrycolumns = (:geometry,), crs = WellKnownText{GeoFormatTypes.CRS}(GeoFormatTypes.CRS(), "PROJCS[\"WGS 84 / UTM zone 12N\",GEOGCS[\"WGS 84\",DATUM[\"WGS_1984\",SPHEROID[\"WGS 84\",6378137,298.257223563,AUTHORITY[\"EPSG\",\"7030\"]],AUTHORITY[\"EPSG\",\"6326\"]],PRIMEM[\"Greenwich\",0,AUTHORITY[\"EPSG\",\"8901\"]],UNIT[\"degree\",0.0174532925199433,AUTHORITY[\"EPSG\",\"9122\"]],AUTHORITY[\"EPSG\",\"4326\"]],PROJECTION[\"Transverse_Mercator\"],PARAMETER[\"latitude_of_origin\",0],PARAMETER[\"central_meridian\",-111],PARAMETER[\"scale_factor\",0.9996],PARAMETER[\"false_easting\",500000],PARAMETER[\"false_northing\",0],UNIT[\"metre\",1,AUTHORITY[\"EPSG\",\"9001\"]],AXIS[\"Easting\",EAST],AXIS[\"Northing\",NORTH],AUTHORITY[\"EPSG\",\"32612\"]]"))Basic operation with lines and polygons
Geometry operations apply to GeoInterface geometries in your table.
julia
using NaturalEarth
using GeoDataFrames: setcrs!
countries = select(
DataFrame(naturalearth("admin_0_countries", 50)),
:NAME,
:geometry,
)
rivers = select(
DataFrame(naturalearth("rivers_lake_centerlines", 50)),
:name_en,
:geometry,
)
candidate_countries = subset(
countries,
:NAME => ByRow(
name -> name in ["Austria", "Germany", "Hungary", "Poland", "Romania"],
),
)
danube = subset(rivers, :name_en => ByRow(isequal("Danube")))
selected = subset(
candidate_countries,
:geometry => ByRow(
country -> any(
river -> intersects(country, river),
danube.geometry,
),
),
)
selected.NAME4-element Vector{String}:
"Romania"
"Hungary"
"Germany"
"Austria"Plot geometries
julia
using CairoMakie
fig = plot(
candidate_countries.geometry;
color = (:lightgray, 0.35),
strokecolor = :gray,
axis = (; title = "Countries intersected by the Danube"),
)
plot!(selected.geometry; color = (:tomato, 0.5), strokecolor = :tomato)
plot!(danube.geometry; color = :dodgerblue, linewidth = 3)
fig
Write
Write any Tables.jl-compatible table that has geometry metadata (or pass geometrycolumn/crs keywords when needed):
julia
tmp = mktempdir()
path = joinpath(tmp, "zones.gpkg")
GeoDataFrames.write(path, candidate_countries)
isfile(path)trueFor layers, advanced ArchGDAL options, native-driver behavior, metadata management, reprojection, spatial joins, and performance trade-offs, use the how-to guides and reference.