This is an automated email from the ASF dual-hosted git repository.
desruisseaux pushed a commit to branch geoapi-4.0
in repository https://gitbox.apache.org/repos/asf/sis.git
The following commit(s) were added to refs/heads/geoapi-4.0 by this push:
new 67491ac139 Make possible to write a raster with a `BandedSampleModel`
where the data are stored in a single bank.
67491ac139 is described below
commit 67491ac1393f1a5f8e1e2c4fa0a7fb14bb5f9d14
Author: Martin Desruisseaux <[email protected]>
AuthorDate: Mon Jul 28 17:49:29 2025 +0200
Make possible to write a raster with a `BandedSampleModel` where the data
are stored in a single bank.
---
.../apache/sis/io/stream/HyperRectangleWriter.java | 39 +++++++++++++++++++---
1 file changed, 34 insertions(+), 5 deletions(-)
diff --git
a/endorsed/src/org.apache.sis.storage/main/org/apache/sis/io/stream/HyperRectangleWriter.java
b/endorsed/src/org.apache.sis.storage/main/org/apache/sis/io/stream/HyperRectangleWriter.java
index 61aa85eeb3..30f001d47d 100644
---
a/endorsed/src/org.apache.sis.storage/main/org/apache/sis/io/stream/HyperRectangleWriter.java
+++
b/endorsed/src/org.apache.sis.storage/main/org/apache/sis/io/stream/HyperRectangleWriter.java
@@ -23,8 +23,10 @@ import java.awt.Rectangle;
import java.awt.image.Raster;
import java.awt.image.DataBuffer;
import java.awt.image.SampleModel;
+import java.awt.image.BandedSampleModel;
import java.awt.image.ComponentSampleModel;
import java.awt.image.MultiPixelPackedSampleModel;
+import java.awt.image.PixelInterleavedSampleModel;
import java.awt.image.SinglePixelPackedSampleModel;
import java.awt.image.RasterFormatException;
import org.apache.sis.util.ArraysExt;
@@ -265,7 +267,18 @@ public class HyperRectangleWriter {
/**
* Creates a new writer for raster data described by the given sample
model.
* The returned writer will need to be applied repetitively for each
bank
- * if {@link #bankIndices()} returns an array with a length greater
than one.
+ * if {@link #numBanks()} returns a value greater than one.
+ *
+ * <h4>Banded versus interleaved</h4>
+ * If the given sample model is an instance of {@link
BandedSampleModel},
+ * then this method will unconditionally handle each band as if it was
stored in a separated bank,
+ * even if it would be more efficient to handle the data as a {@link
PixelInterleavedSampleModel}.
+ * For example, the GeoTIFF writer does its own analysis of the sample
model for deciding whether
+ * to declare in <abbr>TIFF</abbr> tags that the data are in "planar"
or "chunky" configuration.
+ * The {@code HyperRectangleWriter} must follow that configuration.
+ *
+ * <p>If the given sample model is the generic {@link
ComponentSampleModel}, then this method decides
+ * automatically whether the banded or pixel interleaved sample model
is the best match for the data.</p>
*
* @param sm the sample model of the rasters to write.
* @return writer for rasters using the specified sample model (never
{@code null}).
@@ -276,7 +289,23 @@ public class HyperRectangleWriter {
scanlineStride = sm.getScanlineStride();
bankIndices = sm.getBankIndices();
bandOffsets = sm.getBandOffsets();
- if (ArraysExt.allEquals(bankIndices, bankIndices[0])) {
+ boolean isInterleaved = (sm instanceof
PixelInterleavedSampleModel);
+ if (!(isInterleaved || sm instanceof BandedSampleModel)) {
+ /*
+ * Generic `ComponentSampleModel`. Detect whether it can be
handled as interleaved.
+ * The sample model shall use only one bank (actually, that
condition is true even
+ * for `PixelInterleavedSampleModel`). Furthermore, the index
of each sample value
+ * (relative to the base index) should be inside a pixel
stride.
+ */
+ int min = Integer.MAX_VALUE;
+ int max = Integer.MIN_VALUE; // (max - min) defaut to 1 if
`bandOffsets` is empty.
+ for (int b : bandOffsets) {
+ if (b < min) min = b;
+ if (b > max) max = b;
+ }
+ isInterleaved = (max - min) < pixelStride;
+ }
+ if (isInterleaved && ArraysExt.allEquals(bankIndices,
bankIndices[0])) {
/*
* PixelInterleavedSampleModel (at least conceptually, no
matter the actual type).
* The returned `HyperRectangleWriter` instance may write all
sample values in a
@@ -430,7 +459,7 @@ public class HyperRectangleWriter {
/**
* Creates a new writer for raster data described by the given sample
model.
* The returned writer will need to be applied repetitively for each
bank
- * if {@link #bankIndices()} returns an array with a length greater
than one.
+ * if {@link #numBanks()} returns a value greater than one.
*
* @param sm the sample model of the rasters to write.
* @return writer for rasters using the specified sample model (never
{@code null}).
@@ -448,7 +477,7 @@ public class HyperRectangleWriter {
/**
* Creates a new writer for data of the specified raster.
* The returned writer will need to be applied repetitively for each
bank
- * if {@link #bankIndices()} returns an array with a length greater
than one.
+ * if {@link #numBanks()} returns a value greater than one.
*
* <h4>Tile size</h4>
* Many formats such as GeoTIFF require that all tiles have the same
size,
@@ -520,7 +549,7 @@ public class HyperRectangleWriter {
* Returns the offset to add to a bank to write with {@code
HyperRectangleWriter}.
* This is in addition of offsets declared in {@link
DataBuffer#getOffsets()}.
*
- * @param i index from 0 inclusive to {@link #numBanks()} exclusive.
+ * @param i index from 0 inclusive to {@link #numBanks()}
exclusive.
* @param bufferOffset the value of <code>{@link
DataBuffer#getOffsets()}[bankIndex(i)]</code>.
* @return offset of a banks to write with {@code
HyperRectangleWriter}.
*/