c# - 使用 .net 2.0 从 C# 程序将焦点设置到已打开的 Internet Explorer 选项卡

标签 c# .net internet-explorer

我有两个问题。

  1. 如何使用 .net 2.0 从 C# 程序将焦点设置到已打开的 Internet Explorer 选项卡。

  2. 如何从 C# 程序在运行 Internet Explorer 实例(而不是在新窗口中)的新选项卡中打开新 URL。

我最多只能使用 .net 2.0。

我们将不胜感激。

最佳答案

这是如何根据选项卡的 URL 地址激活选项卡的代码。我测试过,效果很好。您可以添加如何根据文本/描述等激活选项卡的功能。如果您需要它在 .net 2.0 下运行,则将 var 更改为特定类型。

这是一个实际的代码本身。我将它包装在单独的类中。

using System;
using System.Collections.Generic;
using System.Runtime.InteropServices;
using Accessibility;

namespace IETabsInteraction
{
    internal class TabActivator
    {
        #region Nested type: OBJID

        private enum OBJID : uint
        {
            OBJID_WINDOW = 0x00000000,
        }

        #endregion

        #region Declarations

        private const int CHILDID_SELF = 0;
        private readonly IntPtr _hWnd;
        private IAccessible _accessible;

        [DllImport("oleacc.dll")]
        private static extern int AccessibleObjectFromWindow(IntPtr hwnd, uint id, ref Guid iid,
                                                             [In, Out, MarshalAs(UnmanagedType.IUnknown)] ref object
                                                                 ppvObject);

        [DllImport("user32.dll", SetLastError = true)]
        private static extern IntPtr FindWindowEx(IntPtr hwndParent, IntPtr hwndChildAfter, string lpszClass,
                                                  string lpszWindow);

        [DllImport("oleacc.dll")]
        private static extern int AccessibleChildren(IAccessible paccContainer, int iChildStart, int cChildren,
                                                     [In, Out, MarshalAs(UnmanagedType.LPArray, SizeParamIndex = 2)] object[] rgvarChildren, out int pcObtained);

        #endregion

        #region Constructors

        internal TabActivator(IntPtr ieHandle)
        {
            _hWnd = ieHandle;
            AccessibleObjectFromWindow(GetDirectUIHWND(ieHandle), OBJID.OBJID_WINDOW, ref _accessible);

            CheckForAccessible();
        }

        private TabActivator(IAccessible acc)
        {
            if (acc == null)
                throw new Exception("Could not get accessible");

            _accessible = acc;
        }

        #endregion

        private TabActivator[] Children
        {
            get
            {
                var num = 0;
                var res = GetAccessibleChildren(_accessible, out num);

                if (res == null)
                    return new TabActivator[0];

                var list = new List<TabActivator>(res.Length);

                foreach (object obj in res)
                {
                    var acc = obj as IAccessible;

                    if (acc != null)
                        list.Add(new TabActivator(acc));
                }

                return list.ToArray();
            }
        }

        private int ChildCount
        {
            get { return _accessible.accChildCount; }
        }

        /// <summary>
        /// Gets LocationUrl of the tab
        /// </summary>
        private string LocationUrl
        {
            get
            {
                var url = _accessible.accDescription[CHILDID_SELF];

                if (url.Contains(Environment.NewLine))
                    url = url.Split('\n')[1];

                return url;
            }
        }

        private void CheckForAccessible()
        {
            if (_accessible == null)
                throw new Exception("Could not get accessible.  Accessible can't be null");
        }

        internal void ActivateByTabsUrl(string tabsUrl)
        {
            var tabIndexToActivate = GetTabIndexToActivate(tabsUrl);

            AccessibleObjectFromWindow(GetDirectUIHWND(_hWnd), OBJID.OBJID_WINDOW, ref _accessible);

            CheckForAccessible();

            var index = 0;
            var ieDirectUIHWND = new TabActivator(_hWnd);

            foreach (var accessor in ieDirectUIHWND.Children)
            {
                foreach (var child in accessor.Children)
                {
                    foreach (var tab in child.Children)
                    {
                        if (tabIndexToActivate >= child.ChildCount - 1)
                            return;

                        if (index == tabIndexToActivate)
                        {
                            tab.ActivateTab();
                            return;
                        }

                        index++;
                    }
                }
            }
        }

        private void ActivateTab()
        {
            _accessible.accDoDefaultAction(CHILDID_SELF);
        }

