Added formats conversion
Functor, NonCopyable, Tuple are now parts of NazaraCore (NazaraCore no longer needs NazaraUtility) Added loadFormat image parameter (ask loader to load image in specific format) Fixed utility project building It is now possible to convert, get validity or get name of pixel formats Changed endianness macros' name Removed useless NazaraEndianness macro Removed unused files
This commit is contained in:
@@ -36,6 +36,79 @@ NzImage::~NzImage()
|
||||
ReleaseImage();
|
||||
}
|
||||
|
||||
bool NzImage::Convert(nzPixelFormat format)
|
||||
{
|
||||
if (format == m_sharedImage->format)
|
||||
return true;
|
||||
|
||||
#if NAZARA_UTILITY_SAFE
|
||||
if (!IsValid())
|
||||
{
|
||||
NazaraError("Image must be valid");
|
||||
return false;
|
||||
}
|
||||
|
||||
if (!NzPixelFormat::IsValid(format))
|
||||
{
|
||||
NazaraError("Invalid pixel format");
|
||||
return false;
|
||||
}
|
||||
#endif
|
||||
|
||||
EnsureOwnership();
|
||||
|
||||
unsigned int depth = (IsCubemap()) ? 6 : m_sharedImage->depth;
|
||||
unsigned int pixelsPerFace = m_sharedImage->width*m_sharedImage->height;
|
||||
|
||||
nzUInt8* buffer;
|
||||
if (depth > 1)
|
||||
{
|
||||
// Les images 3D sont un empilement d'images 2D
|
||||
// Quant aux cubemaps, ils sont stockés côte à côte, ce qui revient au même
|
||||
buffer = new nzUInt8[pixelsPerFace*depth*NzPixelFormat::GetBPP(format)];
|
||||
|
||||
nzUInt8* ptr = buffer;
|
||||
nzUInt8* pixels = m_sharedImage->pixels;
|
||||
unsigned int srcStride = pixelsPerFace * NzPixelFormat::GetBPP(m_sharedImage->format);
|
||||
unsigned int dstStride = pixelsPerFace * NzPixelFormat::GetBPP(format);
|
||||
|
||||
for (unsigned int i = 0; i < depth; ++i)
|
||||
{
|
||||
if (!NzPixelFormat::Convert(m_sharedImage->format, format, pixels, &pixels[srcStride], ptr))
|
||||
{
|
||||
NazaraError("Failed to convert image");
|
||||
delete[] buffer;
|
||||
|
||||
return false;
|
||||
}
|
||||
|
||||
pixels += srcStride;
|
||||
ptr += dstStride;
|
||||
}
|
||||
|
||||
delete[] buffer;
|
||||
}
|
||||
else
|
||||
{
|
||||
buffer = new nzUInt8[pixelsPerFace*NzPixelFormat::GetBPP(format)];
|
||||
|
||||
if (!NzPixelFormat::Convert(m_sharedImage->format, format, m_sharedImage->pixels, &m_sharedImage->pixels[pixelsPerFace*NzPixelFormat::GetBPP(m_sharedImage->format)], buffer))
|
||||
{
|
||||
NazaraError("Failed to convert image");
|
||||
delete[] buffer;
|
||||
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
delete[] m_sharedImage->pixels;
|
||||
|
||||
m_sharedImage->format = format;
|
||||
m_sharedImage->pixels = buffer;
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
bool NzImage::Copy(const NzImage& source, const NzRectui& srcRect, const NzVector2ui& dstPos)
|
||||
{
|
||||
#if NAZARA_UTILITY_SAFE
|
||||
@@ -78,6 +151,14 @@ bool NzImage::Create(nzImageType type, nzPixelFormat format, unsigned int width,
|
||||
{
|
||||
ReleaseImage();
|
||||
|
||||
#if NAZARA_UTILITY_SAFE
|
||||
if (!NzPixelFormat::IsValid(format))
|
||||
{
|
||||
NazaraError("Invalid pixel format");
|
||||
return false;
|
||||
}
|
||||
#endif
|
||||
|
||||
unsigned int size = width*height*depth*NzPixelFormat::GetBPP(format);
|
||||
if (size == 0)
|
||||
return true;
|
||||
@@ -131,7 +212,19 @@ bool NzImage::Create(nzImageType type, nzPixelFormat format, unsigned int width,
|
||||
size *= 6; // Les cubemaps ont six faces
|
||||
#endif
|
||||
|
||||
m_sharedImage = new SharedImage(1, type, format, new nzUInt8[size], width, height, depth);
|
||||
// Cette allocation est protégée car sa taille dépend directement de paramètres utilisateurs
|
||||
nzUInt8* buffer;
|
||||
try
|
||||
{
|
||||
buffer = new nzUInt8[size];
|
||||
}
|
||||
catch (const std::exception& e)
|
||||
{
|
||||
NazaraError("Failed to allocate image buffer (" + NzString(e.what()) + ')');
|
||||
return false;
|
||||
}
|
||||
|
||||
m_sharedImage = new SharedImage(1, type, format, buffer, width, height, depth);
|
||||
|
||||
return true;
|
||||
}
|
||||
@@ -472,4 +565,4 @@ void NzImage::ReleaseImage()
|
||||
m_sharedImage = &emptyImage;
|
||||
}
|
||||
|
||||
NzImage::SharedImage NzImage::emptyImage(0, nzImageType_2D, nzPixelFormat_R8G8B8, nullptr, 0, 0, 0);
|
||||
NzImage::SharedImage NzImage::emptyImage(0, nzImageType_2D, nzPixelFormat_Undefined, nullptr, 0, 0, 0);
|
||||
|
||||
@@ -74,7 +74,7 @@ namespace
|
||||
return false;
|
||||
}
|
||||
|
||||
#if NAZARA_ENDIANNESS_BIGENDIAN
|
||||
#if NAZARA_BIG_ENDIAN
|
||||
// Les fichiers PCX sont en little endian
|
||||
NzByteSwap(&header.xmin, sizeof(nzUInt16));
|
||||
NzByteSwap(&header.ymin, sizeof(nzUInt16));
|
||||
@@ -93,7 +93,7 @@ namespace
|
||||
unsigned int width = header.xmax - header.xmin+1;
|
||||
unsigned int height = header.ymax - header.ymin+1;
|
||||
|
||||
if (!resource->Create(nzImageType_2D, nzPixelFormat_R8G8B8, width, height))
|
||||
if (!resource->Create(nzImageType_2D, nzPixelFormat_RGB8, width, height))
|
||||
{
|
||||
NazaraError("Failed to create image");
|
||||
return false;
|
||||
@@ -343,6 +343,9 @@ namespace
|
||||
return false;
|
||||
}
|
||||
|
||||
if (parameters.loadFormat != nzPixelFormat_Undefined)
|
||||
resource->Convert(parameters.loadFormat);
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
|
||||
@@ -63,15 +63,44 @@ namespace
|
||||
{
|
||||
NazaraUnused(parameters);
|
||||
|
||||
static nzPixelFormat format[4] = {
|
||||
static nzPixelFormat formats[4] = {
|
||||
nzPixelFormat_L8,
|
||||
nzPixelFormat_L8A8,
|
||||
nzPixelFormat_R8G8B8,
|
||||
nzPixelFormat_R8G8B8A8
|
||||
nzPixelFormat_LA8,
|
||||
nzPixelFormat_RGB8,
|
||||
nzPixelFormat_RGBA8
|
||||
};
|
||||
|
||||
nzPixelFormat format;
|
||||
int stbiFormat;
|
||||
switch (parameters.loadFormat)
|
||||
{
|
||||
case nzPixelFormat_L8:
|
||||
format = nzPixelFormat_L8;
|
||||
stbiFormat = STBI_grey;
|
||||
break;
|
||||
|
||||
case nzPixelFormat_LA8:
|
||||
format = nzPixelFormat_LA8;
|
||||
stbiFormat = STBI_grey_alpha;
|
||||
break;
|
||||
|
||||
case nzPixelFormat_RGB8:
|
||||
format = nzPixelFormat_RGB8;
|
||||
stbiFormat = STBI_rgb;
|
||||
break;
|
||||
|
||||
case nzPixelFormat_RGBA8:
|
||||
format = nzPixelFormat_RGBA8;
|
||||
stbiFormat = STBI_rgb_alpha;
|
||||
break;
|
||||
|
||||
default:
|
||||
format = nzPixelFormat_Undefined;
|
||||
stbiFormat = STBI_default;
|
||||
}
|
||||
|
||||
int width, height, bpp;
|
||||
nzUInt8* ptr = stbi_load_from_callbacks(&callbacks, &stream, &width, &height, &bpp, STBI_default);
|
||||
nzUInt8* ptr = stbi_load_from_callbacks(&callbacks, &stream, &width, &height, &bpp, stbiFormat);
|
||||
|
||||
if (!ptr)
|
||||
{
|
||||
@@ -79,7 +108,10 @@ namespace
|
||||
return false;
|
||||
}
|
||||
|
||||
if (!resource->Create(nzImageType_2D, format[bpp-1], width, height))
|
||||
if (format == nzPixelFormat_Undefined)
|
||||
format = formats[bpp-1];
|
||||
|
||||
if (!resource->Create(nzImageType_2D, format, width, height))
|
||||
{
|
||||
NazaraError("Failed to create image");
|
||||
stbi_image_free(ptr);
|
||||
@@ -90,6 +122,9 @@ namespace
|
||||
resource->Update(ptr);
|
||||
stbi_image_free(ptr);
|
||||
|
||||
if (stbiFormat == STBI_default && parameters.loadFormat != nzPixelFormat_Undefined)
|
||||
resource->Convert(parameters.loadFormat);
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
|
||||
1161
src/Nazara/Utility/PixelFormat.cpp
Normal file
1161
src/Nazara/Utility/PixelFormat.cpp
Normal file
File diff suppressed because it is too large
Load Diff
@@ -7,6 +7,7 @@
|
||||
#include <Nazara/Utility/Config.hpp>
|
||||
#include <Nazara/Utility/Loaders/PCX.hpp>
|
||||
#include <Nazara/Utility/Loaders/STB.hpp>
|
||||
#include <Nazara/Utility/PixelFormat.hpp>
|
||||
#include <Nazara/Utility/Debug.hpp>
|
||||
|
||||
NzUtility::NzUtility()
|
||||
@@ -29,6 +30,12 @@ bool NzUtility::Initialize()
|
||||
}
|
||||
#endif
|
||||
|
||||
if (!NzPixelFormat::Initialize())
|
||||
{
|
||||
NazaraError("Failed to initialize pixel format");
|
||||
return false;
|
||||
}
|
||||
|
||||
// Loaders spécialisés
|
||||
NzLoaders_PCX_Register(); // Loader de fichiers .PCX (1, 4, 8, 24)
|
||||
|
||||
@@ -53,6 +60,8 @@ void NzUtility::Uninitialize()
|
||||
NzLoaders_STB_Unregister();
|
||||
NzLoaders_PCX_Unregister();
|
||||
|
||||
NzPixelFormat::Uninitialize();
|
||||
|
||||
s_initialized = false;
|
||||
}
|
||||
|
||||
|
||||
@@ -9,12 +9,12 @@
|
||||
#ifndef NAZARA_WINDOWIMPL_HPP
|
||||
#define NAZARA_WINDOWIMPL_HPP
|
||||
|
||||
#include <Nazara/Core/NonCopyable.hpp>
|
||||
#include <Nazara/Core/String.hpp>
|
||||
#include <Nazara/Math/Vector2.hpp>
|
||||
#include <Nazara/Utility/Config.hpp>
|
||||
#include <Nazara/Utility/Keyboard.hpp>
|
||||
#include <Nazara/Utility/Mouse.hpp>
|
||||
#include <Nazara/Utility/NonCopyable.hpp>
|
||||
#include <Nazara/Utility/VideoMode.hpp>
|
||||
#include <Nazara/Utility/Window.hpp>
|
||||
#include <windows.h>
|
||||
|
||||
Reference in New Issue
Block a user