Beispiel #1
0
	bool WicFile::Read(RasterImage &imgDst, unsigned int frameNo)
	{
		::IWICBitmapFrameDecode *frame(nullptr);
		::IWICFormatConverter *format_converter(nullptr);
		try
		{
			// Get a frame.
			if (FAILED(decoder->GetFrame(frameNo, &frame)))
				throw std::runtime_error("Failed to get a frame.");

			// Create a format converter,
			// and convert the source image frame to 32bit BGRA regardless of original format.
			if (FAILED(this->factory->CreateFormatConverter(&format_converter)))
				throw std::runtime_error("Failed to create a format converter.");
			if (FAILED(format_converter->Initialize(frame, ::GUID_WICPixelFormat32bppPBGRA, ::WICBitmapDitherTypeNone,
				nullptr, 0.0, ::WICBitmapPaletteTypeCustom)))
				throw std::runtime_error("Failed to convert the source image frame.");

			// Copy image data to the destination.
			// Set the size with unsigned int instead of ::size_t because ::size_t (== unsigned long)
			// can be wider than unsigned int.
			unsigned int w, h;
			if (FAILED(format_converter->GetSize(&w, &h)))
				throw std::runtime_error("Failed to get the size of the source image frame.");
			unsigned int sz = w * h * 4;
			imgDst.Resize(1, 4, w, h);
			if (FAILED(format_converter->CopyPixels(nullptr, w * 4, sz, imgDst.data.data())))
				throw std::runtime_error("Failed to copy pixels from the source image frame.");
		}
		catch (const std::exception &ex)
		{
			SafeRelease(format_converter);
			SafeRelease(frame);
			throw ex;	// Re-throw the exception.
		}

		SafeRelease(format_converter);
		SafeRelease(frame);

		return true;	// redundant response to maintain the class protocol.
	}