I created an application in C# that gets icon images from window handles using user32.dll like this:
[DllImport("user32.dll", EntryPoint = "GetClassLong")]
private static extern int GetClassLongPtr32(IntPtr hWnd, int nIndex);
public static IntPtr GetAppIcon(IntPtr hwnd)
{
return WI.GetClassLongPtr32(hwnd, WI.ICON_SMALL);
}
And I want to create a BitmapSource from this icon pointer. Usually for WPF I would use
Imaging.CreateBitmapSourceFromHIcon(handle, Int32Rect.Empty, BitmapSizeOptions.FromEmptyOptions());
But since I need the BitmapSource to draw it in a Direct2D render target I would need to use DirectX's BitmapSource
Microsoft.WindowsAPICodePack.DirectX.WindowImagingComponent.BitmapSource
How can I create this kind of BitmapSource using the icon handle or can I transfer one BitmapSource type to the other?
The ID2D1DeviceContext
has a method CreateBitmapFromWicBitmap
.
With its help you can create an ID2D1Bitmap
. The only thing you have to do is to create an IWICBitmap
from your HICON
and then create an IWICFormatConverter
, so you can keep the alpha channel. You can do it this way (The snippet from below is a delphi one but in C# should be very similar):
procedure iconToD2D1Bitmap;
var
hIcon: HICON;
wicBitmap: IWICBitmap;
wicConverter: IWICFormatConverter;
wicFactory: IWICImagingFactory;
bitmapProps: D2D1_BITMAP_PROPERTIES1;
bitmap: ID2D1Bitmap1;
begin
// get a HICON
hIcon := SendMessage(Handle, WM_GETICON, ICON_BIG, 0);
try
// create wic imaging factory
CoCreateInstance(CLSID_WICImagingFactory, nil, CLSCTX_INPROC_SERVER or CLSCTX_LOCAL_SERVER, IUnknown, wicFactory);
wicFactory.CreateBitmapFromHICON(hIcon, wicBitmap);
wicFactory.CreateFormatConverter(wicConverter);
wicConverter.Initialize(wicBitmap, GUID_WICPixelFormat32bppPBGRA, WICBitmapDitherTypeNone, nil, 0, WICBitmapPaletteTypeMedianCut);
bitmapProps.bitmapOptions := D2D1_BITMAP_OPTIONS_NONE;
bitmapProps.pixelFormat.format := DXGI_FORMAT_B8G8R8A8_UNORM;
bitmapProps.pixelFormat.alphaMode := D2D1_ALPHA_MODE_PREMULTIPLIED;
bitmapProps.dpiX := 96;
bitmapProps.dpiY := 96;
bitmapProps.colorContext := nil;
// deviceContext should be a valid D2D1DeviceContext
deviceContext.CreateBitmapFromWicBitmap(wicConverter, @bitmapProps, bitmap);
// the bitmap variable contains your icon
except
//
end;
end;