What is 32 bit windows imaging component

Windows Imaging Component Overview

The Windows Imaging Component (WIC) provides an extensible framework for working with images and image metadata. WIC makes it possible for independent software vendors (ISVs) and independent hardware vendors (IHVs) to develop their own image codecs and get the same platform support as standard image formats (for example, TIFF, JPEG, PNG, GIF, BMP, and HDPhoto). A single, consistent set of interfaces is used for all image processing, regardless of image format, so any application using the WIC gets automatic support for new image formats as soon as the codec is installed. The extensible metadata framework makes it possible for applications to read and write their own proprietary metadata directly to image files, so the metadata never gets lost or separated from the image.

This topic includes the following sections.

Windows Imaging Component Features

The primary features of WIC are:

  • Enables application developers to perform image processing operations on any image format through a single, consistent set of common interfaces, without requiring prior knowledge of specific image formats.
  • Provides an extensible «plug and play» architecture for image codecs, pixel formats, and metadata, with automatic run-time discovery of new formats.
  • Supports reading and writing of arbitrary metadata in image files, with the ability to preserve unrecognized metadata during editing.
  • Preserves high bit depth image data, up to 32 bits per channel, throughout the image processing pipeline.
  • Provides built-in support for most popular image formats, pixel formats, and metadata schemas.

Native Codecs

WIC includes several built-in codecs. The following standard codecs are provided with the platform.

How the Windows Imaging Component Works

This topic contains the following sections:

Discovery and Arbitration

Before an image can be decoded, an appropriate codec must be found that can decode that image format. In most systems, because the supported image formats are hard-coded, no discovery process is required. Because the Windows Imaging Component (WIC) platform is extensible, it’s necessary to be able to identify the format of an image and match it with an appropriate codec.

To support run-time discovery, each image format must have an identifying pattern that can be used to identify the appropriate decoder for that format. (It is strongly recommended that, for new file formats, you use a GUID for the identifying pattern, because it is guaranteed to be unique.) The identifying pattern must be embedded in each image file that conforms to that image format. Each decoder has a registry entry that specifies the identifying pattern or patterns of the image formats it can decode. When an application needs to open an image, it requests a decoder from WIC. WIC looks up the available decoders in the registry, and checks each registry entry for an identifying pattern that matches the pattern embedded in the image file. For more information on decoder registry entries, see Encoder-Specific Registry Entries

When WIC finds a single decoder that matches the identifying pattern in the image, it creates an instance of the decoder and passes the image file to it. If WIC finds more than one match, it invokes a method called QueryCapability on each matching decoder to arbitrate among them and find the best match. For more information, see the QueryCapabilities section in the Implementing IWICBitmapDecoder.

Decoding

After the appropriate decoder has been selected and instantiated, the application talks directly to the decoder. The decoder has several responsibilities, which it implements through various interfaces. These services can be classified as:

  • Container-level services
  • Frame-level services
  • Metadata enumeration services
  • Native decoder transforms
  • Progress notifications and cancellation support
  • Raw processing services

Container-level services include retrieving the top-level thumbnail (if supported), preview, color contexts, palette (if applicable), and container format, as well as providing access to the individual image frames within the container. (Some containers contain only a single frame while others, such as Tagged Image File Format (TIFF), can contain multiple frames.) This set of services also includes providing information about the decoder itself, and its capabilities with respect to a specific image file.

Individual frames have their own thumbnails, and may also have their own color contexts, palettes, and other properties, which are exposed at the frame level. The most important operation performed at the frame level, though, is the actual decoding of the image bits for that frame.

WIC provides metadata readers for the most common metadata formats (IFD, EXIF, IPTC, XMP, APP0, APP1, and other formats), and also supports extensibility for third-party metadata formats. This frees the codec of the responsibility for parsing metadata. However, the codec is responsible for enumerating the metadata blocks and requesting a metadata reader for each block. WIC performs discovery for metadata handlers the same way it does for codecs, based on a pattern in the block header matching a pattern in the metadata handler’s registry entry. For more information, see the Encoder-Specific Registry Entries

