Skip to content

Commit cc1a847

Browse files
authored
Merge pull request #221 from siapy/fix
2 parents 06bf4b0 + beead97 commit cc1a847

File tree

11 files changed

+328
-173
lines changed

11 files changed

+328
-173
lines changed

CONTRIBUTING.md

Lines changed: 144 additions & 118 deletions
Large diffs are not rendered by default.

docs/concepts/entities.md

Lines changed: 63 additions & 29 deletions
Original file line numberDiff line numberDiff line change
@@ -22,79 +22,113 @@ SiaPy's architecture follows several key design principles:
2222

2323
The class structure is depicted in the following diagram:
2424

25-
![Entities Schematics](images/entities_schematics.png)
25+
![Entities Schematics](images/entities_schematics.svg)
2626

27-
## Spectral Image
27+
## Pixels
2828

29-
A `SpectralImage` is the primary container for spectral image data. It's a generic class that can wrap different image backends, allowing you to work with various file formats through a unified interface.
29+
??? api "API Documentation"
30+
[`siapy.entities.Pixels`][siapy.entities.Pixels]<br>
3031

31-
### Image Initialization Options
32+
The `Pixels` class represents spatial coordinates within spectral image, providing a container for *(x, y)* coordinate pairs. It uses pandas DataFrame internally for storage, enabling high-performance operations. The class provides multiple initialization methods and conversion functions to work with different data representations (i.e. DataFrames, list, arrays)
3233

33-
#### 1. Load from ENVI format (using spectral python)
34+
```python
35+
--8<-- "docs/concepts/src/pixels_01.py"
36+
```
3437

35-
This is commonly used for hyperspectral imagery from airborne or satellite sensors.
38+
## Signals
39+
40+
??? api "API Documentation"
41+
[`siapy.entities.signatures.Signals`][siapy.entities.signatures.Signals]<br>
42+
43+
The `Signals` class stores spectral data for each pixel in a pandas DataFrame, allowing you to use any column names you choose (e.g. "band_1", "nir", "red_edge"). You can initialize it from a DataFrame, lists, dicts or NumPy arrays.
3644

3745
```python
38-
--8<-- "docs/concepts/src/spectral_image_01.py"
46+
--8<-- "docs/concepts/src/signals_01.py"
3947
```
4048

41-
#### 2. Load from GeoTIFF or other geospatial formats (using rasterio)
49+
However, direct initialization of `Signals` is typically not necessary in practice. When you create a `Signatures` instance, the underlying `Signals` object is automatically generated and managed for you. This section demonstrates the `Signals` class primarily to illustrate how the `Signatures` class (discussed next) is composed internally and to provide insight into the data structure that powers spectral analysis.
4250

43-
Perfect for georeferenced data with spatial information.
51+
## Signatures
52+
53+
??? api "API Documentation"
54+
[`siapy.entities.Signatures`][siapy.entities.Signatures]<br>
55+
56+
The `Signatures` class represents spectral data collections by combining spatial coordinates (`Pixels`) with their corresponding spectral values (`Signals`). It provides a unified container that maintains the spatial-spectral relationship, allowing for analysis of spectral information at specific image locations. Internally, the data is stored as pandas DataFrames for efficient operations and indexing.
57+
58+
`Signatures` can be initialized in multiple ways. The explicit approach creates each component separately before combining them, providing clarity about the composition:
4459

4560
```python
46-
--8<-- "docs/concepts/src/spectral_image_02.py"
61+
--8<-- "docs/concepts/src/signatures_01.py:long"
4762
```
4863

49-
#### 3. Create from numpy array
64+
For more concise code, you can initialize a `Signatures` object directly from coordinate and signal values:
5065

51-
Useful for testing or when you already have image data in memory.
66+
```python
67+
--8<-- "docs/concepts/src/signatures_01.py:short"
68+
```
69+
70+
Both approaches yield equivalent results when initialized with the same data. You can access and work with the data using various DataFrame operations and conversion methods:
5271