        private int GetTabIndexToActivate(string tabsUrl)
        {
            AccessibleObjectFromWindow(GetDirectUIHWND(_hWnd), OBJID.OBJID_WINDOW, ref _accessible);

            CheckForAccessible();

            var index = 0;
            var ieDirectUIHWND = new TabActivator(_hWnd);

            foreach (var accessor in ieDirectUIHWND.Children)
            {
                foreach (var child in accessor.Children)
                {
                    foreach (var tab in child.Children)
                    {
                        var tabUrl = tab.LocationUrl;

                        if (!string.IsNullOrEmpty(tabUrl))
                        {
                            if (tab.LocationUrl.Contains(tabsUrl))
                                return index;
                        }

                        index++;
                    }
                }
            }

            return -1;
        }

        private IntPtr GetDirectUIHWND(IntPtr ieFrame)
        {
            // For IE 8:
            var directUI = FindWindowEx(ieFrame, IntPtr.Zero, "CommandBarClass", null);
            directUI = FindWindowEx(directUI, IntPtr.Zero, "ReBarWindow32", null);
            directUI = FindWindowEx(directUI, IntPtr.Zero, "TabBandClass", null);
            directUI = FindWindowEx(directUI, IntPtr.Zero, "DirectUIHWND", null);

            if (directUI == IntPtr.Zero)
            {
                // For IE 9:
                //directUI = FindWindowEx(ieFrame, IntPtr.Zero, "WorkerW", "Navigation Bar");
                directUI = FindWindowEx(ieFrame, IntPtr.Zero, "WorkerW", null);
                directUI = FindWindowEx(directUI, IntPtr.Zero, "ReBarWindow32", null);
                directUI = FindWindowEx(directUI, IntPtr.Zero, "TabBandClass", null);
                directUI = FindWindowEx(directUI, IntPtr.Zero, "DirectUIHWND", null);
            }

            return directUI;
        }

        private static int AccessibleObjectFromWindow(IntPtr hwnd, OBJID idObject, ref IAccessible acc)
        {
            var guid = new Guid("{618736e0-3c3d-11cf-810c-00aa00389b71}"); // IAccessibleobject obj = null;
            object obj = null;

            var num = AccessibleObjectFromWindow(hwnd, (uint) idObject, ref guid, ref obj);

            acc = (IAccessible) obj;

            return num;
        }

        private static object[] GetAccessibleChildren(IAccessible ao, out int childs)
        {
            childs = 0;
            object[] ret = null;
            var count = ao.accChildCount;

            if (count > 0)
            {
                ret = new object[count];
                AccessibleChildren(ao, 0, count, ret, out childs);
            }

            return ret;
        }
    }
}

要执行此代码,请使用:

var hWnd = (IntPtr)ie.HWND;
new TabActivator(hWnd).ActivateByTabsUrl("www.stackoverflow.com");

回答你的第二个问题。您将需要找到您已经运行的 ie:

    private static void OpenTabInExistingIE()
    {
        var shellWindows = new ShellWindows();

        // check if IE is open
        if (shellWindows.Count > 0)
            ((InternetExplorer)shellWindows.Item(0)).Navigate2("www.stackoverflow.com", 2048);
    }

对于所有这些代码,您必须添加对 SHDocVw.dll 和

的引用
#using SHDocVw;

这是 Navigate2 方法的标志

Enum BrowserNavConstants
    navOpenInNewWindow = 1
    navNoHistory = 2
    navNoReadFromCache = 4
    navNoWriteToCache = 8
    navAllowAutosearch = 16
    navBrowserBar = 32
    navHyperlink = 64
    navEnforceRestricted = 128
    navNewWindowsManaged = 256
    navUntrustedForDownload = 512
    navTrustedForActiveX = 1024
    navOpenInNewTab = 2048
    navOpenInBackgroundTab = 4096
    navKeepWordWheelText = 8192
    navVirtualTab = 16384
    navBlockRedirectsXDomain = 32768
    navOpenNewForegroundTab = 65536
End Enum

关于c# - 使用 .net 2.0 从 C# 程序将焦点设置到已打开的 Internet Explorer 选项卡,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/3820228/

相关文章:

c# - 从 VS.NET MSI 安装程序项目为所有用户安装快捷方式

.net - 如果队列为空,则停止 Rabbit MQ 消费者事件

c# - 我在哪里可以找到 C# 中的机器 epsilon?

html - Flash 播放器上的下拉菜单

.net - Windows 定时任务加载 URL 的推荐方法

c# - Outlook 插件项目保存

c# - C#中的视频转换

c# - Telegram C# 示例发送消息

c# - 绑定(bind)到来自两个不同 ViewModel 的两个属性的差异

javascript - 通过 Javascript 检查加载时的控件状态的最佳方法是什么