Exemplo n.º 1
0
        /// <summary>
        ///  Creates a window handle for this window.
        /// </summary>
        public virtual void CreateHandle(CreateParams cp)
        {
            lock (this)
            {
                CheckReleased();
                WindowClass windowClass = WindowClass.Create(cp.ClassName, (NativeMethods.ClassStyle)cp.ClassStyle);
                lock (s_createWindowSyncObject)
                {
                    // The CLR will sometimes pump messages while we're waiting on the lock.
                    // If a message comes through (say a WM_ACTIVATE for the parent) which
                    // causes the handle to be created, we can try to create the handle twice
                    // for NativeWindow. Check the handle again to avoid this.
                    if (Handle != IntPtr.Zero)
                    {
                        return;
                    }

                    windowClass._targetWindow = this;
                    IntPtr createResult   = IntPtr.Zero;
                    int    lastWin32Error = 0;

                    // Parking window dpi awarness context need to match with dpi awarenss context of control being
                    // parented to this parkign window. Otherwise, reparenting of control will fail.
                    using (DpiHelper.EnterDpiAwarenessScope(DpiAwarenessContext))
                    {
                        IntPtr modHandle = Kernel32.GetModuleHandleW(null);

                        // Older versions of Windows AV rather than returning E_OUTOFMEMORY.
                        // Catch this and then we re-throw an out of memory error.
                        try
                        {
                            // CreateWindowEx throws if WindowText is greater than the max
                            // length of a 16 bit int (32767).
                            // If it exceeds the max, we should take the substring....
                            if (cp.Caption != null && cp.Caption.Length > short.MaxValue)
                            {
                                cp.Caption = cp.Caption.Substring(0, short.MaxValue);
                            }

                            createResult = UnsafeNativeMethods.CreateWindowEx(
                                cp.ExStyle,
                                windowClass._windowClassName,
                                cp.Caption,
                                cp.Style,
                                cp.X,
                                cp.Y,
                                cp.Width,
                                cp.Height,
                                new HandleRef(cp, cp.Parent),
                                NativeMethods.NullHandleRef,
                                new HandleRef(null, modHandle),
                                cp.Param);

                            lastWin32Error = Marshal.GetLastWin32Error();
                        }
                        catch (NullReferenceException e)
                        {
                            throw new OutOfMemoryException(SR.ErrorCreatingHandle, e);
                        }
                    }
                    windowClass._targetWindow = null;

                    Debug.WriteLineIf(CoreSwitches.PerfTrack.Enabled, "Handle created of type '" + cp.ClassName + "' with caption '" + cp.Caption + "' from NativeWindow of type '" + GetType().FullName + "'");

                    if (createResult == IntPtr.Zero)
                    {
                        throw new Win32Exception(lastWin32Error, SR.ErrorCreatingHandle);
                    }
                    _ownHandle = true;
                }
            }
        }