5372
```python
54-
--8<-- "docs/concepts/src/spectral_image_03.py"
73+
--8<-- "docs/concepts/src/signatures_01.py:assert"
5574
```
5675

57-
#### 4. Create your own custom image class
76+
## Shape
5877

59-
For specialized file formats or custom processing needs, you can extend the ImageBase class.
78+
??? api "API Documentation"
79+
[`siapy.entities.Shape`][siapy.entities.Shape]<br>
80+
81+
The `Shape` class represents geometric shapes that can be associated with images, such as points, lines, and polygons.
6082

6183
```python
62-
--8<-- "docs/concepts/src/spectral_image_04.py"
84+
--8<-- "docs/concepts/src/shapes_01.py"
6385
```
6486

65-
## Pixels
87+
## Spectral Image
6688

67-
The `Pixels` class represents spatial coordinates within spectral image, providing a container for *(x, y)* coordinate pairs. It uses pandas DataFrame internally for storage, enabling high-performance operations. The class provides multiple initialization methods and conversion functions to work with different data representations (i.e. DataFrames, list, arrays)
89+
??? api "API Documentation"
90+
[`siapy.entities.SpectralImage`][siapy.entities.SpectralImage]<br>
91+
92+
A `SpectralImage` is the primary container for spectral image data. It's a generic class that can wrap different image backends, allowing you to work with various file formats through a unified interface.
93+
94+
### Image Initialization Options
95+
96+
#### 1. Load from ENVI format (using spectral python)
97+
98+
This is commonly used for hyperspectral imagery from airborne or satellite sensors.
6899

69100
```python
70-
--8<-- "docs/concepts/src/pixels_01.py"
101+
--8<-- "docs/concepts/src/spectral_image_01.py"
71102
```
72103

73-
## Signals
104+
#### 2. Load from GeoTIFF or other geospatial formats (using rasterio)
74105

75-
The `Signals` class stores spectral data for each pixel in a pandas DataFrame, allowing you to use any column names you choose (e.g. "band_1", "nir", "red_edge"). You can initialize it from a DataFrame, lists, dicts or NumPy arrays.
106+
Perfect for georeferenced data with spatial information.
76107

77108
```python
78-
--8<-- "docs/concepts/src/signals_01.py"
109+
--8<-- "docs/concepts/src/spectral_image_02.py"
79110
```
80111

81-
## Signatures
112+
#### 3. Create from numpy array
82113

83-
The `Signatures` class represents spectral data collections by combining spatial coordinates (`Pixels`) with their corresponding spectral values (`Signals`). It provides a unified container that maintains the spatial-spectral relationship, allowing for analysis of spectral information at specific image locations. Internally, the data is stored as pandas DataFrames for efficient operations and indexing.
114+
Useful for testing or when you already have image data in memory.
84115

85116
```python
86-
--8<-- "docs/concepts/src/signatures_01.py"
117+
--8<-- "docs/concepts/src/spectral_image_03.py"
87118
```
88119

89-
## Shape
120+
#### 4. Create your own custom image class
90121

91-
The `Shape` class represents geometric shapes that can be associated with images, such as points, lines, and polygons.
122+
For specialized file formats or custom processing needs, you can extend the ImageBase class.
92123

93124
```python
94-
--8<-- "docs/concepts/src/shapes_01.py"
125+
--8<-- "docs/concepts/src/spectral_image_04.py"
95126
```
96127

97-
## SpectralImageSet
128+
## Spectral Image Set
129+
130+
??? api "API Documentation"
131+
[`siapy.entities.SpectralImageSet`][siapy.entities.SpectralImageSet]<br>
98132

99133
The `SpectralImageSet` class manages a collection of spectral images.
100134

-50.3 KB
Binary file not shown.

docs/concepts/images/entities_schematics.svg

Lines changed: 4 additions & 0 deletions
Loading

docs/concepts/overview.md

Lines changed: 28 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -4,7 +4,10 @@
44

55
SiaPy follows a modular architecture organized around key components that work together to provide a comprehensive toolkit for spectral image analysis.
66