Decoders are not required to natively support transform operations, but doing so enables significant performance optimizations that provide a better end-user experience. For example, an application can create a pipeline of various transforms (scaling, cropping, rotation, and pixel format conversion) to perform on an image before the image is rendered. For more information on transform pipelines, see IWICBitmapSource. After creating a transform pipeline, the application requests the final transform in the pipeline to produce the bitmap that results from applying all the transforms to the image source. At that point, if the decoder itself is able to perform transform operations, WIC asks which of the requested transforms it can perform. Any requested transforms the decoder cannot perform will be performed by WIC on the decoded image before returning it to the caller. This optimized transform pipeline provides better performance than performing each transform sequentially in memory, particularly when some or all of the transforms can be accomplished during the decoding process.

Progress notifications and cancellation support enable an application to request progress notifications for lengthy operations, and also enable the application to give the user an opportunity to cancel an operation that is taking too long. This is important because if a user cannot cancel an operation, he or she may feel the process has hung, and try to cancel it by closing the application.

These interfaces are described in detail in the section on Implementing a WIC-Enabled Decoder.

Raw processing services include adjusting camera settings, such as exposure, contrast, and sharpening, or changing the color space before processing the raw bits.

Encoding

Like decoders, encoders have responsibilities that they implement through interfaces. The services that encoders provide are complementary to the services provided by decoders, except they write out image data rather than reading it. Encoders also provide services in the following categories:

  • Container-level services
  • Frame-level services
  • Metadata enumeration and update services
  • Progress notification and cancellation support
Читайте также:  Windows 10 планировщик заданий не может создать задание

Container-level services for an encoder include setting the top-level thumbnail (if supported), preview, and palette (if applicable), and iterating through the individual image frames so they can be serialized into the container.

Frame-level services for an encoder mirror those for the decoder, except that they write out the image data, thumbnail, and any associated palette or other component, rather than reading them.

Also, metadata enumeration services for an encoder include iterating through the metadata blocks to be written, and invoking the appropriate metadata writers to serialize the metadata to disk.

These interfaces are described in detail in the section on Implementing a WIC-Enabled Encoder.

The Lifetime of a Codec

A WIC codec is instantiated to handle a single image, and usually has a short lifetime. It’s created when an image is loaded and is released when the image is closed. An application may use a large number of codecs simultaneously with overlapping lifetimes (think of scrolling through a directory containing hundreds of images), and multiple applications may be doing this at the same time.

Although some codecs have a lifetime that is scoped to the lifetime of the process in which they live, this is not the case with WIC codecs. The WindowsВ Vista Photo Gallery, Windows Explorer, and Photo Viewer, as well as numerous other applications, are built on WIC and will be using your codec to display images and thumbnails. If the lifetime of your codec were scoped to the lifetime of the process, every time an image or thumbnail was displayed in the WindowsВ Vista Explorer, the codec instantiated to decode that image would remain in memory until the next time the user restarted his or her computer. If your codec is never unloaded, its resources are, in effect, «leaked» because they can’t be used by any other component in the system.

How to WIC-enabled a Codec

  1. Implement a container-level decoder class and a frame-level decoder class that exposes the required WIC interfaces for decoding images and iterating through blocks of metadata. This enables all WIC-based applications to interact with your codec the same way they interact with standard image formats.
  2. Implement a container-level encoder class and a frame-level encoder class that exposes the required WIC interfaces for encoding images and serializing blocks of metadata into an image file.
  3. If your container format is not based on a TIFF or JPEG container, you may need to write metadata handlers for the common metadata formats (EXIF, XMP). However, if you use a TIFF-based or JPEG-based container format, this is not necessary because you can delegate to the system-provided metadata handlers.
  4. Embed a unique identifying pattern (we recommend a GUID) in all your image files. This enables your image format to be matched against your codec during the discovery. If you are writing a WIC wrapper for an existing image format, you must find a pattern of bits that the encoder always writes into its image files that’s unique to that image format, and use this as the identifying pattern.)
  5. Register your codec at installation time. This enables your codec to be discovered at run time by matching the identifying pattern in the registry with the pattern embedded in the image file.
  6. As of WindowsВ 7, WIC requires that codecs be of COM apartment type «Both». This means that you must do the appropriate locking to handle cross-apartment callers and callers in multi-threaded scenarios. For more information, see the next section on multi-threaded apartment support.
  7. Support for 64-bit platforms: For WindowsВ 7, WIC will require that third-party WIC codecs be delivered as both 32-bit and 64-bit native binaries. Further, the 32-bit form must install and run on 64-bit systems, and the third party WindowsВ 7 codec installer must install both the 32-bit and 64-bit binaries on 64-bit systems.

