在WPF中绑定WebBrowser的Source属性

有谁知道如何绑定WPF(3.5SP1)WebBrowser的.Source属性? 我有一个列表视图,我想在左边有一个小的WebBrowser,内容在右边,并绑定每个绑定到列表项的对象的URI的每个WebBrowser的源数据绑定。

这是我迄今为止的概念certificate,但是“ <WebBrowser Source="{Binding Path=WebAddress}" ”不能编译。

 <DataTemplate x:Key="dealerLocatorLayout" DataType="DealerLocatorAddress"> <StackPanel Orientation="Horizontal"> <!--Web Control Here--> <WebBrowser Source="{Binding Path=WebAddress}" ScrollViewer.HorizontalScrollBarVisibility="Disabled" ScrollViewer.VerticalScrollBarVisibility="Disabled" Width="300" Height="200" /> <StackPanel Orientation="Vertical"> <StackPanel Orientation="Horizontal"> <Label Content="{Binding Path=CompanyName}" FontWeight="Bold" Foreground="Blue" /> <TextBox Text="{Binding Path=DisplayName}" FontWeight="Bold" /> </StackPanel> <TextBox Text="{Binding Path=Street[0]}" /> <TextBox Text="{Binding Path=Street[1]}" /> <TextBox Text="{Binding Path=PhoneNumber}"/> <TextBox Text="{Binding Path=FaxNumber}"/> <TextBox Text="{Binding Path=Email}"/> <TextBox Text="{Binding Path=WebAddress}"/> </StackPanel> </StackPanel> </DataTemplate> 

问题是WebBrowser.Source不是一个DependencyProperty。 一种解决方法是使用一些AttachedProperty魔法来启用此function。

 public static class WebBrowserUtility { public static readonly DependencyProperty BindableSourceProperty = DependencyProperty.RegisterAttached("BindableSource", typeof(string), typeof(WebBrowserUtility), new UIPropertyMetadata(null, BindableSourcePropertyChanged)); public static string GetBindableSource(DependencyObject obj) { return (string) obj.GetValue(BindableSourceProperty); } public static void SetBindableSource(DependencyObject obj, string value) { obj.SetValue(BindableSourceProperty, value); } public static void BindableSourcePropertyChanged(DependencyObject o, DependencyPropertyChangedEventArgs e) { WebBrowser browser = o as WebBrowser; if (browser != null) { string uri = e.NewValue as string; browser.Source = !String.IsNullOrEmpty(uri) ? new Uri(uri) : null; } } } 

然后在你的xaml中做:

 <WebBrowser ns:WebBrowserUtility.BindableSource="{Binding WebAddress}"/> 

我写了一个包装用户控件,它使用了DependencyProperties:

XAML:

 <UserControl x:Class="HtmlBox"> <WebBrowser x:Name="browser" /> </UserControl> 

C#:

 public static readonly DependencyProperty HtmlTextProperty = DependencyProperty.Register("HtmlText", typeof(string), typeof(HtmlBox)); public string HtmlText { get { return (string)GetValue(HtmlTextProperty); } set { SetValue(HtmlTextProperty, value); } } protected override void OnPropertyChanged(DependencyPropertyChangedEventArgs e) { base.OnPropertyChanged(e); if (e.Property == HtmlTextProperty) { DoBrowse(); } } private void DoBrowse() { if (!string.IsNullOrEmpty(HtmlText)) { browser.NavigateToString(HtmlText); } } 

并像这样使用它:

 <Controls:HtmlBox HtmlText="{Binding MyHtml}" /> 

唯一的麻烦是这个WebBrowser控件不是“纯粹的”WPF …它实际上只是一个win32组件的包装。 这意味着控件将不会尊重z-index,并且总是会覆盖其他元素(例如:在scrollviewer中,这可能会导致一些麻烦)有关MSDN上这些win32-wpf问题的更多信息

我已经修改了Todd的一些很好的答案,以便从Binding源文件中生成一个可以处理string或Uris的版本:

 public static class WebBrowserBehaviors { public static readonly DependencyProperty BindableSourceProperty = DependencyProperty.RegisterAttached("BindableSource", typeof(object), typeof(WebBrowserBehaviors), new UIPropertyMetadata(null, BindableSourcePropertyChanged)); public static object GetBindableSource(DependencyObject obj) { return (string)obj.GetValue(BindableSourceProperty); } public static void SetBindableSource(DependencyObject obj, object value) { obj.SetValue(BindableSourceProperty, value); } public static void BindableSourcePropertyChanged(DependencyObject o, DependencyPropertyChangedEventArgs e) { WebBrowser browser = o as WebBrowser; if (browser == null) return; Uri uri = null; if (e.NewValue is string ) { var uriString = e.NewValue as string; uri = string.IsNullOrWhiteSpace(uriString) ? null : new Uri(uriString); } else if (e.NewValue is Uri) { uri = e.NewValue as Uri; } browser.Source = uri; } 

很酷的想法托德。

我现在已经在Silverlight 4中完成了类似于RichTextBox.Selection.Text的工作。 感谢您的post。 工作正常。

 public class RichTextBoxHelper { public static readonly DependencyProperty BindableSelectionTextProperty = DependencyProperty.RegisterAttached("BindableSelectionText", typeof(string), typeof(RichTextBoxHelper), new PropertyMetadata(null, BindableSelectionTextPropertyChanged)); public static string GetBindableSelectionText(DependencyObject obj) { return (string)obj.GetValue(BindableSelectionTextProperty); } public static void SetBindableSelectionText(DependencyObject obj, string value) { obj.SetValue(BindableSelectionTextProperty, value); } public static void BindableSelectionTextPropertyChanged(DependencyObject o, DependencyPropertyChangedEventArgs e) { RichTextBox rtb = o as RichTextBox; if (rtb != null) { string text = e.NewValue as string; if (text != null) rtb.Selection.Text = text; } } } 

这是Xaml代码。

 <RichTextBox IsReadOnly='False' TextWrapping='Wrap' utilities:RichTextBoxHelper.BindableSelectionText="{Binding Content}"/> 

您也可以使用一个特殊的独立代理控制 。 它不仅适用于WebBrowser案件,而且适用于任何此类控制。

这是托德和塞缪尔的回答利用一些基本的逻辑前提,以及使用空合并运算符的改进。

 public static void BindableSourcePropertyChanged(DependencyObject o, DependencyPropertyChangedEventArgs e) { WebBrowser browser = o as WebBrowser; if ((browser != null) && (e.NewValue != null)) browser.Source = e.NewValue as Uri ?? new Uri((string)e.NewValue); } 
  1. 如果浏览器为空或位置为空,则我们无法使用或导航到空白页面。
  2. 当#1中的项目不为空时,则在分配时,如果新值是一个URI,则使用它。 如果不是,URI是空的,那么合并它就必须是一个可以放入URI的string。 因为#1强制该string不能为空。

您需要在指向类文件的xaml文件的前几行声明它

 xmlns:reportViewer="clr-namespace:CoMS.Modules.Report"