// David Eberly, Geometric Tools, Redmond WA 98052 // Copyright (c) 1998-2020 // Distributed under the Boost Software License, Version 1.0. // https://www.boost.org/LICENSE_1_0.txt // https://www.geometrictools.com/License/Boost/LICENSE_1_0.txt // Version: 4.0.2019.08.13 #pragma once #include namespace WwiseGTE { template class Image { public: // Construction and destruction. virtual ~Image() { } Image() { } Image(std::vector const& dimensions) { Reconstruct(dimensions); } // Support for copy semantics. Image(Image const& image) { *this = image; } Image& operator=(Image const& image) { mDimensions = image.mDimensions; mOffsets = image.mOffsets; mPixels = image.mPixels; return *this; } // Support for move semantics. Image(Image&& image) { *this = std::move(image); } Image& operator=(Image&& image) { mDimensions = std::move(image.mDimensions); mOffsets = std::move(image.mOffsets); mPixels = std::move(image.mPixels); return *this; } // Support for changing the image dimensions. All pixel data is lost // by this operation. void Reconstruct(std::vector const& dimensions) { mDimensions.clear(); mOffsets.clear(); mPixels.clear(); if (dimensions.size() > 0) { for (auto dim : dimensions) { if (dim <= 0) { return; } } mDimensions = dimensions; mOffsets.resize(dimensions.size()); size_t numPixels = 1; for (size_t d = 0; d < dimensions.size(); ++d) { numPixels *= static_cast(mDimensions[d]); } mOffsets[0] = 1; for (size_t d = 1; d < dimensions.size(); ++d) { mOffsets[d] = static_cast(mDimensions[d - 1]) * mOffsets[d - 1]; } mPixels.resize(numPixels); } } // Access to image data. inline std::vector const& GetDimensions() const { return mDimensions; } inline int GetNumDimensions() const { return static_cast(mDimensions.size()); } inline int GetDimension(int d) const { return mDimensions[d]; } inline std::vector const& GetOffsets() const { return mOffsets; } inline size_t GetOffset(int d) const { return mOffsets[d]; } inline std::vector const& GetPixels() const { return mPixels; } inline std::vector& GetPixels() { return mPixels; } inline size_t GetNumPixels() const { return mPixels.size(); } // Conversions between n-dim and 1-dim structures. The 'coord' arrays // must have GetNumDimensions() elements. size_t GetIndex(int const* coord) const { // assert: coord is array of mNumDimensions elements int const numDimensions = static_cast(mDimensions.size()); size_t index = coord[0]; for (int d = 1; d < numDimensions; ++d) { index += mOffsets[d] * coord[d]; } return index; } void GetCoordinates(size_t index, int* coord) const { // assert: coord is array of numDimensions elements int const numDimensions = static_cast(mDimensions.size()); for (int d = 0; d < numDimensions; ++d) { coord[d] = index % mDimensions[d]; index /= mDimensions[d]; } } // Access the data as a 1-dimensional array. The operator[] functions // test for valid i when iterator checking is enabled and assert on // invalid i. The Get() functions test for valid i and clamp when // invalid; these functions cannot fail. inline PixelType& operator[] (size_t i) { return mPixels[i]; } inline PixelType const& operator[] (size_t i) const { return mPixels[i]; } PixelType& Get(size_t i) { return (i < mPixels.size() ? mPixels[i] : mPixels.front()); } PixelType const& Get(size_t i) const { return (i < mPixels.size() ? mPixels[i] : mPixels.front()); } protected: std::vector mDimensions; std::vector mOffsets; std::vector mPixels; }; }