7-
### Core (`siapy.core`)
7+
### Core
8+
9+
??? note "API Documentation"
10+
`siapy.core`
811

912
The foundation of the library providing essential functionality:
1013

@@ -13,7 +16,10 @@ The foundation of the library providing essential functionality:
1316
- **Type definitions**: Common types used throughout the library
1417
- **Configuration**: System paths and global configuration settings
1518

16-
### Entities (`siapy.entities`)
19+
### Entities
20+
21+
??? note "API Documentation"
22+
`siapy.entities`
1723

1824
Fundamental data structures that represent spectral imaging data:
1925

@@ -23,34 +29,49 @@ Fundamental data structures that represent spectral imaging data:
2329
- **Shapes**: Geometric shapes for images' regions selection and masking
2430
- **Signatures**: Spectral signatures extracted from images
2531

26-
### Datasets (`siapy.datasets`)
32+
### Datasets
33+
34+
??? note "API Documentation"
35+
`siapy.datasets`
2736

2837
Tools for managing and working with datasets:
2938

3039
- **Tabular datasets**: Handling tabular data with spectral information
3140

32-
### Features (`siapy.features`)
41+
### Features
42+
43+
??? note "API Documentation"
44+
`siapy.features`
3345

3446
Functionality for working with spectral features:
3547

3648
- **Features**: Abstractions for feature extraction and selection
3749
- **Spectral indices**: Calculation of various spectral indices
3850

39-
### Transformations (`siapy.transformations`)
51+
### Transformations
52+
53+
??? note "API Documentation"
54+
`siapy.transformations`
4055

4156
Transformation capabilities:
4257

4358
- **Co-registration**: Aligning images from different sources
4459
- **Image processing**: Functions for image manipulation
4560

46-
### Optimizers (`siapy.optimizers`)
61+
### Optimizers
62+
63+
??? note "API Documentation"
64+
`siapy.optimizers`
4765

4866
Optimization, hyperparameter tuning and evaluation:
4967

5068
- **Optimization**: Machine learning training and optimization of hyperparameters
5169
- **Evaluation metrics and scoring mechanisms**: Tools for assessing model performance
5270

53-
### Utils (`siapy.utils`)
71+
### Utils
72+
73+
??? note "API Documentation"
74+
`siapy.utils`
5475

5576
Utility and plotting functions:
5677

docs/concepts/src/signals_01.py

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,3 +1,4 @@
11
from siapy.entities.signatures import Signals
22

3+
# Create from iterable (e.g. list, array)
34
signals = Signals.from_iterable([[0.1, 0.2, 0.3], [0.4, 0.5, 0.6]])

docs/concepts/src/signatures_01.py

Lines changed: 33 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -1,11 +1,39 @@
1-
from siapy.entities import Signatures
1+
# --8<-- [start:long]
2+
import pandas as pd
3+
from rich import print
24

