Fix msvc warnings and errors.
Test TexImage stuff more througly. Test YCoCg and RGBM.
This commit is contained in:
@ -6,6 +6,7 @@
|
|||||||
#include "TgaFile.h"
|
#include "TgaFile.h"
|
||||||
#include "PsdFile.h"
|
#include "PsdFile.h"
|
||||||
#include "DirectDrawSurface.h"
|
#include "DirectDrawSurface.h"
|
||||||
|
#include "PixelFormat.h"
|
||||||
|
|
||||||
#include "nvmath/Color.h"
|
#include "nvmath/Color.h"
|
||||||
#include "nvmath/Half.h"
|
#include "nvmath/Half.h"
|
||||||
@ -290,7 +291,7 @@ bool nv::ImageIO::saveFloat(const char * fileName, Stream & s, const FloatImage
|
|||||||
image->setFormat(Image::Format_ARGB);
|
image->setFormat(Image::Format_ARGB);
|
||||||
}
|
}
|
||||||
|
|
||||||
return ImageIO::save(fileName, image.ptr());
|
return ImageIO::save(fileName, s, image.ptr());
|
||||||
}
|
}
|
||||||
#endif // defined(HAVE_FREEIMAGE)
|
#endif // defined(HAVE_FREEIMAGE)
|
||||||
|
|
||||||
@ -299,9 +300,9 @@ bool nv::ImageIO::saveFloat(const char * fileName, Stream & s, const FloatImage
|
|||||||
|
|
||||||
bool nv::ImageIO::saveFloat(const char * fileName, const FloatImage * fimage, uint baseComponent, uint componentCount)
|
bool nv::ImageIO::saveFloat(const char * fileName, const FloatImage * fimage, uint baseComponent, uint componentCount)
|
||||||
{
|
{
|
||||||
#if !defined(HAVE_FREEIMAGE)
|
|
||||||
const char * extension = Path::extension(fileName);
|
const char * extension = Path::extension(fileName);
|
||||||
|
|
||||||
|
#if !defined(HAVE_FREEIMAGE)
|
||||||
#if defined(HAVE_OPENEXR)
|
#if defined(HAVE_OPENEXR)
|
||||||
if (strCaseCmp(extension, ".exr") == 0) {
|
if (strCaseCmp(extension, ".exr") == 0) {
|
||||||
return saveFloatEXR(fileName, fimage, baseComponent, componentCount);
|
return saveFloatEXR(fileName, fimage, baseComponent, componentCount);
|
||||||
@ -312,16 +313,15 @@ bool nv::ImageIO::saveFloat(const char * fileName, const FloatImage * fimage, ui
|
|||||||
return saveFloatTIFF(fileName, fimage, baseComponent, componentCount);
|
return saveFloatTIFF(fileName, fimage, baseComponent, componentCount);
|
||||||
}
|
}
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
#endif // !defined(HAVE_FREEIMAGE)
|
#endif // !defined(HAVE_FREEIMAGE)
|
||||||
|
|
||||||
StdInputStream stream(fileName);
|
StdOutputStream stream(fileName);
|
||||||
|
|
||||||
if (stream.isError()) {
|
if (stream.isError()) {
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
return saveFloat(fileName, stream, fimage, baseComponent, componentCount);
|
return saveFloat(fileName, stream, fimage, baseComponent, componentCount);
|
||||||
}
|
}
|
||||||
|
|
||||||
#if defined(HAVE_FREEIMAGE)
|
#if defined(HAVE_FREEIMAGE)
|
||||||
@ -448,6 +448,38 @@ FloatImage * nv::ImageIO::loadFloatFreeImage(FREE_IMAGE_FORMAT fif, Stream & s)
|
|||||||
|
|
||||||
switch (fit)
|
switch (fit)
|
||||||
{
|
{
|
||||||
|
case FIT_BITMAP:
|
||||||
|
{
|
||||||
|
floatImage->allocate(4, w, h);
|
||||||
|
FIBITMAP * tmp = FreeImage_ConvertTo32Bits(bitmap);
|
||||||
|
|
||||||
|
uint bitcount = FreeImage_GetBPP(bitmap);
|
||||||
|
uint byteCount = bitcount / 8;
|
||||||
|
|
||||||
|
for (int y=0; y < h; y++)
|
||||||
|
{
|
||||||
|
const Color32 * src = (const Color32 *)FreeImage_GetScanLine(bitmap, h - y - 1 );
|
||||||
|
|
||||||
|
float * r = floatImage->scanline(y, 0);
|
||||||
|
float * g = floatImage->scanline(y, 1);
|
||||||
|
float * b = floatImage->scanline(y, 2);
|
||||||
|
float * a = floatImage->scanline(y, 3);
|
||||||
|
|
||||||
|
for (int x=0; x < w; x++)
|
||||||
|
{
|
||||||
|
r[x] = float(src[x].r) / 255.0f;
|
||||||
|
g[x] = float(src[x].g) / 255.0f;
|
||||||
|
b[x] = float(src[x].b) / 255.0f;
|
||||||
|
a[x] = float(src[x].a) / 255.0f;
|
||||||
|
}
|
||||||
|
|
||||||
|
src += byteCount;
|
||||||
|
}
|
||||||
|
|
||||||
|
FreeImage_Unload(tmp);
|
||||||
|
}
|
||||||
|
|
||||||
|
break;
|
||||||
case FIT_FLOAT:
|
case FIT_FLOAT:
|
||||||
floatImage->allocate(1, w, h);
|
floatImage->allocate(1, w, h);
|
||||||
|
|
||||||
@ -1216,7 +1248,7 @@ bool nv::ImageIO::savePNG(Stream & s, const Image * img, const ImageMetaData * t
|
|||||||
png_set_write_fn(png_ptr, (void*)&s, user_write_data, user_write_flush);
|
png_set_write_fn(png_ptr, (void*)&s, user_write_data, user_write_flush);
|
||||||
|
|
||||||
// Set image header information
|
// Set image header information
|
||||||
int color_type = PNG_COLOR_TYPE_RGB;
|
int color_type = PNG_COLOR_TYPE_RGBA;
|
||||||
switch(img->format())
|
switch(img->format())
|
||||||
{
|
{
|
||||||
case Image::Format_RGB: color_type = PNG_COLOR_TYPE_RGB; break;
|
case Image::Format_RGB: color_type = PNG_COLOR_TYPE_RGB; break;
|
||||||
@ -1231,6 +1263,7 @@ bool nv::ImageIO::savePNG(Stream & s, const Image * img, const ImageMetaData * t
|
|||||||
png_bytep * row_data = new png_bytep[sizeof(png_byte) * img->height()];
|
png_bytep * row_data = new png_bytep[sizeof(png_byte) * img->height()];
|
||||||
for (uint i = 0; i < img->height(); i++) {
|
for (uint i = 0; i < img->height(); i++) {
|
||||||
row_data[i] = (png_byte*)img->scanline (i);
|
row_data[i] = (png_byte*)img->scanline (i);
|
||||||
|
if (img->format() == Image::Format_RGB) row_data[i]--; // This is a bit of a hack, libpng expects images in ARGB format not BGRA, it supports BGR swapping, but not alpha swapping.
|
||||||
}
|
}
|
||||||
png_set_rows(png_ptr, info_ptr, row_data);
|
png_set_rows(png_ptr, info_ptr, row_data);
|
||||||
|
|
||||||
@ -1252,9 +1285,10 @@ bool nv::ImageIO::savePNG(Stream & s, const Image * img, const ImageMetaData * t
|
|||||||
|
|
||||||
png_write_png(png_ptr, info_ptr,
|
png_write_png(png_ptr, info_ptr,
|
||||||
// component order is BGR(A)
|
// component order is BGR(A)
|
||||||
PNG_TRANSFORM_BGR
|
PNG_TRANSFORM_BGR |
|
||||||
// Strip alpha byte for RGB images
|
// Strip alpha byte for RGB images
|
||||||
| (img->format() == Image::Format_RGB ? PNG_TRANSFORM_STRIP_FILLER : 0),
|
(img->format() == Image::Format_RGB ? PNG_TRANSFORM_STRIP_FILLER : 0)
|
||||||
|
,
|
||||||
NULL);
|
NULL);
|
||||||
|
|
||||||
// Finish things up
|
// Finish things up
|
||||||
|
@ -1,4 +1,5 @@
|
|||||||
// Copyright NVIDIA Corporation 2007 -- Ignacio Castano <icastano@nvidia.com>
|
// Copyright (c) 2009-2011 Ignacio Castano <castano@gmail.com>
|
||||||
|
// Copyright (c) 2007-2009 NVIDIA Corporation -- Ignacio Castano <icastano@nvidia.com>
|
||||||
//
|
//
|
||||||
// Permission is hereby granted, free of charge, to any person
|
// Permission is hereby granted, free of charge, to any person
|
||||||
// obtaining a copy of this software and associated documentation
|
// obtaining a copy of this software and associated documentation
|
||||||
|
@ -1,4 +1,5 @@
|
|||||||
// Copyright NVIDIA Corporation 2007 -- Ignacio Castano <icastano@nvidia.com>
|
// Copyright (c) 2009-2011 Ignacio Castano <castano@gmail.com>
|
||||||
|
// Copyright (c) 2007-2009 NVIDIA Corporation -- Ignacio Castano <icastano@nvidia.com>
|
||||||
//
|
//
|
||||||
// Permission is hereby granted, free of charge, to any person
|
// Permission is hereby granted, free of charge, to any person
|
||||||
// obtaining a copy of this software and associated documentation
|
// obtaining a copy of this software and associated documentation
|
||||||
|
@ -1,4 +1,5 @@
|
|||||||
// Copyright Ignacio Castano <icastano@nvidia.com> 2009
|
// Copyright (c) 2009-2011 Ignacio Castano <castano@gmail.com>
|
||||||
|
// Copyright (c) 2007-2009 NVIDIA Corporation -- Ignacio Castano <icastano@nvidia.com>
|
||||||
//
|
//
|
||||||
// Permission is hereby granted, free of charge, to any person
|
// Permission is hereby granted, free of charge, to any person
|
||||||
// obtaining a copy of this software and associated documentation
|
// obtaining a copy of this software and associated documentation
|
||||||
|
@ -1,4 +1,5 @@
|
|||||||
// Copyright NVIDIA Corporation 2007 -- Ignacio Castano <icastano@nvidia.com>
|
// Copyright (c) 2009-2011 Ignacio Castano <castano@gmail.com>
|
||||||
|
// Copyright (c) 2007-2009 NVIDIA Corporation -- Ignacio Castano <icastano@nvidia.com>
|
||||||
//
|
//
|
||||||
// Permission is hereby granted, free of charge, to any person
|
// Permission is hereby granted, free of charge, to any person
|
||||||
// obtaining a copy of this software and associated documentation
|
// obtaining a copy of this software and associated documentation
|
||||||
|
@ -1,4 +1,5 @@
|
|||||||
// Copyright NVIDIA Corporation 2007 -- Ignacio Castano <icastano@nvidia.com>
|
// Copyright (c) 2009-2011 Ignacio Castano <castano@gmail.com>
|
||||||
|
// Copyright (c) 2007-2009 NVIDIA Corporation -- Ignacio Castano <icastano@nvidia.com>
|
||||||
//
|
//
|
||||||
// Permission is hereby granted, free of charge, to any person
|
// Permission is hereby granted, free of charge, to any person
|
||||||
// obtaining a copy of this software and associated documentation
|
// obtaining a copy of this software and associated documentation
|
||||||
|
@ -1,4 +1,5 @@
|
|||||||
// Copyright NVIDIA Corporation 2007 -- Ignacio Castano <icastano@nvidia.com>
|
// Copyright (c) 2009-2011 Ignacio Castano <castano@gmail.com>
|
||||||
|
// Copyright (c) 2007-2009 NVIDIA Corporation -- Ignacio Castano <icastano@nvidia.com>
|
||||||
//
|
//
|
||||||
// Permission is hereby granted, free of charge, to any person
|
// Permission is hereby granted, free of charge, to any person
|
||||||
// obtaining a copy of this software and associated documentation
|
// obtaining a copy of this software and associated documentation
|
||||||
|
@ -1,4 +1,4 @@
|
|||||||
// Copyright NVIDIA Corporation 2007 -- Ignacio Castano <icastano@nvidia.com>
|
// Copyright (c) 2009-2011 Ignacio Castano <castano@gmail.com>
|
||||||
//
|
//
|
||||||
// Permission is hereby granted, free of charge, to any person
|
// Permission is hereby granted, free of charge, to any person
|
||||||
// obtaining a copy of this software and associated documentation
|
// obtaining a copy of this software and associated documentation
|
||||||
|
@ -1,4 +1,5 @@
|
|||||||
// Copyright NVIDIA Corporation 2007 -- Ignacio Castano <icastano@nvidia.com>
|
// Copyright (c) 2009-2011 Ignacio Castano <castano@gmail.com>
|
||||||
|
// Copyright (c) 2007-2009 NVIDIA Corporation -- Ignacio Castano <icastano@nvidia.com>
|
||||||
//
|
//
|
||||||
// Permission is hereby granted, free of charge, to any person
|
// Permission is hereby granted, free of charge, to any person
|
||||||
// obtaining a copy of this software and associated documentation
|
// obtaining a copy of this software and associated documentation
|
||||||
|
@ -1,4 +1,5 @@
|
|||||||
// Copyright NVIDIA Corporation 2007 -- Ignacio Castano <icastano@nvidia.com>
|
// Copyright (c) 2009-2011 Ignacio Castano <castano@gmail.com>
|
||||||
|
// Copyright (c) 2007-2009 NVIDIA Corporation -- Ignacio Castano <icastano@nvidia.com>
|
||||||
//
|
//
|
||||||
// Permission is hereby granted, free of charge, to any person
|
// Permission is hereby granted, free of charge, to any person
|
||||||
// obtaining a copy of this software and associated documentation
|
// obtaining a copy of this software and associated documentation
|
||||||
|
@ -1,4 +1,5 @@
|
|||||||
// Copyright NVIDIA Corporation 2007 -- Ignacio Castano <icastano@nvidia.com>
|
// Copyright (c) 2009-2011 Ignacio Castano <castano@gmail.com>
|
||||||
|
// Copyright (c) 2007-2009 NVIDIA Corporation -- Ignacio Castano <icastano@nvidia.com>
|
||||||
//
|
//
|
||||||
// Permission is hereby granted, free of charge, to any person
|
// Permission is hereby granted, free of charge, to any person
|
||||||
// obtaining a copy of this software and associated documentation
|
// obtaining a copy of this software and associated documentation
|
||||||
|
@ -1,4 +1,5 @@
|
|||||||
// Copyright NVIDIA Corporation 2007 -- Ignacio Castano <icastano@nvidia.com>
|
// Copyright (c) 2009-2011 Ignacio Castano <castano@gmail.com>
|
||||||
|
// Copyright (c) 2007-2009 NVIDIA Corporation -- Ignacio Castano <icastano@nvidia.com>
|
||||||
//
|
//
|
||||||
// Permission is hereby granted, free of charge, to any person
|
// Permission is hereby granted, free of charge, to any person
|
||||||
// obtaining a copy of this software and associated documentation
|
// obtaining a copy of this software and associated documentation
|
||||||
|
@ -1,4 +1,5 @@
|
|||||||
// Copyright NVIDIA Corporation 2007 -- Ignacio Castano <icastano@nvidia.com>
|
// Copyright (c) 2009-2011 Ignacio Castano <castano@gmail.com>
|
||||||
|
// Copyright (c) 2007-2009 NVIDIA Corporation -- Ignacio Castano <icastano@nvidia.com>
|
||||||
//
|
//
|
||||||
// Permission is hereby granted, free of charge, to any person
|
// Permission is hereby granted, free of charge, to any person
|
||||||
// obtaining a copy of this software and associated documentation
|
// obtaining a copy of this software and associated documentation
|
||||||
|
@ -1,4 +1,5 @@
|
|||||||
// Copyright NVIDIA Corporation 2007 -- Ignacio Castano <icastano@nvidia.com>
|
// Copyright (c) 2009-2011 Ignacio Castano <castano@gmail.com>
|
||||||
|
// Copyright (c) 2007-2009 NVIDIA Corporation -- Ignacio Castano <icastano@nvidia.com>
|
||||||
//
|
//
|
||||||
// Permission is hereby granted, free of charge, to any person
|
// Permission is hereby granted, free of charge, to any person
|
||||||
// obtaining a copy of this software and associated documentation
|
// obtaining a copy of this software and associated documentation
|
||||||
|
@ -1,4 +1,5 @@
|
|||||||
// Copyright NVIDIA Corporation 2007 -- Ignacio Castano <icastano@nvidia.com>
|
// Copyright (c) 2009-2011 Ignacio Castano <castano@gmail.com>
|
||||||
|
// Copyright (c) 2007-2009 NVIDIA Corporation -- Ignacio Castano <icastano@nvidia.com>
|
||||||
//
|
//
|
||||||
// Permission is hereby granted, free of charge, to any person
|
// Permission is hereby granted, free of charge, to any person
|
||||||
// obtaining a copy of this software and associated documentation
|
// obtaining a copy of this software and associated documentation
|
||||||
|
@ -1,4 +1,4 @@
|
|||||||
// Copyright NVIDIA Corporation 2007 -- Ignacio Castano <icastano@nvidia.com>
|
// Copyright (c) 2009-2011 Ignacio Castano <castano@gmail.com>
|
||||||
//
|
//
|
||||||
// Permission is hereby granted, free of charge, to any person
|
// Permission is hereby granted, free of charge, to any person
|
||||||
// obtaining a copy of this software and associated documentation
|
// obtaining a copy of this software and associated documentation
|
||||||
|
@ -1,4 +1,5 @@
|
|||||||
// Copyright NVIDIA Corporation 2008 -- Ignacio Castano <icastano@nvidia.com>
|
// Copyright (c) 2009-2011 Ignacio Castano <castano@gmail.com>
|
||||||
|
// Copyright (c) 2008-2009 NVIDIA Corporation -- Ignacio Castano <icastano@nvidia.com>
|
||||||
//
|
//
|
||||||
// Permission is hereby granted, free of charge, to any person
|
// Permission is hereby granted, free of charge, to any person
|
||||||
// obtaining a copy of this software and associated documentation
|
// obtaining a copy of this software and associated documentation
|
||||||
@ -133,9 +134,9 @@ bool Compressor::outputHeader(const TexImage & tex, int mipmapCount, const Compr
|
|||||||
return m.outputHeader(TextureType_2D, tex.width(), tex.height(), tex.depth(), mipmapCount, tex.isNormalMap(), compressionOptions.m, outputOptions.m);
|
return m.outputHeader(TextureType_2D, tex.width(), tex.height(), tex.depth(), mipmapCount, tex.isNormalMap(), compressionOptions.m, outputOptions.m);
|
||||||
}
|
}
|
||||||
|
|
||||||
bool Compressor::compress(const TexImage & tex, const CompressionOptions & compressionOptions, const OutputOptions & outputOptions) const
|
bool Compressor::compress(const TexImage & tex, int face, int mipmap, const CompressionOptions & compressionOptions, const OutputOptions & outputOptions) const
|
||||||
{
|
{
|
||||||
return m.compress(tex, compressionOptions.m, outputOptions.m);
|
return m.compress(tex, face, mipmap, compressionOptions.m, outputOptions.m);
|
||||||
}
|
}
|
||||||
|
|
||||||
int Compressor::estimateSize(const TexImage & tex, int mipmapCount, const CompressionOptions & compressionOptions) const
|
int Compressor::estimateSize(const TexImage & tex, int mipmapCount, const CompressionOptions & compressionOptions) const
|
||||||
@ -149,9 +150,9 @@ int Compressor::estimateSize(const TexImage & tex, int mipmapCount, const Compre
|
|||||||
|
|
||||||
|
|
||||||
// Raw API.
|
// Raw API.
|
||||||
bool Compressor::compress(int w, int h, int d, const float * rgba, const CompressionOptions & compressionOptions, const OutputOptions & outputOptions) const
|
bool Compressor::compress(int w, int h, int d, int face, int mipmap, const float * rgba, const CompressionOptions & compressionOptions, const OutputOptions & outputOptions) const
|
||||||
{
|
{
|
||||||
return m.compress(AlphaMode_None, w, h, d, rgba, compressionOptions.m, outputOptions.m);
|
return m.compress(AlphaMode_None, w, h, d, face, mipmap, rgba, compressionOptions.m, outputOptions.m);
|
||||||
}
|
}
|
||||||
|
|
||||||
int Compressor::estimateSize(int w, int h, int d, int mipmapCount, const CompressionOptions & compressionOptions) const
|
int Compressor::estimateSize(int w, int h, int d, int mipmapCount, const CompressionOptions & compressionOptions) const
|
||||||
@ -244,20 +245,14 @@ bool Compressor::Private::compress(const InputOptions::Private & inputOptions, c
|
|||||||
tmp.toGamma(inputOptions.outputGamma);
|
tmp.toGamma(inputOptions.outputGamma);
|
||||||
}
|
}
|
||||||
|
|
||||||
int size = computeImageSize(w, h, d, compressionOptions.bitcount, compressionOptions.pitchAlignment, compressionOptions.format);
|
|
||||||
outputOptions.beginImage(size, w, h, d, f, 0);
|
|
||||||
|
|
||||||
quantize(tmp, compressionOptions);
|
quantize(tmp, compressionOptions);
|
||||||
compress(tmp, compressionOptions, outputOptions);
|
compress(tmp, f, 0, compressionOptions, outputOptions);
|
||||||
|
|
||||||
for (int m = 1; m < mipmapCount; m++) {
|
for (int m = 1; m < mipmapCount; m++) {
|
||||||
w = max(1, w/2);
|
w = max(1, w/2);
|
||||||
h = max(1, h/2);
|
h = max(1, h/2);
|
||||||
d = max(1, d/2);
|
d = max(1, d/2);
|
||||||
|
|
||||||
int size = computeImageSize(w, h, d, compressionOptions.bitcount, compressionOptions.pitchAlignment, compressionOptions.format);
|
|
||||||
outputOptions.beginImage(size, w, h, d, f, m);
|
|
||||||
|
|
||||||
int idx = m * faceCount + f;
|
int idx = m * faceCount + f;
|
||||||
|
|
||||||
bool useSourceImages = false;
|
bool useSourceImages = false;
|
||||||
@ -296,24 +291,27 @@ bool Compressor::Private::compress(const InputOptions::Private & inputOptions, c
|
|||||||
}
|
}
|
||||||
|
|
||||||
quantize(tmp, compressionOptions);
|
quantize(tmp, compressionOptions);
|
||||||
compress(tmp, compressionOptions, outputOptions);
|
compress(tmp, f, m, compressionOptions, outputOptions);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
bool Compressor::Private::compress(const TexImage & tex, const CompressionOptions::Private & compressionOptions, const OutputOptions::Private & outputOptions) const
|
bool Compressor::Private::compress(const TexImage & tex, int face, int mipmap, const CompressionOptions::Private & compressionOptions, const OutputOptions::Private & outputOptions) const
|
||||||
{
|
{
|
||||||
if (!compress(tex.alphaMode(), tex.width(), tex.height(), tex.depth(), tex.data(), compressionOptions, outputOptions)) {
|
if (!compress(tex.alphaMode(), tex.width(), tex.height(), tex.depth(), face, mipmap, tex.data(), compressionOptions, outputOptions)) {
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
bool Compressor::Private::compress(AlphaMode alphaMode, int w, int h, int d, const float * rgba, const CompressionOptions::Private & compressionOptions, const OutputOptions::Private & outputOptions) const
|
bool Compressor::Private::compress(AlphaMode alphaMode, int w, int h, int d, int face, int mipmap, const float * rgba, const CompressionOptions::Private & compressionOptions, const OutputOptions::Private & outputOptions) const
|
||||||
{
|
{
|
||||||
|
int size = computeImageSize(w, h, d, compressionOptions.bitcount, compressionOptions.pitchAlignment, compressionOptions.format);
|
||||||
|
outputOptions.beginImage(size, w, h, d, face, mipmap);
|
||||||
|
|
||||||
// Decide what compressor to use.
|
// Decide what compressor to use.
|
||||||
AutoPtr<CompressorInterface> compressor;
|
AutoPtr<CompressorInterface> compressor;
|
||||||
#if defined HAVE_CUDA
|
#if defined HAVE_CUDA
|
||||||
@ -340,7 +338,7 @@ bool Compressor::Private::compress(AlphaMode alphaMode, int w, int h, int d, con
|
|||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
bool Compressor::Private::quantize(TexImage & img, const CompressionOptions::Private & compressionOptions) const
|
void Compressor::Private::quantize(TexImage & img, const CompressionOptions::Private & compressionOptions) const
|
||||||
{
|
{
|
||||||
if (compressionOptions.enableColorDithering) {
|
if (compressionOptions.enableColorDithering) {
|
||||||
if (compressionOptions.format >= Format_BC1 && compressionOptions.format <= Format_BC3) {
|
if (compressionOptions.format >= Format_BC1 && compressionOptions.format <= Format_BC3) {
|
||||||
@ -362,7 +360,7 @@ bool Compressor::Private::quantize(TexImage & img, const CompressionOptions::Pri
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
else if (compressionOptions.binaryAlpha) {
|
else if (compressionOptions.binaryAlpha) {
|
||||||
img.binarize(3, compressionOptions.alphaThreshold, compressionOptions.enableAlphaDithering);
|
img.binarize(3, float(compressionOptions.alphaThreshold)/255.0f, compressionOptions.enableAlphaDithering);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -1,4 +1,5 @@
|
|||||||
// Copyright NVIDIA Corporation 2008 -- Ignacio Castano <icastano@nvidia.com>
|
// Copyright (c) 2009-2011 Ignacio Castano <castano@gmail.com>
|
||||||
|
// Copyright (c) 2007-2009 NVIDIA Corporation -- Ignacio Castano <icastano@nvidia.com>
|
||||||
//
|
//
|
||||||
// Permission is hereby granted, free of charge, to any person
|
// Permission is hereby granted, free of charge, to any person
|
||||||
// obtaining a copy of this software and associated documentation
|
// obtaining a copy of this software and associated documentation
|
||||||
@ -43,11 +44,11 @@ namespace nvtt
|
|||||||
{
|
{
|
||||||
Private() {}
|
Private() {}
|
||||||
|
|
||||||
bool compress(const TexImage & tex, const CompressionOptions::Private & compressionOptions, const OutputOptions::Private & outputOptions) const;
|
|
||||||
bool compress(const InputOptions::Private & inputOptions, const CompressionOptions::Private & compressionOptions, const OutputOptions::Private & outputOptions) const;
|
bool compress(const InputOptions::Private & inputOptions, const CompressionOptions::Private & compressionOptions, const OutputOptions::Private & outputOptions) const;
|
||||||
bool compress(AlphaMode alphaMode, int w, int h, int d, const float * data, const CompressionOptions::Private & compressionOptions, const OutputOptions::Private & outputOptions) const;
|
bool compress(const TexImage & tex, int face, int mipmap, const CompressionOptions::Private & compressionOptions, const OutputOptions::Private & outputOptions) const;
|
||||||
|
bool compress(AlphaMode alphaMode, int w, int h, int d, int face, int mipmap, const float * data, const CompressionOptions::Private & compressionOptions, const OutputOptions::Private & outputOptions) const;
|
||||||
|
|
||||||
bool quantize(TexImage & tex, const CompressionOptions::Private & compressionOptions) const;
|
void quantize(TexImage & tex, const CompressionOptions::Private & compressionOptions) const;
|
||||||
|
|
||||||
bool outputHeader(nvtt::TextureType textureType, int w, int h, int d, int mipmapCount, bool isNormalMap, const CompressionOptions::Private & compressionOptions, const OutputOptions::Private & outputOptions) const;
|
bool outputHeader(nvtt::TextureType textureType, int w, int h, int d, int mipmapCount, bool isNormalMap, const CompressionOptions::Private & compressionOptions, const OutputOptions::Private & outputOptions) const;
|
||||||
//bool outputHeader(const InputOptions::Private & inputOptions, const CompressionOptions::Private & compressionOptions, const OutputOptions::Private & outputOptions) const;
|
//bool outputHeader(const InputOptions::Private & inputOptions, const CompressionOptions::Private & compressionOptions, const OutputOptions::Private & outputOptions) const;
|
||||||
|
@ -1,4 +1,5 @@
|
|||||||
// Copyright NVIDIA Corporation 2007 -- Ignacio Castano <icastano@nvidia.com>
|
// Copyright (c) 2009-2011 Ignacio Castano <castano@gmail.com>
|
||||||
|
// Copyright (c) 2007-2009 NVIDIA Corporation -- Ignacio Castano <icastano@nvidia.com>
|
||||||
//
|
//
|
||||||
// Permission is hereby granted, free of charge, to any person
|
// Permission is hereby granted, free of charge, to any person
|
||||||
// obtaining a copy of this software and associated documentation
|
// obtaining a copy of this software and associated documentation
|
||||||
@ -157,7 +158,7 @@ void InputOptions::resetTextureLayout()
|
|||||||
if (m.images != NULL)
|
if (m.images != NULL)
|
||||||
{
|
{
|
||||||
// Delete images.
|
// Delete images.
|
||||||
for (int i = 0; i < m.imageCount; i++) {
|
for (uint i = 0; i < m.imageCount; i++) {
|
||||||
free(m.images[i]);
|
free(m.images[i]);
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -178,14 +179,14 @@ bool InputOptions::setMipmapData(const void * data, int width, int height, int d
|
|||||||
if (depth != 1) {
|
if (depth != 1) {
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
if (face >= m.faceCount) {
|
if (uint(face) >= m.faceCount) {
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
if (mipLevel >= m.mipmapCount) {
|
if (uint(mipLevel) >= m.mipmapCount) {
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
const int idx = mipLevel * m.faceCount + face;
|
const uint idx = mipLevel * m.faceCount + face;
|
||||||
if (idx >= m.imageCount) {
|
if (idx >= m.imageCount) {
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
@ -1,4 +1,5 @@
|
|||||||
// Copyright NVIDIA Corporation 2007 -- Ignacio Castano <icastano@nvidia.com>
|
// Copyright (c) 2009-2011 Ignacio Castano <castano@gmail.com>
|
||||||
|
// Copyright (c) 2007-2009 NVIDIA Corporation -- Ignacio Castano <icastano@nvidia.com>
|
||||||
//
|
//
|
||||||
// Permission is hereby granted, free of charge, to any person
|
// Permission is hereby granted, free of charge, to any person
|
||||||
// obtaining a copy of this software and associated documentation
|
// obtaining a copy of this software and associated documentation
|
||||||
|
@ -1,4 +1,5 @@
|
|||||||
// Copyright NVIDIA Corporation 2007 -- Ignacio Castano <icastano@nvidia.com>
|
// Copyright (c) 2009-2011 Ignacio Castano <castano@gmail.com>
|
||||||
|
// Copyright (c) 2007-2009 NVIDIA Corporation -- Ignacio Castano <icastano@nvidia.com>
|
||||||
//
|
//
|
||||||
// Permission is hereby granted, free of charge, to any person
|
// Permission is hereby granted, free of charge, to any person
|
||||||
// obtaining a copy of this software and associated documentation
|
// obtaining a copy of this software and associated documentation
|
||||||
|
@ -1,4 +1,5 @@
|
|||||||
// Copyright NVIDIA Corporation 2008 -- Ignacio Castano <icastano@nvidia.com>
|
// Copyright (c) 2009-2011 Ignacio Castano <castano@gmail.com>
|
||||||
|
// Copyright (c) 2007-2009 NVIDIA Corporation -- Ignacio Castano <icastano@nvidia.com>
|
||||||
//
|
//
|
||||||
// Permission is hereby granted, free of charge, to any person
|
// Permission is hereby granted, free of charge, to any person
|
||||||
// obtaining a copy of this software and associated documentation
|
// obtaining a copy of this software and associated documentation
|
||||||
|
@ -1,4 +1,5 @@
|
|||||||
// Copyright NVIDIA Corporation 2007 -- Ignacio Castano <icastano@nvidia.com>
|
// Copyright (c) 2009-2011 Ignacio Castano <castano@gmail.com>
|
||||||
|
// Copyright (c) 2007-2009 NVIDIA Corporation -- Ignacio Castano <icastano@nvidia.com>
|
||||||
//
|
//
|
||||||
// Permission is hereby granted, free of charge, to any person
|
// Permission is hereby granted, free of charge, to any person
|
||||||
// obtaining a copy of this software and associated documentation
|
// obtaining a copy of this software and associated documentation
|
||||||
|
@ -1,4 +1,5 @@
|
|||||||
// Copyright NVIDIA Corporation 2007 -- Ignacio Castano <icastano@nvidia.com>
|
// Copyright (c) 2009-2011 Ignacio Castano <castano@gmail.com>
|
||||||
|
// Copyright (c) 2007-2009 NVIDIA Corporation -- Ignacio Castano <icastano@nvidia.com>
|
||||||
//
|
//
|
||||||
// Permission is hereby granted, free of charge, to any person
|
// Permission is hereby granted, free of charge, to any person
|
||||||
// obtaining a copy of this software and associated documentation
|
// obtaining a copy of this software and associated documentation
|
||||||
|
@ -1,4 +1,5 @@
|
|||||||
// Copyright NVIDIA Corporation 2007 -- Ignacio Castano <icastano@nvidia.com>
|
// Copyright (c) 2009-2011 Ignacio Castano <castano@gmail.com>
|
||||||
|
// Copyright (c) 2007-2009 NVIDIA Corporation -- Ignacio Castano <icastano@nvidia.com>
|
||||||
//
|
//
|
||||||
// Permission is hereby granted, free of charge, to any person
|
// Permission is hereby granted, free of charge, to any person
|
||||||
// obtaining a copy of this software and associated documentation
|
// obtaining a copy of this software and associated documentation
|
||||||
|
@ -1,4 +1,5 @@
|
|||||||
// Copyright NVIDIA Corporation 2007 -- Ignacio Castano <icastano@nvidia.com>
|
// Copyright (c) 2009-2011 Ignacio Castano <castano@gmail.com>
|
||||||
|
// Copyright (c) 2007-2009 NVIDIA Corporation -- Ignacio Castano <icastano@nvidia.com>
|
||||||
//
|
//
|
||||||
// Permission is hereby granted, free of charge, to any person
|
// Permission is hereby granted, free of charge, to any person
|
||||||
// obtaining a copy of this software and associated documentation
|
// obtaining a copy of this software and associated documentation
|
||||||
|
@ -1,4 +1,5 @@
|
|||||||
// Copyright NVIDIA Corporation 2007 -- Ignacio Castano <icastano@nvidia.com>
|
// Copyright (c) 2009-2011 Ignacio Castano <castano@gmail.com>
|
||||||
|
// Copyright (c) 2007-2009 NVIDIA Corporation -- Ignacio Castano <icastano@nvidia.com>
|
||||||
//
|
//
|
||||||
// Permission is hereby granted, free of charge, to any person
|
// Permission is hereby granted, free of charge, to any person
|
||||||
// obtaining a copy of this software and associated documentation
|
// obtaining a copy of this software and associated documentation
|
||||||
@ -472,9 +473,7 @@ bool TexImage::setImage2D(InputFormat format, int w, int h, const void * r, cons
|
|||||||
|
|
||||||
bool TexImage::setImage2D(Format format, Decoder decoder, int w, int h, const void * data)
|
bool TexImage::setImage2D(Format format, Decoder decoder, int w, int h, const void * data)
|
||||||
{
|
{
|
||||||
#pragma NV_MESSAGE("TODO: Add support for all compressed formats in TexImage::setImage2D.")
|
if (format != nvtt::Format_BC1 && format != nvtt::Format_BC2 && format != nvtt::Format_BC3 && format != nvtt::Format_BC4 && format != nvtt::Format_BC5)
|
||||||
|
|
||||||
if (format != nvtt::Format_BC1 && format != nvtt::Format_BC2 && format != nvtt::Format_BC3)
|
|
||||||
{
|
{
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
@ -500,59 +499,69 @@ bool TexImage::setImage2D(Format format, Decoder decoder, int w, int h, const vo
|
|||||||
{
|
{
|
||||||
ColorBlock colors;
|
ColorBlock colors;
|
||||||
|
|
||||||
if (format == nvtt::Format_BC1)
|
if (format == nvtt::Format_BC1)
|
||||||
{
|
{
|
||||||
const BlockDXT1 * block = (const BlockDXT1 *)ptr;
|
const BlockDXT1 * block = (const BlockDXT1 *)ptr;
|
||||||
|
|
||||||
if (decoder == Decoder_Reference) {
|
if (decoder == Decoder_Reference) {
|
||||||
block->decodeBlock(&colors);
|
block->decodeBlock(&colors);
|
||||||
}
|
}
|
||||||
else if (decoder == Decoder_NV5x) {
|
else if (decoder == Decoder_NV5x) {
|
||||||
block->decodeBlockNV5x(&colors);
|
block->decodeBlockNV5x(&colors);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
else if (format == nvtt::Format_BC2)
|
else if (format == nvtt::Format_BC2)
|
||||||
{
|
{
|
||||||
const BlockDXT3 * block = (const BlockDXT3 *)ptr;
|
const BlockDXT3 * block = (const BlockDXT3 *)ptr;
|
||||||
|
|
||||||
if (decoder == Decoder_Reference) {
|
if (decoder == Decoder_Reference) {
|
||||||
block->decodeBlock(&colors);
|
block->decodeBlock(&colors);
|
||||||
}
|
}
|
||||||
else if (decoder == Decoder_NV5x) {
|
else if (decoder == Decoder_NV5x) {
|
||||||
block->decodeBlockNV5x(&colors);
|
block->decodeBlockNV5x(&colors);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
else if (format == nvtt::Format_BC3)
|
else if (format == nvtt::Format_BC3)
|
||||||
{
|
{
|
||||||
const BlockDXT5 * block = (const BlockDXT5 *)ptr;
|
const BlockDXT5 * block = (const BlockDXT5 *)ptr;
|
||||||
|
|
||||||
if (decoder == Decoder_Reference) {
|
if (decoder == Decoder_Reference) {
|
||||||
block->decodeBlock(&colors);
|
block->decodeBlock(&colors);
|
||||||
}
|
}
|
||||||
else if (decoder == Decoder_NV5x) {
|
else if (decoder == Decoder_NV5x) {
|
||||||
block->decodeBlockNV5x(&colors);
|
block->decodeBlockNV5x(&colors);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
else if (format == nvtt::Format_BC4)
|
||||||
|
{
|
||||||
|
const BlockATI1 * block = (const BlockATI1 *)ptr;
|
||||||
|
block->decodeBlock(&colors);
|
||||||
|
}
|
||||||
|
else if (format == nvtt::Format_BC5)
|
||||||
|
{
|
||||||
|
const BlockATI2 * block = (const BlockATI2 *)ptr;
|
||||||
|
block->decodeBlock(&colors);
|
||||||
|
}
|
||||||
|
|
||||||
for (int yy = 0; yy < 4; yy++)
|
for (int yy = 0; yy < 4; yy++)
|
||||||
{
|
{
|
||||||
for (int xx = 0; xx < 4; xx++)
|
for (int xx = 0; xx < 4; xx++)
|
||||||
{
|
{
|
||||||
Color32 c = colors.color(xx, yy);
|
Color32 c = colors.color(xx, yy);
|
||||||
|
|
||||||
if (x * 4 + xx < w && y * 4 + yy < h)
|
if (x * 4 + xx < w && y * 4 + yy < h)
|
||||||
{
|
{
|
||||||
m->image->pixel(x*4 + xx, y*4 + yy, 0) = float(c.r) * 1.0f/255.0f;
|
m->image->pixel(x*4 + xx, y*4 + yy, 0) = float(c.r) * 1.0f/255.0f;
|
||||||
m->image->pixel(x*4 + xx, y*4 + yy, 1) = float(c.g) * 1.0f/255.0f;
|
m->image->pixel(x*4 + xx, y*4 + yy, 1) = float(c.g) * 1.0f/255.0f;
|
||||||
m->image->pixel(x*4 + xx, y*4 + yy, 2) = float(c.b) * 1.0f/255.0f;
|
m->image->pixel(x*4 + xx, y*4 + yy, 2) = float(c.b) * 1.0f/255.0f;
|
||||||
m->image->pixel(x*4 + xx, y*4 + yy, 3) = float(c.a) * 1.0f/255.0f;
|
m->image->pixel(x*4 + xx, y*4 + yy, 3) = float(c.a) * 1.0f/255.0f;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
ptr += bs;
|
ptr += bs;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
|
||||||
}
|
}
|
||||||
catch(...) {
|
catch(...) {
|
||||||
return false;
|
return false;
|
||||||
@ -803,6 +812,7 @@ void TexImage::swizzle(int r, int g, int b, int a)
|
|||||||
m->image->swizzle(0, r, g, b, a);
|
m->image->swizzle(0, r, g, b, a);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// color * scale + bias
|
||||||
void TexImage::scaleBias(int channel, float scale, float bias)
|
void TexImage::scaleBias(int channel, float scale, float bias)
|
||||||
{
|
{
|
||||||
if (m->image == NULL) return;
|
if (m->image == NULL) return;
|
||||||
@ -1038,21 +1048,44 @@ void TexImage::toRGBM(float range/*= 1*/, float threshold/*= 0.25*/)
|
|||||||
|
|
||||||
const uint count = img->width() * img->height();
|
const uint count = img->width() * img->height();
|
||||||
for (uint i = 0; i < count; i++) {
|
for (uint i = 0; i < count; i++) {
|
||||||
float ri = nv::clamp(r[i] * irange, 0.0f, 1.0f);
|
float R = nv::clamp(r[i] * irange, 0.0f, 1.0f);
|
||||||
float gi = nv::clamp(g[i] * irange, 0.0f, 1.0f);
|
float G = nv::clamp(g[i] * irange, 0.0f, 1.0f);
|
||||||
float bi = nv::clamp(b[i] * irange, 0.0f, 1.0f);
|
float B = nv::clamp(b[i] * irange, 0.0f, 1.0f);
|
||||||
|
|
||||||
float m = max(max(ri, gi), max(bi, 1e-6f)); // Avoid division by zero.
|
float M = max(max(R, G), max(B, 1e-6f)); // Avoid division by zero.
|
||||||
//m = quantizeCeil(m, 8);
|
//m = quantizeCeil(m, 8);
|
||||||
float im = 1.0f / m;
|
|
||||||
|
|
||||||
r[i] = ri * im;
|
r[i] = R / M;
|
||||||
g[i] = gi * im;
|
g[i] = G / M;
|
||||||
b[i] = bi * im;
|
b[i] = B / M;
|
||||||
a[i] = m;
|
a[i] = M;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void TexImage::fromRGBM(float range/*= 1*/)
|
||||||
|
{
|
||||||
|
if (m->image == NULL) return;
|
||||||
|
|
||||||
|
detach();
|
||||||
|
|
||||||
|
FloatImage * img = m->image;
|
||||||
|
float * r = img->channel(0);
|
||||||
|
float * g = img->channel(1);
|
||||||
|
float * b = img->channel(2);
|
||||||
|
float * a = img->channel(3);
|
||||||
|
|
||||||
|
const uint count = img->width() * img->height();
|
||||||
|
for (uint i = 0; i < count; i++) {
|
||||||
|
float M = a[i] * range;
|
||||||
|
|
||||||
|
r[i] *= M;
|
||||||
|
g[i] *= M;
|
||||||
|
b[i] *= M;
|
||||||
|
a[i] = 1.0f;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
// Y is in the [0, 1] range, while CoCg are in the [-1, 1] range.
|
// Y is in the [0, 1] range, while CoCg are in the [-1, 1] range.
|
||||||
void TexImage::toYCoCg()
|
void TexImage::toYCoCg()
|
||||||
{
|
{
|
||||||
@ -1068,13 +1101,13 @@ void TexImage::toYCoCg()
|
|||||||
|
|
||||||
const uint count = img->width() * img->height();
|
const uint count = img->width() * img->height();
|
||||||
for (uint i = 0; i < count; i++) {
|
for (uint i = 0; i < count; i++) {
|
||||||
float ri = r[i];
|
float R = r[i];
|
||||||
float gi = g[i];
|
float G = g[i];
|
||||||
float bi = b[i];
|
float B = b[i];
|
||||||
|
|
||||||
float Y = (2*gi + ri + bi) * 0.25f;
|
float Y = (2*G + R + B) * 0.25f;
|
||||||
float Co = (ri - bi);
|
float Co = (R - B);
|
||||||
float Cg = (2*gi - ri - bi) * 0.5f;
|
float Cg = (2*G - R - B) * 0.5f;
|
||||||
|
|
||||||
r[i] = Co;
|
r[i] = Co;
|
||||||
g[i] = Cg;
|
g[i] = Cg;
|
||||||
@ -1146,6 +1179,40 @@ void TexImage::blockScaleCoCg(int bits/*= 5*/, float threshold/*= 0.0*/)
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void TexImage::fromYCoCg()
|
||||||
|
{
|
||||||
|
if (m->image == NULL) return;
|
||||||
|
|
||||||
|
detach();
|
||||||
|
|
||||||
|
FloatImage * img = m->image;
|
||||||
|
float * r = img->channel(0);
|
||||||
|
float * g = img->channel(1);
|
||||||
|
float * b = img->channel(2);
|
||||||
|
float * a = img->channel(3);
|
||||||
|
|
||||||
|
const uint count = img->width() * img->height();
|
||||||
|
for (uint i = 0; i < count; i++) {
|
||||||
|
float Co = r[i];
|
||||||
|
float Cg = g[i];
|
||||||
|
float scale = b[i];
|
||||||
|
float Y = a[i];
|
||||||
|
|
||||||
|
Co *= scale;
|
||||||
|
Cg *= scale;
|
||||||
|
|
||||||
|
float R = Y + Co - Cg;
|
||||||
|
float G = Y + Cg;
|
||||||
|
float B = Y - Co - Cg;
|
||||||
|
|
||||||
|
r[i] = R;
|
||||||
|
g[i] = G;
|
||||||
|
b[i] = B;
|
||||||
|
a[i] = 1.0f;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
void TexImage::binarize(int channel, float threshold, bool dither)
|
void TexImage::binarize(int channel, float threshold, bool dither)
|
||||||
{
|
{
|
||||||
@ -1189,79 +1256,6 @@ void TexImage::normalizeNormalMap()
|
|||||||
nv::normalizeNormalMap(m->image);
|
nv::normalizeNormalMap(m->image);
|
||||||
}
|
}
|
||||||
|
|
||||||
float TexImage::rootMeanSquaredError_rgb(const TexImage & reference) const
|
|
||||||
{
|
|
||||||
double mse = 0;
|
|
||||||
|
|
||||||
const FloatImage * img = m->image;
|
|
||||||
const FloatImage * ref = reference.m->image;
|
|
||||||
|
|
||||||
if (img == NULL || ref == NULL || img->width() != ref->width() || img->height() != ref->height()) {
|
|
||||||
return FLT_MAX;
|
|
||||||
}
|
|
||||||
nvDebugCheck(img->componentNum() == 4);
|
|
||||||
nvDebugCheck(ref->componentNum() == 4);
|
|
||||||
|
|
||||||
const uint count = img->width() * img->height();
|
|
||||||
for (uint i = 0; i < count; i++)
|
|
||||||
{
|
|
||||||
float r0 = img->pixel(4 * i + count * 0);
|
|
||||||
float g0 = img->pixel(4 * i + count * 1);
|
|
||||||
float b0 = img->pixel(4 * i + count * 2);
|
|
||||||
//float a0 = img->pixel(4 * i + count * 3);
|
|
||||||
float r1 = ref->pixel(4 * i + count * 0);
|
|
||||||
float g1 = ref->pixel(4 * i + count * 1);
|
|
||||||
float b1 = ref->pixel(4 * i + count * 2);
|
|
||||||
float a1 = ref->pixel(4 * i + count * 3);
|
|
||||||
|
|
||||||
float r = r0 - r1;
|
|
||||||
float g = g0 - g1;
|
|
||||||
float b = b0 - b1;
|
|
||||||
//float a = a0 - a1;
|
|
||||||
|
|
||||||
if (reference.alphaMode() == nvtt::AlphaMode_Transparency)
|
|
||||||
{
|
|
||||||
mse += double(r * r) * a1 / 255.0;
|
|
||||||
mse += double(g * g) * a1 / 255.0;
|
|
||||||
mse += double(b * b) * a1 / 255.0;
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
mse += r * r;
|
|
||||||
mse += g * g;
|
|
||||||
mse += b * b;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
return float(sqrt(mse / count));
|
|
||||||
}
|
|
||||||
|
|
||||||
float TexImage::rootMeanSquaredError_alpha(const TexImage & reference) const
|
|
||||||
{
|
|
||||||
double mse = 0;
|
|
||||||
|
|
||||||
const FloatImage * img = m->image;
|
|
||||||
const FloatImage * ref = reference.m->image;
|
|
||||||
|
|
||||||
if (img == NULL || ref == NULL || img->width() != ref->width() || img->height() != ref->height()) {
|
|
||||||
return FLT_MAX;
|
|
||||||
}
|
|
||||||
nvDebugCheck(img->componentNum() == 4 && ref->componentNum() == 4);
|
|
||||||
|
|
||||||
const uint count = img->width() * img->height();
|
|
||||||
for (uint i = 0; i < count; i++)
|
|
||||||
{
|
|
||||||
float a0 = img->pixel(4 * i + count * 3);
|
|
||||||
float a1 = ref->pixel(4 * i + count * 3);
|
|
||||||
|
|
||||||
float a = a0 - a1;
|
|
||||||
|
|
||||||
mse += double(a * a);
|
|
||||||
}
|
|
||||||
|
|
||||||
return float(sqrt(mse / count));
|
|
||||||
}
|
|
||||||
|
|
||||||
void TexImage::flipVertically()
|
void TexImage::flipVertically()
|
||||||
{
|
{
|
||||||
if (m->image == NULL) return;
|
if (m->image == NULL) return;
|
||||||
@ -1299,3 +1293,117 @@ bool TexImage::copyChannel(const TexImage & srcImage, int srcChannel, int dstCha
|
|||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
float nvtt::rmsError(const TexImage & reference, const TexImage & image)
|
||||||
|
{
|
||||||
|
double mse = 0;
|
||||||
|
|
||||||
|
const FloatImage * ref = reference.m->image;
|
||||||
|
const FloatImage * img = image.m->image;
|
||||||
|
|
||||||
|
if (img == NULL || ref == NULL || img->width() != ref->width() || img->height() != ref->height()) {
|
||||||
|
return FLT_MAX;
|
||||||
|
}
|
||||||
|
nvDebugCheck(img->componentNum() == 4);
|
||||||
|
nvDebugCheck(ref->componentNum() == 4);
|
||||||
|
|
||||||
|
const uint count = img->width() * img->height();
|
||||||
|
for (uint i = 0; i < count; i++)
|
||||||
|
{
|
||||||
|
float r0 = img->pixel(i + count * 0);
|
||||||
|
float g0 = img->pixel(i + count * 1);
|
||||||
|
float b0 = img->pixel(i + count * 2);
|
||||||
|
//float a0 = img->pixel(i + count * 3);
|
||||||
|
float r1 = ref->pixel(i + count * 0);
|
||||||
|
float g1 = ref->pixel(i + count * 1);
|
||||||
|
float b1 = ref->pixel(i + count * 2);
|
||||||
|
float a1 = ref->pixel(i + count * 3);
|
||||||
|
|
||||||
|
float r = r0 - r1;
|
||||||
|
float g = g0 - g1;
|
||||||
|
float b = b0 - b1;
|
||||||
|
//float a = a0 - a1;
|
||||||
|
|
||||||
|
if (reference.alphaMode() == nvtt::AlphaMode_Transparency)
|
||||||
|
{
|
||||||
|
mse += double(r * r) * a1;
|
||||||
|
mse += double(g * g) * a1;
|
||||||
|
mse += double(b * b) * a1;
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
mse += r * r;
|
||||||
|
mse += g * g;
|
||||||
|
mse += b * b;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
return float(sqrt(mse / count));
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
/*float rmsError(const Image * a, const Image * b)
|
||||||
|
{
|
||||||
|
nvCheck(a != NULL);
|
||||||
|
nvCheck(b != NULL);
|
||||||
|
nvCheck(a->width() == b->width());
|
||||||
|
nvCheck(a->height() == b->height());
|
||||||
|
|
||||||
|
double mse = 0;
|
||||||
|
|
||||||
|
const uint count = a->width() * a->height();
|
||||||
|
|
||||||
|
for (uint i = 0; i < count; i++)
|
||||||
|
{
|
||||||
|
Color32 c0 = a->pixel(i);
|
||||||
|
Color32 c1 = b->pixel(i);
|
||||||
|
|
||||||
|
int r = c0.r - c1.r;
|
||||||
|
int g = c0.g - c1.g;
|
||||||
|
int b = c0.b - c1.b;
|
||||||
|
int a = c0.a - c1.a;
|
||||||
|
|
||||||
|
mse += double(r * r * c0.a) / 255;
|
||||||
|
mse += double(g * g * c0.a) / 255;
|
||||||
|
mse += double(b * b * c0.a) / 255;
|
||||||
|
}
|
||||||
|
|
||||||
|
return float(sqrt(mse / count));
|
||||||
|
}*/
|
||||||
|
|
||||||
|
|
||||||
|
float nvtt::rmsAlphaError(const TexImage & reference, const TexImage & image)
|
||||||
|
{
|
||||||
|
double mse = 0;
|
||||||
|
|
||||||
|
const FloatImage * img = image.m->image;
|
||||||
|
const FloatImage * ref = reference.m->image;
|
||||||
|
|
||||||
|
if (img == NULL || ref == NULL || img->width() != ref->width() || img->height() != ref->height()) {
|
||||||
|
return FLT_MAX;
|
||||||
|
}
|
||||||
|
nvDebugCheck(img->componentNum() == 4 && ref->componentNum() == 4);
|
||||||
|
|
||||||
|
const uint count = img->width() * img->height();
|
||||||
|
for (uint i = 0; i < count; i++)
|
||||||
|
{
|
||||||
|
float a0 = img->pixel(i + count * 3);
|
||||||
|
float a1 = ref->pixel(i + count * 3);
|
||||||
|
|
||||||
|
float a = a0 - a1;
|
||||||
|
|
||||||
|
mse += double(a * a);
|
||||||
|
}
|
||||||
|
|
||||||
|
return float(sqrt(mse / count));
|
||||||
|
}
|
||||||
|
|
||||||
|
TexImage nvtt::diff(const TexImage & reference, const TexImage & image)
|
||||||
|
{
|
||||||
|
// @@ TODO.
|
||||||
|
return TexImage();
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
@ -1,4 +1,5 @@
|
|||||||
// Copyright NVIDIA Corporation 2007 -- Ignacio Castano <icastano@nvidia.com>
|
// Copyright (c) 2009-2011 Ignacio Castano <castano@gmail.com>
|
||||||
|
// Copyright (c) 2007-2009 NVIDIA Corporation -- Ignacio Castano <icastano@nvidia.com>
|
||||||
//
|
//
|
||||||
// Permission is hereby granted, free of charge, to any person
|
// Permission is hereby granted, free of charge, to any person
|
||||||
// obtaining a copy of this software and associated documentation
|
// obtaining a copy of this software and associated documentation
|
||||||
|
@ -1,4 +1,5 @@
|
|||||||
// Copyright NVIDIA Corporation 2007 -- Ignacio Castano <icastano@nvidia.com>
|
// Copyright (c) 2009-2011 Ignacio Castano <castano@gmail.com>
|
||||||
|
// Copyright (c) 2007-2009 NVIDIA Corporation -- Ignacio Castano <icastano@nvidia.com>
|
||||||
//
|
//
|
||||||
// Permission is hereby granted, free of charge, to any person
|
// Permission is hereby granted, free of charge, to any person
|
||||||
// obtaining a copy of this software and associated documentation
|
// obtaining a copy of this software and associated documentation
|
||||||
|
@ -1,4 +1,5 @@
|
|||||||
// Copyright NVIDIA Corporation 2007 -- Ignacio Castano <icastano@nvidia.com>
|
// Copyright (c) 2009-2011 Ignacio Castano <castano@gmail.com>
|
||||||
|
// Copyright (c) 2007-2009 NVIDIA Corporation -- Ignacio Castano <icastano@nvidia.com>
|
||||||
//
|
//
|
||||||
// Permission is hereby granted, free of charge, to any person
|
// Permission is hereby granted, free of charge, to any person
|
||||||
// obtaining a copy of this software and associated documentation
|
// obtaining a copy of this software and associated documentation
|
||||||
|
@ -1,4 +1,5 @@
|
|||||||
// Copyright NVIDIA Corporation 2007 -- Ignacio Castano <icastano@nvidia.com>
|
// Copyright (c) 2009-2011 Ignacio Castano <castano@gmail.com>
|
||||||
|
// Copyright (c) 2007-2009 NVIDIA Corporation -- Ignacio Castano <icastano@nvidia.com>
|
||||||
//
|
//
|
||||||
// Permission is hereby granted, free of charge, to any person
|
// Permission is hereby granted, free of charge, to any person
|
||||||
// obtaining a copy of this software and associated documentation
|
// obtaining a copy of this software and associated documentation
|
||||||
@ -133,11 +134,11 @@ void CudaCompressor::compress(nvtt::AlphaMode alphaMode, uint w, uint h, const f
|
|||||||
// Allocate image as a cuda array.
|
// Allocate image as a cuda array.
|
||||||
const uint count = w * h;
|
const uint count = w * h;
|
||||||
Color32 * tmp = malloc<Color32>(count);
|
Color32 * tmp = malloc<Color32>(count);
|
||||||
for (int i = 0; i < count; i++) {
|
for (uint i = 0; i < count; i++) {
|
||||||
tmp[i].r = clamp(data[i + count*0], 0.0f, 1.0f) * 255;
|
tmp[i].r = uint8(clamp(data[i + count*0], 0.0f, 1.0f) * 255);
|
||||||
tmp[i].g = clamp(data[i + count*1], 0.0f, 1.0f) * 255;
|
tmp[i].g = uint8(clamp(data[i + count*1], 0.0f, 1.0f) * 255);
|
||||||
tmp[i].b = clamp(data[i + count*2], 0.0f, 1.0f) * 255;
|
tmp[i].b = uint8(clamp(data[i + count*2], 0.0f, 1.0f) * 255);
|
||||||
tmp[i].a = clamp(data[i + count*3], 0.0f, 1.0f) * 255;
|
tmp[i].a = uint8(clamp(data[i + count*3], 0.0f, 1.0f) * 255);
|
||||||
}
|
}
|
||||||
|
|
||||||
cudaArray * d_image;
|
cudaArray * d_image;
|
||||||
|
@ -1,4 +1,5 @@
|
|||||||
// Copyright NVIDIA Corporation 2007 -- Ignacio Castano <icastano@nvidia.com>
|
// Copyright (c) 2009-2011 Ignacio Castano <castano@gmail.com>
|
||||||
|
// Copyright (c) 2007-2009 NVIDIA Corporation -- Ignacio Castano <icastano@nvidia.com>
|
||||||
//
|
//
|
||||||
// Permission is hereby granted, free of charge, to any person
|
// Permission is hereby granted, free of charge, to any person
|
||||||
// obtaining a copy of this software and associated documentation
|
// obtaining a copy of this software and associated documentation
|
||||||
|
@ -1,4 +1,5 @@
|
|||||||
// Copyright NVIDIA Corporation 2007 -- Ignacio Castano <icastano@nvidia.com>
|
// Copyright (c) 2009-2011 Ignacio Castano <castano@gmail.com>
|
||||||
|
// Copyright (c) 2007-2009 NVIDIA Corporation -- Ignacio Castano <icastano@nvidia.com>
|
||||||
//
|
//
|
||||||
// Permission is hereby granted, free of charge, to any person
|
// Permission is hereby granted, free of charge, to any person
|
||||||
// obtaining a copy of this software and associated documentation
|
// obtaining a copy of this software and associated documentation
|
||||||
|
@ -1,239 +1,240 @@
|
|||||||
// Copyright NVIDIA Corporation 2007 -- Ignacio Castano <icastano@nvidia.com>
|
// Copyright (c) 2009-2011 Ignacio Castano <castano@gmail.com>
|
||||||
//
|
// Copyright (c) 2007-2009 NVIDIA Corporation -- Ignacio Castano <icastano@nvidia.com>
|
||||||
// Permission is hereby granted, free of charge, to any person
|
//
|
||||||
// obtaining a copy of this software and associated documentation
|
// Permission is hereby granted, free of charge, to any person
|
||||||
// files (the "Software"), to deal in the Software without
|
// obtaining a copy of this software and associated documentation
|
||||||
// restriction, including without limitation the rights to use,
|
// files (the "Software"), to deal in the Software without
|
||||||
// copy, modify, merge, publish, distribute, sublicense, and/or sell
|
// restriction, including without limitation the rights to use,
|
||||||
// copies of the Software, and to permit persons to whom the
|
// copy, modify, merge, publish, distribute, sublicense, and/or sell
|
||||||
// Software is furnished to do so, subject to the following
|
// copies of the Software, and to permit persons to whom the
|
||||||
// conditions:
|
// Software is furnished to do so, subject to the following
|
||||||
//
|
// conditions:
|
||||||
// The above copyright notice and this permission notice shall be
|
//
|
||||||
// included in all copies or substantial portions of the Software.
|
// The above copyright notice and this permission notice shall be
|
||||||
//
|
// included in all copies or substantial portions of the Software.
|
||||||
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
|
//
|
||||||
// EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES
|
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
|
||||||
// OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
|
// EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES
|
||||||
// NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT
|
// OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
|
||||||
// HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY,
|
// NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT
|
||||||
// WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
|
// HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY,
|
||||||
// FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR
|
// WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
|
||||||
// OTHER DEALINGS IN THE SOFTWARE.
|
// FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR
|
||||||
|
// OTHER DEALINGS IN THE SOFTWARE.
|
||||||
#include "nvcore/Debug.h"
|
|
||||||
#include "nvcore/Library.h"
|
#include "nvcore/Debug.h"
|
||||||
#include "CudaUtils.h"
|
#include "nvcore/Library.h"
|
||||||
|
#include "CudaUtils.h"
|
||||||
#if defined HAVE_CUDA
|
|
||||||
#include <cuda.h>
|
#if defined HAVE_CUDA
|
||||||
#include <cuda_runtime_api.h>
|
#include <cuda.h>
|
||||||
#endif
|
#include <cuda_runtime_api.h>
|
||||||
|
#endif
|
||||||
using namespace nv;
|
|
||||||
using namespace cuda;
|
using namespace nv;
|
||||||
|
using namespace cuda;
|
||||||
/* @@ Move this to win32 utils or somewhere else.
|
|
||||||
#if NV_OS_WIN32
|
/* @@ Move this to win32 utils or somewhere else.
|
||||||
|
#if NV_OS_WIN32
|
||||||
#define WINDOWS_LEAN_AND_MEAN
|
|
||||||
#include <windows.h>
|
#define WINDOWS_LEAN_AND_MEAN
|
||||||
|
#include <windows.h>
|
||||||
static bool isWindowsVista()
|
|
||||||
{
|
static bool isWindowsVista()
|
||||||
OSVERSIONINFO osvi;
|
{
|
||||||
osvi.dwOSVersionInfoSize = sizeof(OSVERSIONINFO);
|
OSVERSIONINFO osvi;
|
||||||
|
osvi.dwOSVersionInfoSize = sizeof(OSVERSIONINFO);
|
||||||
::GetVersionEx(&osvi);
|
|
||||||
return osvi.dwMajorVersion >= 6;
|
::GetVersionEx(&osvi);
|
||||||
}
|
return osvi.dwMajorVersion >= 6;
|
||||||
|
}
|
||||||
|
|
||||||
typedef BOOL (WINAPI *LPFN_ISWOW64PROCESS) (HANDLE, PBOOL);
|
|
||||||
|
typedef BOOL (WINAPI *LPFN_ISWOW64PROCESS) (HANDLE, PBOOL);
|
||||||
static bool isWow32()
|
|
||||||
{
|
static bool isWow32()
|
||||||
LPFN_ISWOW64PROCESS fnIsWow64Process = (LPFN_ISWOW64PROCESS)GetProcAddress(GetModuleHandle("kernel32"), "IsWow64Process");
|
{
|
||||||
|
LPFN_ISWOW64PROCESS fnIsWow64Process = (LPFN_ISWOW64PROCESS)GetProcAddress(GetModuleHandle("kernel32"), "IsWow64Process");
|
||||||
BOOL bIsWow64 = FALSE;
|
|
||||||
|
BOOL bIsWow64 = FALSE;
|
||||||
if (NULL != fnIsWow64Process)
|
|
||||||
{
|
if (NULL != fnIsWow64Process)
|
||||||
if (!fnIsWow64Process(GetCurrentProcess(), &bIsWow64))
|
{
|
||||||
{
|
if (!fnIsWow64Process(GetCurrentProcess(), &bIsWow64))
|
||||||
// Assume 32 bits.
|
{
|
||||||
return true;
|
// Assume 32 bits.
|
||||||
}
|
return true;
|
||||||
}
|
}
|
||||||
|
}
|
||||||
return !bIsWow64;
|
|
||||||
}
|
return !bIsWow64;
|
||||||
|
}
|
||||||
#endif
|
|
||||||
*/
|
#endif
|
||||||
|
*/
|
||||||
|
|
||||||
static bool isCudaDriverAvailable(int version)
|
|
||||||
{
|
static bool isCudaDriverAvailable(int version)
|
||||||
#if defined HAVE_CUDA
|
{
|
||||||
#if NV_OS_WIN32
|
#if defined HAVE_CUDA
|
||||||
Library nvcuda("nvcuda.dll");
|
#if NV_OS_WIN32
|
||||||
#else
|
Library nvcuda("nvcuda.dll");
|
||||||
Library nvcuda(NV_LIBRARY_NAME(cuda));
|
#else
|
||||||
#endif
|
Library nvcuda(NV_LIBRARY_NAME(cuda));
|
||||||
|
#endif
|
||||||
if (!nvcuda.isValid())
|
|
||||||
{
|
if (!nvcuda.isValid())
|
||||||
nvDebug("*** CUDA driver not found.\n");
|
{
|
||||||
return false;
|
nvDebug("*** CUDA driver not found.\n");
|
||||||
}
|
return false;
|
||||||
|
}
|
||||||
if (version >= 2000)
|
|
||||||
{
|
if (version >= 2000)
|
||||||
void * address = nvcuda.bindSymbol("cuStreamCreate");
|
{
|
||||||
if (address == NULL) {
|
void * address = nvcuda.bindSymbol("cuStreamCreate");
|
||||||
nvDebug("*** CUDA driver version < 2.0.\n");
|
if (address == NULL) {
|
||||||
return false;
|
nvDebug("*** CUDA driver version < 2.0.\n");
|
||||||
}
|
return false;
|
||||||
}
|
}
|
||||||
|
}
|
||||||
if (version >= 2010)
|
|
||||||
{
|
if (version >= 2010)
|
||||||
void * address = nvcuda.bindSymbol("cuModuleLoadDataEx");
|
{
|
||||||
if (address == NULL) {
|
void * address = nvcuda.bindSymbol("cuModuleLoadDataEx");
|
||||||
nvDebug("*** CUDA driver version < 2.1.\n");
|
if (address == NULL) {
|
||||||
return false;
|
nvDebug("*** CUDA driver version < 2.1.\n");
|
||||||
}
|
return false;
|
||||||
}
|
}
|
||||||
|
}
|
||||||
if (version >= 2020)
|
|
||||||
{
|
if (version >= 2020)
|
||||||
typedef CUresult (CUDAAPI * PFCU_DRIVERGETVERSION)(int * version);
|
{
|
||||||
|
typedef CUresult (CUDAAPI * PFCU_DRIVERGETVERSION)(int * version);
|
||||||
PFCU_DRIVERGETVERSION driverGetVersion = (PFCU_DRIVERGETVERSION)nvcuda.bindSymbol("cuDriverGetVersion");
|
|
||||||
if (driverGetVersion == NULL) {
|
PFCU_DRIVERGETVERSION driverGetVersion = (PFCU_DRIVERGETVERSION)nvcuda.bindSymbol("cuDriverGetVersion");
|
||||||
nvDebug("*** CUDA driver version < 2.2.\n");
|
if (driverGetVersion == NULL) {
|
||||||
return false;
|
nvDebug("*** CUDA driver version < 2.2.\n");
|
||||||
}
|
return false;
|
||||||
|
}
|
||||||
int driverVersion;
|
|
||||||
CUresult err = driverGetVersion(&driverVersion);
|
int driverVersion;
|
||||||
if (err != CUDA_SUCCESS) {
|
CUresult err = driverGetVersion(&driverVersion);
|
||||||
nvDebug("*** Error querying driver version: '%s'.\n", cudaGetErrorString((cudaError_t)err));
|
if (err != CUDA_SUCCESS) {
|
||||||
return false;
|
nvDebug("*** Error querying driver version: '%s'.\n", cudaGetErrorString((cudaError_t)err));
|
||||||
}
|
return false;
|
||||||
|
}
|
||||||
return driverVersion >= version;
|
|
||||||
}
|
return driverVersion >= version;
|
||||||
#endif // HAVE_CUDA
|
}
|
||||||
|
#endif // HAVE_CUDA
|
||||||
return true;
|
|
||||||
}
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
/// Determine if CUDA is available.
|
|
||||||
bool nv::cuda::isHardwarePresent()
|
/// Determine if CUDA is available.
|
||||||
{
|
bool nv::cuda::isHardwarePresent()
|
||||||
#if defined HAVE_CUDA
|
{
|
||||||
// Make sure that CUDA driver matches CUDA runtime.
|
#if defined HAVE_CUDA
|
||||||
if (!isCudaDriverAvailable(CUDART_VERSION))
|
// Make sure that CUDA driver matches CUDA runtime.
|
||||||
{
|
if (!isCudaDriverAvailable(CUDART_VERSION))
|
||||||
nvDebug("CUDA driver not available for CUDA runtime %d\n", CUDART_VERSION);
|
{
|
||||||
return false;
|
nvDebug("CUDA driver not available for CUDA runtime %d\n", CUDART_VERSION);
|
||||||
}
|
return false;
|
||||||
|
}
|
||||||
int count = deviceCount();
|
|
||||||
if (count == 1)
|
int count = deviceCount();
|
||||||
{
|
if (count == 1)
|
||||||
// Make sure it's not an emulation device.
|
{
|
||||||
cudaDeviceProp deviceProp;
|
// Make sure it's not an emulation device.
|
||||||
cudaGetDeviceProperties(&deviceProp, 0);
|
cudaDeviceProp deviceProp;
|
||||||
|
cudaGetDeviceProperties(&deviceProp, 0);
|
||||||
// deviceProp.name != Device Emulation (CPU)
|
|
||||||
if (deviceProp.major == -1 || deviceProp.minor == -1)
|
// deviceProp.name != Device Emulation (CPU)
|
||||||
{
|
if (deviceProp.major == -1 || deviceProp.minor == -1)
|
||||||
return false;
|
{
|
||||||
}
|
return false;
|
||||||
}
|
}
|
||||||
|
}
|
||||||
// @@ Make sure that warp size == 32
|
|
||||||
|
// @@ Make sure that warp size == 32
|
||||||
return count > 0;
|
|
||||||
#else
|
return count > 0;
|
||||||
return false;
|
#else
|
||||||
#endif
|
return false;
|
||||||
}
|
#endif
|
||||||
|
}
|
||||||
/// Get number of CUDA enabled devices.
|
|
||||||
int nv::cuda::deviceCount()
|
/// Get number of CUDA enabled devices.
|
||||||
{
|
int nv::cuda::deviceCount()
|
||||||
#if defined HAVE_CUDA
|
{
|
||||||
int gpuCount = 0;
|
#if defined HAVE_CUDA
|
||||||
|
int gpuCount = 0;
|
||||||
cudaError_t result = cudaGetDeviceCount(&gpuCount);
|
|
||||||
|
cudaError_t result = cudaGetDeviceCount(&gpuCount);
|
||||||
if (result == cudaSuccess)
|
|
||||||
{
|
if (result == cudaSuccess)
|
||||||
return gpuCount;
|
{
|
||||||
}
|
return gpuCount;
|
||||||
#endif
|
}
|
||||||
return 0;
|
#endif
|
||||||
}
|
return 0;
|
||||||
|
}
|
||||||
int nv::cuda::getFastestDevice()
|
|
||||||
{
|
int nv::cuda::getFastestDevice()
|
||||||
int max_gflops_device = 0;
|
{
|
||||||
#if defined HAVE_CUDA
|
int max_gflops_device = 0;
|
||||||
int max_gflops = 0;
|
#if defined HAVE_CUDA
|
||||||
|
int max_gflops = 0;
|
||||||
const int device_count = deviceCount();
|
|
||||||
int current_device = 0;
|
const int device_count = deviceCount();
|
||||||
while (current_device < device_count)
|
int current_device = 0;
|
||||||
{
|
while (current_device < device_count)
|
||||||
cudaDeviceProp device_properties;
|
{
|
||||||
cudaGetDeviceProperties(&device_properties, current_device);
|
cudaDeviceProp device_properties;
|
||||||
int gflops = device_properties.multiProcessorCount * device_properties.clockRate;
|
cudaGetDeviceProperties(&device_properties, current_device);
|
||||||
|
int gflops = device_properties.multiProcessorCount * device_properties.clockRate;
|
||||||
if (device_properties.major != -1 && device_properties.minor != -1)
|
|
||||||
{
|
if (device_properties.major != -1 && device_properties.minor != -1)
|
||||||
if( gflops > max_gflops )
|
{
|
||||||
{
|
if( gflops > max_gflops )
|
||||||
max_gflops = gflops;
|
{
|
||||||
max_gflops_device = current_device;
|
max_gflops = gflops;
|
||||||
}
|
max_gflops_device = current_device;
|
||||||
}
|
}
|
||||||
|
}
|
||||||
current_device++;
|
|
||||||
}
|
current_device++;
|
||||||
#endif
|
}
|
||||||
return max_gflops_device;
|
#endif
|
||||||
}
|
return max_gflops_device;
|
||||||
|
}
|
||||||
|
|
||||||
/// Activate the given devices.
|
|
||||||
bool nv::cuda::setDevice(int i)
|
/// Activate the given devices.
|
||||||
{
|
bool nv::cuda::setDevice(int i)
|
||||||
nvCheck(i < deviceCount());
|
{
|
||||||
#if defined HAVE_CUDA
|
nvCheck(i < deviceCount());
|
||||||
cudaError_t result = cudaSetDevice(i);
|
#if defined HAVE_CUDA
|
||||||
|
cudaError_t result = cudaSetDevice(i);
|
||||||
if (result != cudaSuccess) {
|
|
||||||
nvDebug("*** CUDA Error: %s\n", cudaGetErrorString(result));
|
if (result != cudaSuccess) {
|
||||||
}
|
nvDebug("*** CUDA Error: %s\n", cudaGetErrorString(result));
|
||||||
|
}
|
||||||
return result == cudaSuccess;
|
|
||||||
#else
|
return result == cudaSuccess;
|
||||||
return false;
|
#else
|
||||||
#endif
|
return false;
|
||||||
}
|
#endif
|
||||||
|
}
|
||||||
void nv::cuda::exit()
|
|
||||||
{
|
void nv::cuda::exit()
|
||||||
#if defined HAVE_CUDA
|
{
|
||||||
cudaError_t result = cudaThreadExit();
|
#if defined HAVE_CUDA
|
||||||
|
cudaError_t result = cudaThreadExit();
|
||||||
if (result != cudaSuccess) {
|
|
||||||
nvDebug("*** CUDA Error: %s\n", cudaGetErrorString(result));
|
if (result != cudaSuccess) {
|
||||||
}
|
nvDebug("*** CUDA Error: %s\n", cudaGetErrorString(result));
|
||||||
#endif
|
}
|
||||||
}
|
#endif
|
||||||
|
}
|
||||||
|
@ -1,4 +1,5 @@
|
|||||||
// Copyright NVIDIA Corporation 2007 -- Ignacio Castano <icastano@nvidia.com>
|
// Copyright (c) 2009-2011 Ignacio Castano <castano@gmail.com>
|
||||||
|
// Copyright (c) 2007-2009 NVIDIA Corporation -- Ignacio Castano <icastano@nvidia.com>
|
||||||
//
|
//
|
||||||
// Permission is hereby granted, free of charge, to any person
|
// Permission is hereby granted, free of charge, to any person
|
||||||
// obtaining a copy of this software and associated documentation
|
// obtaining a copy of this software and associated documentation
|
||||||
|
@ -1,4 +1,5 @@
|
|||||||
// Copyright NVIDIA Corporation 2007 -- Ignacio Castano <icastano@nvidia.com>
|
// Copyright (c) 2009-2011 Ignacio Castano <castano@gmail.com>
|
||||||
|
// Copyright (c) 2007-2009 NVIDIA Corporation -- Ignacio Castano <icastano@nvidia.com>
|
||||||
//
|
//
|
||||||
// Permission is hereby granted, free of charge, to any person
|
// Permission is hereby granted, free of charge, to any person
|
||||||
// obtaining a copy of this software and associated documentation
|
// obtaining a copy of this software and associated documentation
|
||||||
|
@ -1,4 +1,5 @@
|
|||||||
// Copyright NVIDIA Corporation 2007 -- Ignacio Castano <icastano@nvidia.com>
|
// Copyright (c) 2009-2011 Ignacio Castano <castano@gmail.com>
|
||||||
|
// Copyright (c) 2007-2009 NVIDIA Corporation -- Ignacio Castano <icastano@nvidia.com>
|
||||||
//
|
//
|
||||||
// Permission is hereby granted, free of charge, to any person
|
// Permission is hereby granted, free of charge, to any person
|
||||||
// obtaining a copy of this software and associated documentation
|
// obtaining a copy of this software and associated documentation
|
||||||
@ -350,11 +351,11 @@ namespace nvtt
|
|||||||
|
|
||||||
// TexImage API.
|
// TexImage API.
|
||||||
NVTT_API bool outputHeader(const TexImage & tex, int mipmapCount, const CompressionOptions & compressionOptions, const OutputOptions & outputOptions) const;
|
NVTT_API bool outputHeader(const TexImage & tex, int mipmapCount, const CompressionOptions & compressionOptions, const OutputOptions & outputOptions) const;
|
||||||
NVTT_API bool compress(const TexImage & tex, const CompressionOptions & compressionOptions, const OutputOptions & outputOptions) const;
|
NVTT_API bool compress(const TexImage & tex, int face, int mipmap, const CompressionOptions & compressionOptions, const OutputOptions & outputOptions) const;
|
||||||
NVTT_API int estimateSize(const TexImage & tex, int mipmapCount, const CompressionOptions & compressionOptions) const;
|
NVTT_API int estimateSize(const TexImage & tex, int mipmapCount, const CompressionOptions & compressionOptions) const;
|
||||||
|
|
||||||
// Raw API.
|
// Raw API.
|
||||||
NVTT_API bool compress(int w, int h, int d, const float * rgba, const CompressionOptions & compressionOptions, const OutputOptions & outputOptions) const;
|
NVTT_API bool compress(int w, int h, int d, int face, int mipmap, const float * rgba, const CompressionOptions & compressionOptions, const OutputOptions & outputOptions) const;
|
||||||
NVTT_API int estimateSize(int w, int h, int d, int mipmapCount, const CompressionOptions & compressionOptions) const;
|
NVTT_API int estimateSize(int w, int h, int d, int mipmapCount, const CompressionOptions & compressionOptions) const;
|
||||||
};
|
};
|
||||||
|
|
||||||
@ -427,8 +428,10 @@ namespace nvtt
|
|||||||
NVTT_API void scaleAlphaToCoverage(float coverage, float alphaRef = 0.5f);
|
NVTT_API void scaleAlphaToCoverage(float coverage, float alphaRef = 0.5f);
|
||||||
NVTT_API bool normalizeRange(float * rangeMin, float * rangeMax);
|
NVTT_API bool normalizeRange(float * rangeMin, float * rangeMax);
|
||||||
NVTT_API void toRGBM(float range = 1.0f, float threshold = 0.0f);
|
NVTT_API void toRGBM(float range = 1.0f, float threshold = 0.0f);
|
||||||
|
NVTT_API void fromRGBM(float range = 1.0f);
|
||||||
NVTT_API void toYCoCg();
|
NVTT_API void toYCoCg();
|
||||||
NVTT_API void blockScaleCoCg(int bits = 5, float threshold = 0.0f);
|
NVTT_API void blockScaleCoCg(int bits = 5, float threshold = 0.0f);
|
||||||
|
NVTT_API void fromYCoCg();
|
||||||
|
|
||||||
// Color quantization.
|
// Color quantization.
|
||||||
NVTT_API void binarize(int channel, float threshold, bool dither);
|
NVTT_API void binarize(int channel, float threshold, bool dither);
|
||||||
@ -438,10 +441,6 @@ namespace nvtt
|
|||||||
NVTT_API void toNormalMap(float sm, float medium, float big, float large);
|
NVTT_API void toNormalMap(float sm, float medium, float big, float large);
|
||||||
NVTT_API void normalizeNormalMap();
|
NVTT_API void normalizeNormalMap();
|
||||||
|
|
||||||
// Error compare.
|
|
||||||
NVTT_API float rootMeanSquaredError_rgb(const TexImage & reference) const;
|
|
||||||
NVTT_API float rootMeanSquaredError_alpha(const TexImage & reference) const;
|
|
||||||
|
|
||||||
// Geometric transforms.
|
// Geometric transforms.
|
||||||
NVTT_API void flipVertically();
|
NVTT_API void flipVertically();
|
||||||
|
|
||||||
@ -449,6 +448,11 @@ namespace nvtt
|
|||||||
NVTT_API bool copyChannel(const TexImage & srcImage, int srcChannel);
|
NVTT_API bool copyChannel(const TexImage & srcImage, int srcChannel);
|
||||||
NVTT_API bool copyChannel(const TexImage & srcImage, int srcChannel, int dstChannel);
|
NVTT_API bool copyChannel(const TexImage & srcImage, int srcChannel, int dstChannel);
|
||||||
|
|
||||||
|
// Error compare.
|
||||||
|
friend NVTT_API float rmsError(const TexImage & reference, const TexImage & img);
|
||||||
|
friend NVTT_API float rmsAlphaError(const TexImage & reference, const TexImage & img);
|
||||||
|
friend NVTT_API TexImage diff(const TexImage & reference, const TexImage & img);
|
||||||
|
|
||||||
private:
|
private:
|
||||||
void detach();
|
void detach();
|
||||||
|
|
||||||
|
@ -1,3 +1,26 @@
|
|||||||
|
// Copyright (c) 2009-2011 Ignacio Castano <castano@gmail.com>
|
||||||
|
// Copyright (c) 2007-2009 NVIDIA Corporation -- Ignacio Castano <icastano@nvidia.com>
|
||||||
|
//
|
||||||
|
// Permission is hereby granted, free of charge, to any person
|
||||||
|
// obtaining a copy of this software and associated documentation
|
||||||
|
// files (the "Software"), to deal in the Software without
|
||||||
|
// restriction, including without limitation the rights to use,
|
||||||
|
// copy, modify, merge, publish, distribute, sublicense, and/or sell
|
||||||
|
// copies of the Software, and to permit persons to whom the
|
||||||
|
// Software is furnished to do so, subject to the following
|
||||||
|
// conditions:
|
||||||
|
//
|
||||||
|
// The above copyright notice and this permission notice shall be
|
||||||
|
// included in all copies or substantial portions of the Software.
|
||||||
|
//
|
||||||
|
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
|
||||||
|
// EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES
|
||||||
|
// OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
|
||||||
|
// NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT
|
||||||
|
// HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY,
|
||||||
|
// WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
|
||||||
|
// FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR
|
||||||
|
// OTHER DEALINGS IN THE SOFTWARE.
|
||||||
|
|
||||||
#include "nvtt.h"
|
#include "nvtt.h"
|
||||||
#include "nvtt_wrapper.h"
|
#include "nvtt_wrapper.h"
|
||||||
|
@ -1,4 +1,5 @@
|
|||||||
// Copyright NVIDIA Corporation 2007 -- Ignacio Castano <icastano@nvidia.com>
|
// Copyright (c) 2009-2011 Ignacio Castano <castano@gmail.com>
|
||||||
|
// Copyright (c) 2007-2009 NVIDIA Corporation -- Ignacio Castano <icastano@nvidia.com>
|
||||||
//
|
//
|
||||||
// Permission is hereby granted, free of charge, to any person
|
// Permission is hereby granted, free of charge, to any person
|
||||||
// obtaining a copy of this software and associated documentation
|
// obtaining a copy of this software and associated documentation
|
||||||
|
@ -64,7 +64,7 @@ int main(int argc, char *argv[])
|
|||||||
image.setAlphaMode(nvtt::AlphaMode_Transparency);
|
image.setAlphaMode(nvtt::AlphaMode_Transparency);
|
||||||
|
|
||||||
// Output first mipmap.
|
// Output first mipmap.
|
||||||
context.compress(image, compressionOptions, outputOptions);
|
context.compress(image, 0, 0, compressionOptions, outputOptions);
|
||||||
|
|
||||||
float gamma = 2.2f;
|
float gamma = 2.2f;
|
||||||
image.toLinear(gamma);
|
image.toLinear(gamma);
|
||||||
@ -73,6 +73,7 @@ int main(int argc, char *argv[])
|
|||||||
float coverage = image.alphaTestCoverage(alphaRef);
|
float coverage = image.alphaTestCoverage(alphaRef);
|
||||||
|
|
||||||
// Build mimaps.
|
// Build mimaps.
|
||||||
|
int m = 1;
|
||||||
while (image.buildNextMipmap(nvtt::MipmapFilter_Kaiser))
|
while (image.buildNextMipmap(nvtt::MipmapFilter_Kaiser))
|
||||||
{
|
{
|
||||||
nvtt::TexImage tmpImage = image;
|
nvtt::TexImage tmpImage = image;
|
||||||
@ -80,7 +81,8 @@ int main(int argc, char *argv[])
|
|||||||
|
|
||||||
tmpImage.scaleAlphaToCoverage(coverage, alphaRef);
|
tmpImage.scaleAlphaToCoverage(coverage, alphaRef);
|
||||||
|
|
||||||
context.compress(tmpImage, compressionOptions, outputOptions);
|
context.compress(tmpImage, 0, m, compressionOptions, outputOptions);
|
||||||
|
m++;
|
||||||
}
|
}
|
||||||
|
|
||||||
return EXIT_SUCCESS;
|
return EXIT_SUCCESS;
|
||||||
|
@ -1,4 +1,5 @@
|
|||||||
// Copyright NVIDIA Corporation 2007 -- Ignacio Castano <icastano@nvidia.com>
|
// Copyright (c) 2009-2011 Ignacio Castano <castano@gmail.com>
|
||||||
|
// Copyright (c) 2007-2009 NVIDIA Corporation -- Ignacio Castano <icastano@nvidia.com>
|
||||||
//
|
//
|
||||||
// Permission is hereby granted, free of charge, to any person
|
// Permission is hereby granted, free of charge, to any person
|
||||||
// obtaining a copy of this software and associated documentation
|
// obtaining a copy of this software and associated documentation
|
||||||
@ -127,30 +128,39 @@ static const char * s_quake3ImageSet[] = {
|
|||||||
"q3-wires02.tga",
|
"q3-wires02.tga",
|
||||||
};
|
};
|
||||||
|
|
||||||
|
enum Mode {
|
||||||
|
Mode_BC1,
|
||||||
|
Mode_BC3_Alpha,
|
||||||
|
Mode_BC3_YCoCg,
|
||||||
|
Mode_BC3_RGBM,
|
||||||
|
Mode_BC3_Normal,
|
||||||
|
Mode_BC5_Normal,
|
||||||
|
};
|
||||||
struct ImageSet
|
struct ImageSet
|
||||||
{
|
{
|
||||||
|
const char * name;
|
||||||
const char ** fileNames;
|
const char ** fileNames;
|
||||||
int fileCount;
|
int fileCount;
|
||||||
nvtt::Format format;
|
Mode mode;
|
||||||
};
|
};
|
||||||
|
|
||||||
|
#define ARRAY_SIZE(a) sizeof(a)/sizeof(a[0])
|
||||||
|
|
||||||
static ImageSet s_imageSets[] = {
|
static ImageSet s_imageSets[] = {
|
||||||
{s_kodakImageSet, sizeof(s_kodakImageSet)/sizeof(s_kodakImageSet[0]), nvtt::Format_DXT1},
|
{"Kodak - BC1", s_kodakImageSet, ARRAY_SIZE(s_kodakImageSet), Mode_BC1},
|
||||||
{s_waterlooImageSet, sizeof(s_waterlooImageSet)/sizeof(s_waterlooImageSet[0]), nvtt::Format_DXT1},
|
{"Kodak - BC3-YCoCg", s_kodakImageSet, ARRAY_SIZE(s_kodakImageSet), Mode_BC3_YCoCg},
|
||||||
{s_epicImageSet, sizeof(s_epicImageSet)/sizeof(s_epicImageSet[0]), nvtt::Format_DXT1},
|
{"Kodak - BC3-RGBM", s_kodakImageSet, ARRAY_SIZE(s_kodakImageSet), Mode_BC3_RGBM},
|
||||||
{s_farbrauschImageSet, sizeof(s_farbrauschImageSet)/sizeof(s_farbrauschImageSet[0]), nvtt::Format_DXT1},
|
{"Waterloo - BC1", s_waterlooImageSet, ARRAY_SIZE(s_waterlooImageSet), Mode_BC1},
|
||||||
{s_lugaruImageSet, sizeof(s_lugaruImageSet)/sizeof(s_lugaruImageSet[0]), nvtt::Format_DXT5},
|
{"Waterloo - BC3-YCoCg", s_waterlooImageSet, ARRAY_SIZE(s_waterlooImageSet), Mode_BC3_YCoCg},
|
||||||
{s_quake3ImageSet, sizeof(s_quake3ImageSet)/sizeof(s_quake3ImageSet[0]), nvtt::Format_DXT5},
|
{"Epic - BC1", s_epicImageSet, ARRAY_SIZE(s_epicImageSet), Mode_BC1},
|
||||||
|
{"Epic - BC1-YCoCg", s_epicImageSet, ARRAY_SIZE(s_epicImageSet), Mode_BC3_YCoCg},
|
||||||
|
{"Farbraush - BC1", s_farbrauschImageSet, ARRAY_SIZE(s_farbrauschImageSet), Mode_BC1},
|
||||||
|
{"Farbraush - BC1-YCoCg", s_farbrauschImageSet, ARRAY_SIZE(s_farbrauschImageSet), Mode_BC3_YCoCg},
|
||||||
|
{"Lugaru - BC3", s_lugaruImageSet, ARRAY_SIZE(s_lugaruImageSet), Mode_BC3_Alpha},
|
||||||
|
{"Quake3 - BC3", s_quake3ImageSet, ARRAY_SIZE(s_quake3ImageSet), Mode_BC3_Alpha},
|
||||||
};
|
};
|
||||||
const int s_imageSetCount = sizeof(s_imageSets)/sizeof(s_imageSets[0]);
|
const int s_imageSetCount = sizeof(s_imageSets)/sizeof(s_imageSets[0]);
|
||||||
|
|
||||||
enum Decoder
|
|
||||||
{
|
|
||||||
Decoder_Reference,
|
|
||||||
Decoder_NVIDIA,
|
|
||||||
};
|
|
||||||
|
|
||||||
struct MyOutputHandler : public nvtt::OutputHandler
|
struct MyOutputHandler : public nvtt::OutputHandler
|
||||||
{
|
{
|
||||||
MyOutputHandler() : m_data(NULL), m_ptr(NULL) {}
|
MyOutputHandler() : m_data(NULL), m_ptr(NULL) {}
|
||||||
@ -176,83 +186,17 @@ struct MyOutputHandler : public nvtt::OutputHandler
|
|||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
Image * decompress(nvtt::Format format, Decoder decoder)
|
nvtt::TexImage decompress(Mode mode, nvtt::Decoder decoder)
|
||||||
{
|
{
|
||||||
int bw = (m_width + 3) / 4;
|
nvtt::Format format;
|
||||||
int bh = (m_height + 3) / 4;
|
if (mode == Mode_BC1) format = nvtt::Format_BC1;
|
||||||
|
else if (mode == Mode_BC5_Normal) format = nvtt::Format_BC5;
|
||||||
|
else format = nvtt::Format_BC3;
|
||||||
|
|
||||||
AutoPtr<Image> img( new Image() );
|
nvtt::TexImage img;
|
||||||
img->allocate(m_width, m_height);
|
img.setImage2D(format, decoder, m_width, m_height, m_data);
|
||||||
|
|
||||||
if (format == nvtt::Format_BC1)
|
return img;
|
||||||
{
|
|
||||||
BlockDXT1 * block = (BlockDXT1 *)m_data;
|
|
||||||
|
|
||||||
for (int y = 0; y < bh; y++)
|
|
||||||
{
|
|
||||||
for (int x = 0; x < bw; x++)
|
|
||||||
{
|
|
||||||
ColorBlock colors;
|
|
||||||
if (decoder == Decoder_Reference) {
|
|
||||||
block->decodeBlock(&colors);
|
|
||||||
}
|
|
||||||
else if (decoder == Decoder_NVIDIA) {
|
|
||||||
block->decodeBlockNV5x(&colors);
|
|
||||||
}
|
|
||||||
|
|
||||||
for (int yy = 0; yy < 4; yy++)
|
|
||||||
{
|
|
||||||
for (int xx = 0; xx < 4; xx++)
|
|
||||||
{
|
|
||||||
Color32 c = colors.color(xx, yy);
|
|
||||||
|
|
||||||
if (x * 4 + xx < m_width && y * 4 + yy < m_height)
|
|
||||||
{
|
|
||||||
img->pixel(x * 4 + xx, y * 4 + yy) = c;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
block++;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
else if (format == nvtt::Format_BC3)
|
|
||||||
{
|
|
||||||
BlockDXT5 * block = (BlockDXT5 *)m_data;
|
|
||||||
|
|
||||||
for (int y = 0; y < bh; y++)
|
|
||||||
{
|
|
||||||
for (int x = 0; x < bw; x++)
|
|
||||||
{
|
|
||||||
ColorBlock colors;
|
|
||||||
if (decoder == Decoder_Reference) {
|
|
||||||
block->decodeBlock(&colors);
|
|
||||||
}
|
|
||||||
else if (decoder == Decoder_NVIDIA) {
|
|
||||||
block->decodeBlockNV5x(&colors);
|
|
||||||
}
|
|
||||||
|
|
||||||
for (int yy = 0; yy < 4; yy++)
|
|
||||||
{
|
|
||||||
for (int xx = 0; xx < 4; xx++)
|
|
||||||
{
|
|
||||||
Color32 c = colors.color(xx, yy);
|
|
||||||
|
|
||||||
if (x * 4 + xx < m_width && y * 4 + yy < m_height)
|
|
||||||
{
|
|
||||||
img->pixel(x * 4 + xx, y * 4 + yy) = c;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
block++;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
return img.release();
|
|
||||||
}
|
}
|
||||||
|
|
||||||
int m_size;
|
int m_size;
|
||||||
@ -263,36 +207,6 @@ struct MyOutputHandler : public nvtt::OutputHandler
|
|||||||
};
|
};
|
||||||
|
|
||||||
|
|
||||||
float rmsError(const Image * a, const Image * b)
|
|
||||||
{
|
|
||||||
nvCheck(a != NULL);
|
|
||||||
nvCheck(b != NULL);
|
|
||||||
nvCheck(a->width() == b->width());
|
|
||||||
nvCheck(a->height() == b->height());
|
|
||||||
|
|
||||||
double mse = 0;
|
|
||||||
|
|
||||||
const uint count = a->width() * a->height();
|
|
||||||
|
|
||||||
for (uint i = 0; i < count; i++)
|
|
||||||
{
|
|
||||||
Color32 c0 = a->pixel(i);
|
|
||||||
Color32 c1 = b->pixel(i);
|
|
||||||
|
|
||||||
int r = c0.r - c1.r;
|
|
||||||
int g = c0.g - c1.g;
|
|
||||||
int b = c0.b - c1.b;
|
|
||||||
int a = c0.a - c1.a;
|
|
||||||
|
|
||||||
mse += double(r * r * c0.a) / 255;
|
|
||||||
mse += double(g * g * c0.a) / 255;
|
|
||||||
mse += double(b * b * c0.a) / 255;
|
|
||||||
}
|
|
||||||
|
|
||||||
return float(sqrt(mse / count));
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
int main(int argc, char *argv[])
|
int main(int argc, char *argv[])
|
||||||
{
|
{
|
||||||
MyAssertHandler assertHandler;
|
MyAssertHandler assertHandler;
|
||||||
@ -305,11 +219,11 @@ int main(int argc, char *argv[])
|
|||||||
|
|
||||||
printf("NVIDIA Texture Tools %u.%u.%u - Copyright NVIDIA Corporation 2007\n\n", major, minor, rev);
|
printf("NVIDIA Texture Tools %u.%u.%u - Copyright NVIDIA Corporation 2007\n\n", major, minor, rev);
|
||||||
|
|
||||||
int set = 0;
|
int setIndex = 0;
|
||||||
bool fast = false;
|
bool fast = false;
|
||||||
bool nocuda = false;
|
bool nocuda = false;
|
||||||
bool showHelp = false;
|
bool showHelp = false;
|
||||||
Decoder decoder = Decoder_Reference;
|
nvtt::Decoder decoder = nvtt::Decoder_Reference;
|
||||||
const char * basePath = "";
|
const char * basePath = "";
|
||||||
const char * outPath = "output";
|
const char * outPath = "output";
|
||||||
const char * regressPath = NULL;
|
const char * regressPath = NULL;
|
||||||
@ -320,14 +234,14 @@ int main(int argc, char *argv[])
|
|||||||
if (strcmp("-set", argv[i]) == 0)
|
if (strcmp("-set", argv[i]) == 0)
|
||||||
{
|
{
|
||||||
if (i+1 < argc && argv[i+1][0] != '-') {
|
if (i+1 < argc && argv[i+1][0] != '-') {
|
||||||
set = atoi(argv[i+1]);
|
setIndex = atoi(argv[i+1]);
|
||||||
i++;
|
i++;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
else if (strcmp("-dec", argv[i]) == 0)
|
else if (strcmp("-dec", argv[i]) == 0)
|
||||||
{
|
{
|
||||||
if (i+1 < argc && argv[i+1][0] != '-') {
|
if (i+1 < argc && argv[i+1][0] != '-') {
|
||||||
decoder = (Decoder)atoi(argv[i+1]);
|
decoder = (nvtt::Decoder)atoi(argv[i+1]);
|
||||||
i++;
|
i++;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -394,10 +308,6 @@ int main(int argc, char *argv[])
|
|||||||
return 1;
|
return 1;
|
||||||
}
|
}
|
||||||
|
|
||||||
nvtt::InputOptions inputOptions;
|
|
||||||
inputOptions.setMipmapGeneration(false);
|
|
||||||
inputOptions.setAlphaMode(nvtt::AlphaMode_Transparency);
|
|
||||||
|
|
||||||
nvtt::CompressionOptions compressionOptions;
|
nvtt::CompressionOptions compressionOptions;
|
||||||
compressionOptions.setFormat(nvtt::Format_BC1);
|
compressionOptions.setFormat(nvtt::Format_BC1);
|
||||||
if (fast)
|
if (fast)
|
||||||
@ -413,7 +323,22 @@ int main(int argc, char *argv[])
|
|||||||
//compressionOptions.setExternalCompressor("d3dx");
|
//compressionOptions.setExternalCompressor("d3dx");
|
||||||
//compressionOptions.setExternalCompressor("stb");
|
//compressionOptions.setExternalCompressor("stb");
|
||||||
|
|
||||||
compressionOptions.setFormat(s_imageSets[set].format);
|
|
||||||
|
const ImageSet & set = s_imageSets[setIndex];
|
||||||
|
|
||||||
|
if (set.mode == Mode_BC1) {
|
||||||
|
compressionOptions.setFormat(nvtt::Format_BC1);
|
||||||
|
}
|
||||||
|
else if (set.mode == Mode_BC3_Alpha || set.mode == Mode_BC3_YCoCg || set.mode == Mode_BC3_RGBM) {
|
||||||
|
compressionOptions.setFormat(nvtt::Format_BC3);
|
||||||
|
}
|
||||||
|
else if (set.mode == Mode_BC3_Normal) {
|
||||||
|
compressionOptions.setFormat(nvtt::Format_BC3n);
|
||||||
|
}
|
||||||
|
else if (set.mode == Mode_BC5_Normal) {
|
||||||
|
compressionOptions.setFormat(nvtt::Format_BC5);
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
nvtt::OutputOptions outputOptions;
|
nvtt::OutputOptions outputOptions;
|
||||||
@ -429,7 +354,7 @@ int main(int argc, char *argv[])
|
|||||||
FileSystem::createDirectory(outPath);
|
FileSystem::createDirectory(outPath);
|
||||||
|
|
||||||
Path csvFileName;
|
Path csvFileName;
|
||||||
csvFileName.format("%s/result-%d.csv", outPath, set);
|
csvFileName.format("%s/result-%d.csv", outPath, setIndex);
|
||||||
StdOutputStream csvStream(csvFileName.str());
|
StdOutputStream csvStream(csvFileName.str());
|
||||||
TextWriter csvWriter(&csvStream);
|
TextWriter csvWriter(&csvStream);
|
||||||
|
|
||||||
@ -438,46 +363,85 @@ int main(int argc, char *argv[])
|
|||||||
int failedTests = 0;
|
int failedTests = 0;
|
||||||
float totalDiff = 0;
|
float totalDiff = 0;
|
||||||
|
|
||||||
const char ** fileNames = s_imageSets[set].fileNames;
|
const char ** fileNames = set.fileNames;
|
||||||
int fileCount = s_imageSets[set].fileCount;
|
int fileCount = set.fileCount;
|
||||||
|
|
||||||
Timer timer;
|
Timer timer;
|
||||||
|
|
||||||
|
nvtt::TexImage img;
|
||||||
|
if (set.mode == Mode_BC3_Alpha) {
|
||||||
|
img.setAlphaMode(nvtt::AlphaMode_Transparency);
|
||||||
|
}
|
||||||
|
if (set.mode == Mode_BC3_Normal || set.mode == Mode_BC5_Normal) {
|
||||||
|
img.setNormalMap(true);
|
||||||
|
}
|
||||||
|
|
||||||
|
printf("Processing Set: %s\n", set.name);
|
||||||
|
|
||||||
for (int i = 0; i < fileCount; i++)
|
for (int i = 0; i < fileCount; i++)
|
||||||
{
|
{
|
||||||
AutoPtr<Image> img( new Image() );
|
if (!img.load(fileNames[i]))
|
||||||
|
|
||||||
if (!img->load(fileNames[i]))
|
|
||||||
{
|
{
|
||||||
printf("Input image '%s' not found.\n", fileNames[i]);
|
printf("Input image '%s' not found.\n", fileNames[i]);
|
||||||
return EXIT_FAILURE;
|
return EXIT_FAILURE;
|
||||||
}
|
}
|
||||||
|
|
||||||
inputOptions.setTextureLayout(nvtt::TextureType_2D, img->width(), img->height());
|
if (img.isNormalMap()) {
|
||||||
inputOptions.setMipmapData(img->pixels(), img->width(), img->height());
|
img.normalizeNormalMap();
|
||||||
|
}
|
||||||
|
|
||||||
|
if (set.mode == Mode_BC3_YCoCg) {
|
||||||
|
img.toYCoCg();
|
||||||
|
img.blockScaleCoCg();
|
||||||
|
img.scaleBias(0, 0.5, 0.5);
|
||||||
|
img.scaleBias(1, 0.5, 0.5);
|
||||||
|
}
|
||||||
|
else if (set.mode == Mode_BC3_RGBM) {
|
||||||
|
img.toRGBM();
|
||||||
|
}
|
||||||
|
|
||||||
printf("Compressing: \t'%s'\n", fileNames[i]);
|
printf("Compressing: \t'%s'\n", fileNames[i]);
|
||||||
|
|
||||||
timer.start();
|
timer.start();
|
||||||
|
|
||||||
context.process(inputOptions, compressionOptions, outputOptions);
|
context.compress(img, 0, 0, compressionOptions, outputOptions);
|
||||||
|
|
||||||
timer.stop();
|
timer.stop();
|
||||||
printf(" Time: \t%.3f sec\n", timer.elapsed());
|
printf(" Time: \t%.3f sec\n", timer.elapsed());
|
||||||
totalTime += timer.elapsed();
|
totalTime += timer.elapsed();
|
||||||
|
|
||||||
AutoPtr<Image> img_out( outputHandler.decompress(s_imageSets[set].format, decoder) );
|
nvtt::TexImage img_out = outputHandler.decompress(set.mode, decoder);
|
||||||
|
if (set.mode == Mode_BC3_Alpha) {
|
||||||
|
img_out.setAlphaMode(nvtt::AlphaMode_Transparency);
|
||||||
|
}
|
||||||
|
if (set.mode == Mode_BC3_Normal || set.mode == Mode_BC5_Normal) {
|
||||||
|
img_out.setNormalMap(true);
|
||||||
|
}
|
||||||
|
|
||||||
|
if (set.mode == Mode_BC3_YCoCg) {
|
||||||
|
img_out.scaleBias(0, 1.0, -0.5);
|
||||||
|
img_out.scaleBias(1, 1.0, -0.5);
|
||||||
|
img_out.fromYCoCg();
|
||||||
|
|
||||||
|
img.scaleBias(0, 1.0, -0.5);
|
||||||
|
img.scaleBias(1, 1.0, -0.5);
|
||||||
|
img.fromYCoCg();
|
||||||
|
}
|
||||||
|
else if (set.mode == Mode_BC3_RGBM) {
|
||||||
|
img_out.fromRGBM();
|
||||||
|
img.fromRGBM();
|
||||||
|
}
|
||||||
|
|
||||||
Path outputFileName;
|
Path outputFileName;
|
||||||
outputFileName.format("%s/%s", outPath, fileNames[i]);
|
outputFileName.format("%s/%s", outPath, fileNames[i]);
|
||||||
outputFileName.stripExtension();
|
outputFileName.stripExtension();
|
||||||
outputFileName.append(".png");
|
outputFileName.append(".png");
|
||||||
if (!ImageIO::save(outputFileName.str(), img_out.ptr()))
|
if (!img_out.save(outputFileName.str()))
|
||||||
{
|
{
|
||||||
printf("Error saving file '%s'.\n", outputFileName.str());
|
printf("Error saving file '%s'.\n", outputFileName.str());
|
||||||
}
|
}
|
||||||
|
|
||||||
float rmse = rmsError(img.ptr(), img_out.ptr());
|
float rmse = nvtt::rmsError(img, img_out);
|
||||||
totalRMSE += rmse;
|
totalRMSE += rmse;
|
||||||
|
|
||||||
printf(" RMSE: \t%.4f\n", rmse);
|
printf(" RMSE: \t%.4f\n", rmse);
|
||||||
@ -492,14 +456,14 @@ int main(int argc, char *argv[])
|
|||||||
regressFileName.stripExtension();
|
regressFileName.stripExtension();
|
||||||
regressFileName.append(".png");
|
regressFileName.append(".png");
|
||||||
|
|
||||||
AutoPtr<Image> img_reg( new Image() );
|
nvtt::TexImage img_reg;
|
||||||
if (!img_reg->load(regressFileName.str()))
|
if (!img_reg.load(regressFileName.str()))
|
||||||
{
|
{
|
||||||
printf("Regression image '%s' not found.\n", regressFileName.str());
|
printf("Regression image '%s' not found.\n", regressFileName.str());
|
||||||
return EXIT_FAILURE;
|
return EXIT_FAILURE;
|
||||||
}
|
}
|
||||||
|
|
||||||
float rmse_reg = rmsError(img.ptr(), img_reg.ptr());
|
float rmse_reg = rmsError(img, img_reg);
|
||||||
|
|
||||||
float diff = rmse_reg - rmse;
|
float diff = rmse_reg - rmse;
|
||||||
totalDiff += diff;
|
totalDiff += diff;
|
||||||
|
Reference in New Issue
Block a user