private bool EvalWindows(IntPtr hWnd, IntPtr lParam) { if (!NativeMethods.IsWindowVisible(hWnd)) { return(true); } foreach (KeyValuePair <IntPtr, Rectangle> window in windows) { if (window.Key == hWnd) { return(true); } } uint processId; NativeMethods.GetWindowThreadProcessId(hWnd, out processId); if (this.processId == processId) { Rectangle rect = CaptureHelpers.GetWindowRectangle(hWnd); windows.Enqueue(new KeyValuePair <IntPtr, Rectangle>(hWnd, rect)); } return(true); }
/// <summary>Captures a screenshot of a window using Windows GDI</summary> /// <param name="handle">handle of the window to capture</param> /// <returns>the captured window image</returns> private static Image CaptureWithGDI(Workflow wfgdi, IntPtr handle, out Rectangle windowRect) { DebugHelper.WriteLine("Capturing with GDI"); windowRect = CaptureHelpers.GetWindowRectangle(handle); Image windowImageGdi = null; if (wfgdi.ActiveWindowClearBackground) { windowImageGdi = CaptureWindowWithGDI(wfgdi, handle, out windowRect); } if (windowImageGdi == null) { using (new Freeze(wfgdi, handle)) { windowImageGdi = Screenshot.CaptureRectangleNative(windowRect); } Image result = RemoveCorners(handle, windowImageGdi, null, windowRect); if (result != null) { windowImageGdi = result; } } return(windowImageGdi); }
public static Image CaptureWindow(IntPtr handle) { if (handle.ToInt32() > 0) { Rectangle rect = CaptureHelpers.GetWindowRectangle(handle); return(CaptureRectangle(rect)); } return(null); }
private bool CheckHandle(IntPtr handle, bool isWindow) { if (handle == IgnoreHandle || !NativeMethods.IsWindowVisible(handle) || (isWindow && NativeMethods.IsWindowCloaked(handle))) { return(true); } SimpleWindowInfo windowInfo = new SimpleWindowInfo(handle); if (isWindow) { windowInfo.IsWindow = true; windowInfo.Rectangle = CaptureHelpers.GetWindowRectangle(handle); } else { windowInfo.Rectangle = NativeMethods.GetWindowRect(handle); } if (!windowInfo.Rectangle.IsValid()) { return(true); } if (IncludeChildWindows && !parentHandles.Contains(handle)) { parentHandles.Add(handle); EnumWindowsProc ewp = EvalControl; NativeMethods.EnumChildWindows(handle, ewp, IntPtr.Zero); } if (isWindow) { Rectangle clientRect = NativeMethods.GetClientRect(handle); if (clientRect.IsValid() && clientRect != windowInfo.Rectangle) { windows.Add(new SimpleWindowInfo(handle, clientRect)); } } windows.Add(windowInfo); return(true); }
private bool CheckHandle(IntPtr handle, bool isWindow) { if (handle == IgnoreHandle || !NativeMethods.IsWindowVisible(handle)) { return(true); } Rectangle rect; if (isWindow) { rect = CaptureHelpers.GetWindowRectangle(handle); } else { rect = NativeMethods.GetWindowRect(handle); } if (!rect.IsValid()) { return(true); } if (IncludeChildWindows) { NativeMethods.EnumWindowsProc ewp = EvalControl; NativeMethods.EnumChildWindows(handle, ewp, IntPtr.Zero); } if (isWindow) { Rectangle clientRect = NativeMethods.GetClientRect(handle); if (clientRect.IsValid()) { rectangles.Add(clientRect); } } rectangles.Add(rect); return(true); }
private void ActiveWindowRegion(TaskSettings taskSettings) { IntPtr handle = NativeMethods.GetForegroundWindow(); if (handle.ToInt32() > 0) { if (taskSettings.CaptureSettings.CaptureClientArea) { captureRectangle = NativeMethods.GetClientRect(handle); } else { captureRectangle = CaptureHelpers.GetWindowRectangle(handle); } } else { SelectRegion(); } }
public Rectangle CalculateWindowRectangle() { if (handle.ToInt32() > 0) { rectangle = CaptureHelpers.GetWindowRectangle(handle); NativeMethods.GetWindowThreadProcessId(handle, out processId); string processName = Process.GetProcessById((int)processId).ProcessName; if (!Engine.ConfigWorkflow.ActiveWindowTryCaptureChildren || processName == "explorer") { windows.Enqueue(new KeyValuePair <IntPtr, Rectangle>(handle, rectangle)); } else { NativeMethods.EnumWindowsProc ewpWindows = new NativeMethods.EnumWindowsProc(EvalWindows); NativeMethods.EnumWindows(ewpWindows, IntPtr.Zero); } foreach (KeyValuePair <IntPtr, Rectangle> window in windows) { rectangle = rectangle.Merge(window.Value); NativeMethods.EnumWindowsProc ewpControls = new NativeMethods.EnumWindowsProc(EvalControls); NativeMethods.EnumChildWindows(window.Key, ewpControls, IntPtr.Zero); } foreach (KeyValuePair <IntPtr, Rectangle> control in controls) { rectangle = rectangle.Merge(control.Value); } rectangle.Intersect(bounds); //TestRectangle(rectangle); return(rectangle); } return(Rectangle.Empty); }
private bool EvalControls(IntPtr hWnd, IntPtr lParam) { if (!NativeMethods.IsWindowVisible(hWnd)) { return(true); } foreach (KeyValuePair <IntPtr, Rectangle> control in controls) { if (control.Key == hWnd) { return(true); } } Rectangle rect = CaptureHelpers.GetWindowRectangle(hWnd); controls.Enqueue(new KeyValuePair <IntPtr, Rectangle>(hWnd, rect)); return(true); }
public static Image CaptureWindow(IntPtr handle) { if (handle.ToInt32() > 0) { Rectangle rect; if (CaptureClientArea) { rect = NativeMethods.GetClientRect(handle); } else { rect = CaptureHelpers.GetWindowRectangle(handle); } bool isTaskbarHide = false; try { if (AutoHideTaskbar) { isTaskbarHide = NativeMethods.SetTaskbarVisibilityIfIntersect(false, rect); } return(CaptureRectangle(rect)); } finally { if (isTaskbarHide) { NativeMethods.SetTaskbarVisibility(true); } } } return(null); }
public Image CaptureWindowTransparent(IntPtr handle) { if (handle.ToInt32() > 0) { Rectangle rect = CaptureHelpers.GetWindowRectangle(handle); if (CaptureShadow && !NativeMethods.IsZoomed(handle) && NativeMethods.IsDWMEnabled()) { rect.Inflate(ShadowOffset, ShadowOffset); Rectangle intersectBounds = Screen.AllScreens.Select(x => x.Bounds).Where(x => x.IntersectsWith(rect)).Combine(); rect.Intersect(intersectBounds); } Bitmap whiteBackground = null, blackBackground = null, whiteBackground2 = null; CursorData cursorData = null; bool isTransparent = false, isTaskbarHide = false; try { if (AutoHideTaskbar) { isTaskbarHide = NativeMethods.SetTaskbarVisibilityIfIntersect(false, rect); } if (CaptureCursor) { try { cursorData = new CursorData(); } catch (Exception e) { DebugHelper.WriteException(e, "Cursor capture failed."); } } using (Form form = new Form()) { form.BackColor = Color.White; form.FormBorderStyle = FormBorderStyle.None; form.ShowInTaskbar = false; form.StartPosition = FormStartPosition.Manual; form.Location = new Point(rect.X, rect.Y); form.Size = new Size(rect.Width, rect.Height); NativeMethods.ShowWindow(form.Handle, (int)WindowShowStyle.ShowNoActivate); if (!NativeMethods.SetWindowPos(form.Handle, handle, 0, 0, 0, 0, SetWindowPosFlags.SWP_NOMOVE | SetWindowPosFlags.SWP_NOSIZE | SetWindowPosFlags.SWP_NOACTIVATE)) { form.Close(); DebugHelper.WriteLine("Transparent capture failed. Reason: SetWindowPos fail."); return(CaptureWindow(handle)); } Thread.Sleep(10); Application.DoEvents(); whiteBackground = (Bitmap)CaptureRectangleNative(rect); form.BackColor = Color.Black; Application.DoEvents(); blackBackground = (Bitmap)CaptureRectangleNative(rect); form.BackColor = Color.White; Application.DoEvents(); whiteBackground2 = (Bitmap)CaptureRectangleNative(rect); form.Close(); } Bitmap transparentImage; if (ImageHelpers.IsImagesEqual(whiteBackground, whiteBackground2)) { transparentImage = CreateTransparentImage(whiteBackground, blackBackground); isTransparent = true; } else { DebugHelper.WriteLine("Transparent capture failed. Reason: Images not equal."); transparentImage = whiteBackground2; } if (cursorData != null) { cursorData.DrawCursor(transparentImage, rect.Location); } if (isTransparent) { transparentImage = ImageHelpers.AutoCropImage(transparentImage); if (!CaptureShadow) { TrimShadow(transparentImage); } } return(transparentImage); } finally { if (isTaskbarHide) { NativeMethods.SetTaskbarVisibility(true); } if (whiteBackground != null) { whiteBackground.Dispose(); } if (blackBackground != null) { blackBackground.Dispose(); } if (isTransparent && whiteBackground2 != null) { whiteBackground2.Dispose(); } } } return(null); }
/// <summary>Captures a screenshot of a window using the Windows DWM</summary> /// <param name="handle">handle of the window to capture</param> /// <returns>the captured window image with or without cursor</returns> public static Image CaptureWithDWM(Workflow wfdwm, IntPtr handle) { DebugHelper.WriteLine("Capturing with DWM"); Image windowImageDwm = null; Bitmap redBGImage = null; Rectangle windowRect = CaptureHelpers.GetWindowRectangle(handle); if (windowRect.Width == 0) { System.Threading.Thread.Sleep(250); windowRect = CaptureHelpers.GetWindowRectangle(handle); // try again } if (windowRect.Width > 0 && NativeMethods.IsDWMEnabled()) { if (wfdwm.ActiveWindowDwmUseCustomBackground) { windowImageDwm = CaptureWindowWithDWM(handle, windowRect, out redBGImage, wfdwm.ActiveWindowDwmBackColor); } else if (wfdwm.ActiveWindowClearBackground) { windowImageDwm = CaptureWindowWithDWM(handle, windowRect, out redBGImage, Color.White); } } if (windowImageDwm == null) { DebugHelper.WriteLine("Standard capture (no transparency)"); windowImageDwm = Screenshot.CaptureRectangleNative(windowRect); } Image result = RemoveCorners(handle, windowImageDwm, redBGImage, windowRect); if (result != null) { windowImageDwm = result; } if (wfdwm.ActiveWindowIncludeShadows) { // Draw shadow manually to be able to have shadows in every case windowImageDwm = HelpersLib.GraphicsHelper.Core.AddBorderShadow((Bitmap)windowImageDwm, true); if (wfdwm.DrawCursor) { Point shadowOffset = HelpersLib.GraphicsHelper.Core.ShadowOffset; #if DEBUG DebugHelper.WriteLine("Fixed cursor position (before): " + windowRect.ToString()); #endif windowRect.X -= shadowOffset.X; windowRect.Y -= shadowOffset.Y; #if DEBUG DebugHelper.WriteLine("Fixed cursor position (after): " + windowRect.ToString()); #endif } } if (wfdwm.DrawCursor) { CaptureHelpers.DrawCursorToImage(windowImageDwm, windowRect.Location); } return(windowImageDwm); }
/// <summary>Captures a screenshot of a window using Windows GDI. Captures transparency.</summary> /// <param name="handle">handle of the window to capture</param> /// <returns>the captured window image</returns> private static Image CaptureWindowWithGDI(Workflow wfgdi, IntPtr handle, out Rectangle windowRect) { Image windowImageGdi = null; Bitmap whiteBGImage = null, blackBGImage = null, white2BGImage = null; if (wfgdi.ActiveWindowTryCaptureChildren) { windowRect = new WindowRectangle(handle).CalculateWindowRectangle(); } else { windowRect = CaptureHelpers.GetWindowRectangle(handle); } try { using (new Freeze(wfgdi, handle)) using (Form form = new Form()) { form.BackColor = Color.White; form.FormBorderStyle = FormBorderStyle.None; form.ShowInTaskbar = false; int offset = wfgdi.ActiveWindowIncludeShadows && !NativeMethods.IsWindowMaximized(handle) ? 20 : 0; windowRect.Inflate(offset, offset); windowRect.Intersect(CaptureHelpers.GetScreenBounds()); NativeMethods.ShowWindow(form.Handle, (int)WindowShowStyle.ShowNormalNoActivate); NativeMethods.SetWindowPos(form.Handle, handle, windowRect.X, windowRect.Y, windowRect.Width, windowRect.Height, NativeMethods.SWP_NOACTIVATE); Application.DoEvents(); whiteBGImage = (Bitmap)Screenshot.CaptureRectangleNative2(windowRect); form.BackColor = Color.Black; Application.DoEvents(); blackBGImage = (Bitmap)Screenshot.CaptureRectangleNative2(windowRect); if (!wfgdi.ActiveWindowGDIFreezeWindow) { form.BackColor = Color.White; Application.DoEvents(); white2BGImage = (Bitmap)Screenshot.CaptureRectangleNative2(windowRect); } } if (wfgdi.ActiveWindowGDIFreezeWindow || whiteBGImage.AreBitmapsEqual(white2BGImage)) { windowImageGdi = HelpersLib.GraphicsHelper.Core.ComputeOriginal(whiteBGImage, blackBGImage); } else { windowImageGdi = (Image)whiteBGImage.Clone(); } } finally { if (whiteBGImage != null) { whiteBGImage.Dispose(); } if (blackBGImage != null) { blackBGImage.Dispose(); } if (white2BGImage != null) { white2BGImage.Dispose(); } } if (windowImageGdi != null) { Rectangle windowRectCropped = HelpersLib.GraphicsHelper.Core.GetCroppedArea((Bitmap)windowImageGdi); windowImageGdi = CaptureHelpers.CropImage(windowImageGdi, windowRectCropped); if (wfgdi.DrawCursor) { #if DEBUG DebugHelper.WriteLine("Fixed cursor position (before): " + windowRect.ToString()); #endif windowRect.X += windowRectCropped.X; windowRect.Y += windowRectCropped.Y; #if DEBUG DebugHelper.WriteLine("Fixed cursor position (after): " + windowRect.ToString()); #endif } } return(windowImageGdi); }
/// <summary> /// Make a full-size thumbnail of the captured window on a new topmost form, and capture /// this new form with a black and then white background. Then compute the transparency by /// difference between the black and white versions. /// This method has these advantages: /// - the full form is captured even if it is obscured on the Windows desktop /// - there is no problem with unpredictable Z-order anymore (the background and /// the window to capture are drawn on the same window) /// </summary> /// <param name="handle">handle of the window to capture</param> /// <param name="windowRect">the bounds of the window</param> /// <param name="redBGImage">the window captured with a red background</param> /// <param name="captureRedBGImage">whether to do the capture of the window with a red background</param> /// <returns>the captured window image</returns> private static Image CaptureWindowWithDWM(IntPtr handle, Rectangle windowRect, out Bitmap redBGImage, Color backColor) { Image windowImage = null; redBGImage = null; if (backColor != Color.White) { backColor = Color.FromArgb(255, backColor.R, backColor.G, backColor.B); } using (Form form = new Form()) { form.StartPosition = FormStartPosition.Manual; form.FormBorderStyle = FormBorderStyle.None; form.ShowInTaskbar = false; form.BackColor = backColor; form.TopMost = true; form.Bounds = CaptureHelpers.GetWindowRectangle(handle, false); IntPtr thumb; NativeMethods.DwmRegisterThumbnail(form.Handle, handle, out thumb); SIZE size; NativeMethods.DwmQueryThumbnailSourceSize(thumb, out size); #if DEBUG DebugHelper.WriteLine("Rectangle Size: " + windowRect.ToString()); DebugHelper.WriteLine("Window Size: " + size.ToString()); #endif if (size.Width <= 0 || size.Height <= 0) { return(null); } DWM_THUMBNAIL_PROPERTIES props = new DWM_THUMBNAIL_PROPERTIES(); props.dwFlags = NativeMethods.DWM_TNP_VISIBLE | NativeMethods.DWM_TNP_RECTDESTINATION | NativeMethods.DWM_TNP_OPACITY; props.fVisible = true; props.opacity = (byte)255; props.rcDestination = new RECT(0, 0, size.Width, size.Height); NativeMethods.DwmUpdateThumbnailProperties(thumb, ref props); form.Show(); System.Threading.Thread.Sleep(250); if (form.BackColor != Color.White) { // no need for transparency; user has requested custom background color NativeMethods.ActivateWindowRepeat(form.Handle, 250); windowImage = Screenshot.CaptureRectangleNative(windowRect) as Bitmap; } else if (form.BackColor == Color.White) { // transparent capture NativeMethods.ActivateWindowRepeat(handle, 250); Bitmap whiteBGImage = Screenshot.CaptureRectangleNative(windowRect) as Bitmap; form.BackColor = Color.Black; form.Refresh(); NativeMethods.ActivateWindowRepeat(handle, 250); Bitmap blackBGImage = Screenshot.CaptureRectangleNative(windowRect) as Bitmap; // Capture rounded corners with except for Windows 8 if (ZAppHelper.IsWindows8()) { form.BackColor = Color.Red; form.Refresh(); NativeMethods.ActivateWindowRepeat(handle, 250); redBGImage = Screenshot.CaptureRectangleNative(windowRect) as Bitmap; } form.BackColor = Color.White; form.Refresh(); NativeMethods.ActivateWindowRepeat(handle, 250); Bitmap whiteBGImage2 = Screenshot.CaptureRectangleNative(windowRect) as Bitmap; // Don't do transparency calculation if an animated picture is detected if (whiteBGImage.AreBitmapsEqual(whiteBGImage2)) { windowImage = HelpersLib.GraphicsHelper.Core.ComputeOriginal(whiteBGImage, blackBGImage); } else { DebugHelper.WriteLine("Detected animated image => cannot compute transparency"); form.Close(); Application.DoEvents(); Image result = new Bitmap(whiteBGImage.Width, whiteBGImage.Height, PixelFormat.Format32bppArgb); using (Graphics g = Graphics.FromImage(result)) { // Redraw the image on a black background to avoid transparent pixels artifacts g.Clear(Color.Black); g.DrawImage(whiteBGImage, 0, 0); } windowImage = result; } blackBGImage.Dispose(); whiteBGImage.Dispose(); whiteBGImage2.Dispose(); } NativeMethods.DwmUnregisterThumbnail(thumb); } return(windowImage); }
public static Image CaptureWindowTransparent(IntPtr handle) { if (handle.ToInt32() > 0) { Rectangle rect = CaptureHelpers.GetWindowRectangle(handle); Bitmap whiteBackground = null, blackBackground = null, whiteBackground2 = null; MyCursor cursor = null; bool isTransparent = false; try { if (DrawCursor) { cursor = NativeMethods.CaptureCursor(); } using (Form form = new Form()) { form.BackColor = Color.White; form.FormBorderStyle = FormBorderStyle.None; form.ShowInTaskbar = false; if (CaptureShadow && !NativeMethods.IsZoomed(handle) && NativeMethods.IsDWMEnabled()) { const int offset = 20; rect.Inflate(offset, offset); rect.Intersect(CaptureHelpers.GetScreenBounds()); } NativeMethods.ShowWindow(form.Handle, (int)WindowShowStyle.ShowNormalNoActivate); if (!NativeMethods.SetWindowPos(form.Handle, handle, rect.X, rect.Y, rect.Width, rect.Height, NativeMethods.SWP_NOACTIVATE)) { form.Close(); DebugHelper.WriteLine("Transparent capture failed. Reason: SetWindowPos fail."); return(CaptureWindow(handle)); } Thread.Sleep(10); Application.DoEvents(); whiteBackground = (Bitmap)Screenshot.CaptureRectangleNative(rect); form.BackColor = Color.Black; Application.DoEvents(); blackBackground = (Bitmap)Screenshot.CaptureRectangleNative(rect); form.BackColor = Color.White; Application.DoEvents(); whiteBackground2 = (Bitmap)Screenshot.CaptureRectangleNative(rect); form.Close(); } Bitmap transparentImage; if (IsImagesEqual(whiteBackground, whiteBackground2)) { transparentImage = CreateTransparentImage(whiteBackground, blackBackground); isTransparent = true; } else { DebugHelper.WriteLine("Transparent capture failed. Reason: Images not equal."); transparentImage = whiteBackground2; } if (cursor != null) { Point cursorOffset = CaptureHelpers.FixScreenCoordinates(rect.Location); CaptureHelpers.DrawCursorToImage(cursor, transparentImage, cursorOffset); } if (isTransparent) { transparentImage = TrimTransparent(transparentImage); if (!CaptureShadow) { TrimShadow(transparentImage); } } return(transparentImage); } finally { if (whiteBackground != null) { whiteBackground.Dispose(); } if (blackBackground != null) { blackBackground.Dispose(); } if (isTransparent && whiteBackground2 != null) { whiteBackground2.Dispose(); } if (cursor != null) { cursor.Dispose(); } } } return(null); }