Multi-Threaded Apartment Support in WIC

Objects within a Multi-Threaded Apartment (MTA) may be called concurrently by any number of threads within the MTA. This allows for better performance on multi-core systems and certain server scenarios. In addition, WIC codecs in an MTA can call other objects in the MTA without the marshalling cost associated with calling between threads in different STA apartments. In WindowsВ 7, all in-box WIC codecs have been updated to support MTAs, including JPEG, TIFF, PNG, GIF, ICO, and BMP. It is highly recommended that third-party codecs be written to support MTAs. Third-party codecs that do not to support MTAs cause significant performance costs in multi-threaded applications because of marshaling. Enabling MTA support requires proper synchronization to be implemented in the third-party codec. Exact implementation of these synchronization techniques is beyond the scope of this paper. For more information on synchronizing COM objects, see Understanding and Using COM Threading Models.

What is 32 bit windows imaging component

Windows Imaging Component Basics

Contents

Getting Started
Decoding Images
Encoding Images
The WIC Imaging Factory
Working with Streams
WIC via WPF
What’s Next?

The MicrosoftВ® WindowsВ® Imaging Component (WIC) is an extensible framework for encoding, decoding, and manipulating images. Originally designed for Windows VistaВ® and Windows Presentation Foundation (WPF), today WIC not only ships with Windows Vista and the Microsoft .NET Framework 3.0 and later, but it is also available as a download for Windows XP and Windows ServerВ® 2003 for use in native applications.

One of several powerful native frameworks that power WPF, WIC in this context is the framework used in the implementation of the System.Windows.Media.Imaging namespace. It is, however, also ideally suited for native applications written in C++ because it provides a simple-yet-powerful API exposed through a set of COM interfaces.

WIC supports different image formats using an extensible set of imaging codecs. Each codec supports a different image format and typically provides both an encoder and decoder. WIC includes a set of built-in codecs for virtually all of the major image formats including PNG, JPEG, GIF, TIFF, HD Photo (HDP), ICO, and of course the Windows BMP.

HDP is the only format you may not have heard about. It was originally called Windows Media Photo and was developed in conjunction with Windows Vista to overcome some of the limitations with existing formats and provide better performance and higher image quality. For more information on HDP, check out the specification at microsoft.com/whdc/xps/wmphoto.mspx. Fortunately, WIC provides great support for this new image format, so applications don’t have to know the specifics of the formats to use them.

This month I’ll show you how to use WIC to encode and decode different image formats and a few things in between. Next time I’ll explore some of the more advanced features and show you how to extend WIC with your own imaging codecs.

The WIC API consists of COM interfaces, functions, structures, and error codes, as well as GUIDs identifying various codecs, containers, and formats. All of the declarations you will need are included in the wincodec.h and wincodecsdk.h header files that are provided as part of the Windows SDK (and included with Visual StudioВ® 2008). It will also be necessary for you to link to the WindowsCodecs.lib library, which provides the various definitions you may need. You can add the following to your project’s precompiled header to make it all available:

Читайте также:  Linux приставка для телевизора

Since the WIC API consists primarily of COM interfaces, I use the Active Template Library (ATL) CComPtr class to handle the creation and management of the interface pointers. If you would like to do the same, you’ll need to also include the atlbase.h header file that defines the CComPtr template class:

