/// <include file='doc\TextBox.uex' path='docs/doc[@for="TextBox.SetAutoComplete"]/*' /> /// <devdoc> /// Sets the AutoComplete mode in TextBox. /// </devdoc> internal void SetAutoComplete(bool reset) { //Autocomplete Not Enabled for Password enabled and MultiLine Textboxes. if (Multiline || passwordChar != 0 || useSystemPasswordChar || AutoCompleteSource == AutoCompleteSource.None) { return; } if (AutoCompleteMode != AutoCompleteMode.None) { if (!fromHandleCreate) { //RecreateHandle to avoid Leak. // notice the use of member variable to avoid re-entrancy AutoCompleteMode backUpMode = this.AutoCompleteMode; autoCompleteMode = AutoCompleteMode.None; RecreateHandle(); autoCompleteMode = backUpMode; } if (AutoCompleteSource == AutoCompleteSource.CustomSource) { if (IsHandleCreated && AutoCompleteCustomSource != null) { if (AutoCompleteCustomSource.Count == 0) { ResetAutoComplete(true); } else { if (stringSource == null) { stringSource = new StringSource(GetStringsForAutoComplete()); if (!stringSource.Bind(new HandleRef(this, Handle), (int)AutoCompleteMode)) { throw new ArgumentException(SR.AutoCompleteFailure); } } else { stringSource.RefreshList(GetStringsForAutoComplete()); } } } } else { try { if (IsHandleCreated) { int mode = 0; if (AutoCompleteMode == AutoCompleteMode.Suggest) { mode |= NativeMethods.AUTOSUGGEST | NativeMethods.AUTOAPPEND_OFF; } if (AutoCompleteMode == AutoCompleteMode.Append) { mode |= NativeMethods.AUTOAPPEND | NativeMethods.AUTOSUGGEST_OFF; } if (AutoCompleteMode == AutoCompleteMode.SuggestAppend) { mode |= NativeMethods.AUTOSUGGEST; mode |= NativeMethods.AUTOAPPEND; } int ret = SafeNativeMethods.SHAutoComplete(new HandleRef(this, Handle), (int)AutoCompleteSource | mode); } } catch (SecurityException) { // If we don't have full trust, degrade gracefully. Allow the control to // function without auto-complete. Allow the app to continue running. } } } else if (reset) { ResetAutoComplete(true); } }
private static DialogResult ShowCore(IWin32Window owner, string text, string caption, MessageBoxButtons buttons, MessageBoxIcon icon, MessageBoxDefaultButton defaultButton, MessageBoxOptions options, bool showHelp) { if (!ClientUtils.IsEnumValid(buttons, (int)buttons, (int)MessageBoxButtons.OK, (int)MessageBoxButtons.RetryCancel)) { throw new InvalidEnumArgumentException(nameof(buttons), (int)buttons, typeof(MessageBoxButtons)); } // valid values are 0x0 0x10 0x20 0x30 0x40, chop off the last 4 bits and check that it's between 0 and 4. if (!WindowsFormsUtils.EnumValidator.IsEnumWithinShiftedRange(icon, /*numBitsToShift*/4, /*min*/0x0,/*max*/0x4)) { throw new InvalidEnumArgumentException(nameof(icon), (int)icon, typeof(MessageBoxIcon)); } // valid values are 0x0 0x100, 0x200, chop off the last 8 bits and check that it's between 0 and 2. if (!WindowsFormsUtils.EnumValidator.IsEnumWithinShiftedRange(defaultButton, /*numBitsToShift*/8, /*min*/0x0,/*max*/0x2)) { throw new InvalidEnumArgumentException(nameof(defaultButton), (int)defaultButton, typeof(DialogResult)); } // options intentionally not verified because we don't expose all the options Win32 supports. if (!SystemInformation.UserInteractive && (options & (MessageBoxOptions.ServiceNotification | MessageBoxOptions.DefaultDesktopOnly)) == 0) { throw new InvalidOperationException(SR.CantShowModalOnNonInteractive); } if (owner != null && (options & (MessageBoxOptions.ServiceNotification | MessageBoxOptions.DefaultDesktopOnly)) != 0) { throw new ArgumentException(SR.CantShowMBServiceWithOwner, "options"); } if (showHelp && (options & (MessageBoxOptions.ServiceNotification | MessageBoxOptions.DefaultDesktopOnly)) != 0) { throw new ArgumentException(SR.CantShowMBServiceWithHelp, "options"); } int style = (showHelp) ? HELP_BUTTON : 0; style |= (int)buttons | (int)icon | (int)defaultButton | (int)options; IntPtr handle = IntPtr.Zero; if (showHelp || ((options & (MessageBoxOptions.ServiceNotification | MessageBoxOptions.DefaultDesktopOnly)) == 0)) { if (owner == null) { handle = UnsafeNativeMethods.GetActiveWindow(); } else { handle = Control.GetSafeHandle(owner); } } IntPtr userCookie = IntPtr.Zero; if (Application.UseVisualStyles) { // CLR4.0 or later, shell32.dll needs to be loaded explicitly. if (Interop.Kernel32.GetModuleHandleW(Interop.Libraries.Shell32) == IntPtr.Zero) { if (Interop.Kernel32.LoadLibraryFromSystemPathIfAvailable(Interop.Libraries.Shell32) == IntPtr.Zero) { int lastWin32Error = Marshal.GetLastWin32Error(); throw new Win32Exception(lastWin32Error, string.Format(SR.LoadDLLError, Interop.Libraries.Shell32)); } } // Activate theming scope to get theming for controls at design time and when hosted in browser. // NOTE: If a theming context is already active, this call is very fast, so shouldn't be a perf issue. userCookie = UnsafeNativeMethods.ThemingScope.Activate(); } Application.BeginModalMessageLoop(); DialogResult result; try { result = Win32ToDialogResult(SafeNativeMethods.MessageBox(new HandleRef(owner, handle), text, caption, style)); } finally { Application.EndModalMessageLoop(); UnsafeNativeMethods.ThemingScope.Deactivate(userCookie); } // Right after the dialog box is closed, Windows sends WM_SETFOCUS back to the previously active control // but since we have disabled this thread main window the message is lost. So we have to send it again after // we enable the main window. // UnsafeNativeMethods.SendMessage(new HandleRef(owner, handle), Interop.WindowMessages.WM_SETFOCUS, 0, 0); return result; }
private int AdjustScroll(Message m, int pos, int maxPos, bool horizontal) { switch (NativeMethods.Util.LOWORD(m.WParam)) { case NativeMethods.SB_THUMBPOSITION: case NativeMethods.SB_THUMBTRACK: NativeMethods.SCROLLINFO si = new NativeMethods.SCROLLINFO(); si.cbSize = Marshal.SizeOf(typeof(NativeMethods.SCROLLINFO)); si.fMask = NativeMethods.SIF_TRACKPOS; int direction = horizontal ? NativeMethods.SB_HORZ : NativeMethods.SB_VERT; if (SafeNativeMethods.GetScrollInfo(new HandleRef(this, m.HWnd), direction, si)) { pos = si.nTrackPos; } else { pos = NativeMethods.Util.HIWORD(m.WParam); } break; case NativeMethods.SB_LINEUP: if (pos > SCROLL_LINE) { pos -= SCROLL_LINE; } else { pos = 0; } break; case NativeMethods.SB_LINEDOWN: if (pos < maxPos - SCROLL_LINE) { pos += SCROLL_LINE; } else { pos = maxPos; } break; case NativeMethods.SB_PAGEUP: if (pos > SCROLL_PAGE) { pos -= SCROLL_PAGE; } else { pos = 0; } break; case NativeMethods.SB_PAGEDOWN: if (pos < maxPos - SCROLL_PAGE) { pos += SCROLL_PAGE; } else { pos = maxPos; } break; } return(pos); }
/// <include file='doc\Help.uex' path='docs/doc[@for="Help.ShowHTML10Help"]/*' /> /// <devdoc> /// Displays HTML 1.0 Help with the specified parameters /// </devdoc> /// <internalonly/> private static void ShowHTML10Help(Control parent, string url, HelpNavigator command, object param) { Debug.WriteLineIf(Help.WindowsFormsHelpTrace.TraceVerbose, "Help:: ShowHTML10Help:: " + url + ", " + command.ToString("G") + ", " + param); IntSecurity.UnmanagedCode.Demand(); // See if we can get a full path and file name and if that will // resolve the out of memory condition with file names that include spaces. // If we can't, though, we can't assume that the path's no good: it might be in // the Windows help directory. Uri file = null; string pathAndFileName = url; //This is our best guess at the path yet. file = Resolve(url); if (file != null) // Can't assume we have a good url { pathAndFileName = file.AbsoluteUri; } if (file == null || file.IsFile) { StringBuilder newPath = new StringBuilder(); string localPath = (file != null && file.IsFile) ? file.LocalPath : url; // If this is a local path, convert it to a short path name. Pass 0 as the length the first time uint requiredStringSize = UnsafeNativeMethods.GetShortPathName(localPath, newPath, 0); if (requiredStringSize > 0) { //It's able to make it a short path. Happy day. newPath.Capacity = (int)requiredStringSize; requiredStringSize = UnsafeNativeMethods.GetShortPathName(localPath, newPath, requiredStringSize); //If it can't make it a short path, just leave the path we had. pathAndFileName = newPath.ToString(); } } HandleRef handle; if (parent != null) { handle = new HandleRef(parent, parent.Handle); } else { handle = new HandleRef(null, UnsafeNativeMethods.GetActiveWindow()); } object htmlParam; string stringParam = param as string; if (stringParam != null) { int htmlCommand = MapCommandToHTMLCommand(command, stringParam, out htmlParam); string stringHtmlParam = htmlParam as string; if (stringHtmlParam != null) { SafeNativeMethods.HtmlHelp(handle, pathAndFileName, htmlCommand, stringHtmlParam); } else if (htmlParam is int) { SafeNativeMethods.HtmlHelp(handle, pathAndFileName, htmlCommand, (int)htmlParam); } else if (htmlParam is NativeMethods.HH_FTS_QUERY) { SafeNativeMethods.HtmlHelp(handle, pathAndFileName, htmlCommand, (NativeMethods.HH_FTS_QUERY)htmlParam); } else if (htmlParam is NativeMethods.HH_AKLINK) { // According to MSDN documentation, we have to ensure that the help window is up // before we call ALINK lookup. // SafeNativeMethods.HtmlHelp(NativeMethods.NullHandleRef, pathAndFileName, HH_DISPLAY_TOPIC, (string)null); SafeNativeMethods.HtmlHelp(handle, pathAndFileName, htmlCommand, (NativeMethods.HH_AKLINK)htmlParam); } else { Debug.Fail("Cannot handle HTML parameter of type: " + htmlParam.GetType()); SafeNativeMethods.HtmlHelp(handle, pathAndFileName, htmlCommand, (string)param); } } else if (param == null) { SafeNativeMethods.HtmlHelp(handle, pathAndFileName, MapCommandToHTMLCommand(command, null, out htmlParam), 0); } else if (param is NativeMethods.HH_POPUP) { SafeNativeMethods.HtmlHelp(handle, pathAndFileName, HH_DISPLAY_TEXT_POPUP, (NativeMethods.HH_POPUP)param); } else if (param.GetType() == typeof(Int32)) { throw new ArgumentException(string.Format(SR.InvalidArgument, "param", "Integer")); } }
public unsafe DCMapping(IntPtr hDC, Rectangle bounds) { if (hDC == IntPtr.Zero) { throw new ArgumentNullException(nameof(hDC)); } bool success; IntPtr hOriginalClippingRegion = IntPtr.Zero; _translatedBounds = bounds; _graphics = null; _dc = DeviceContext.FromHdc(hDC); _dc.SaveHdc(); // Retrieve the x-coordinates and y-coordinates of the viewport origin for the specified device context. success = SafeNativeMethods.GetViewportOrgEx(hDC, out Point viewportOrg); Debug.Assert(success, "GetViewportOrgEx() failed."); // Create a new rectangular clipping region based off of the bounds specified, shifted over by the x & y specified in the viewport origin. IntPtr hClippingRegion = Gdi32.CreateRectRgn(viewportOrg.X + bounds.Left, viewportOrg.Y + bounds.Top, viewportOrg.X + bounds.Right, viewportOrg.Y + bounds.Bottom); Debug.Assert(hClippingRegion != IntPtr.Zero, "CreateRectRgn() failed."); try { // Create an empty region oriented at 0,0 so we can populate it with the original clipping region of the hDC passed in. hOriginalClippingRegion = Gdi32.CreateRectRgn(0, 0, 0, 0); Debug.Assert(hOriginalClippingRegion != IntPtr.Zero, "CreateRectRgn() failed."); // Get the clipping region from the hDC: result = {-1 = error, 0 = no region, 1 = success} per MSDN int result = Gdi32.GetClipRgn(hDC, hOriginalClippingRegion); Debug.Assert(result != -1, "GetClipRgn() failed."); // Shift the viewpoint origint by coordinates specified in "bounds". var lastViewPort = new Point(); success = SafeNativeMethods.SetViewportOrgEx(hDC, viewportOrg.X + bounds.Left, viewportOrg.Y + bounds.Top, &lastViewPort); Debug.Assert(success, "SetViewportOrgEx() failed."); RegionType originalRegionType; if (result != 0) { // Get the origninal clipping region so we can determine its type (we'll check later if we've restored the region back properly.) RECT originalClipRect = new RECT(); originalRegionType = Gdi32.GetRgnBox(hOriginalClippingRegion, ref originalClipRect); Debug.Assert(originalRegionType != RegionType.ERROR, "ERROR returned from SelectClipRgn while selecting the original clipping region.."); if (originalRegionType == RegionType.SIMPLEREGION) { // Find the intersection of our clipping region and the current clipping region (our parent's) // Returns a NULLREGION, the two didn't intersect. // Returns a SIMPLEREGION, the two intersected // Resulting region (stuff that was in hOriginalClippingRegion AND hClippingRegion is placed in hClippingRegion RegionType combineResult = Gdi32.CombineRgn(hClippingRegion, hClippingRegion, hOriginalClippingRegion, Gdi32.CombineMode.RGN_AND); Debug.Assert((combineResult == RegionType.SIMPLEREGION) || (combineResult == RegionType.NULLREGION), "SIMPLEREGION or NULLREGION expected."); } } else { // If there was no clipping region, then the result is a simple region. // We don't need to keep track of the original now, since it is empty. Gdi32.DeleteObject(hOriginalClippingRegion); hOriginalClippingRegion = IntPtr.Zero; originalRegionType = RegionType.SIMPLEREGION; } // Select the new clipping region; make sure it's a SIMPLEREGION or NULLREGION RegionType selectResult = Gdi32.SelectClipRgn(hDC, hClippingRegion); Debug.Assert((selectResult == RegionType.SIMPLEREGION || selectResult == RegionType.NULLREGION), "SIMPLEREGION or NULLLREGION expected."); } catch (Exception ex) when(!ClientUtils.IsSecurityOrCriticalException(ex)) { _dc.RestoreHdc(); _dc.Dispose(); } finally { // Delete the new clipping region, as the clipping region for the HDC is now set // to this rectangle. Hold on to hOriginalClippingRegion, as we'll need to restore // it when this object is disposed. success = Gdi32.DeleteObject(hClippingRegion).IsTrue(); Debug.Assert(success, "DeleteObject(hClippingRegion) failed."); if (hOriginalClippingRegion != IntPtr.Zero) { success = Gdi32.DeleteObject(hOriginalClippingRegion).IsTrue(); Debug.Assert(success, "DeleteObject(hOriginalClippingRegion) failed."); } } }
/// <summary> /// Duplicates this the Win32 handle of this <see cref='Cursor'/>. /// </summary> public IntPtr CopyHandle() { Size sz = Size; return(SafeNativeMethods.CopyImage(new HandleRef(this, Handle), NativeMethods.IMAGE_CURSOR, sz.Width, sz.Height, 0)); }
/// <summary> /// Draws this image to a graphics object. The drawing command originates on the graphics /// object, but a graphics object generally has no idea how to render a given image. So, /// it passes the call to the actual image. This version crops the image to the given /// dimensions and allows the user to specify a rectangle within the image to draw. /// </summary> // This method is way more powerful than what we expose, but I'll leave it in place. private void DrawImageCore(Graphics graphics, Rectangle imageRect, Rectangle targetRect, bool stretch) { // Support GDI+ Translate method targetRect.X += (int)graphics.Transform.OffsetX; targetRect.Y += (int)graphics.Transform.OffsetY; int rop = 0xcc0020; // RasterOp.SOURCE.GetRop(); IntPtr dc = graphics.GetHdc(); try { // want finally clause to release dc int imageX = 0; int imageY = 0; int imageWidth; int imageHeight; int targetX = 0; int targetY = 0; int targetWidth = 0; int targetHeight = 0; Size cursorSize = Size; // compute the dimensions of the icon, if needed // if (!imageRect.IsEmpty) { imageX = imageRect.X; imageY = imageRect.Y; imageWidth = imageRect.Width; imageHeight = imageRect.Height; } else { imageWidth = cursorSize.Width; imageHeight = cursorSize.Height; } if (!targetRect.IsEmpty) { targetX = targetRect.X; targetY = targetRect.Y; targetWidth = targetRect.Width; targetHeight = targetRect.Height; } else { targetWidth = cursorSize.Width; targetHeight = cursorSize.Height; } int drawWidth, drawHeight; int clipWidth, clipHeight; if (stretch) { // Short circuit the simple case of blasting an icon to the // screen // if (targetWidth == imageWidth && targetHeight == imageHeight && imageX == 0 && imageY == 0 && rop == NativeMethods.SRCCOPY && imageWidth == cursorSize.Width && imageHeight == cursorSize.Height) { SafeNativeMethods.DrawIcon(new HandleRef(graphics, dc), targetX, targetY, new HandleRef(this, handle)); return; } drawWidth = cursorSize.Width * targetWidth / imageWidth; drawHeight = cursorSize.Height * targetHeight / imageHeight; clipWidth = targetWidth; clipHeight = targetHeight; } else { // Short circuit the simple case of blasting an icon to the // screen // if (imageX == 0 && imageY == 0 && rop == NativeMethods.SRCCOPY && cursorSize.Width <= targetWidth && cursorSize.Height <= targetHeight && cursorSize.Width == imageWidth && cursorSize.Height == imageHeight) { SafeNativeMethods.DrawIcon(new HandleRef(graphics, dc), targetX, targetY, new HandleRef(this, handle)); return; } drawWidth = cursorSize.Width; drawHeight = cursorSize.Height; clipWidth = targetWidth < imageWidth ? targetWidth : imageWidth; clipHeight = targetHeight < imageHeight ? targetHeight : imageHeight; } if (rop == NativeMethods.SRCCOPY) { // The ROP is SRCCOPY, so we can be simple here and take // advantage of clipping regions. Drawing the cursor // is merely a matter of offsetting and clipping. // SafeNativeMethods.IntersectClipRect(new HandleRef(this, Handle), targetX, targetY, targetX + clipWidth, targetY + clipHeight); SafeNativeMethods.DrawIconEx(new HandleRef(graphics, dc), targetX - imageX, targetY - imageY, new HandleRef(this, handle), drawWidth, drawHeight, 0, NativeMethods.NullHandleRef, NativeMethods.DI_NORMAL); // Let GDI+ restore clipping return; } Debug.Fail("Cursor.Draw does not support raster ops. How did you even pass one in?"); } finally { graphics.ReleaseHdcInternal(dc); } }
/// <summary> /// Sets the DPI awareness. If not available on the current OS, it falls back to the next possible. /// </summary> /// <returns>true/false - If the process DPI awareness is successfully set, returns true. Otherwise false.</returns> internal static bool SetWinformsApplicationDpiAwareness(HighDpiMode highDpiMode) { NativeMethods.PROCESS_DPI_AWARENESS dpiFlag = NativeMethods.PROCESS_DPI_AWARENESS.PROCESS_DPI_UNINITIALIZED; // For Windows 10 RS2 and above if (ApiHelper.IsApiAvailable(ExternDll.User32, nameof(SafeNativeMethods.SetProcessDpiAwarenessContext))) { int rs2AndAboveDpiFlag; switch (highDpiMode) { case HighDpiMode.SystemAware: rs2AndAboveDpiFlag = NativeMethods.DPI_AWARENESS_CONTEXT_SYSTEM_AWARE; break; case HighDpiMode.PerMonitor: rs2AndAboveDpiFlag = NativeMethods.DPI_AWARENESS_CONTEXT_PER_MONITOR_AWARE; break; case HighDpiMode.PerMonitorV2: // Necessary for RS1, since this SetProcessDpiAwarenessContext IS available here. rs2AndAboveDpiFlag = SafeNativeMethods.IsValidDpiAwarenessContext(NativeMethods.DPI_AWARENESS_CONTEXT_PER_MONITOR_AWARE_V2) ? NativeMethods.DPI_AWARENESS_CONTEXT_PER_MONITOR_AWARE_V2 : NativeMethods.DPI_AWARENESS_CONTEXT_SYSTEM_AWARE; break; case HighDpiMode.DpiUnawareGdiScaled: // Let's make sure, we do not try to set a value which has been introduced in later Windows releases. rs2AndAboveDpiFlag = SafeNativeMethods.IsValidDpiAwarenessContext(NativeMethods.DPI_AWARENESS_CONTEXT_UNAWARE_GDISCALED) ? NativeMethods.DPI_AWARENESS_CONTEXT_UNAWARE_GDISCALED : NativeMethods.DPI_AWARENESS_CONTEXT_UNAWARE; break; default: rs2AndAboveDpiFlag = NativeMethods.DPI_AWARENESS_CONTEXT_UNAWARE; break; } return(SafeNativeMethods.SetProcessDpiAwarenessContext(rs2AndAboveDpiFlag)); } // For operating systems Windows 8.1 to Windows 10 RS1 version. else if (ApiHelper.IsApiAvailable(ExternDll.ShCore, nameof(SafeNativeMethods.SetProcessDpiAwareness))) { switch (highDpiMode) { case HighDpiMode.DpiUnaware: case HighDpiMode.DpiUnawareGdiScaled: dpiFlag = NativeMethods.PROCESS_DPI_AWARENESS.PROCESS_DPI_UNAWARE; break; case HighDpiMode.SystemAware: dpiFlag = NativeMethods.PROCESS_DPI_AWARENESS.PROCESS_SYSTEM_DPI_AWARE; break; case HighDpiMode.PerMonitor: case HighDpiMode.PerMonitorV2: dpiFlag = NativeMethods.PROCESS_DPI_AWARENESS.PROCESS_PER_MONITOR_DPI_AWARE; break; default: dpiFlag = NativeMethods.PROCESS_DPI_AWARENESS.PROCESS_SYSTEM_DPI_AWARE; break; } return(SafeNativeMethods.SetProcessDpiAwareness(dpiFlag) == NativeMethods.S_OK); } // For operating systems windows 7 to windows 8 else if (ApiHelper.IsApiAvailable(ExternDll.User32, nameof(SafeNativeMethods.SetProcessDPIAware))) { switch (highDpiMode) { case HighDpiMode.DpiUnaware: case HighDpiMode.DpiUnawareGdiScaled: // We can return, there is nothing to set if we assume we're already in DpiUnaware. return(true); case HighDpiMode.SystemAware: case HighDpiMode.PerMonitor: case HighDpiMode.PerMonitorV2: dpiFlag = NativeMethods.PROCESS_DPI_AWARENESS.PROCESS_SYSTEM_DPI_AWARE; break; } if (dpiFlag == NativeMethods.PROCESS_DPI_AWARENESS.PROCESS_SYSTEM_DPI_AWARE) { return(SafeNativeMethods.SetProcessDPIAware()); } } return(false); }
public DialogResult ShowDialog(IWin32Window owner) { if (!SystemInformation.UserInteractive) { throw new InvalidOperationException(SR.CantShowModalOnNonInteractive); } NativeWindow native = null;//This will be used if there is no owner or active window (declared here so it can be kept alive) IntPtr hwndOwner = IntPtr.Zero; DialogResult result = DialogResult.Cancel; try { if (owner != null) { hwndOwner = Control.GetSafeHandle(owner); } if (hwndOwner == IntPtr.Zero) { hwndOwner = UnsafeNativeMethods.GetActiveWindow(); } if (hwndOwner == IntPtr.Zero) { //We will have to create our own Window native = new NativeWindow(); native.CreateHandle(new CreateParams()); hwndOwner = native.Handle; } if (helpMsg == 0) { helpMsg = SafeNativeMethods.RegisterWindowMessage("commdlg_help"); } NativeMethods.WndProc ownerProc = new NativeMethods.WndProc(this.OwnerWndProc); hookedWndProc = System.Runtime.InteropServices.Marshal.GetFunctionPointerForDelegate(ownerProc); System.Diagnostics.Debug.Assert(IntPtr.Zero == defOwnerWndProc, "The previous subclass wasn't properly cleaned up"); IntPtr userCookie = IntPtr.Zero; try { //UnsafeNativeMethods.[Get|Set]WindowLong is smart enough to call SetWindowLongPtr on 64-bit OS defOwnerWndProc = UnsafeNativeMethods.SetWindowLong(new HandleRef(this, hwndOwner), NativeMethods.GWL_WNDPROC, ownerProc); if (Application.UseVisualStyles) { userCookie = UnsafeNativeMethods.ThemingScope.Activate(); } Application.BeginModalMessageLoop(); try { result = RunDialog(hwndOwner) ? DialogResult.OK : DialogResult.Cancel; } finally { Application.EndModalMessageLoop(); } } finally { IntPtr currentSubClass = UnsafeNativeMethods.GetWindowLong(new HandleRef(this, hwndOwner), NativeMethods.GWL_WNDPROC); if (IntPtr.Zero != defOwnerWndProc || currentSubClass != hookedWndProc) { UnsafeNativeMethods.SetWindowLong(new HandleRef(this, hwndOwner), NativeMethods.GWL_WNDPROC, new HandleRef(this, defOwnerWndProc)); } UnsafeNativeMethods.ThemingScope.Deactivate(userCookie); defOwnerWndProc = IntPtr.Zero; hookedWndProc = IntPtr.Zero; //Ensure that the subclass delegate will not be GC collected until after it has been subclassed GC.KeepAlive(ownerProc); } } finally { if (null != native) { native.DestroyHandle(); } } return(result); }
// ported form VB6 (Ctls\PortUtil\StdCtl.cpp:6176) private unsafe bool DICopy(IntPtr hdcDest, IntPtr hdcSrc, RECT rect, bool bStretch) { long i; // Get the bitmap from the DC by selecting in a 1x1 pixel temp bitmap IntPtr hNullBitmap = SafeNativeMethods.CreateBitmap(1, 1, 1, 1, IntPtr.Zero); if (hNullBitmap == IntPtr.Zero) { return(false); } try { IntPtr hBitmap = Gdi32.SelectObject(hdcSrc, hNullBitmap); if (hBitmap == IntPtr.Zero) { return(false); } // Restore original bitmap Gdi32.SelectObject(hdcSrc, hBitmap); if (!Gdi32.GetObjectW(hBitmap, out Gdi32.BITMAP bmp)) { return(false); } NativeMethods.BITMAPINFO_FLAT lpbmi = new NativeMethods.BITMAPINFO_FLAT { bmiHeader_biSize = Marshal.SizeOf <NativeMethods.BITMAPINFOHEADER>(), bmiHeader_biWidth = bmp.bmWidth, bmiHeader_biHeight = bmp.bmHeight, bmiHeader_biPlanes = 1, bmiHeader_biBitCount = (short)bmp.bmBitsPixel, bmiHeader_biCompression = NativeMethods.BI_RGB, bmiHeader_biSizeImage = 0, //Not needed since using BI_RGB bmiHeader_biXPelsPerMeter = 0, bmiHeader_biYPelsPerMeter = 0, bmiHeader_biClrUsed = 0, bmiHeader_biClrImportant = 0, bmiColors = new byte[NativeMethods.BITMAPINFO_MAX_COLORSIZE * 4] }; // Include the palette for 256 color bitmaps long iColors = 1 << (bmp.bmBitsPixel * bmp.bmPlanes); if (iColors <= 256) { byte[] aj = new byte[sizeof(Gdi32.PALETTEENTRY) * 256]; SafeNativeMethods.GetSystemPaletteEntries(hdcSrc, 0, (int)iColors, aj); fixed(byte *pcolors = lpbmi.bmiColors) { fixed(byte *ppal = aj) { Gdi32.RGBQUAD * prgb = (Gdi32.RGBQUAD *)pcolors; Gdi32.PALETTEENTRY *lppe = (Gdi32.PALETTEENTRY *)ppal; // Convert the palette entries to RGB quad entries for (i = 0; i < (int)iColors; i++) { prgb[i].rgbRed = lppe[i].peRed; prgb[i].rgbBlue = lppe[i].peBlue; prgb[i].rgbGreen = lppe[i].peGreen; } } } } // Allocate memory to hold the bitmap bits long bitsPerScanLine = bmp.bmBitsPixel * (long)bmp.bmWidth; long bytesPerScanLine = (bitsPerScanLine + 7) / 8; long totalBytesReqd = bytesPerScanLine * bmp.bmHeight; byte[] lpBits = new byte[totalBytesReqd]; // Get the bitmap bits int diRet = SafeNativeMethods.GetDIBits(hdcSrc, hBitmap, 0, bmp.bmHeight, lpBits, ref lpbmi, NativeMethods.DIB_RGB_COLORS); if (diRet == 0) { return(false); } // Set the destination coordiates depending on whether stretch-to-fit was chosen int xDest, yDest, cxDest, cyDest; if (bStretch) { xDest = rect.left; yDest = rect.top; cxDest = rect.right - rect.left; cyDest = rect.bottom - rect.top; } else { xDest = rect.left; yDest = rect.top; cxDest = bmp.bmWidth; cyDest = bmp.bmHeight; } // Paint the bitmap int iRet = SafeNativeMethods.StretchDIBits(hdcDest, xDest, yDest, cxDest, cyDest, 0, 0, bmp.bmWidth, bmp.bmHeight, lpBits, ref lpbmi, NativeMethods.DIB_RGB_COLORS, NativeMethods.SRCCOPY); if (iRet == NativeMethods.GDI_ERROR) { return(false); } } finally { Gdi32.DeleteObject(hNullBitmap); } return(true); }
/// <summary> /// Gets the DPI awareness. /// </summary> /// <returns>The thread's/process' current HighDpi mode</returns> internal static HighDpiMode GetWinformsApplicationDpiAwareness() { // For Windows 10 RS2 and above if (ApiHelper.IsApiAvailable(ExternDll.User32, nameof(CommonUnsafeNativeMethods.GetThreadDpiAwarenessContext))) { DpiAwarenessContext dpiAwareness = CommonUnsafeNativeMethods.GetThreadDpiAwarenessContext(); if (CommonUnsafeNativeMethods.TryFindDpiAwarenessContextsEqual(dpiAwareness, DpiAwarenessContext.DPI_AWARENESS_CONTEXT_SYSTEM_AWARE)) { return(HighDpiMode.SystemAware); } if (CommonUnsafeNativeMethods.TryFindDpiAwarenessContextsEqual(dpiAwareness, DpiAwarenessContext.DPI_AWARENESS_CONTEXT_UNAWARE)) { return(HighDpiMode.DpiUnaware); } if (CommonUnsafeNativeMethods.TryFindDpiAwarenessContextsEqual(dpiAwareness, DpiAwarenessContext.DPI_AWARENESS_CONTEXT_PER_MONITOR_AWARE_V2)) { return(HighDpiMode.PerMonitorV2); } if (CommonUnsafeNativeMethods.TryFindDpiAwarenessContextsEqual(dpiAwareness, DpiAwarenessContext.DPI_AWARENESS_CONTEXT_PER_MONITOR_AWARE)) { return(HighDpiMode.PerMonitor); } if (CommonUnsafeNativeMethods.TryFindDpiAwarenessContextsEqual(dpiAwareness, DpiAwarenessContext.DPI_AWARENESS_CONTEXT_UNAWARE_GDISCALED)) { return(HighDpiMode.DpiUnawareGdiScaled); } } // For operating systems windows 8.1 to Windows 10 redstone 1 version. else if (ApiHelper.IsApiAvailable(ExternDll.ShCore, nameof(SafeNativeMethods.GetProcessDpiAwareness))) { CAPS.PROCESS_DPI_AWARENESS processDpiAwareness; SafeNativeMethods.GetProcessDpiAwareness(IntPtr.Zero, out processDpiAwareness); switch (processDpiAwareness) { case CAPS.PROCESS_DPI_AWARENESS.PROCESS_DPI_UNAWARE: return(HighDpiMode.DpiUnaware); case CAPS.PROCESS_DPI_AWARENESS.PROCESS_SYSTEM_DPI_AWARE: return(HighDpiMode.SystemAware); case CAPS.PROCESS_DPI_AWARENESS.PROCESS_PER_MONITOR_DPI_AWARE: return(HighDpiMode.PerMonitor); } } // For operating systems windows 7 to windows 8 else if (ApiHelper.IsApiAvailable(ExternDll.User32, nameof(SafeNativeMethods.IsProcessDPIAware))) { return(SafeNativeMethods.IsProcessDPIAware() ? HighDpiMode.SystemAware : HighDpiMode.DpiUnaware); } // We should never get here, except someone ported this with force to < Windows 7. return(HighDpiMode.DpiUnaware); }
/// <summary> /// Sets the DPI awareness. If not available on the current OS, it falls back to the next possible. /// </summary> /// <returns>true/false - If the process DPI awareness is successfully set, returns true. Otherwise false.</returns> internal static bool SetWinformsApplicationDpiAwareness(HighDpiMode highDpiMode) { CAPS.PROCESS_DPI_AWARENESS dpiFlag = CAPS.PROCESS_DPI_AWARENESS.PROCESS_DPI_UNINITIALIZED; if (OsVersion.IsWindows10_1703OrGreater) { // SetProcessDpiAwarenessContext needs Windows 10 RS2 and above int rs2AndAboveDpiFlag; switch (highDpiMode) { case HighDpiMode.SystemAware: rs2AndAboveDpiFlag = CAPS.DPI_AWARENESS_CONTEXT_SYSTEM_AWARE; break; case HighDpiMode.PerMonitor: rs2AndAboveDpiFlag = CAPS.DPI_AWARENESS_CONTEXT_PER_MONITOR_AWARE; break; case HighDpiMode.PerMonitorV2: // Necessary for RS1, since this SetProcessDpiAwarenessContext IS available here. rs2AndAboveDpiFlag = SafeNativeMethods.IsValidDpiAwarenessContext(CAPS.DPI_AWARENESS_CONTEXT_PER_MONITOR_AWARE_V2) ? CAPS.DPI_AWARENESS_CONTEXT_PER_MONITOR_AWARE_V2 : CAPS.DPI_AWARENESS_CONTEXT_SYSTEM_AWARE; break; case HighDpiMode.DpiUnawareGdiScaled: // Let's make sure, we do not try to set a value which has been introduced in later Windows releases. rs2AndAboveDpiFlag = SafeNativeMethods.IsValidDpiAwarenessContext(CAPS.DPI_AWARENESS_CONTEXT_UNAWARE_GDISCALED) ? CAPS.DPI_AWARENESS_CONTEXT_UNAWARE_GDISCALED : CAPS.DPI_AWARENESS_CONTEXT_UNAWARE; break; default: rs2AndAboveDpiFlag = CAPS.DPI_AWARENESS_CONTEXT_UNAWARE; break; } return(SafeNativeMethods.SetProcessDpiAwarenessContext(rs2AndAboveDpiFlag)); } else if (OsVersion.IsWindows8_1OrGreater) { // 8.1 introduced SetProcessDpiAwareness switch (highDpiMode) { case HighDpiMode.DpiUnaware: case HighDpiMode.DpiUnawareGdiScaled: dpiFlag = CAPS.PROCESS_DPI_AWARENESS.PROCESS_DPI_UNAWARE; break; case HighDpiMode.SystemAware: dpiFlag = CAPS.PROCESS_DPI_AWARENESS.PROCESS_SYSTEM_DPI_AWARE; break; case HighDpiMode.PerMonitor: case HighDpiMode.PerMonitorV2: dpiFlag = CAPS.PROCESS_DPI_AWARENESS.PROCESS_PER_MONITOR_DPI_AWARE; break; default: dpiFlag = CAPS.PROCESS_DPI_AWARENESS.PROCESS_SYSTEM_DPI_AWARE; break; } return(SafeNativeMethods.SetProcessDpiAwareness(dpiFlag) == CAPS.S_OK); } else { // Vista or higher has SetProcessDPIAware switch (highDpiMode) { case HighDpiMode.DpiUnaware: case HighDpiMode.DpiUnawareGdiScaled: // We can return, there is nothing to set if we assume we're already in DpiUnaware. return(true); case HighDpiMode.SystemAware: case HighDpiMode.PerMonitor: case HighDpiMode.PerMonitorV2: dpiFlag = CAPS.PROCESS_DPI_AWARENESS.PROCESS_SYSTEM_DPI_AWARE; break; } if (dpiFlag == CAPS.PROCESS_DPI_AWARENESS.PROCESS_SYSTEM_DPI_AWARE) { return(SafeNativeMethods.SetProcessDPIAware()); } } return(false); }
/// <include file='doc\StringSorter.uex' path='docs/doc[@for="StringSorter.Compare1"]/*' /> /// <devdoc> /// Compares two strings using the default locale with the given set of /// string comparison flags. /// </devdoc> public static int Compare(string s1, string s2, int options) { return(Compare(SafeNativeMethods.GetThreadLocale(), s1, s2, options)); }
public DCMapping(HandleRef hDC, Rectangle bounds) { if (hDC.Handle == IntPtr.Zero) { throw new ArgumentNullException("hDC"); } bool success; NativeMethods.POINT viewportOrg = new NativeMethods.POINT(); HandleRef hOriginalClippingRegion = NativeMethods.NullHandleRef; NativeMethods.RegionFlags originalRegionType = NativeMethods.RegionFlags.NULLREGION; this.translatedBounds = bounds; this.graphics = null; this.dc = DeviceContext.FromHdc(hDC.Handle); this.dc.SaveHdc(); // Retrieve the x-coordinates and y-coordinates of the viewport origin for the specified device context. success = SafeNativeMethods.GetViewportOrgEx(hDC, viewportOrg); Debug.Assert(success, "GetViewportOrgEx() failed."); // Create a new rectangular clipping region based off of the bounds specified, shifted over by the x & y specified in the viewport origin. HandleRef hClippingRegion = new HandleRef(null, SafeNativeMethods.CreateRectRgn(viewportOrg.x + bounds.Left, viewportOrg.y + bounds.Top, viewportOrg.x + bounds.Right, viewportOrg.y + bounds.Bottom)); Debug.Assert(hClippingRegion.Handle != IntPtr.Zero, "CreateRectRgn() failed."); try { // Create an empty region oriented at 0,0 so we can populate it with the original clipping region of the hDC passed in. hOriginalClippingRegion = new HandleRef(this, SafeNativeMethods.CreateRectRgn(0, 0, 0, 0)); Debug.Assert(hOriginalClippingRegion.Handle != IntPtr.Zero, "CreateRectRgn() failed."); // Get the clipping region from the hDC: result = {-1 = error, 0 = no region, 1 = success} per MSDN int result = SafeNativeMethods.GetClipRgn(hDC, hOriginalClippingRegion); Debug.Assert(result != -1, "GetClipRgn() failed."); // Shift the viewpoint origint by coordinates specified in "bounds". NativeMethods.POINT lastViewPort = new NativeMethods.POINT(); success = SafeNativeMethods.SetViewportOrgEx(hDC, viewportOrg.x + bounds.Left, viewportOrg.y + bounds.Top, lastViewPort); Debug.Assert(success, "SetViewportOrgEx() failed."); if (result != 0) { // Get the origninal clipping region so we can determine its type (we'll check later if we've restored the region back properly.) NativeMethods.RECT originalClipRect = new NativeMethods.RECT(); originalRegionType = (NativeMethods.RegionFlags)SafeNativeMethods.GetRgnBox(hOriginalClippingRegion, ref originalClipRect); Debug.Assert(originalRegionType != NativeMethods.RegionFlags.ERROR, "ERROR returned from SelectClipRgn while selecting the original clipping region.."); if (originalRegionType == NativeMethods.RegionFlags.SIMPLEREGION) { // Find the intersection of our clipping region and the current clipping region (our parent's) // Returns a NULLREGION, the two didn't intersect. // Returns a SIMPLEREGION, the two intersected // Resulting region (stuff that was in hOriginalClippingRegion AND hClippingRegion is placed in hClippingRegion NativeMethods.RegionFlags combineResult = (NativeMethods.RegionFlags)SafeNativeMethods.CombineRgn(hClippingRegion, hClippingRegion, hOriginalClippingRegion, NativeMethods.RGN_AND); Debug.Assert((combineResult == NativeMethods.RegionFlags.SIMPLEREGION) || (combineResult == NativeMethods.RegionFlags.NULLREGION), "SIMPLEREGION or NULLREGION expected."); } } else { // If there was no clipping region, then the result is a simple region. // We don't need to keep track of the original now, since it is empty. SafeNativeMethods.DeleteObject(hOriginalClippingRegion); hOriginalClippingRegion = new HandleRef(null, IntPtr.Zero); originalRegionType = NativeMethods.RegionFlags.SIMPLEREGION; } // Select the new clipping region; make sure it's a SIMPLEREGION or NULLREGION NativeMethods.RegionFlags selectResult = (NativeMethods.RegionFlags)SafeNativeMethods.SelectClipRgn(hDC, hClippingRegion); Debug.Assert((selectResult == NativeMethods.RegionFlags.SIMPLEREGION || selectResult == NativeMethods.RegionFlags.NULLREGION), "SIMPLEREGION or NULLLREGION expected."); } catch (Exception ex) { if (ClientUtils.IsSecurityOrCriticalException(ex)) { throw; } this.dc.RestoreHdc(); this.dc.Dispose(); } finally { // Delete the new clipping region, as the clipping region for the HDC is now set // to this rectangle. Hold on to hOriginalClippingRegion, as we'll need to restore // it when this object is disposed. success = SafeNativeMethods.DeleteObject(hClippingRegion); Debug.Assert(success, "DeleteObject(hClippingRegion) failed."); if (hOriginalClippingRegion.Handle != IntPtr.Zero) { success = SafeNativeMethods.DeleteObject(hOriginalClippingRegion); Debug.Assert(success, "DeleteObject(hOriginalClippingRegion) failed."); } } }
/// <include file='doc\FontDialog.uex' path='docs/doc[@for="FontDialog.RunDialog"]/*' /> /// <internalonly/> /// <devdoc> /// <para> /// The actual implementation of running the dialog. Inheriting classes /// should override this if they want to add more functionality, and call /// base.runDialog() if necessary /// /// </para> /// </devdoc> protected override bool RunDialog(IntPtr hWndOwner) { NativeMethods.WndProc hookProcPtr = new NativeMethods.WndProc(this.HookProc); NativeMethods.CHOOSEFONT cf = new NativeMethods.CHOOSEFONT(); IntPtr screenDC = UnsafeNativeMethods.GetDC(NativeMethods.NullHandleRef); NativeMethods.LOGFONT lf = new NativeMethods.LOGFONT(); Graphics graphics = Graphics.FromHdcInternal(screenDC); IntSecurity.ObjectFromWin32Handle.Assert(); try { Font.ToLogFont(lf, graphics); } finally { graphics.Dispose(); CodeAccessPermission.RevertAssert(); } UnsafeNativeMethods.ReleaseDC(NativeMethods.NullHandleRef, new HandleRef(null, screenDC)); IntPtr logFontPtr = IntPtr.Zero; try { logFontPtr = Marshal.AllocCoTaskMem(Marshal.SizeOf(typeof(NativeMethods.LOGFONT))); Marshal.StructureToPtr(lf, logFontPtr, false); cf.lStructSize = Marshal.SizeOf(typeof(NativeMethods.CHOOSEFONT)); cf.hwndOwner = hWndOwner; cf.hDC = IntPtr.Zero; cf.lpLogFont = logFontPtr; cf.Flags = Options | NativeMethods.CF_INITTOLOGFONTSTRUCT | NativeMethods.CF_ENABLEHOOK; if (minSize > 0 || maxSize > 0) { cf.Flags |= NativeMethods.CF_LIMITSIZE; } //if ShowColor=true then try to draw the sample text in color, //if ShowEffects=false then we will draw the sample text in black regardless. //(limitation of windows control) // if (ShowColor || ShowEffects) { cf.rgbColors = ColorTranslator.ToWin32(color); } else { cf.rgbColors = ColorTranslator.ToWin32(Color.Black); } cf.lpfnHook = hookProcPtr; cf.hInstance = UnsafeNativeMethods.GetModuleHandle(null); cf.nSizeMin = minSize; if (maxSize == 0) { cf.nSizeMax = Int32.MaxValue; } else { cf.nSizeMax = maxSize; } Debug.Assert(cf.nSizeMin <= cf.nSizeMax, "min and max font sizes are the wrong way around"); if (!SafeNativeMethods.ChooseFont(cf)) { return(false); } NativeMethods.LOGFONT lfReturned = null; lfReturned = (NativeMethods.LOGFONT)UnsafeNativeMethods.PtrToStructure(logFontPtr, typeof(NativeMethods.LOGFONT)); if (lfReturned.lfFaceName != null && lfReturned.lfFaceName.Length > 0) { lf = lfReturned; UpdateFont(lf); UpdateColor(cf.rgbColors); } return(true); } finally { if (logFontPtr != IntPtr.Zero) { Marshal.FreeCoTaskMem(logFontPtr); } } }
// <include file='doc\TextBox.uex' path='docs/doc[@for="TextBox.ResetAutoComplete"]/*' /> /// <devdoc> /// Resets the AutoComplete mode in TextBox. /// </devdoc> private void ResetAutoComplete(bool force) { if ((AutoCompleteMode != AutoCompleteMode.None || force) && IsHandleCreated) { int mode = (int)AutoCompleteSource.AllSystemSources | NativeMethods.AUTOSUGGEST_OFF | NativeMethods.AUTOAPPEND_OFF; SafeNativeMethods.SHAutoComplete(new HandleRef(this, Handle) , mode); } }