public static IconHandle Create(ImageSource imageSource) { IconHandle result = IconHandle.Invalid; if (imageSource != null) { // Initialize bitmap rectangle and try to cast image source to bitmap frame Rect bitmapRect = new Rect(new Size(imageSource.Width, imageSource.Height)); BitmapFrame bitmapFrame = imageSource as BitmapFrame; if (bitmapFrame == null || !(bitmapFrame.Decoder is IconBitmapDecoder)) { // Create drawing visual DrawingVisual drawingVisual = new DrawingVisual(); // Open drawing context and draw the image to the visual using (DrawingContext drawingContext = drawingVisual.RenderOpen()) { // Render the image and close drawing context drawingContext.DrawImage(imageSource, bitmapRect); } // Create render target bitmap and render the visual RenderTargetBitmap renderTargetBitmap = new RenderTargetBitmap((Int32)bitmapRect.Width, (Int32)bitmapRect.Height, 96.0d, 96.0d, PixelFormats.Pbgra32); renderTargetBitmap.Render(drawingVisual); renderTargetBitmap.Freeze(); // Create bitmap frame from the render target bitmap bitmapFrame = BitmapFrame.Create(renderTargetBitmap); } // Copy pixels from bitmap frame to pixel array Int32 stride = (bitmapFrame.Format.BitsPerPixel * bitmapFrame.PixelWidth + 31) / 32 * 4; Byte[] pixelArray = new Byte[stride * bitmapFrame.PixelHeight]; bitmapFrame.CopyPixels(pixelArray, stride, 0); // Mask & icon bitmap handles IntPtr maskBitmapPtr = IntPtr.Zero; IntPtr iconBitmapPtr = IntPtr.Zero; // Initialize BITMAPINFO/BITMAPINFOHEADER structure NativeMethods.BITMAPINFO bmi = new NativeMethods.BITMAPINFO(); bmi.bmiHeader.biSize = (UInt32)Marshal.SizeOf(typeof(NativeMethods.BITMAPINFOHEADER)); bmi.bmiHeader.biWidth = (Int32)bitmapRect.Width; bmi.bmiHeader.biHeight -= ((Int32)bitmapRect.Height); bmi.bmiHeader.biPlanes = 1; bmi.bmiHeader.biBitCount = (UInt16)bitmapFrame.Format.BitsPerPixel; // DIB handle IntPtr dibPtr = IntPtr.Zero; // Create icon bitmap DIB section iconBitmapPtr = NativeMethods.CreateDIBSection(IntPtr.Zero, ref bmi, 0, out dibPtr, IntPtr.Zero, 0); // Validate icon bitmap handle if (iconBitmapPtr != IntPtr.Zero && dibPtr != IntPtr.Zero) { // Copy pixels to unmanaged memory Marshal.Copy(pixelArray, 0, dibPtr, pixelArray.Length); // Create mask bitmap maskBitmapPtr = NativeMethods.CreateBitmap((Int32)bitmapRect.Width, (Int32)bitmapRect.Height, 1, 1, IntPtr.Zero); if (maskBitmapPtr != IntPtr.Zero) { // Create and initialize ICONINFO structure NativeMethods.ICONINFO iconInfo = new NativeMethods.ICONINFO(); iconInfo.fIcon = true; iconInfo.hbmMask = maskBitmapPtr; iconInfo.hbmColor = iconBitmapPtr; // Create icon handle IntPtr iconPtr = NativeMethods.CreateIconIndirect(ref iconInfo); if (iconPtr != IntPtr.Zero) { result = new IconHandle(iconPtr); } } } // Clean up resources if (maskBitmapPtr != IntPtr.Zero) { NativeMethods.DeleteObject(maskBitmapPtr); } if (iconBitmapPtr != IntPtr.Zero) { NativeMethods.DeleteObject(iconBitmapPtr); } } // Return result return result; }
/// <summary> /// Displays this <see cref="TaskDialog"/> and returns when it is closed. /// </summary> /// <returns>A <see cref="TaskDialogResult"/> value that represents result data.</returns> public TaskDialogResult Show() { // Validate state if (IsInitialized) { throw new InvalidOperationException("The current instance is already initialized."); } // Check if Common Controls version 6 is present (declared via manifest) NativeMethods.DLLVERSIONINFO dvi = new NativeMethods.DLLVERSIONINFO(); dvi.cbSize = (UInt32)Marshal.SizeOf(typeof(NativeMethods.DLLVERSIONINFO)); // Call DllGetVersion on common controls Int32 hr = NativeMethods.DllGetVersion(ref dvi); // Handle method call exceptions if (hr != NativeMethods.S_OK) { Marshal.ThrowExceptionForHR(hr); } // Check for major version 6 or greater if (!(dvi.dwMajorVersion >= 6)) { throw new NotSupportedException("Missing application manifest dependency "+ "declaration for Microsoft Common Controls " + "version 6."); } // Initialize task dialog configuration NativeMethods.TASKDIALOGCONFIG taskDialogConfig = new NativeMethods.TASKDIALOGCONFIG(); taskDialogConfig.cbSize = (UInt32)Marshal.SizeOf(typeof(NativeMethods.TASKDIALOGCONFIG)); taskDialogConfig.hInstance = NativeMethods.GetModuleHandle(); taskDialogConfig.pfCallback = TaskDialogProc; Debug.Assert(taskDialogConfig.hInstance != IntPtr.Zero); // Check if the task dialog has an owner window if (Owner != null) { WindowInteropHelper wih = new WindowInteropHelper(Owner); if (wih.Handle == IntPtr.Zero) { // Error: The owner window has either not been initialized or is closed. throw new InvalidOperationException("The owner window has either not been " + "initialized or is closed."); } taskDialogConfig.hWndParent = wih.Handle; } // Initialize flags if (AllowCancellation) { taskDialogConfig.dwFlags |= NativeMethods.TASKDIALOG_FLAGS.TDF_ALLOW_DIALOG_CANCELLATION; } switch (ButtonStyle) { case TaskDialogButtonStyle.CommandLinks: taskDialogConfig.dwFlags |= NativeMethods.TASKDIALOG_FLAGS.TDF_USE_COMMAND_LINKS; break; case TaskDialogButtonStyle.CommandLinksNoIcon: taskDialogConfig.dwFlags |= NativeMethods.TASKDIALOG_FLAGS.TDF_USE_COMMAND_LINKS_NO_ICON; break; } if (CanMinimize) { taskDialogConfig.dwFlags |= NativeMethods.TASKDIALOG_FLAGS.TDF_CAN_BE_MINIMIZED; } if (DefaultRadioButton == -1) { taskDialogConfig.dwFlags |= NativeMethods.TASKDIALOG_FLAGS.TDF_NO_DEFAULT_RADIO_BUTTON; } switch (DefaultState) { case TaskDialogState.Expanded: taskDialogConfig.dwFlags |= NativeMethods.TASKDIALOG_FLAGS.TDF_EXPANDED_BY_DEFAULT; break; } if (EnableHyperlinks) { taskDialogConfig.dwFlags |= NativeMethods.TASKDIALOG_FLAGS.TDF_ENABLE_HYPERLINKS; } if (EnableTimer) { taskDialogConfig.dwFlags |= NativeMethods.TASKDIALOG_FLAGS.TDF_CALLBACK_TIMER; } if (ExpandFooter) { taskDialogConfig.dwFlags |= NativeMethods.TASKDIALOG_FLAGS.TDF_EXPAND_FOOTER_AREA; } if (HasProgressBar) { taskDialogConfig.dwFlags |= NativeMethods.TASKDIALOG_FLAGS.TDF_SHOW_PROGRESS_BAR; switch (ProgressBar.Style) { case TaskDialogProgressBarStyle.Marquee: taskDialogConfig.dwFlags |= NativeMethods.TASKDIALOG_FLAGS.TDF_SHOW_MARQUEE_PROGRESS_BAR; break; } } if (IsVerificationChecked) { taskDialogConfig.dwFlags |= NativeMethods.TASKDIALOG_FLAGS.TDF_VERIFICATION_FLAG_CHECKED; } if (SizeToContent) { taskDialogConfig.dwFlags |= NativeMethods.TASKDIALOG_FLAGS.TDF_SIZE_TO_CONTENT; } // Prepare formatted elements, if necessary TaskDialogText taskDialogText; if (Content is TaskDialogText) { taskDialogText = (TaskDialogText)Content; foreach (TaskDialogTextElement element in taskDialogText.Contents) { element.Owner = this; } } if (ExpandedInformation is TaskDialogText) { taskDialogText = (TaskDialogText)ExpandedInformation; foreach (TaskDialogTextElement element in taskDialogText.Contents) { element.Owner = this; } } if (Footer is TaskDialogText) { taskDialogText = (TaskDialogText)Footer; foreach (TaskDialogTextElement element in taskDialogText.Contents) { element.Owner = this; } } // Initialize strings taskDialogConfig.pszWindowTitle = Title; taskDialogConfig.pszMainInstruction = Instruction; if (Content != null) { taskDialogConfig.pszContent = Content.ToString(); } if (ExpandedInformation != null) { taskDialogConfig.pszExpandedInformation = ExpandedInformation.ToString(); } if (Footer != null) { taskDialogConfig.pszFooter = Footer.ToString(); } taskDialogConfig.pszCollapsedControlText = CollapsedControlText; taskDialogConfig.pszExpandedControlText = ExpandedControlText; taskDialogConfig.pszVerificationText = VerificationText; // Initialize common buttons taskDialogConfig.dwCommonButtons = (NativeMethods.TASKDIALOG_COMMON_BUTTON_FLAGS)CommonButtons; // Initialize icons if (UseDefaultIcon) { taskDialogConfig.hMainIcon = (IntPtr)(UInt16)DefaultIcon; } else if (Icon != null) { if (iconHandle != null) { if (!iconHandle.IsClosed) { iconHandle.Close(); } } iconHandle = IconHandle.Create(Icon); taskDialogConfig.hMainIcon = iconHandle.Value; taskDialogConfig.dwFlags |= NativeMethods.TASKDIALOG_FLAGS.TDF_USE_HICON_MAIN; } if (FooterIcon != null) { if (footerIconHandle != null) { if (!footerIconHandle.IsClosed) { footerIconHandle.Close(); } } footerIconHandle = IconHandle.Create(FooterIcon); taskDialogConfig.hFooterIcon = footerIconHandle.Value; } taskDialogConfig.dwFlags |= NativeMethods.TASKDIALOG_FLAGS.TDF_USE_HICON_FOOTER; // Initialize buttons IntPtr buttonPtr = IntPtr.Zero; if (Buttons.Count != 0) { // Allocate unmanaged memory for the button array buttonPtr = Marshal.AllocHGlobal( Marshal.SizeOf(typeof(NativeMethods.TASKDIALOG_BUTTON)) * Buttons.Count); IntPtr offset = buttonPtr; Int32 buttonID = 0; // Copy radio button data from managed list to unmanaged button array foreach (TaskDialogButton button in Buttons) { // Set owner button.Owner = this; // Create and initialize native wrapper structure NativeMethods.TASKDIALOG_BUTTON btn = new NativeMethods.TASKDIALOG_BUTTON(); btn.nButtonID = buttonID; btn.pszButtonText = button.ToString(); // Marshal to unmanaged memory Marshal.StructureToPtr(btn, offset, false); // Adjust offset and button ID offset = (IntPtr)((Int32)offset + Marshal.SizeOf(btn)); buttonID++; } // Set button count and assign pointer to unmanaged button array taskDialogConfig.cButtons = (UInt32)Buttons.Count; taskDialogConfig.pButtons = buttonPtr; } taskDialogConfig.nDefaultButton = DefaultButton; // Initialize radio buttons IntPtr radioButtonPtr = IntPtr.Zero; if (RadioButtons.Count != 0) { // Allocate unmanaged memory for the radio button array radioButtonPtr = Marshal.AllocHGlobal( Marshal.SizeOf(typeof(NativeMethods.TASKDIALOG_BUTTON)) * RadioButtons.Count); IntPtr offset = radioButtonPtr; Int32 radioButtonID = 0; // Copy radio button data from managed list to unmanaged button array foreach (TaskDialogRadioButton radioButton in RadioButtons) { // Set owner radioButton.Owner = this; // Create and initialize native wrapper structure NativeMethods.TASKDIALOG_BUTTON btn = new NativeMethods.TASKDIALOG_BUTTON(); btn.nButtonID = radioButtonID; btn.pszButtonText = radioButton.Title; // Marshal to unmanaged memory Marshal.StructureToPtr(btn, offset, false); // Adjust offset and radio button ID offset = (IntPtr)((Int32)offset + Marshal.SizeOf(btn)); radioButtonID++; } // Set radio button count and assign pointer to unmanaged radio button array taskDialogConfig.cRadioButtons = (UInt32)RadioButtons.Count; taskDialogConfig.pRadioButtons = radioButtonPtr; } taskDialogConfig.nDefaultRadioButton = DefaultRadioButton; // Present task dialog Int32 selectedButton; Int32 selectedRadioButton; Boolean verificationChecked; hr = NativeMethods.TaskDialogIndirect(taskDialogConfig, out selectedButton, out selectedRadioButton, out verificationChecked); try { // Check HRESULT for errors if (hr != NativeMethods.S_OK) { Marshal.ThrowExceptionForHR(hr); } } finally { // Clean up resources if (radioButtonPtr != IntPtr.Zero) { Marshal.FreeHGlobal(radioButtonPtr); } if (buttonPtr != IntPtr.Zero) { Marshal.FreeHGlobal(buttonPtr); } if (footerIconHandle != null) { if (!footerIconHandle.IsClosed) { footerIconHandle.Close(); } } if (iconHandle != null) { if (!iconHandle.IsClosed) { iconHandle.Close(); } } } return new TaskDialogResult(selectedButton, selectedRadioButton, verificationChecked); }
public static IconHandle Create(ImageSource imageSource) { IconHandle result = IconHandle.Invalid; if (imageSource != null) { // Initialize bitmap rectangle and try to cast image source to bitmap frame Rect bitmapRect = new Rect(new Size(imageSource.Width, imageSource.Height)); BitmapFrame bitmapFrame = imageSource as BitmapFrame; if (bitmapFrame == null || !(bitmapFrame.Decoder is IconBitmapDecoder)) { // Create drawing visual DrawingVisual drawingVisual = new DrawingVisual(); // Open drawing context and draw the image to the visual using (DrawingContext drawingContext = drawingVisual.RenderOpen()) { // Render the image and close drawing context drawingContext.DrawImage(imageSource, bitmapRect); } // Create render target bitmap and render the visual RenderTargetBitmap renderTargetBitmap = new RenderTargetBitmap((Int32)bitmapRect.Width, (Int32)bitmapRect.Height, 96.0d, 96.0d, PixelFormats.Pbgra32); renderTargetBitmap.Render(drawingVisual); renderTargetBitmap.Freeze(); // Create bitmap frame from the render target bitmap bitmapFrame = BitmapFrame.Create(renderTargetBitmap); } // Copy pixels from bitmap frame to pixel array Int32 stride = (bitmapFrame.Format.BitsPerPixel * bitmapFrame.PixelWidth + 31) / 32 * 4; Byte[] pixelArray = new Byte[stride * bitmapFrame.PixelHeight]; bitmapFrame.CopyPixels(pixelArray, stride, 0); // Mask & icon bitmap handles IntPtr maskBitmapPtr = IntPtr.Zero; IntPtr iconBitmapPtr = IntPtr.Zero; // Initialize BITMAPINFO/BITMAPINFOHEADER structure NativeMethods.BITMAPINFO bmi = new NativeMethods.BITMAPINFO(); bmi.bmiHeader.biSize = (UInt32)Marshal.SizeOf(typeof(NativeMethods.BITMAPINFOHEADER)); bmi.bmiHeader.biWidth = (Int32)bitmapRect.Width; bmi.bmiHeader.biHeight -= ((Int32)bitmapRect.Height); bmi.bmiHeader.biPlanes = 1; bmi.bmiHeader.biBitCount = (UInt16)bitmapFrame.Format.BitsPerPixel; // DIB handle IntPtr dibPtr = IntPtr.Zero; // Create icon bitmap DIB section iconBitmapPtr = NativeMethods.CreateDIBSection(IntPtr.Zero, ref bmi, 0, out dibPtr, IntPtr.Zero, 0); // Validate icon bitmap handle if (iconBitmapPtr != IntPtr.Zero && dibPtr != IntPtr.Zero) { // Copy pixels to unmanaged memory Marshal.Copy(pixelArray, 0, dibPtr, pixelArray.Length); // Create mask bitmap maskBitmapPtr = NativeMethods.CreateBitmap((Int32)bitmapRect.Width, (Int32)bitmapRect.Height, 1, 1, IntPtr.Zero); if (maskBitmapPtr != IntPtr.Zero) { // Create and initialize ICONINFO structure NativeMethods.ICONINFO iconInfo = new NativeMethods.ICONINFO(); iconInfo.fIcon = true; iconInfo.hbmMask = maskBitmapPtr; iconInfo.hbmColor = iconBitmapPtr; // Create icon handle IntPtr iconPtr = NativeMethods.CreateIconIndirect(ref iconInfo); if (iconPtr != IntPtr.Zero) { result = new IconHandle(iconPtr); } } } // Clean up resources if (maskBitmapPtr != IntPtr.Zero) { NativeMethods.DeleteObject(maskBitmapPtr); } if (iconBitmapPtr != IntPtr.Zero) { NativeMethods.DeleteObject(iconBitmapPtr); } } // Return result return(result); }
void UpdateIcon(NativeMethods.TASKDIALOG_ICON_ELEMENTS iconElement, ImageSource imageSource) { IconHandle newHandle = IconHandle.Invalid; // Create replacement handle first switch (iconElement) { case NativeMethods.TASKDIALOG_ICON_ELEMENTS.TDIE_ICON_MAIN: newHandle = IconHandle.Create(imageSource); break; case NativeMethods.TASKDIALOG_ICON_ELEMENTS.TDIE_ICON_FOOTER: newHandle = IconHandle.Create(imageSource); break; } // Send TDM_UPDATE_ICON message to update the icon NativeMethods.SendMessage( Handle, (UInt32)NativeMethods.TASKDIALOG_MESSAGES.TDM_UPDATE_ICON, new UIntPtr((UInt32)iconElement), newHandle.Value); // Release previous icon handle and replace with new handle switch (iconElement) { case NativeMethods.TASKDIALOG_ICON_ELEMENTS.TDIE_ICON_MAIN: iconHandle.Close(); iconHandle = newHandle; break; case NativeMethods.TASKDIALOG_ICON_ELEMENTS.TDIE_ICON_FOOTER: footerIconHandle.Close(); footerIconHandle = newHandle; break; } }