The WIC API also uses the COM library, so the CoInitializeEx function must be called on any thread that will use the API.

Finally, the WIC API makes use of HRESULTs to describe errors. The samples in this article use the HR macro to clearly identify where methods return an HRESULT that needs to be checked. You can replace this with your own error-handling strategy—whether that is throwing an exception or returning the HRESULT yourself.

Decoders are represented by the IWICBitmapDecoder interface. WIC provides a few ways to create a decoder object, but at a minimum you can simply use a particular decoder’s CLSID to create an instance. The following example creates a decoder for a TIFF image:

Figure 1 lists the codecs included with WIC and the CLSIDs you can use to create the different decoders. Once the decoder is created, it needs to be initialized with a stream containing the pixels and optional metadata in a format understood by the decoder:

FigureВ 1В CLSIDs for Built-In WIC Codecs

Format Decoder Encoder
BMP CLSID_WICBmpDecoder CLSID_WICBmpEncoder
PNG CLSID_WICPngDecoder CLSID_WICPngEncoder
ICO CLSID_WICIcoDecoder Not available
JPEG CLSID_WICJpegDecoder CLSID_WICJpegEncoder
GIF CLSID_WICGifDecoder CLSID_WICGifEncoder
TIFF CLSID_WICTiffDecoder CLSID_WICTiffEncoder
HDP CLSID_WICWmpDecoder CLSID_WICWmpEncoder

I’ll discuss streams later in this article, but IStream is just the traditional COM stream interface used by many APIs including the XmlLite parser I covered in the April 2007 issue of MSDNВ® Magazine (msdn.microsoft.com/msdnmag/issues/07/04/Xml).

The second parameter to the Initialize method describes how you would like the decoder to read the image information from the stream. WICDecodeMetadataCacheOnDemand indicates that the decoder should only read the image information from the stream as it is needed. This can be particularly useful if the image format happens to contain or support multiple frames. The alternative is WICDecodeMetadataCacheOnLoad, which indicates that the decoder should cache all image information immediately. All subsequent requests to the decoder would then be fulfilled directly from memory. This has some further implications for managed code that I’ll talk about later.

With the decoder initialized, you can freely query the decoder for information. The most common thing you’re likely to ask for is the set of frames that make up an image. The frames are the actual bitmaps that contain pixels. You can think of the image format as a container for frames. As I’ve mentioned, some image formats support multiple frames.

The GetFrameCount function is used to determine the number of frames in the image:

Given the number of frames, individual frames can be retrieved using the GetFrame method:

The IWICBitmapFrameDecode interface returned by GetFrame derives from the IWICBitmapSource interface that represents a read-only bitmap. IWICBitmapFrameDecode provides information associated with the frame such as metadata and color profiles. IWICBitmapSource provides the bitmap’s size and resolution, pixel format, and other optional characteristics such as its color table. IWICBitmapSource also provides the CopyPixels method that can be used to actually read pixels from the bitmap.

You can get the dimensions of the frame expressed in pixels using the GetSize method:

And you can get the resolution of the frame expressed in dots per inch (dpi) using the GetResolution method:

Although the resolution has no impact on the pixels themselves, it does affect how the image can be displayed when using a logical coordinate system such as that used by WPF.

The last critical attribute of the frame is the pixel format. The pixel format describes the layout of pixels in memory and also implies the range of colors or color space that it supports. The GetPixelFormat method returns the pixel format:

The pixel formats are defined as GUIDs whose names pretty clearly describe the memory layout. For example, the GUID_WICPixelFormat24bppRGB format indicates that each pixel uses 24 bits (3 bytes) of storage with 1 byte per color channel. In addition, the ordering of the red (R), green (G), and blue (B) letters indicates the order of the bytes from least significant to most significant. As an example, the GUID_WICPixelFormat32bppBGRA format indicates that each pixel uses 32 bits (4 bytes) of storage with 1 byte per color channel as well as 1 byte for the alpha channel. In this case, the channels are ordered with the blue (B) channel being least significant and the alpha (A) channel being the most.

