diff --git a/Greenshot/Destinations/PickerDestination.cs b/Greenshot/Destinations/PickerDestination.cs index ede54a4ec..f050497eb 100644 --- a/Greenshot/Destinations/PickerDestination.cs +++ b/Greenshot/Destinations/PickerDestination.cs @@ -30,6 +30,7 @@ using Greenshot.Plugin; using Greenshot.Helpers; using Greenshot.Forms; using Greenshot.IniFile; +using GreenshotPlugin.UnmanagedHelpers; namespace Greenshot.Destinations { /// @@ -84,26 +85,26 @@ namespace Greenshot.Destinations { if (clickedDestination == null) { return; } - bool isEditor = EditorDestination.DESIGNATION.Equals(clickedDestination.Designation); - // Make sure the menu is invisible, don't close it - menu.Hide(); + bool isEditor = EditorDestination.DESIGNATION.Equals(clickedDestination.Designation); + // Make sure the menu is invisible, don't close it + menu.Hide(); - // Export + // Export bool result = clickedDestination.ExportCapture(true, surface, captureDetails); - LOG.InfoFormat("Destination was {0} and result {1}", clickedDestination.Designation, result); - if (result == true) { - LOG.Info("Export success, closing menu"); - // close menu if the destination wasn't the editor - menu.Close(); + LOG.InfoFormat("Destination was {0} and result {1}", clickedDestination.Designation, result); + if (result == true) { + LOG.Info("Export success, closing menu"); + // close menu if the destination wasn't the editor + menu.Close(); - // Cleanup surface, only if the destination wasn't the editor - if (!isEditor) { - surface.Dispose(); - } - } else { - LOG.Info("Export failed, showing menu again"); - menu.Show(); - } + // Cleanup surface, only if the destination wasn't the editor + if (!isEditor) { + surface.Dispose(); + } + } else { + LOG.Info("Export failed, showing menu again"); + menu.Show(); + } } ); if (item != null) { @@ -136,6 +137,8 @@ namespace Greenshot.Destinations { } else { location.Offset(-40, -10); } + // This prevents the problem that the context menu shows in the task-bar + User32.SetForegroundWindow(MainForm.instance.notifyIcon.ContextMenuStrip.Handle); menu.Show(location); menu.Focus(); } diff --git a/Greenshot/Forms/MainForm.cs b/Greenshot/Forms/MainForm.cs index cd71cfbb4..1ce469666 100644 --- a/Greenshot/Forms/MainForm.cs +++ b/Greenshot/Forms/MainForm.cs @@ -596,7 +596,7 @@ namespace Greenshot { } void CaptureIE() { - CaptureHelper.CaptureIE(true); + CaptureHelper.CaptureIE(true, null); } void CaptureWindow() { @@ -840,7 +840,7 @@ namespace Greenshot { LOG.Error(exception); } try { - CaptureHelper.CaptureIE(false); + CaptureHelper.CaptureIE(false, tabData.Key); } catch (Exception exception) { LOG.Error(exception); } diff --git a/Greenshot/Helpers/CaptureHelper.cs b/Greenshot/Helpers/CaptureHelper.cs index 953c8dcb9..8b0c272a6 100644 --- a/Greenshot/Helpers/CaptureHelper.cs +++ b/Greenshot/Helpers/CaptureHelper.cs @@ -76,9 +76,13 @@ namespace Greenshot.Helpers { public static void CaptureLastRegion(bool captureMouse) { new CaptureHelper(CaptureMode.LastRegion, captureMouse).MakeCapture(); } - public static void CaptureIE(bool captureMouse) { - new CaptureHelper(CaptureMode.IE, captureMouse).MakeCapture(); + + public static void CaptureIE(bool captureMouse, WindowDetails windowToCapture) { + CaptureHelper captureHelper = new CaptureHelper(CaptureMode.IE, captureMouse); + captureHelper.SelectedCaptureWindow = windowToCapture; + captureHelper.MakeCapture(); } + public static void CaptureWindow(bool captureMouse) { new CaptureHelper(CaptureMode.ActiveWindow, captureMouse).MakeCapture(); } @@ -224,7 +228,7 @@ namespace Greenshot.Helpers { HandleCapture(); break; case CaptureMode.IE: - if (IECaptureHelper.CaptureIE(capture) != null) { + if (IECaptureHelper.CaptureIE(capture, SelectedCaptureWindow) != null) { capture.CaptureDetails.AddMetaData("source", "Internet Explorer"); HandleCapture(); } @@ -673,9 +677,10 @@ namespace Greenshot.Helpers { // 2) Is Windows >= Vista & DWM enabled: use DWM // 3) Otherwise use GDI (Screen might be also okay but might lose content) if (isAutoMode) { - if (conf.IECapture && windowToCapture.ClassName == "IEFrame") { + // TODO: Decided if this is smart, although we do consider a part of the window... + if (conf.IECapture && IECaptureHelper.IsMostlyIEWindow(windowToCapture, 60)) { try { - ICapture ieCapture = IECaptureHelper.CaptureIE(captureForWindow); + ICapture ieCapture = IECaptureHelper.CaptureIE(captureForWindow, windowToCapture); if (ieCapture != null) { return ieCapture; } diff --git a/Greenshot/Helpers/IECaptureHelper.cs b/Greenshot/Helpers/IECaptureHelper.cs index 3e1883b85..0e499c004 100644 --- a/Greenshot/Helpers/IECaptureHelper.cs +++ b/Greenshot/Helpers/IECaptureHelper.cs @@ -55,16 +55,56 @@ namespace Greenshot.Helpers { // Activate Tab ieAccessible.ActivateIETab(tabIndex); } - - /// + + /// + /// Return true if the supplied window has a sub-window which covers more than the supplied percentage + /// + /// WindowDetails to check + /// min percentage + /// + public static bool IsMostlyIEWindow(WindowDetails someWindow, int minimumPercentage) { + WindowDetails ieWindow = someWindow.GetChild("Internet Explorer_Server"); + if (ieWindow != null) { + Rectangle wholeClient = someWindow.ClientRectangle; + Rectangle partClient = ieWindow.ClientRectangle; + int percentage = (int)(100*((float)(partClient.Width * partClient.Height)) / ((float)(wholeClient.Width * wholeClient.Height))); + LOG.InfoFormat("Window {0}, ie part {1}, percentage {2}", wholeClient, partClient, percentage); + if (percentage > minimumPercentage) { + return true; + } + } + return false; + } + + /// + /// Does the supplied window have a IE part? + /// + /// + /// + public static bool IsIEWindow(WindowDetails someWindow) { + return someWindow.GetChild("Internet Explorer_Server") != null; + } + + /// + /// Get Windows displaying an IE + /// + /// List + public static List GetIEWindows() { + List ieWindows = new List(); + foreach (WindowDetails possibleIEWindow in WindowDetails.GetVisibleWindows()) { + if (IsIEWindow(possibleIEWindow)) { + ieWindows.Add(possibleIEWindow); + } + } + return ieWindows; + } + + /// /// Simple check if IE is running /// /// bool public static bool IsIERunning() { - foreach (WindowDetails shellWindow in WindowDetails.GetAllWindows("IEFrame")) { - return true; - } - return false; + return GetIEWindows().Count > 0; } /// @@ -76,7 +116,8 @@ namespace Greenshot.Helpers { Dictionary> browserWindows = new Dictionary>(); // Find the IE windows - foreach (WindowDetails ieWindow in WindowDetails.GetAllWindows("IEFrame")) { + List ieWindows = GetIEWindows(); + foreach (WindowDetails ieWindow in ieWindows) { try { if (!ieHandleList.Contains(ieWindow.Handle)) { WindowDetails directUIWD = IEHelper.GetDirectUI(ieWindow); @@ -108,10 +149,10 @@ namespace Greenshot.Helpers { /// Helper method which will retrieve the IHTMLDocument2 for the supplied window, /// or return the first if none is supplied. /// - /// The WindowDetails to get the IHTMLDocument2 for + /// The WindowDetails to get the IHTMLDocument2 for /// Ref to the IHTMLDocument2 to return /// The WindowDetails to which the IHTMLDocument2 belongs - private static DocumentContainer GetDocument(WindowDetails activeWindow) { + private static DocumentContainer GetDocument(WindowDetails browserWindow) { DocumentContainer returnDocumentContainer = null; WindowDetails returnWindow = null; IHTMLDocument2 returnDocument2 = null; @@ -119,8 +160,8 @@ namespace Greenshot.Helpers { WindowDetails alternativeReturnWindow = null; IHTMLDocument2 alternativeReturnDocument2 = null; - // Find the IE window - foreach (WindowDetails ieWindow in WindowDetails.GetAllWindows("IEFrame")) { + // Find the IE windows + foreach (WindowDetails ieWindow in GetIEWindows()) { LOG.DebugFormat("Processing {0} - {1}", ieWindow.ClassName, ieWindow.Text); Accessible ieAccessible = null; @@ -129,8 +170,8 @@ namespace Greenshot.Helpers { ieAccessible = new Accessible(directUIWD.Handle); } if (ieAccessible == null) { - LOG.InfoFormat("Active Window is {0}", activeWindow.Text); - if (!ieWindow.Equals(activeWindow)) { + LOG.InfoFormat("Active Window is {0}", browserWindow.Text); + if (!ieWindow.Equals(browserWindow)) { LOG.WarnFormat("No ieAccessible for {0}", ieWindow.Text); continue; } @@ -185,7 +226,7 @@ namespace Greenshot.Helpers { break; } try { - if (ieWindow.Equals(activeWindow)) { + if (ieWindow.Equals(browserWindow)) { returnDocument2 = document2; returnWindow = new WindowDetails(contentWindowHandle); break; @@ -234,15 +275,25 @@ namespace Greenshot.Helpers { /// ICapture where the capture needs to be stored /// ICapture with the content (if any) public static ICapture CaptureIE(ICapture capture) { - WindowDetails activeWindow = WindowDetails.GetActiveWindow(); - + return CaptureIE(capture, WindowDetails.GetActiveWindow()); + } + /// + /// Here the logic for capturing the IE Content is located + /// + /// ICapture where the capture needs to be stored + /// window to use + /// ICapture with the content (if any) + public static ICapture CaptureIE(ICapture capture, WindowDetails windowToCapture) { + if (windowToCapture == null) { + return CaptureIE(capture, WindowDetails.GetActiveWindow()); + } // Show backgroundform after retrieving the active window.. BackgroundForm backgroundForm = new BackgroundForm(Language.GetString(LangKey.contextmenu_captureie), Language.GetString(LangKey.wait_ie_capture)); backgroundForm.Show(); //BackgroundForm backgroundForm = BackgroundForm.ShowAndWait(language.GetString(LangKey.contextmenu_captureie), language.GetString(LangKey.wait_ie_capture)); try { //Get IHTMLDocument2 for the current active window - DocumentContainer documentContainer = GetDocument(activeWindow); + DocumentContainer documentContainer = GetDocument(windowToCapture); // Nothing found if (documentContainer == null) { @@ -299,7 +350,7 @@ namespace Greenshot.Helpers { if (documentContainer.Name != null) { capture.CaptureDetails.Title = documentContainer.Name; } else { - capture.CaptureDetails.Title = activeWindow.Text; + capture.CaptureDetails.Title = windowToCapture.Text; } // Store the URL of the page