每个样本的位/像素 libtiff 与 WIC
BIts Per Sample / Pixel libtiff vs WIC
TIFF *TiffImage;
uint16 photo, bps, spp, fillorder;
uint32 width,height;
unsigned long stripSize;
unsigned long imageOffset, result;
int stripMax, stripCount;
unsigned char *buffer, tempbyte;
unsigned short *buffer16;
unsigned int *buffer32;
unsigned long bufferSize, count;
bool success = true;
int shiftCount = 0;
//read image to InData
const char *InFileName = fileName.c_str();
if((TiffImage = TIFFOpen(InFileName, "r")) == NULL){
ErrMsg("Could not open incoming image\n");
return false;
}
// Check that it is of a type that we support
if(TIFFGetField(TiffImage, TIFFTAG_BITSPERSAMPLE, &bps) == 0) {
ErrMsg("Either undefined or unsupported number of bits per sample\n");
return false;
}
TBitPrecision bitPrecision = (TBitPrecision)bps;
char* imageDesc = NULL;
TIFFGetField(TiffImage, TIFFTAG_IMAGEDESCRIPTION, &imageDesc);
// Get actual bit precision for CP Images
if (bps > 8 && bps <= 16)
{
if (GetCpTiffTag(imageDesc, CP_TIFFTAG_BITPRECISION, (uint32*)&bitPrecision) == true)
{
shiftCount = 16 - bitPrecision;
}
}
在我的 libtiff 实现中,我使用了每像素图像 12 位和 10 bpp
在 libtiff
中设置此信息非常容易
我在 WIC 中找不到类似的方法
uint16_t photo, bps, spp, fillorder;
uint32_t width,height;
unsigned long stripSize;
unsigned long imageOffset, result;
int stripMax, stripCount;
unsigned char *buffer, tempbyte;
unsigned short *buffer16;
unsigned int *buffer32;
unsigned long bufferSize, count;
bool success = true;
int shiftCount = 0;
//read image to InData
const char *InFileName = fileName.c_str();
IWICImagingFactory* piFactory = NULL;
// Create WIC factory
HRESULT hr = CoCreateInstance(
CLSID_WICImagingFactory,
NULL,
CLSCTX_INPROC_SERVER,
IID_PPV_ARGS(&piFactory)
);
// Create a decoder
IWICBitmapDecoder *pIDecoder = NULL;
IWICBitmapFrameDecode *pIDecoderFrame = NULL;
std::wstring ws;
ws.assign(fileName.begin(), fileName.end());
// get temporary LPCWSTR (pretty safe)
LPCWSTR pcwstr = ws.c_str();
hr = piFactory->CreateDecoderFromFilename(
pcwstr, // Image to be decoded
NULL, // Do not prefer a particular vendor
GENERIC_READ, // Desired read access to the file
WICDecodeMetadataCacheOnDemand, // Cache metadata when needed
&pIDecoder // Pointer to the decoder
);
// Retrieve the first bitmap frame.
if (SUCCEEDED(hr))
{
hr = pIDecoder->GetFrame(0, &pIDecoderFrame);
}
else
{
ErrMsg("Could not open incoming image\n");
}
return true;
我应该使用 EXIF 还是 XMP?我如何找到 WIC 的 TIFFTAG?
DirectXTex 库有很多从 C++ 使用 WIC 的例子。
你需要这样的东西:
using Microsoft::WRL::ComPtr;
ComPtr<IWICMetadataQueryReader> metareader;
hr = pIDecoderFrame->GetMetadataQueryReader(metareader.GetAddressOf());
if (SUCCEEDED(hr))
{
PROPVARIANT value;
PropVariantInit(&value);
if (SUCCEEDED(metareader->GetMetadataByName(L"/ifd/{ushort=258}", &value))
&& value.vt == VT_UI2)
{
// BitsPerSample is in value.uiVal
}
PropVariantClear(&value);
}
You should get in the habit of using a smart-pointer like ComPtr rather than using raw interface pointers to keep the ref counts correct.
TIFF *TiffImage;
uint16 photo, bps, spp, fillorder;
uint32 width,height;
unsigned long stripSize;
unsigned long imageOffset, result;
int stripMax, stripCount;
unsigned char *buffer, tempbyte;
unsigned short *buffer16;
unsigned int *buffer32;
unsigned long bufferSize, count;
bool success = true;
int shiftCount = 0;
//read image to InData
const char *InFileName = fileName.c_str();
if((TiffImage = TIFFOpen(InFileName, "r")) == NULL){
ErrMsg("Could not open incoming image\n");
return false;
}
// Check that it is of a type that we support
if(TIFFGetField(TiffImage, TIFFTAG_BITSPERSAMPLE, &bps) == 0) {
ErrMsg("Either undefined or unsupported number of bits per sample\n");
return false;
}
TBitPrecision bitPrecision = (TBitPrecision)bps;
char* imageDesc = NULL;
TIFFGetField(TiffImage, TIFFTAG_IMAGEDESCRIPTION, &imageDesc);
// Get actual bit precision for CP Images
if (bps > 8 && bps <= 16)
{
if (GetCpTiffTag(imageDesc, CP_TIFFTAG_BITPRECISION, (uint32*)&bitPrecision) == true)
{
shiftCount = 16 - bitPrecision;
}
}
在我的 libtiff 实现中,我使用了每像素图像 12 位和 10 bpp 在 libtiff
中设置此信息非常容易我在 WIC 中找不到类似的方法
uint16_t photo, bps, spp, fillorder;
uint32_t width,height;
unsigned long stripSize;
unsigned long imageOffset, result;
int stripMax, stripCount;
unsigned char *buffer, tempbyte;
unsigned short *buffer16;
unsigned int *buffer32;
unsigned long bufferSize, count;
bool success = true;
int shiftCount = 0;
//read image to InData
const char *InFileName = fileName.c_str();
IWICImagingFactory* piFactory = NULL;
// Create WIC factory
HRESULT hr = CoCreateInstance(
CLSID_WICImagingFactory,
NULL,
CLSCTX_INPROC_SERVER,
IID_PPV_ARGS(&piFactory)
);
// Create a decoder
IWICBitmapDecoder *pIDecoder = NULL;
IWICBitmapFrameDecode *pIDecoderFrame = NULL;
std::wstring ws;
ws.assign(fileName.begin(), fileName.end());
// get temporary LPCWSTR (pretty safe)
LPCWSTR pcwstr = ws.c_str();
hr = piFactory->CreateDecoderFromFilename(
pcwstr, // Image to be decoded
NULL, // Do not prefer a particular vendor
GENERIC_READ, // Desired read access to the file
WICDecodeMetadataCacheOnDemand, // Cache metadata when needed
&pIDecoder // Pointer to the decoder
);
// Retrieve the first bitmap frame.
if (SUCCEEDED(hr))
{
hr = pIDecoder->GetFrame(0, &pIDecoderFrame);
}
else
{
ErrMsg("Could not open incoming image\n");
}
return true;
我应该使用 EXIF 还是 XMP?我如何找到 WIC 的 TIFFTAG?
DirectXTex 库有很多从 C++ 使用 WIC 的例子。
你需要这样的东西:
using Microsoft::WRL::ComPtr;
ComPtr<IWICMetadataQueryReader> metareader;
hr = pIDecoderFrame->GetMetadataQueryReader(metareader.GetAddressOf());
if (SUCCEEDED(hr))
{
PROPVARIANT value;
PropVariantInit(&value);
if (SUCCEEDED(metareader->GetMetadataByName(L"/ifd/{ushort=258}", &value))
&& value.vt == VT_UI2)
{
// BitsPerSample is in value.uiVal
}
PropVariantClear(&value);
}
You should get in the habit of using a smart-pointer like ComPtr rather than using raw interface pointers to keep the ref counts correct.