The actual pixels can be retrieved using the CopyPixels method.

The rect parameter specifies a rectangle within the bitmap to copy. You can set this parameter to zero and it will copy the entire bitmap. I’ll talk about the stride in a moment. The buffer and bufferSize parameters indicate where the pixels will be written and how much space is available.

The stride can be one of the more confusing aspects of bitmaps. Stride is the count of bytes between scanlines. Generally speaking, the bits that make up the pixels of a bitmap are packed into rows. A single row should be long enough to store one row of the bitmap’s pixels. The stride is the length of a row measured in bytes, rounded up to the nearest DWORD (4 bytes). This allows bitmaps with fewer than 32 bits per pixel (bpp) to consume less memory while still providing good performance. You can use the following function to calculate the stride for a given bitmap:

With that out of the way, you can call the CopyPixels method as follows, assuming the frame represents a 32 bpp bitmap:

My example uses the ATL CAtlArray collection class to allocate the buffer, but you can obviously use whatever storage you like. To handle larger bitmaps more efficiently, you can call CopyPixels a number of times to read different portions of the bitmap.

Encoders are represented by the IWICBitmapEncoder interface. As with decoders, WIC provides a few ways to create encoders, but at a minimum you can simply use a particular encoder’s CLSID to create it. This code, for example, creates an encoder for a PNG image:

Figure 1 lists the CLSIDs you can use to create the different encoders included with WIC. After the encoder is created, it needs to be initialized with a stream that will ultimately receive the encoded pixels and optional metadata:

The second parameter to the Initialize method is less interesting, as WICBitmapEncoderNoCache is the only flag now supported.

With the encoder initialized, you can now start adding frames. The CreateNewFrame method creates a new frame that you can then configure and write pixels to:

CreateNewFrame returns both an IWICBitmapFrameEncode interface representing the new frame as well as an IPropertyBag2 interface. The latter is optional and can be used to specify any encoder-specific properties such as the image quality for JPEG or the compression algorithm for TIFF. For example, here’s how you can set the image quality for a JPEG image:

The value for image quality must fall between 0.0 for the lowest possible quality and 1.0 for highest possible quality.

With the encoder properties set, you need to call the Initialize method before configuring and writing to the frame:

The next step is to set the dimensions and pixel format for the new frame before you can write pixels to it:

The SetPixelFormat parameter is an [in, out] parameter. On input it specifies the desired pixel format. On output it contains the closest supported pixel format. This usually isn’t a problem unless the format is set at run time, perhaps based on the pixel format of another bitmap.

Writing pixels to the frame is achieved using the WritePixels method, as shown here:

The lineCount parameter specifies how many lines of pixels are to be written. This implies that you can call WritePixels a number of times to write the complete frame. The stride parameter indicates how the pixels in the buffer are packed into rows. I described how you can calculate the stride in the previous section.

After you’ve called WritePixels one or more times to write the complete frame, you need to tell the encoder that the frame is ready by calling the frame’s Commit method. And once you’ve committed all the frames that make up the image, you need to tell the encoder that the image is ready to be saved by calling the encoder’s Commit method.

So far I’ve covered the basics of encoding and decoding images. Before I move on, I want to drive it home with a simple example. Figure 2 shows a CopyIconToTiff function that demonstrates how to read the individual bitmaps that make up an icon and copy them to a multiframe TIFF image.

FigureВ 2В CopyIconToTiff

In this example, I’ve simplified things further by taking advantage of an alternative to the WritePixels method. Instead of first copying the pixels from the source frame and then writing them to the target frame, I’m using the WriteSource method that reads the pixels directly from a given IWICBitmapSource interface. Since the IWICBitmapFrameDecode interface derives from IWICBitmapSource, this provides an elegant solution.

The WIC Imaging Factory

WIC provides an imaging factory for creating various WIC-related objects. It is exposed through the IWICImagingFactory interface and can be created as follows:

I’ve already shown how you can create a decoder for a specific image format given a CLSID identifying an implementation. Of course, as you probably can tell, it would be much more useful if you didn’t have to specify a particular implementation or even hardcode the format of the image.

