From 98d4317506ccd96929dc5785104a8fb58d7fa29f Mon Sep 17 00:00:00 2001 From: Paul van Genuchten Date: Sat, 20 Jun 2026 23:28:43 +0200 Subject: [PATCH] add section on gdal api --- workshop/jupyter/content/data/world.rgb.tif | Bin 411822 -> 412810 bytes .../content/notebooks/05-raster-data.ipynb | 146 ++++++------------ workshop/jupyter/requirements.txt | 1 + 3 files changed, 46 insertions(+), 101 deletions(-) diff --git a/workshop/jupyter/content/data/world.rgb.tif b/workshop/jupyter/content/data/world.rgb.tif index ed695e151253f0b020f25b6fff32d6a3a9792efd..3d3c49e8c5abfaa75412d5ce5b6bd54b5dc859c4 100644 GIT binary patch delta 417 zcmZ2CQL<~MB&VmR7Q;FZHU^&QcU{>O8?{=s7+bZNTD6#4wOCrUShs4iwRkWJf+d+6 zJg2#_DKWcwu}utAWNP!A?g8X_vU#&H@HO)=Ff%YP@BrCOEj$ctK(-2yy}q59K?2AQ z0kSu?Gcj-g*)2eJ!xAQje?WE*kPQMHAUHkUo$cWC6>e+?rfYbxwbk3WyEyvzrj{h8 zB$g!FaVaR+c$TE*D&!^RrrIjGxCT21c?N`d`uiy<6es2upj>M8?{=s7+bZNTD6#4wOCrUShs4iwRivk8hQ*E diff --git a/workshop/jupyter/content/notebooks/05-raster-data.ipynb b/workshop/jupyter/content/notebooks/05-raster-data.ipynb index 6510c40..39d0782 100644 --- a/workshop/jupyter/content/notebooks/05-raster-data.ipynb +++ b/workshop/jupyter/content/notebooks/05-raster-data.ipynb @@ -47,22 +47,12 @@ "cell_type": "markdown", "metadata": {}, "source": [ - "## Tools\n", + "## GDAL\n", "\n", - "[GDAL](https://gdal.org/) is today the reference toolbox to read and write raster data. It is used by almost all of the FOSS4G programmes and libraries that interact with rasters. GDAL is also used by many commercial products. A [Python API](https://gdal.org/python/) is available for GDAL that provides much of the functionality.\n", - "\n", - "The [RasterIO](https://rasterio.readthedocs.io) library makes interaction with rasters considerably more convenient, however. It is in essence a bridge between GDAL and the [NumPy](https://numpy.org/) package for scientific computing. With RasterIO rasters are easily translated into NumPy arrays and vice-versa." - ] - }, - { - "cell_type": "markdown", - "metadata": {}, - "source": [ - "## Reading in and inspecting a raster\n", - "\n", - "Possibly the most essential operation is to open a raster for processing or inspection. This is rather simple:\n", - "\n" - ] + "[GDAL](https://gdal.org/) is the reference toolbox to read and write raster data. It is used by almost all of the \n", + "FOSS4G programmes and libraries that interact with rasters. GDAL is also used by many commercial products. \n", + "A [Python API](https://gdal.org/python/) is available with most of the GDAL functionality." + ] }, { "cell_type": "code", @@ -70,26 +60,20 @@ "metadata": {}, "outputs": [], "source": [ - "import rasterio" - ] - }, - { - "cell_type": "code", - "execution_count": null, - "metadata": {}, - "outputs": [], - "source": [ - "world = rasterio.open('../data/world.rgb.tif')" + "from osgeo import gdal\n", + "gdal.UseExceptions()\n", + "ds = gdal.Open('../data/world.rgb.tif')\n", + "band = ds.GetRasterBand(1)\n", + "band.GetDescription()" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ - "The `open` method returns an object of the class `DatasetReader`, which contains the raster meta-data and the set of bands included. `open` can also be invoked in write mode (with the extra argument `'w'`), in which case it returns a `DatasetWriter` type object.\n", - "\n", - "`DatasetReader` provides easy access to useful meta-data, for instance the raster dimensions:" - ] + "A typical use case for using gdal in python is resampling a grid and creating overviews, so the tiff can be used as a\n", + "Cloud Optimized GeoTiff" + ] }, { "cell_type": "code", @@ -97,82 +81,43 @@ "metadata": {}, "outputs": [], "source": [ - "world.width" + "# Resample\n", + "gdal.Warp('temp/output_3857_cog.tif','../data/world.rgb.tif',dstSRS='EPSG:3857',format='COG')\n" + ] }, - { - "cell_type": "code", - "execution_count": null, - "metadata": {}, - "outputs": [], - "source": [ - "world.height" - ] - }, - { - "cell_type": "markdown", - "metadata": {}, - "source": [ - "Also information related to the reader object itself:" - ] - }, - { - "cell_type": "code", - "execution_count": null, - "metadata": {}, - "outputs": [], - "source": [ - "world.name" - ] - }, - { - "cell_type": "code", - "execution_count": null, - "metadata": {}, - "outputs": [], - "source": [ - "world.mode" - ] - }, - { - "cell_type": "code", - "execution_count": null, - "metadata": {}, - "outputs": [], - "source": [ - "world.meta" - ] - }, - { +{ "cell_type": "code", "execution_count": null, "metadata": {}, "outputs": [], "source": [ - "world.shape" + "# Display COG in a viewer \n", + "from localtileserver import TileClient, get_leaflet_tile_layer \n", + "from ipyleaflet import Map \n", + "client = TileClient('temp/output_3857_cog.tif') \n", + "m = Map() \n", + "m.add(get_leaflet_tile_layer(client)) \n", + "m\n" ] }, + + { "cell_type": "markdown", "metadata": {}, "source": [ - "The `count` property informs on the number of bands:" - ] - }, - { - "cell_type": "code", - "execution_count": null, - "metadata": {}, - "outputs": [], - "source": [ - "world.count" + "## RasterIO \n", + "\n", + "The [RasterIO](https://rasterio.readthedocs.io) library is a bridge between GDAL and the [NumPy](https://numpy.org/) package\n", + "for scientific computing. With RasterIO rasters are easily translated into NumPy arrays and vice-versa." ] }, { "cell_type": "markdown", "metadata": {}, "source": [ - "Data types of bands are provided with `dtypes`:" + "Open a raster for processing or inspection:\n" ] }, { @@ -181,23 +126,19 @@ "metadata": {}, "outputs": [], "source": [ - "world.dtypes" + "import rasterio\n", + "world = rasterio.open('../data/world.rgb.tif')" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ - "The geographic information is also available:" - ] - }, - { - "cell_type": "code", - "execution_count": null, - "metadata": {}, - "outputs": [], - "source": [ - "world.crs" + "The `open` method returns an object of the class `DatasetReader`, which contains the raster meta-data and the set of \n", + "bands included. `open` can also be invoked in write mode (with the extra argument `'w'`), in which case it returns a \n", + "`DatasetWriter` type object.\n", + "\n", + "`DatasetReader` provides easy access to useful meta-data:" ] }, { @@ -206,14 +147,17 @@ "metadata": {}, "outputs": [], "source": [ - "world.bounds" + "print('size:', world.width, world.height)\n", + "print('crs:', world.crs)\n", + "print('bounds:', world.bounds)\n", + "\n" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ - "## Basic raster plotting" + "## Raster plotting" ] }, { @@ -238,7 +182,7 @@ "cell_type": "markdown", "metadata": {}, "source": [ - "We can also display a single band of a multiband image by passing a tuple (raster source, band):" + "We can also display a single band or a multiband image by passing a tuple (raster source, band):" ] }, { @@ -533,4 +477,4 @@ }, "nbformat": 4, "nbformat_minor": 4 -} +} \ No newline at end of file diff --git a/workshop/jupyter/requirements.txt b/workshop/jupyter/requirements.txt index cbab6b2..ef3e9c5 100644 --- a/workshop/jupyter/requirements.txt +++ b/workshop/jupyter/requirements.txt @@ -7,6 +7,7 @@ geopandas descartes folium bokeh +localtileserver ipyleaflet pydeck pygeometa # >0.7 removed by Just