Added tests for write, and added tests/implementation of operator==. Also added implementation of FillChannel()

This commit is contained in:
Leonetienne
2022-03-06 12:45:09 +01:00
parent eb4fc0e964
commit 04a1104065
8 changed files with 223 additions and 12 deletions

View File

@@ -37,7 +37,11 @@ namespace Leonetienne::BmpPP {
// Re-initialize the pixelbuffer
pixelBuffer.clear();
pixelBuffer.resize(size.x * size.y * GetNumColorChannels());
pixelBuffer.resize(size.x * size.y * GetNumChannels());
// If we're initializing with an alpha channel, set it to 255
if (colormode == Colormode::RGBA)
FillChannel(3, 255);
return;
}
@@ -51,7 +55,11 @@ namespace Leonetienne::BmpPP {
// Re-initialize the pixelbuffer
pixelBuffer.clear();
pixelBuffer.resize(size.x * size.y * GetNumColorChannels());
pixelBuffer.resize(size.x * size.y * GetNumChannels());
// If we're initializing with an alpha channel, set it to 255
if (colormode == Colormode::RGBA)
FillChannel(3, 255);
return;
}
@@ -70,7 +78,7 @@ namespace Leonetienne::BmpPP {
CHECK_IF_INITIALIZED
const std::size_t pixelIndex =
(position.y * size.x + position.x) * GetNumColorChannels();
(position.y * size.x + position.x) * GetNumChannels();
if (pixelIndex >= pixelBuffer.size())
throw std::runtime_error("Pixel index out of range!");
@@ -82,7 +90,7 @@ namespace Leonetienne::BmpPP {
CHECK_IF_INITIALIZED
const std::size_t pixelIndex =
(position.y * size.x + position.x) * GetNumColorChannels();
(position.y * size.x + position.x) * GetNumChannels();
if (pixelIndex >= pixelBuffer.size())
throw std::runtime_error("Pixel index out of range!");
@@ -142,7 +150,7 @@ namespace Leonetienne::BmpPP {
return colormode;
}
std::size_t BMP::GetNumColorChannels() const {
std::size_t BMP::GetNumChannels() const {
CHECK_IF_INITIALIZED
switch (colormode) {
@@ -167,6 +175,34 @@ namespace Leonetienne::BmpPP {
return isInitialized;
}
bool BMP::operator==(const BMP &other) const {
// Check metadata
if (colormode != other.colormode)
return false;
if (size != other.size)
return false;
// Check pixel values
if (pixelBuffer != other.pixelBuffer)
return false;
return true;
}
bool BMP::operator!=(const BMP &other) const {
return !operator==(other);
}
void BMP::FillChannel(const size_t &channel, const std::uint8_t value) {
const std::size_t numChannels = GetNumChannels();
for (std::size_t i = 0; i < pixelBuffer.size(); i += numChannels)
pixelBuffer[i + channel] = value;
return;
}
}
#undef CHECK_IF_INITIALIZED

View File

@@ -50,8 +50,8 @@ namespace Leonetienne::BmpPP {
//! Will return the color mode of the image
[[nodiscard]] const Colormode& GetColormode() const;
//! Will return the amount of color channels used
[[nodiscard]] std::size_t GetNumColorChannels() const;
//! Will return the amount of channels used
[[nodiscard]] std::size_t GetNumChannels() const;
//! Will return the size of the raw pixel buffer, in bytes
[[nodiscard]] std::size_t GetPixelbufferSize() const;
@@ -67,6 +67,12 @@ namespace Leonetienne::BmpPP {
//! Returns false, if unable to open, or parse, file
bool Read(const std::string& filename);
//! Will compare two images for being exactly identical regarding resolution, bit depth, and pixel values.
bool operator==(const BMP& other) const;
//! Will compare two images for not being exactly identical regarding resolution, bit depth, and pixel values.
bool operator!=(const BMP& other) const;
//! Will mirror the image horizontally
void MirrorHorizontally();
@@ -91,6 +97,9 @@ namespace Leonetienne::BmpPP {
//! Will copy the specified rectangle-area, and return it as a new image
BMP Crop(const Eule::Rect& area);
//! Will fill a specific channel with a value
void FillChannel(const std::size_t& channel, const std::uint8_t value);
private:
Eule::Vector2i size;
Colormode colormode;

View File

@@ -21,7 +21,7 @@ namespace Leonetienne::BmpPP {
// Populate dib header
bmpHeader.dibHeader.imageWidth = image.size.x;
bmpHeader.dibHeader.imageHeight = image.size.y;
bmpHeader.dibHeader.numBitsPerPixel = image.GetNumColorChannels() * 8;
bmpHeader.dibHeader.numBitsPerPixel = image.GetNumChannels() * 8;
// The size of the pixel array is not known yet (because rows require to be padded)
@@ -30,7 +30,7 @@ namespace Leonetienne::BmpPP {
packedPixels.reserve(image.pixelBuffer.size());
// How many channels do we have?
const std::size_t numChannels = image.GetNumColorChannels();
const std::size_t numChannels = image.GetNumChannels();
// Calculate how many padding bytes to add per row
const std::size_t paddingBytesPerRow = (4 - ((image.size.x * numChannels) % 4)) % 4;