Fortunately, WIC provides the solution. Before creating a decoder, WIC can examine a given stream for patterns that might identify the image format. Once a best match is found, it will create the appropriate decoder and initialize it with the same stream. This functionality is provided by the CreateDecoderFromStream method:

The second parameter identifies the vendor of the decoder. It is optional but may be useful if you prefer a particular vendor’s codec. Keep in mind that it is only a hint, and if the particular vendor does not have a suitable decoder installed, then a decoder will still be chosen regardless of vendor.

IWICImagingFactory also provides the CreateDecoderFromFilename and CreateDecoderFromFileHandle methods that provide the same functionality given a path to a file and a file handle, respectively. Alternatively, you can create a decoder without specifying a CLSID or a stream but instead indicating the image format. The CreateDecoder method does just that:

Similarly, the CreateEncoder method allows you to create an encoder for a particular image format without regard for its implementation, like so:

Figure 3 lists the GUIDs identifying the implementation-independent image formats, also known as container formats.

FigureВ 3В Container Format GUIDs

Format GUID
BMP GUID_ContainerFormatBmp
PNG GUID_ContainerFormatPng
ICO GUID_ContainerFormatIco
JPEG GUID_ContainerFormatJpeg
GIF GUID_ContainerFormatGif
TIFF GUID_ContainerFormatTiff
HDP GUID_ContainerFormatWmp

Working with Streams

You are free to provide any valid IStream implementation for use with WIC. You can, for example, use the CreateStreamOnHGlobal or SHCreateStreamOnFile functions that I described in my XmlLite article, or even write your own implementation. WIC also provides a flexible IStream implementation that may come in handy.

Using the imaging factory I introduced in the previous section, you can create an uninitialized stream object as follows:

The IWICStream interface inherits from IStream and provides a few methods for associating the stream with different backing storage. For example, you can use InitializeFromFilename to create a stream backed by a particular file:

You can also use InitializeFromIStreamRegion to create a stream as a subset of another stream or use InitializeFromMemory to create a stream over a block of memory.

As I’ve mentioned, WIC provides the framework on which the WPF imaging functionality is based. The various imaging classes are defined in the System.Windows.Media.Imaging namespace. To show you just how easy it is to use from managed code, Figure 4 shows the CopyIconToTiff function from Figure 2 rewritten in C# using the WPF wrapper classes.

FigureВ 4В CopyIconToTiff Rewritten in C# and WPF

The BitmapCacheOption.OnDemand value corresponds to the WICDecodeMetadataCacheOnDemand decoder option used in native code. And in a similar way, the alternative BitmapCacheOption.OnLoad value corresponds to the WICDecodeMetadataCacheOnLoad decoder option.

I’ve already described how these options influence when the decoder reads the image information into memory. There is, however, an additional side effect that you should be aware of when dealing with these options in managed code. Consider what happens when you specify BitmapCacheOption.OnDemand. The decoder will hold onto a reference to the underlying stream and may read from it at some point after the bitmap decoder object has been created. This assumes that the stream is still available. You need to be careful that your application doesn’t close the stream prematurely. It’s a matter of managing the lifetime of the stream so that it is not closed before the decoder is finished with it.

This doesn’t affect native code because the IStream interface is a standard COM interface whose lifetime is controlled by reference counting. Your application may have released all of its references to it, but the decoder will hold onto one as long as is necessary. What’s more, the stream is only closed after all interface pointers have been released.

WIC provides an incredibly powerful and flexible framework on which to base your imaging needs. With a generous set of codecs and a simple API, you can start taking advantage of many of its features in no time.

In my next column I’m going to explore some of the more advanced features offered by WIC. I’ll show you how you can develop your own codecs and illustrate the registration and discovery process, including the pattern-matching facilities, in detail. While I’m at it, I’ll also correct a limitation in one of the built-in codecs.

Читайте также:  Драйвера sound blaster cinema для windows 10
Оцените статью