3-
signatures = Signatures.from_signals_and_pixels(
5+
from siapy.entities import Pixels, Signatures
6+
from siapy.entities.signatures import Signals
7+
8+
# Option 1: Step-by-step initialization
9+
# Initialize Pixels object from a DataFrame
10+
pixels_df = pd.DataFrame({"x": [10, 30], "y": [20, 40]})
11+
pixels = Pixels(pixels_df)
12+
13+
# Initialize Signals object from a DataFrame
14+
signals_df = pd.DataFrame([[1, 2, 3], [4, 5, 6]])
15+
signals = Signals(signals_df)
16+
17+
# Create Signatures object from Pixels and Signals objects
18+
signatures1 = Signatures(pixels, signals)
19+
# --8<-- [end:long]
20+
21+
# --8<-- [start:short]
22+
# Option 2: Direct initialization with raw data
23+
# Initialize Signatures directly from raw signals and coordinates data
24+
signatures2 = Signatures.from_signals_and_pixels(
425
signals=[[1, 2, 3], [4, 5, 6]],
526
pixels=[[10, 20], [30, 40]],
627
)
28+
# --8<-- [end:short]
29+
30+
# --8<-- [start:assert]
31+
# Verify that both approaches produce equivalent results
32+
assert signatures1 == signatures2
733

8-
df_multi = signatures.to_dataframe_multiindex()
34+
# Print the DataFrame representation of Pixels and Signals
35+
df_multi = signatures2.to_dataframe_multiindex()
936
print(f"MultiIndex DataFrame:\n{df_multi}")
10-
print(f"Signals DataFrame:\n{signatures.signals.df}")
11-
print(f"Pixels DataFrame:\n{signatures.pixels.df}")
37+
print(f"Signals DataFrame:\n{signatures2.signals.df}")
38+
print(f"Pixels DataFrame:\n{signatures2.pixels.df}")
39+
# --8<-- [end:assert]

docs/examples/case_study.md

Lines changed: 26 additions & 14 deletions
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,8 @@
11
This section offers an overview of a case study based on real-world data.
22

3+
/// Note
34
> 💡 **All code snippets** used in this case study are available in the [GitHub repository](https://github.com/siapy/siapy-lib/tree/main/docs/examples/src).
5+
///
46

57
To follow along:
68

@@ -16,7 +18,9 @@ The hyperspectral dataset used in this case study was acquired using Hyspex push
1618
| VNIR-1600 | Visible to near-infrared (400–988 nm) | 160 | 3.6 nm |
1719
| SWIR-384 | Short-wave infrared (950–2500 nm) | 288 | 5.4 nm |
1820

19-
> **Note**: All hyperspectral data is provided as calibrated reflectance values, ensuring accuracy and reliability for your analysis.
21+
/// Note
22+
All hyperspectral data is provided as calibrated reflectance values, ensuring accuracy and reliability for your analysis.
23+
///
2024

2125
### 📁 File Naming Convention
2226

@@ -47,12 +51,12 @@ Before diving into the examples, verify that your SiaPy installation and data ar
4751
```
4852

4953
/// Warning
54+
If you encounter issues:
5055

51-
If you encounter issues:
52-
- Check that SiaPy is properly installed and your environment is activated
53-
- Verify that you've downloaded the example data
54-
- Ensure the `data_dir` variable points to the correct location of your dataset
55-
- Make sure both `.img` and `.hdr` files are present in your data directory
56+
- Check that SiaPy is properly installed and your environment is activated
57+
- Verify that you've downloaded the example data
58+
- Ensure the `data_dir` variable points to the correct location of your dataset
59+
- Make sure both `.img` and `.hdr` files are present in your data directory
5660
///
5761

5862
## 🧪 Source Code Examples
@@ -78,7 +82,8 @@ Before diving into the examples, verify that your SiaPy installation and data ar
7882
- File metadata and path information
7983
- Camera identification and associated geometric data
8084

81-
> 💡 **Implementation Note**: This script uses SiaPy's property decorators for read-only access to image attributes, following the library's design pattern for consistent data access.
85+
??? note "Implementation Details"
86+
This script uses decorators for read-only access to image attributes, following the library's design pattern for consistent data access.
8287

8388
**Example:**
8489

@@ -96,7 +101,8 @@ Before diving into the examples, verify that your SiaPy installation and data ar
96101
- **Data Extraction**: Methods for extracting spectral signatures and subarrays from specific image regions
97102
- **Visualization**: Converting hyperspectral data to displayable RGB images with optional histogram equalization
98103

99-
> 💡 **Implementation Note**: Notice how methods follow SiaPy's naming convention: converters use `to_` prefix (e.g., `to_numpy()`, `to_signatures()`, `to_display()`), while calculation methods use descriptive verbs.
104+
??? note "Implementation Details"
105+
Notice how methods follow SiaPy's naming convention: converters use `to_` prefix (e.g., `to_numpy()`, `to_signatures()`, `to_display()`), while calculation methods use descriptive verbs.
100106

101107
### Managing Image Collections
102108

@@ -116,7 +122,8 @@ Before diving into the examples, verify that your SiaPy installation and data ar
116122
- **Iteration Patterns**: Iterating through the image collection with standard Python iteration
117123
- **Filtering and Selection**: Selecting images by specific criteria (e.g., camera ID)
118124

119-
> 💡 **Implementation Note**: SpectralImageSet implements standard Python container interfaces, making it behave like a familiar collection type with additional hyperspectral-specific functionality.
125+
??? note "Implementation Details"
126+
`SpectralImageSet` implements standard Python container interfaces, making it behave like a familiar collection type with additional hyperspectral-specific functionality.
120127

121128
### Interactive Pixel and Area Selection
122129

@@ -139,7 +146,8 @@ The selected pixels are highlighted in the image below.
139146
- **User Interaction**: Simple keyboard-based interaction model (press Enter to finish selection)
140147
- **Results Access**: Accessing the resulting Pixels object and its DataFrame representation
141148

142-
> 💡 **Implementation Note**: The `pixels_select_click` function handles the display, interaction, and collection of pixel coordinates in a single operation, simplifying user interaction code.
149+
??? note "Implementation Details"
150+
The `pixels_select_click` function handles the display, interaction, and collection of pixel coordinates in a single operation, simplifying user interaction code.
143151

144152
**Example:**
145153

@@ -160,7 +168,8 @@ The selected areas are highlighted in the image below.
160168
- **Polygon-Based Selection**: Defining complex shapes for region-based analysis
161169
- **Selection Management**: Organized representation of selected areas for further processing
162170

163-
> 💡 **Implementation Note**: Selected areas are returned as a list of Pixels objects, each representing a distinct region that can be separately analyzed or processed.
171+
??? note "Implementation Details"
172+
Selected areas are returned as a list of `Pixels` objects, each representing a distinct region that can be separately analyzed or processed.
164173

165174
### Image Transformation and Processing
166175

@@ -179,7 +188,8 @@ The selected areas are highlighted in the image below.
179188
- **Transformation Calculation**: Computing the mathematical transformation between coordinate systems
180189
- **Spatial Alignment**: Creating a foundation for aligning multi-sensor hyperspectral data
181190

182-
> 💡 **Implementation Note**: The `corregistrator.align()` function computes a transformation matrix that can transform coordinates from one image space to another, essential for multi-sensor data fusion.
191+
??? note "Implementation Details"
192+
The `corregistrator.align()` function computes a transformation matrix that can transform coordinates from one image space to another, essential for multi-sensor data fusion.
183193

184194
**Example:**
185195

@@ -196,7 +206,8 @@ The selected areas are highlighted in the image below.
196206
- **Cross-Spectral Analysis**: Enabling analysis of the same physical regions across different spectral data
197207
- **Visual Verification**: Displaying both images with highlighted areas to verify correct transformation
198208

199-
> 💡 **Implementation Note**: The transformation is applied to the Pixels objects directly, allowing selected regions to be mapped between different spectral ranges while preserving their shape relationships.
209+
??? note "Implementation Details"
210+
The transformation is applied to the `Pixels` objects directly, allowing selected regions to be mapped between different spectral ranges while preserving their shape relationships.
200211

201212
**Example:**
202213

@@ -213,7 +224,8 @@ The selected areas are highlighted in the image below.
213224
- **Normalization**: Area-based normalization for standardizing image intensity distributions
214225
- **Data Augmentation**: Creating modified versions of images for machine learning training
215226

216-
> 💡 **Implementation Note**: All transformation functions follow a consistent input/output pattern, taking NumPy arrays as input and returning the transformed arrays, making them easily composable for complex processing pipelines.
227+
??? note "Implementation Details"
228+
All transformation functions follow a consistent input/output pattern, taking NumPy arrays as input and returning the transformed arrays, making them easily composable for complex processing pipelines.
217229

218230
---
219231

mkdocs.yml

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -187,6 +187,7 @@ plugins:
187187
- exclude:
188188
glob:
189189
- __pycache__/*
190+
- data/*
190191
- mkdocstrings:
191192
handlers:
192193
python:

0 commit comments

Comments
 (0)