Browse Source

Fix image data size computation with pixel storage skip applied.

It now tries to find smallest line/rectangle/cube that covers the area.
Previously it was a bit more in some cases.
pull/162/merge
Vladimír Vondruš 10 years ago
parent
commit
1cfd2dc7b5
  1. 4
      src/Magnum/BufferImage.h
  2. 4
      src/Magnum/Image.h
  3. 2
      src/Magnum/ImageView.h
  4. 10
      src/Magnum/PixelStorage.cpp
  5. 63
      src/Magnum/PixelStorage.h
  6. 99
      src/Magnum/Test/PixelStorageTest.cpp
  7. 2
      src/Magnum/Trade/ImageData.cpp
  8. 2
      src/Magnum/Trade/ImageData.h
  9. 2
      src/MagnumPlugins/TgaImageConverter/TgaImageConverter.cpp

4
src/Magnum/BufferImage.h

@ -145,7 +145,7 @@ template<UnsignedInt dimensions> class BufferImage {
*
* See @ref PixelStorage::dataProperties() for more information.
*/
std::tuple<std::size_t, VectorTypeFor<dimensions, std::size_t>, std::size_t> dataProperties() const {
std::tuple<VectorTypeFor<dimensions, std::size_t>, VectorTypeFor<dimensions, std::size_t>, std::size_t> dataProperties() const {
return Implementation::imageDataProperties<dimensions>(*this);
}
@ -333,7 +333,7 @@ template<UnsignedInt dimensions> class CompressedBufferImage {
* @requires_gl Compressed pixel storage is hardcoded in OpenGL ES and
* WebGL.
*/
std::tuple<std::size_t, VectorTypeFor<dimensions, std::size_t>, std::size_t> dataProperties() const {
std::tuple<VectorTypeFor<dimensions, std::size_t>, VectorTypeFor<dimensions, std::size_t>, std::size_t> dataProperties() const {
return Implementation::compressedImageDataProperties<dimensions>(*this);
}
#endif

4
src/Magnum/Image.h

@ -135,7 +135,7 @@ template<UnsignedInt dimensions> class Image {
*
* See @ref PixelStorage::dataProperties() for more information.
*/
std::tuple<std::size_t, VectorTypeFor<dimensions, std::size_t>, std::size_t> dataProperties() const {
std::tuple<VectorTypeFor<dimensions, std::size_t>, VectorTypeFor<dimensions, std::size_t>, std::size_t> dataProperties() const {
return Implementation::imageDataProperties<dimensions>(*this);
}
@ -339,7 +339,7 @@ template<UnsignedInt dimensions> class CompressedImage {
* @requires_gl Compressed pixel storage is hardcoded in OpenGL ES and
* WebGL.
*/
std::tuple<std::size_t, VectorTypeFor<dimensions, std::size_t>, std::size_t> dataProperties() const {
std::tuple<VectorTypeFor<dimensions, std::size_t>, VectorTypeFor<dimensions, std::size_t>, std::size_t> dataProperties() const {
return Implementation::compressedImageDataProperties<dimensions>(*this);
}
#endif

2
src/Magnum/ImageView.h

@ -134,7 +134,7 @@ template<UnsignedInt dimensions> class ImageView {
*
* See @ref PixelStorage::dataProperties() for more information.
*/
std::tuple<std::size_t, VectorTypeFor<dimensions, std::size_t>, std::size_t> dataProperties() const {
std::tuple<VectorTypeFor<dimensions, std::size_t>, VectorTypeFor<dimensions, std::size_t>, std::size_t> dataProperties() const {
return Implementation::imageDataProperties<dimensions>(*this);
}

10
src/Magnum/PixelStorage.cpp

@ -156,7 +156,7 @@ std::size_t PixelStorage::pixelSize(PixelFormat format, PixelType type) {
CORRADE_ASSERT_UNREACHABLE();
}
std::tuple<std::size_t, Math::Vector3<std::size_t>, std::size_t> PixelStorage::dataProperties(const PixelFormat format, const PixelType type, const Vector3i& size) const {
std::tuple<Math::Vector3<std::size_t>, Math::Vector3<std::size_t>, std::size_t> PixelStorage::dataProperties(const PixelFormat format, const PixelType type, const Vector3i& size) const {
const std::size_t pixelSize = PixelStorage::pixelSize(format, type);
const Math::Vector3<std::size_t> dataSize{
std::size_t((((
@ -170,13 +170,13 @@ std::tuple<std::size_t, Math::Vector3<std::size_t>, std::size_t> PixelStorage::d
std::size_t(size.y()),
#endif
std::size_t(size.z())};
const std::size_t offset = (Math::Vector3<std::size_t>{pixelSize, dataSize.x(), dataSize.xy().product()}*Math::Vector3<std::size_t>{_skip}).sum();
return std::make_tuple(offset, size.product() ? dataSize : Math::Vector3<std::size_t>{}, pixelSize);
return std::make_tuple(Math::Vector3<std::size_t>{pixelSize, dataSize.x(), dataSize.xy().product()}*Math::Vector3<std::size_t>{_skip},
size.product() ? dataSize : Math::Vector3<std::size_t>{}, pixelSize);
}
#ifndef MAGNUM_TARGET_GLES
std::tuple<std::size_t, Math::Vector3<std::size_t>, std::size_t> CompressedPixelStorage::dataProperties(const Vector3i& size) const {
std::tuple<Math::Vector3<std::size_t>, Math::Vector3<std::size_t>, std::size_t> CompressedPixelStorage::dataProperties(const Vector3i& size) const {
CORRADE_ASSERT(_blockDataSize && _blockSize.product(), "CompressedPixelStorage::dataProperties(): expected non-zero storage parameters", {});
const Vector3i blockCount = (size + _blockSize - Vector3i{1})/_blockSize;
@ -186,7 +186,7 @@ std::tuple<std::size_t, Math::Vector3<std::size_t>, std::size_t> CompressedPixel
std::size_t(blockCount.z())};
const Vector3i skipBlockCount = (_skip + _blockSize - Vector3i{1})/_blockSize;
const std::size_t offset = (Math::Vector3<std::size_t>{1, dataSize.x(), dataSize.xy().product()}*Math::Vector3<std::size_t>{skipBlockCount}).sum()*_blockDataSize;
const Math::Vector3<std::size_t> offset = (Math::Vector3<std::size_t>{1, dataSize.x(), dataSize.xy().product()}*Math::Vector3<std::size_t>{skipBlockCount})*_blockDataSize;
return std::make_tuple(offset, size.product() ? dataSize : Math::Vector3<std::size_t>{}, _blockDataSize);
}

63
src/Magnum/PixelStorage.h

@ -203,14 +203,14 @@ class MAGNUM_EXPORT PixelStorage {
/**
* @brief Data properties for given parameters
*
* Returns byte offset, (row length, row count, layer count) and pixel
* size for image of given @p size with current pixel storage
* parameters, @p format and @p type. The offset reflects the @ref skip()
* parameter. Adding byte offset and product of the vector gives
* minimal byte count to store given data.
* Returns byte offset in each direction, (row length, row count, layer
* count) and pixel size for image of given @p size with current pixel
* storage parameters, @p format and @p type. The offset reflects the
* @ref skip() parameter. Adding byte offset and product of the vector
* gives minimal byte count to store given data.
* @see @ref pixelSize()
*/
std::tuple<std::size_t, Math::Vector3<std::size_t>, std::size_t> dataProperties(PixelFormat format, PixelType type, const Vector3i& size) const;
std::tuple<Math::Vector3<std::size_t>, Math::Vector3<std::size_t>, std::size_t> dataProperties(PixelFormat format, PixelType type, const Vector3i& size) const;
#ifndef DOXYGEN_GENERATING_OUTPUT
protected:
@ -306,15 +306,16 @@ class MAGNUM_EXPORT CompressedPixelStorage: public PixelStorage {
/**
* @brief Data properties for given parameters
*
* Returns byte offset, count of blocks in each dimension and block
* data size for image of given @p size with current pixel storage
* parameters. Adding byte offset and product of the vector multiplied
* with block data size gives minimal byte count to store given data.
* Returns byte offset in each dimension, count of blocks in each
* dimension and block data size for image of given @p size with
* current pixel storage parameters. Adding byte offset and product of
* the vector multiplied with block data size gives minimal byte count
* to store given data.
*
* Expects @ref compressedBlockSize() and @ref compressedBlockDataSize()
* to be non-zero.
*/
std::tuple<std::size_t, Math::Vector3<std::size_t>, std::size_t> dataProperties(const Vector3i& size) const;
std::tuple<Math::Vector3<std::size_t>, Math::Vector3<std::size_t>, std::size_t> dataProperties(const Vector3i& size) const;
/* Overloads to remove WTF-factor from method chaining order */
#ifndef DOXYGEN_GENERATING_OUTPUT
@ -369,37 +370,38 @@ constexpr PixelStorage::PixelStorage() noexcept:
namespace Implementation {
/* Used in *Image::dataProperties() */
template<std::size_t dimensions, class T> std::tuple<std::size_t, Math::Vector<dimensions, std::size_t>, std::size_t> imageDataProperties(const T& image) {
std::size_t offset;
Math::Vector3<std::size_t> dataSize;
template<std::size_t dimensions, class T> std::tuple<Math::Vector<dimensions, std::size_t>, Math::Vector<dimensions, std::size_t>, std::size_t> imageDataProperties(const T& image) {
Math::Vector3<std::size_t> offset, dataSize;
std::size_t pixelSize;
std::tie(offset, dataSize, pixelSize) = image.storage().dataProperties(image.format(), image.type(), Vector3i::pad(image.size(), 1));
return std::make_tuple(offset, Math::Vector<dimensions, std::size_t>::pad(dataSize), pixelSize);
return std::make_tuple(Math::Vector<dimensions, std::size_t>::pad(offset), Math::Vector<dimensions, std::size_t>::pad(dataSize), pixelSize);
}
#ifndef MAGNUM_TARGET_GLES2
/* Used in Compressed*Image::dataProperties() */
template<std::size_t dimensions, class T> std::tuple<std::size_t, Math::Vector<dimensions, std::size_t>, std::size_t> compressedImageDataProperties(const T& image) {
std::size_t offset;
Math::Vector3<std::size_t> blockCount;
template<std::size_t dimensions, class T> std::tuple<Math::Vector<dimensions, std::size_t>, Math::Vector<dimensions, std::size_t>, std::size_t> compressedImageDataProperties(const T& image) {
Math::Vector3<std::size_t> offset, blockCount;
std::size_t blockSize;
std::tie(offset, blockCount, blockSize) = image.storage().dataProperties(Vector3i::pad(image.size(), 1));
return std::make_tuple(offset, Math::Vector<dimensions, std::size_t>::pad(blockCount), blockSize);
return std::make_tuple(Math::Vector<dimensions, std::size_t>::pad(offset), Math::Vector<dimensions, std::size_t>::pad(blockCount), blockSize);
}
#endif
/* Used in image query functions */
template<std::size_t dimensions, class T> std::size_t imageDataSizeFor(const T& image, const Math::Vector<dimensions, Int>& size) {
const auto paddedSize = Vector3i::pad(size, 1);
std::size_t offset;
Math::Vector3<std::size_t> dataSize;
Math::Vector3<std::size_t> offset, dataSize;
std::size_t pixelSize;
std::tie(offset, dataSize, pixelSize) = image.storage().dataProperties(image.format(), image.type(), paddedSize);
/* I would subtract also (dataSize.x() - pixelSize*paddedSize.x()) but NVidia
then complains that the buffer is too small */
return offset + dataSize.product() - (dataSize.y() - paddedSize.y())*dataSize.x();
std::tie(offset, dataSize, pixelSize) = image.storage().dataProperties(image.format(), image.type(), Vector3i::pad(size, 1));
/* Smallest line/rectangle/cube that covers the area */
std::size_t dataOffset = 0;
if(offset.z())
dataOffset += offset.z();
else if(offset.y())
dataOffset += offset.y();
else if(offset.x())
dataOffset += offset.x();
return dataOffset + dataSize.product();
}
/* Used in data size assertions */
@ -419,14 +421,13 @@ namespace Implementation {
if(!image.storage().compressedBlockSize().product() || !image.storage().compressedBlockDataSize())
return {0, dataSize};
std::size_t offset;
Math::Vector3<std::size_t> blockCount;
Math::Vector3<std::size_t> offset, blockCount;
std::size_t blockDataSize;
std::tie(offset, blockCount, blockDataSize) = image.storage().dataProperties(Vector3i::pad(size, 1));
const auto realBlockCount = Math::Vector3<std::size_t>{(Vector3i::pad(size, 1) + image.storage().compressedBlockSize() - Vector3i{1})/image.storage().compressedBlockSize()};
return {offset, (blockCount.product() - (blockCount.x() - realBlockCount.x()) - (blockCount.y() - realBlockCount.y())*blockCount.x())*blockDataSize};
return {offset.sum(), (blockCount.product() - (blockCount.x() - realBlockCount.x()) - (blockCount.y() - realBlockCount.y())*blockCount.x())*blockDataSize};
}
/* Used in image query functions */

99
src/Magnum/Test/PixelStorageTest.cpp

@ -45,7 +45,9 @@ struct PixelStorageTest: TestSuite::Tester {
void dataPropertiesImageHeight();
#endif
void dataSize();
void dataSize1D();
void dataSize2D();
void dataSize3D();
#ifndef MAGNUM_TARGET_GLES
void dataPropertiesCompressed();
@ -70,7 +72,9 @@ PixelStorageTest::PixelStorageTest() {
&PixelStorageTest::dataPropertiesImageHeight,
#endif
&PixelStorageTest::dataSize,
&PixelStorageTest::dataSize1D,
&PixelStorageTest::dataSize2D,
&PixelStorageTest::dataSize3D,
#ifndef MAGNUM_TARGET_GLES
&PixelStorageTest::dataPropertiesCompressed,
@ -96,16 +100,16 @@ void PixelStorageTest::dataProperties() {
storage.setAlignment(1);
CORRADE_COMPARE(storage.dataProperties(PixelFormat::RGBA, PixelType::UnsignedByte, Vector3i{0}),
(std::tuple<std::size_t, Vector3st, std::size_t>{0, {0, 0, 0}, 4}));
(std::tuple<Vector3st, Vector3st, std::size_t>{{}, {0, 0, 0}, 4}));
CORRADE_COMPARE(storage.dataProperties(PixelFormat::RGBA, PixelType::UnsignedByte, Vector3i{1}),
(std::tuple<std::size_t, Vector3st, std::size_t>{0, {4, 1, 1}, 4}));
(std::tuple<Vector3st, Vector3st, std::size_t>{{}, {4, 1, 1}, 4}));
#if !defined(MAGNUM_TARGET_WEBGL) && !defined(MAGNUM_TARGET_GLES2)
CORRADE_COMPARE(storage.dataProperties(PixelFormat::Red, PixelType::UnsignedByte, {8, 2, 1}),
(std::tuple<std::size_t, Vector3st, std::size_t>{0, {8, 2, 1}, 1}));
(std::tuple<Vector3st, Vector3st, std::size_t>{{}, {8, 2, 1}, 1}));
CORRADE_COMPARE(storage.dataProperties(PixelFormat::Red, PixelType::UnsignedByte, {2, 4, 1}),
(std::tuple<std::size_t, Vector3st, std::size_t>{0, {2, 4, 1}, 1}));
(std::tuple<Vector3st, Vector3st, std::size_t>{{}, {2, 4, 1}, 1}));
CORRADE_COMPARE(storage.dataProperties(PixelFormat::Red, PixelType::UnsignedByte, {2, 4, 6}),
(std::tuple<std::size_t, Vector3st, std::size_t>{0, {2, 4, 6}, 1}));
(std::tuple<Vector3st, Vector3st, std::size_t>{{}, {2, 4, 6}, 1}));
#endif
}
@ -115,16 +119,16 @@ void PixelStorageTest::dataPropertiesAlignment() {
.setSkip({3, 2, 1});
CORRADE_COMPARE(storage.dataProperties(PixelFormat::RGBA, PixelType::UnsignedByte, Vector3i{0}),
(std::tuple<std::size_t, Vector3st, std::size_t>{3*4, {0, 0, 0}, 4}));
(std::tuple<Vector3st, Vector3st, std::size_t>{{3*4, 0, 0}, {0, 0, 0}, 4}));
CORRADE_COMPARE(storage.dataProperties(PixelFormat::RGBA, PixelType::UnsignedByte, Vector3i{1}),
(std::tuple<std::size_t, Vector3st, std::size_t>{8 + 16 + 3*4, {8, 1, 1}, 4}));
(std::tuple<Vector3st, Vector3st, std::size_t>{{12, 16, 8}, {8, 1, 1}, 4}));
#if !defined(MAGNUM_TARGET_WEBGL) && !defined(MAGNUM_TARGET_GLES2)
CORRADE_COMPARE(storage.dataProperties(PixelFormat::Red, PixelType::UnsignedByte, {8, 2, 1}),
(std::tuple<std::size_t, Vector3st, std::size_t>{16 + 16 + 3, {8, 2, 1}, 1}));
(std::tuple<Vector3st, Vector3st, std::size_t>{{3, 16, 16}, {8, 2, 1}, 1}));
CORRADE_COMPARE(storage.dataProperties(PixelFormat::Red, PixelType::UnsignedByte, {2, 4, 1}),
(std::tuple<std::size_t, Vector3st, std::size_t>{32 + 16 + 3, {8, 4, 1}, 1}));
(std::tuple<Vector3st, Vector3st, std::size_t>{{3, 16, 32}, {8, 4, 1}, 1}));
CORRADE_COMPARE(storage.dataProperties(PixelFormat::Red, PixelType::UnsignedByte, {2, 4, 6}),
(std::tuple<std::size_t, Vector3st, std::size_t>{32 + 16 + 3, {8, 4, 6}, 1}));
(std::tuple<Vector3st, Vector3st, std::size_t>{{3, 16, 32}, {8, 4, 6}, 1}));
#endif
}
@ -136,15 +140,15 @@ void PixelStorageTest::dataPropertiesRowLength() {
.setSkip({3, 7, 0});
CORRADE_COMPARE(storage.dataProperties(PixelFormat::RGBA, PixelType::UnsignedByte, Vector3i{0}),
(std::tuple<std::size_t, Vector3st, std::size_t>{3*4 + 7*15*4, {0, 0, 0}, 4}));
(std::tuple<Vector3st, Vector3st, std::size_t>{{3*4, 7*15*4, 0}, {0, 0, 0}, 4}));
CORRADE_COMPARE(storage.dataProperties(PixelFormat::RGBA, PixelType::UnsignedByte, Vector3i{1}),
(std::tuple<std::size_t, Vector3st, std::size_t>{3*4 + 7*15*4, {60, 1, 1}, 4}));
(std::tuple<Vector3st, Vector3st, std::size_t>{{3*4, 7*15*4, 0}, {60, 1, 1}, 4}));
CORRADE_COMPARE(storage.dataProperties(PixelFormat::Red, PixelType::UnsignedByte, {4, 2, 1}),
(std::tuple<std::size_t, Vector3st, std::size_t>{3 + 7*16, {16, 2, 1}, 1}));
(std::tuple<Vector3st, Vector3st, std::size_t>{{3, 7*16, 0}, {16, 2, 1}, 1}));
CORRADE_COMPARE(storage.dataProperties(PixelFormat::Red, PixelType::UnsignedByte, {2, 4, 1}),
(std::tuple<std::size_t, Vector3st, std::size_t>{3 + 7*16, {16, 4, 1}, 1}));
(std::tuple<Vector3st, Vector3st, std::size_t>{{3, 7*16, 0}, {16, 4, 1}, 1}));
CORRADE_COMPARE(storage.dataProperties(PixelFormat::Red, PixelType::UnsignedByte, {2, 4, 6}),
(std::tuple<std::size_t, Vector3st, std::size_t>{3 + 7*16, {16, 4, 6}, 1}));
(std::tuple<Vector3st, Vector3st, std::size_t>{{3, 7*16, 0}, {16, 4, 6}, 1}));
}
#endif
@ -156,39 +160,66 @@ void PixelStorageTest::dataPropertiesImageHeight() {
.setSkip({3, 7, 2});
CORRADE_COMPARE(storage.dataProperties(PixelFormat::RGBA, PixelType::UnsignedByte, Vector3i{0}),
(std::tuple<std::size_t, Vector3st, std::size_t>{3*4, {0, 0, 0}, 4}));
(std::tuple<Vector3st, Vector3st, std::size_t>{{3*4, 0, 0}, {0, 0, 0}, 4}));
CORRADE_COMPARE(storage.dataProperties(PixelFormat::RGBA, PixelType::UnsignedByte, Vector3i{1}),
(std::tuple<std::size_t, Vector3st, std::size_t>{3*4 + 7*1*4 + 2*128*1*4, {4, 128, 1}, 4}));
(std::tuple<Vector3st, Vector3st, std::size_t>{{3*4, 7*1*4, 2*128*1*4}, {4, 128, 1}, 4}));
CORRADE_COMPARE(storage.dataProperties(PixelFormat::Red, PixelType::UnsignedByte, {4, 2, 1}),
(std::tuple<std::size_t, Vector3st, std::size_t>{3 + 7*1*4 + 2*128*4, {4, 128, 1}, 1}));
(std::tuple<Vector3st, Vector3st, std::size_t>{{3, 7*1*4, 2*128*4}, {4, 128, 1}, 1}));
CORRADE_COMPARE(storage.dataProperties(PixelFormat::Red, PixelType::UnsignedByte, {2, 4, 1}),
(std::tuple<std::size_t, Vector3st, std::size_t>{3 + 7*1*2 + 2*128*2, {2, 128, 1}, 1}));
(std::tuple<Vector3st, Vector3st, std::size_t>{{3, 7*1*2, 2*128*2}, {2, 128, 1}, 1}));
CORRADE_COMPARE(storage.dataProperties(PixelFormat::Red, PixelType::UnsignedByte, {2, 4, 6}),
(std::tuple<std::size_t, Vector3st, std::size_t>{3 + 7*1*2 + 2*128*2, {2, 128, 6}, 1}));
(std::tuple<Vector3st, Vector3st, std::size_t>{{3, 7*1*2, 2*128*2}, {2, 128, 6}, 1}));
}
#endif
void PixelStorageTest::dataSize() {
void PixelStorageTest::dataSize1D() {
const Image1D image{PixelStorage{}.setAlignment(2)
.setSkip({2, 0, 0}),
PixelFormat::RGB, PixelType::UnsignedByte};
CORRADE_COMPARE(Implementation::imageDataSizeFor(image, Math::Vector<1, Int>{3}),
16);
}
void PixelStorageTest::dataSize2D() {
/* The same parameters as in PixelStorageGLTest 3D case */
const Image2D image{PixelStorage{}.setAlignment(2)
#if !(defined(MAGNUM_TARGET_WEBGL) && defined(MAGNUM_TARGET_GLES2))
.setRowLength(3)
.setRowLength(7)
#endif
.setSkip({2, 3, 0}),
PixelFormat::RGB, PixelType::UnsignedByte};
#if defined(MAGNUM_TARGET_WEBGL) && defined(MAGNUM_TARGET_GLES2)
CORRADE_COMPARE(Implementation::imageDataSizeFor(image, Vector2i{5, 9}),
(3 + 9)*15);
#else
CORRADE_COMPARE(Implementation::imageDataSizeFor(image, Vector2i{5, 9}),
(3 + 9)*22);
#endif
}
void PixelStorageTest::dataSize3D() {
/* The same parameters as in PixelStorageGLTest 3D case */
const Image3D image{PixelStorage{}.setAlignment(2)
#if !(defined(MAGNUM_TARGET_WEBGL) && defined(MAGNUM_TARGET_GLES2))
.setRowLength(7)
#endif
#ifndef MAGNUM_TARGET_GLES2
.setImageHeight(5)
.setImageHeight(10)
#endif
.setSkip({2, 3, 1}),
PixelFormat::RGB, PixelType::UnsignedByte};
#if defined(MAGNUM_TARGET_WEBGL) && defined(MAGNUM_TARGET_GLES2)
CORRADE_COMPARE(Implementation::imageDataSizeFor(image, Vector2i{2, 3}),
3*6 + 3*6 + 6 + 3*6);
CORRADE_COMPARE(Implementation::imageDataSizeFor(image, Vector3i{5, 9, 3}),
(1 + 3)*9*15);
#elif defined(MAGNUM_TARGET_GLES2)
CORRADE_COMPARE(Implementation::imageDataSizeFor(image, Vector2i{2, 3}),
3*10 + 3*10 + 6 + 3*10);
CORRADE_COMPARE(Implementation::imageDataSizeFor(image, Vector3i{5, 9, 3}),
(1 + 3)*9*22);
#else
CORRADE_COMPARE(Implementation::imageDataSizeFor(image, Vector2i{2, 3}),
5*10 + 3*10 + 6 + 3*10);
CORRADE_COMPARE(Implementation::imageDataSizeFor(image, Vector3i{5, 9, 3}),
(1 + 3)*10*22);
#endif
}
@ -199,7 +230,7 @@ void PixelStorageTest::dataPropertiesCompressed() {
.setCompressedBlockDataSize(16);
CORRADE_COMPARE(storage.dataProperties({2, 8, 11}),
(std::tuple<std::size_t, Vector3st, std::size_t>{0, {1, 2, 3}, 16}));
(std::tuple<Vector3st, Vector3st, std::size_t>{{}, {1, 2, 3}, 16}));
}
void PixelStorageTest::dataPropertiesCompressedRowLength() {
@ -210,7 +241,7 @@ void PixelStorageTest::dataPropertiesCompressedRowLength() {
.setSkip({5, 8, 0});
CORRADE_COMPARE(storage.dataProperties({2, 8, 11}),
(std::tuple<std::size_t, Vector3st, std::size_t>{(2 + 8)*9, {4, 2, 3}, 9}));
(std::tuple<Vector3st, Vector3st, std::size_t>{{2*9, 8*9, 0}, {4, 2, 3}, 9}));
}
void PixelStorageTest::dataPropertiesCompressedImageHeight() {
@ -221,7 +252,7 @@ void PixelStorageTest::dataPropertiesCompressedImageHeight() {
.setSkip({5, 8, 11});
CORRADE_COMPARE(storage.dataProperties({2, 8, 11}),
(std::tuple<std::size_t, Vector3st, std::size_t>{(2 + 2 + 9)*16, {1, 3, 3}, 16}));
(std::tuple<Vector3st, Vector3st, std::size_t>{{2*16, 2*16, 9*16}, {1, 3, 3}, 16}));
}
void PixelStorageTest::dataOffsetSizeCompressed() {

2
src/Magnum/Trade/ImageData.cpp

@ -63,7 +63,7 @@ template<UnsignedInt dimensions> std::size_t ImageData<dimensions>::pixelSize()
return PixelStorage::pixelSize(_format, _type);
}
template<UnsignedInt dimensions> std::tuple<std::size_t, VectorTypeFor<dimensions, std::size_t>, std::size_t> ImageData<dimensions>::dataProperties() const {
template<UnsignedInt dimensions> std::tuple<VectorTypeFor<dimensions, std::size_t>, VectorTypeFor<dimensions, std::size_t>, std::size_t> ImageData<dimensions>::dataProperties() const {
CORRADE_ASSERT(!_compressed, "Trade::ImageData::dataProperties(): the image is compressed", {});
return Implementation::imageDataProperties<dimensions>(*this);
}

2
src/Magnum/Trade/ImageData.h

@ -210,7 +210,7 @@ template<UnsignedInt dimensions> class ImageData {
* @ref PixelStorage::dataProperties() for more information.
* @see @ref isCompressed()
*/
std::tuple<std::size_t, VectorTypeFor<dimensions, std::size_t>, std::size_t> dataProperties() const;
std::tuple<VectorTypeFor<dimensions, std::size_t>, VectorTypeFor<dimensions, std::size_t>, std::size_t> dataProperties() const;
/* compressed data properties are not available because the importers
are not setting any block size pixel storage properties to avoid

2
src/MagnumPlugins/TgaImageConverter/TgaImageConverter.cpp

@ -98,7 +98,7 @@ Containers::Array<char> TgaImageConverter::doExportToData(const ImageView2D& ima
header->height = UnsignedShort(Utility::Endianness::littleEndian(image.size().y()));
/* Image data pointer including skip */
const char* imageData = image.data() + std::get<0>(image.dataProperties());
const char* imageData = image.data() + std::get<0>(image.dataProperties()).sum();
/* Fill data or copy them row by row if we need to drop the padding */
const std::size_t rowSize = image.size().x()*pixelSize;

Loading…
Cancel
Save