在 WebBrowser 控件加载的文档中获取标题

3

我有一个文本块和一个webbrowser控件。我有一个问题,例如,我的webbrowser导航到了google.com。当webbrowser导航到google.com时,我希望文本块的标题更改为google.com。

请帮助我使用c#实现此功能。

5个回答

6

已在IE上测试过

XAML:

<Grid>
    <WebBrowser LoadCompleted="webBrowser1_LoadCompleted" Height="100" HorizontalAlignment="Left" Margin="73,72,0,0" Name="webBrowser1" VerticalAlignment="Top" Width="200" />
    <Button Content="Go" Click="Button_Click" HorizontalAlignment="Right" VerticalAlignment="Bottom"/>
</Grid>

代码:

private void webBrowser1_LoadCompleted(object sender, NavigationEventArgs e)
{
    dynamic doc = webBrowser1.Document;
    this.Title = doc.Title;
}

private void Button_Click(object sender, RoutedEventArgs e)
{
    webBrowser1.Navigate("http://google.com");
}

没有动态和几乎没有异常处理:

private void webBrowser1_LoadCompleted(object sender, NavigationEventArgs e)
{
    Object doc = webBrowser1.Document;
    this.Title = GetPropertyValue<string>(doc, "Title");
}

private T GetPropertyValue<T>(object obj, string propertyName)
{
    Type objectType = obj.GetType(); 
    PropertyInfo propertyInfo = objectType.GetProperty(propertyName);
    Type propertyType = propertyInfo.PropertyType;
    if(propertyType == typeof(T))
    {
        object propertyValue = (T)info.GetValue(obj, null);   
        return value;
    }
    else
    {
        throw new Exception("Property " + propertyName + " is not of type " + T);
    }
}

这个问题也可以通过绑定来解决吗?比如 <Window Title={Binding Path=Title}> 然后将窗口的上下文设置为浏览器或类似的东西?或者你可能可以给 WebBrowser 命名,而不设置窗口的 DataContext。 - Alxandr
如果你的意思是 Title="{Binding ElementName=webBrowser1, Path=Document.Title}",那么据我所知不行,因为文档的 Title 属性不会引发 PropertyChanged 事件,所以绑定不会被更新。 - Emond
将示例更改为使用LoadCompleted而不是Navigated。 - Emond
我可以使用哪些类来替代动态类型? - Doug
@Doug - 我添加了一个没有使用 dynamic 的示例。警告:我省略了异常处理并且没有测试过这个代码。 - Emond
显示剩余2条评论

1

您可以从WebBrowser的Text属性中提取标题标签,只需订阅LoadCompleted事件即可。


没有Text属性。但是LoadCompleted比Navigated更好。我会更新我的代码。 - Emond
糟糕,看来我忘记了确切的名称。不管怎样,Erno的解决方案更好。 - Poma

0

Document.Title属性存在问题,如果在JavaScript中设置或更改标题,则一旦设置,您将无法获得最新值。

我们使用FormsHost而不是WPF中的默认Web浏览器,并且使用Windows窗体的Web浏览器,该浏览器支持DocumentTitle属性和DocumentTitleChanged事件。

因此,我建议使用以下控件,您可以使用更多在窗体版本中可用的功能。如果仔细注意,两者在性能方面完全相同,因为两者都创建一个Win32控件并与其交互。

public class FormsWebBrowser : 
    System.Windows.Forms.Integration.WindowsFormsHost
{

    System.Windows.Forms.WebBrowser Browser = 
        new System.Windows.Forms.WebBrowser();

    public FormsWebBrowser()
    {
        Child = Browser;
        Browser.DocumentTitleChanged += 
            new EventHandler(Browser_DocumentTitleChanged);
    }

    void Browser_DocumentTitleChanged(object sender, EventArgs e)
    {
        this.DocumentTitle = Browser.DocumentTitle;
    }

    ///<summary>
    /// This will let you bind
    ///</summary>
    public string DocumentTitle
    {
        get { return (string)GetValue(DocumentTitleProperty); }
        private set { SetValue(DocumentTitleProperty, value); }
    }

    public static readonly DependencyProperty DocumentTitleProperty =
        DependencyProperty.Register("DocumentTitle", typeof(string), 
        typeof(FormsWebBrowser), new FrameworkPropertyMetadata(""));
}

可能需要一些额外的代码来实现一些小功能,但是通过添加更多的依赖属性和控制逻辑,一切都是可能的。


0

针对Erno de Weerd的答案,仅进行了一些微小的拼写修正,适用于.NET 4.5 *) 属性名称为IHTMLDocument2_nameProp *) 在if块中修正了拼写错误

  private void webBrowser1_LoadCompleted(object sender, NavigationEventArgs e)
{
    Object doc = webBrowser1.Document;
    this.Title = GetPropertyValue<string>(doc, "IHTMLDocument2_nameProp");
}

private T GetPropertyValue<T>(object obj, string propertyName)
{
    Type objectType = obj.GetType(); 
    PropertyInfo propertyInfo = objectType.GetProperty(propertyName);
    Type propertyType = propertyInfo.PropertyType;
    if(propertyType == typeof(T))
    {
        object alue = (T)propertyInfo.GetValue(obj, null);   
        return value;
    }
    else
    {
        throw new Exception("Property " + propertyName + " is not of type " + T);
    }
}

0

这个会起作用

var docTitle = document.getElementsByTagName("title")
        .Cast<IHTMLElement>()
        .FirstOrDefault().innerText;    

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接