diff --git a/QuickView/ImageLoader.cpp b/QuickView/ImageLoader.cpp index 4daa3e9..30a0a51 100644 --- a/QuickView/ImageLoader.cpp +++ b/QuickView/ImageLoader.cpp @@ -5,17 +5,6 @@ #include #include -// Helper -static std::vector ReadFileToVector(const std::wstring& path) { - std::ifstream file(path, std::ios::binary | std::ios::ate); - if (!file) return {}; - size_t size = file.tellg(); - file.seekg(0, std::ios::beg); - std::vector buffer(size); - if (file.read((char*)buffer.data(), size)) return buffer; - return {}; -} - #include "ImageLoader.h" #include "MemoryArena.h" // [Fix] Include for QuantumArena definition @@ -6282,51 +6271,39 @@ HRESULT CImageLoader::LoadPCX(LPCWSTR filePath, IWICBitmap** ppBitmap) { #include #pragma comment(lib, "propsys.lib") -static HRESULT GetMetadataString(IWICMetadataQueryReader* reader, LPCWSTR query, std::wstring& out) { - if (!reader) return E_INVALIDARG; - PROPVARIANT val; PropVariantInit(&val); - HRESULT hr = reader->GetMetadataByName(query, &val); - if (SUCCEEDED(hr)) { - WCHAR buf[512] = {}; - if (SUCCEEDED(PropVariantToString(val, buf, 512))) { - out = buf; - } - PropVariantClear(&val); +template +static double DecodeRationalT(unsigned __int64 val) { + if constexpr (IsSigned) { + int32_t num = (int32_t)(val & 0xFFFFFFFF); + int32_t den = (int32_t)(val >> 32); + if (den == 0) return 0.0; + return (double)num / (double)den; + } else { + uint32_t num = (uint32_t)(val & 0xFFFFFFFF); + uint32_t den = (uint32_t)(val >> 32); + if (den == 0) return 0.0; + return (double)num / (double)den; } - return hr; -} - -static double DecodeRational(unsigned __int64 val) { - uint32_t num = (uint32_t)(val & 0xFFFFFFFF); - uint32_t den = (uint32_t)(val >> 32); - if (den == 0) return 0.0; - return (double)num / (double)den; -} - -static double DecodeSignedRational(unsigned __int64 val) { - // EXIF SRATIONAL: Low 32 bits = signed numerator, High 32 bits = signed denominator - int32_t num = (int32_t)(val & 0xFFFFFFFF); - int32_t den = (int32_t)(val >> 32); - if (den == 0) return 0.0; - return (double)num / (double)den; } -static HRESULT GetMetadataSignedRational(IWICMetadataQueryReader* reader, LPCWSTR query, double* out) { +template +static HRESULT GetMetadataRationalT(IWICMetadataQueryReader* reader, LPCWSTR query, double* out) { if (!reader || !out) return E_INVALIDARG; PROPVARIANT val; PropVariantInit(&val); HRESULT hr = reader->GetMetadataByName(query, &val); if (SUCCEEDED(hr)) { if (val.vt == VT_UI8) { - *out = DecodeSignedRational(val.uhVal.QuadPart); + *out = DecodeRationalT(val.uhVal.QuadPart); } else if (val.vt == VT_I8) { - *out = DecodeSignedRational((unsigned __int64)val.hVal.QuadPart); + *out = DecodeRationalT((unsigned __int64)val.hVal.QuadPart); } else if (val.vt == VT_I4) { - *out = (double)val.lVal; // Already a ratio? + *out = (double)val.lVal; } else if (val.vt == VT_R8) { *out = val.dblVal; + } else if constexpr (!IsSigned) { + PropVariantToDouble(val, out); } else { - // Fallback: Try standard conversion but it may fail for RATIONAL - hr = E_FAIL; // Skip if unknown type + hr = E_FAIL; } PropVariantClear(&val); } @@ -6334,18 +6311,11 @@ static HRESULT GetMetadataSignedRational(IWICMetadataQueryReader* reader, LPCWST } static HRESULT GetMetadataRational(IWICMetadataQueryReader* reader, LPCWSTR query, double* out) { - if (!reader || !out) return E_INVALIDARG; - PROPVARIANT val; PropVariantInit(&val); - HRESULT hr = reader->GetMetadataByName(query, &val); - if (SUCCEEDED(hr)) { - if (val.vt == VT_UI8) { - *out = DecodeRational(val.uhVal.QuadPart); - } else { - PropVariantToDouble(val, out); - } - PropVariantClear(&val); - } - return hr; + return GetMetadataRationalT(reader, query, out); +} + +static HRESULT GetMetadataSignedRational(IWICMetadataQueryReader* reader, LPCWSTR query, double* out) { + return GetMetadataRationalT(reader, query, out); } @@ -6370,9 +6340,9 @@ static HRESULT GetMetadataGPS(IWICMetadataQueryReader* reader, LPCWSTR coordQuer if (varCoord.vt == (VT_UI8 | VT_VECTOR)) { if (varCoord.cauh.cElems == 3) { - double deg = DecodeRational(varCoord.cauh.pElems[0].QuadPart); - double min = DecodeRational(varCoord.cauh.pElems[1].QuadPart); - double sec = DecodeRational(varCoord.cauh.pElems[2].QuadPart); + double deg = DecodeRationalT(varCoord.cauh.pElems[0].QuadPart); + double min = DecodeRationalT(varCoord.cauh.pElems[1].QuadPart); + double sec = DecodeRationalT(varCoord.cauh.pElems[2].QuadPart); result = deg + min/60.0 + sec/3600.0; } } @@ -6730,26 +6700,6 @@ static void PopulateExifFromQueryReader(IWICMetadataQueryReader* reader, CImageL } } -// [v5.3] Extract Metadata from Memory (Zero-IO) -static void ExtractExifFromMemory(IWICImagingFactory* factory, const uint8_t* data, size_t size, CImageLoader::ImageMetadata* meta) { - if (!factory || !data || !size || !meta) return; - - ComPtr stream; - if (FAILED(factory->CreateStream(&stream))) return; - if (FAILED(stream->InitializeFromMemory(const_cast(data), static_cast(size)))) return; - - ComPtr decoder; - if (FAILED(factory->CreateDecoderFromStream(stream.Get(), NULL, WICDecodeMetadataCacheOnDemand, &decoder))) return; - - ComPtr frame; - if (FAILED(decoder->GetFrame(0, &frame))) return; - - ComPtr reader; - if (FAILED(frame->GetMetadataQueryReader(&reader))) return; - - PopulateExifFromQueryReader(reader.Get(), meta); -} - // [v5.3] File Stats static void PopulateFileStats(LPCWSTR filePath, CImageLoader::ImageMetadata* meta) { if (!filePath || !meta) return;