diff --git a/doc/index.rst b/doc/index.rst index 58b573a..aa51296 100644 --- a/doc/index.rst +++ b/doc/index.rst @@ -78,7 +78,7 @@ Here's a quick example: Open an Issue on GitHub. - .. button-link:: https://github.com/compgeolab/xlandsat + .. button-link:: https://github.com/compgeolab/xlandsat/issues :click-parent: :color: primary :outline: @@ -131,7 +131,7 @@ Here's a quick example: time to bring new ideas on how we can improve the project. Submit `issues on GitHub `__. -.. admonition:: Looking for large-scale cloud-based processing? +.. admonition:: Looking for large-scale processing or other satellites? :class: seealso Our goal is **not** to provide a solution for large-scale data processing. diff --git a/doc/overview.rst b/doc/overview.rst index e26f600..4e2d571 100644 --- a/doc/overview.rst +++ b/doc/overview.rst @@ -16,69 +16,96 @@ single import: import xlandsat as xls +Why use xlandsat? +----------------- + +One of the main features of xlandsat is the ability to read a scene downloaded +from `USGS EarthExplorer `__ into an +:class:`xarray.Dataset`, which is very useful for processing and plotting +multidimensional array data. +The downloaded scenes can come in 2 main formats: + +1. A ``.tar`` file which includes several bands in ``.TIF`` format and metadata in text files. +2. The bands and metadata files downloaded individually. + +When reading the TIF files using tools like +`rioxarray `__, some of +the rich metadata can be missing since it's not always present in the TIF files +themselves. +Things like UTM zones, conversion factors, units, data provenance, WRS path/row +numbers, etc. +We take care of fetching that information from the ``*_MTL.txt`` files provided +by EarthExplorer so that xarray can use it, for example when annotating plots. + + Download a sample scene ----------------------- -As an example, lets download a tar archive of a Landsat 8 scene of the -`Brumadinho tailings dam disaster `__ -that happened in 2019 in Brazil. -The archive is available on figshare at -https://doi.org/10.6084/m9.figshare.21665630 and includes scenes from before -and after the disaster as both the full scene and a cropped version. +The :mod:`xlandsat.datasets` module includes functions for downloading some +sample scenes that we can use. These are cropped to smaller regions of interest +in order to save download time. But everything we do here with these sample +scenes is exactly the same as you would do with a full scene from +EarthExplorer. -We'll use the functions in :mod:`xlandsat.datasets` to download the scenes from -before and after the disaster to our computer. To save space and bandwidth, -these are cropped versions of the full Landsat scenes. +As an example, lets download a ``.tar`` archive of a Landsat 9 scene of the +city of Manaus, in the Brazilian Amazon: .. jupyter-execute:: - path_before = xls.datasets.fetch_brumadinho_before() - path_after = xls.datasets.fetch_brumadinho_after() - print(path_before) - print(path_after) + path_to_archive = xls.datasets.fetch_manaus() + print(path_to_archive) +The :func:`~xlandsat.datasets.fetch_manaus` function downloads the data file +and returns the **path** to the archive on your machine as an :class:`str`. +The rest of this tutorial can be executed with your own data by changing the +``path_to_archive`` to point to your data file instead. .. tip:: + The path can also point to a folder with the ``.TIF`` and the ``*_MTL.txt`` + file instead of a ``.tar`` archive. + +.. note:: + Running the code above will only download the data once. We use `Pooch `__ to handle the downloads and it's smart - enough to check if the file already exists on your computer. See - :func:`pooch.retrieve` for more information. + enough to check if the file already exists on your computer. .. seealso:: If you want to use the full scenes instead of the cropped version, use :func:`pooch.retrieve` to fetch them from the figshare archive - https://doi.org/10.6084/m9.figshare.21665630. + https://doi.org/10.6084/m9.figshare.24167235.v1. -Load the scenes ---------------- +Load the scene +-------------- -Now that we have paths to the tar archives of the scenes, we can use +Now that we have the path to the tar archive of the scene, we can use :func:`xlandsat.load_scene` to read the bands and metadata directly from the -archives (without unpacking): +archive: .. jupyter-execute:: - before = xls.load_scene(path_before) - before + scene = xls.load_scene(path_to_archive) + scene -And the after scene: -.. jupyter-execute:: +.. tip:: - after = xls.load_scene(path_after) - after + Placing the ``scene`` variable at the end of a code cell in a Jupyter + notebook will display a nice preview of the data. This is very useful for + looking up metadata and seeing which bands were loaded. -.. admonition:: Did you notice? - :class: note +The scene is an :class:`xarray.Dataset`. It contains general metadata for the +scene and all of the bands available in the archive as +:class:`xarray.DataArray`. +The bands each have their own set of metadata as well and can be accessed by +name: + +.. jupyter-execute:: - If you look carefully at the coordinates for each scene, you may notice - that they don't exactly coincide in area. That's OK since :mod:`xarray` - knows how to take the pixel coordinates into account when doing - mathematical operations like calculating indices and differences between - scenes. + scene.nir Plot some reflectance bands @@ -87,25 +114,26 @@ Plot some reflectance bands Now we can use the :meth:`xarray.DataArray.plot` method to make plots of individual bands with :mod:`matplotlib`. A bonus is that :mod:`xarray` uses the metadata that :func:`xlandsat.load_scene` inserts into the scene to -automatically add labels and annotations to the plot. +automatically add labels and annotations to the plot: .. jupyter-execute:: import matplotlib.pyplot as plt - fig, (ax1, ax2) = plt.subplots(2, 1, figsize=(10, 12)) + band_names = list(scene.data_vars.keys()) - # Make the pseudocolor plots of the near infrared band - before.nir.plot(ax=ax1) - after.nir.plot(ax=ax2) + fig, axes = plt.subplots( + len(band_names), 1, figsize=(8, 16), layout="compressed", + ) # Set the title using metadata from each scene - ax1.set_title(f"Before: {before.attrs['title']}") - ax2.set_title(f"After: {after.attrs['title']}") + fig.suptitle(scene.attrs["title"]) - # Set the aspect to equal so that pixels are squares, not rectangles - ax1.set_aspect("equal") - ax2.set_aspect("equal") + for band, ax in zip(band_names, axes.ravel()): + # Make a pseudocolor plot of the band + scene[band].plot(ax=ax) + # Set the aspect to equal so that pixels are squares, not rectangles + ax.set_aspect("equal") plt.show() @@ -113,13 +141,12 @@ automatically add labels and annotations to the plot. What now? --------- -Learn more about what you can do with xlandsat and xarray: +Checkout some of the other things that you can do with xlandsat: * :ref:`composites` * :ref:`indices` -* :ref:`pansharpen` -By getting the data into an :class:`xarray.Dataset`, xlandsat opens the door -for a huge range of operations. You now have access to everything that -:mod:`xarray` can do: interpolation, reduction, slicing, grouping, saving to -cloud-optimized formats, and much more. So go off and do something cool! +Plus, by getting the data into an :class:`xarray.Dataset`, xlandsat opens the +door for a huge range of operations. You now have access to everything that +:mod:`xarray` can do: reduction, slicing, grouping, saving to cloud-optimized +formats, and much more. So go off and do something cool!