我目前在WPF中遇到绑定问题。我有一个双标签应用程序。第一个选项卡包含由列表填充的数据网格控件。第二个选项卡包含由列表填充的列表框控件。问题是如果我在第一个选项卡上运行检查并返回数据网格中的示例5行,则第二个选项卡将填充5个虚拟列表框项。所以控件显然是在分享一些背景,但我不确定如何纠正。
显示绑定的第一个选项卡的XAML:
<DataGrid Name="WinUpdateDataGrid" Margin="10,79,0,114" ItemsSource="{Binding}" CanUserAddRows="false" AutoGenerateColumns="true" HorizontalAlignment="Left" VerticalAlignment="Center" ColumnWidth="*" Height="161" Width="509" MaxHeight="150" MaxWidth="700"></DataGrid>
显示datacontext的第一个标签的代码:
private void CheckforWindowsUpdates_Click(object sender, RoutedEventArgs e)
{
CheckforWindowsUpdates.IsEnabled = false;
WinUpdateStatusText.Text = "Evaluation in progress...";
WinUpdateProgressBar.Visibility = Visibility.Visible;
WinUpdateProgressBar.IsIndeterminate = true;
worker = new BackgroundWorker();
worker.WorkerReportsProgress = true;
worker.WorkerSupportsCancellation = true;
DataContext = WindowsUpdate.updateClassList;
worker.DoWork += delegate(object s, DoWorkEventArgs args)
{
WindowsUpdate.getCollectionofMissingSecurityUpdates(WindowsUpdate.windowsKBExceptionsList, WindowsUpdate.CabFilePath);
};
worker.ProgressChanged += delegate(object s, ProgressChangedEventArgs args)
{
};
worker.RunWorkerCompleted += delegate(object s, RunWorkerCompletedEventArgs args)
{
CheckforWindowsUpdates.IsEnabled = true;
WinUpdateStatusText.Text = "Evaluation completed. Missing the following updates:";
WinUpdateProgressBar.IsIndeterminate = false;
WinUpdateProgressBar.Visibility = Visibility.Hidden;
if (WindowsUpdate.updateClassList.Count > 0)
{
WinUpdateDataGrid.Visibility = Visibility.Visible;
DownloadandInstallWinUpdatesButton.Visibility = Visibility.Visible;
}
else
{
WinUpdateDataGrid.Visibility = Visibility.Hidden;
WinUpdateStatusText.Text = "Evaluation completed. No missing updates.";
}
};
worker.RunWorkerAsync();
}
第二个标签的XAML:
<ListBox Name="ThirdPartyListBox" ItemsSource="{Binding}" Margin="0,70,0,0">
<ListBox.ItemTemplate>
<DataTemplate>
<StackPanel Orientation="Horizontal">
<Image Source="C:\Users\Test\Desktop\Project\ACME-WPF\ACME-WPF\window-new-3.ico" Margin="5" Width="50"/>
<Button Name="ThirdPartyInstallButton" Content="Install" Click="InstallThirdPartyUpdatesButton_Click" Margin="5,5,0,0" Height="25"></Button>
<Button Name="ThirdPartyPostoneButton" Content="Postpone" Margin="5,5,0,0" Height="25"></Button>
<TextBlock FontWeight="Bold" Text="{Binding Item2.Name}" Margin="12,25,0,0"/>
<TextBlock FontWeight="Bold" Text="{Binding Item2.RequiredVersion}" Margin="3,25,0,0"/>
<TextBlock Text="{Binding Item2.CustomUIMessage}" Margin="10,25,0,0" TextWrapping="Wrap" Foreground="Red"/>
<TextBlock Text="You have used " Margin="3,25,0,0"/>
<TextBlock Text="{Binding Item3.UsedDeferrals}" Margin="3,25,0,0"/>
<TextBlock Text=" of " Margin="3,25,0,0"/>
<TextBlock Text="{Binding Item2.MaxDefferals}" Margin="3,25,0,0"/>
<TextBlock Text=" deferrals for this update." Margin="3,25,0,0"/>
</StackPanel>
</DataTemplate>
</ListBox.ItemTemplate>
</ListBox>
第二个标签的代码:
private void CheckforThirdPartyUpdatesButton_Click(object sender, RoutedEventArgs e)
{
CheckforThirdPartyUpdatesButton.IsEnabled = false;
worker = new BackgroundWorker();
worker.WorkerReportsProgress = true;
worker.WorkerSupportsCancellation = true;
DataContext = RegScan_ThirdParty.comparisonListWithState;
worker.DoWork += delegate(object s, DoWorkEventArgs args)
{
MainEntry.checkFor3PUpdates();
};
worker.ProgressChanged += delegate(object s, ProgressChangedEventArgs args)
{
};
worker.RunWorkerCompleted += delegate(object s, RunWorkerCompletedEventArgs args)
{
CheckforThirdPartyUpdatesButton.IsEnabled = true;
};
worker.RunWorkerAsync();
}
按要求提供完整的XAML:
<Window x:Class="ACME_WPF.MainWindow"
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
Title="ACME" Height="411.085" MaxWidth="555.668"
SizeToContent="WidthAndHeight" WindowStartupLocation="CenterScreen"
WindowStyle="ToolWindow"
>
<Grid>
<TabControl>
<TabItem Header="Windows Updates">
<Grid>
<Image Name="WindowsUpdateDefaultImage" Source="C:\Users\Test\Desktop\Project\ACME-WPF\ACME-WPF\windowsupdate.png" Margin="0,16,488,286" Width="50"/>
<TextBlock Name="WinUpdateStatusText" Width="Auto" HorizontalAlignment="Left" Margin="267,22,0,0" TextWrapping="Wrap" Text="{Binding Path=WindowsUpdateCompliance, UpdateSourceTrigger=PropertyChanged}" VerticalAlignment="Top" FontSize="14" Foreground="DarkSlateBlue"/>
<Button Name="CheckforWindowsUpdates" HorizontalAlignment="Left" Margin="54,18,0,0" VerticalAlignment="Top" Width="207" Content="Check for Windows Security Updates" Height="25" Click="CheckforWindowsUpdates_Click"/>
<ProgressBar Name="WinUpdateProgressBar" HorizontalAlignment="Left" Height="18" Margin="54,52,0,0" VerticalAlignment="Top" Width="207"/>
<DataGrid Name="WinUpdateDataGrid" Margin="10,79,0,114" ItemsSource="{Binding}" CanUserAddRows="false" AutoGenerateColumns="true" HorizontalAlignment="Left" VerticalAlignment="Center" ColumnWidth="*" Height="161" Width="509" MaxHeight="150" MaxWidth="700"></DataGrid>
<Button Name="DownloadandInstallWinUpdatesButton" Content="Download and Install Windows Updates" HorizontalAlignment="Left" Margin="10,250,0,0" VerticalAlignment="Top" Width="227" Height="26" Click="DownloadandInstallWinUpdatesButton_Click"/>
<ProgressBar Name="DownloadandInstallWinUpdatesButtonProgressBar" HorizontalAlignment="Left" Height="26" Margin="10,286,0,0" VerticalAlignment="Top" Width="227"/>
<TextBlock Name="WinUpdateInstallationText" HorizontalAlignment="Left" Margin="256,250,0,0" TextWrapping="Wrap" Text="" VerticalAlignment="Top" Width="Auto"/>
</Grid>
</TabItem>
<TabItem Header="Third Party Updates">
<Grid>
<Button Name="CheckforThirdPartyUpdatesButton" Content="Check for Third Party Updates" Margin="10,11,339,304" Click="CheckforThirdPartyUpdatesButton_Click" MaxWidth="200"/>
<ListBox Name="ThirdPartyListBox" ItemsSource="{Binding}" Margin="0,70,0,0">
<ListBox.ItemTemplate>
<DataTemplate>
<StackPanel Orientation="Horizontal">
<Image Source="C:\Users\Test\Desktop\Project\ACME-WPF\ACME-WPF\window-new-3.ico" Margin="5" Width="50"/>
<Button Name="ThirdPartyInstallButton" Content="Install" Click="InstallThirdPartyUpdatesButton_Click" CommandParameter="{Binding Path=.}" Command="{Binding ElementName=ThirdPartyListBox, Path=DataContext.InstallComponentCommand}" Margin="5,5,0,0" Height="25"></Button>
<Button Name="ThirdPartyPostoneButton" Content="Postpone" Margin="5,5,0,0" Height="25"></Button>
<TextBlock FontWeight="Bold" Text="{Binding Item2.Name}" Margin="12,25,0,0"/>
<TextBlock FontWeight="Bold" Text="{Binding Item2.RequiredVersion}" Margin="3,25,0,0"/>
<TextBlock Text="{Binding Item2.CustomUIMessage}" Margin="10,25,0,0" TextWrapping="Wrap" Foreground="Red"/>
<TextBlock Text="You have used " Margin="3,25,0,0"/>
<TextBlock Text="{Binding Item3.UsedDeferrals}" Margin="3,25,0,0"/>
<TextBlock Text=" of " Margin="3,25,0,0"/>
<TextBlock Text="{Binding Item2.MaxDefferals}" Margin="3,25,0,0"/>
<TextBlock Text=" deferrals for this update." Margin="3,25,0,0"/>
</StackPanel>
</DataTemplate>
</ListBox.ItemTemplate>
</ListBox>
</Grid>
</TabItem>
<TabItem Header="Information">
<Grid>
<Label Name="Info_ComputerNameLabel" Content="Computer Name: " Margin="10,13,397,253" RenderTransformOrigin="0.49,1"/>
<Label Name="Info_UserNameLabel" Content="User Name: " Width="100" Margin="10,54,419,222"/>
<Label Name="Info_IPAddressLabel" Content="IP Address: " Width="100" Margin="10,96,419,180"/>
<TextBlock Name="Info_ComputerNameText" HorizontalAlignment="Left" Margin="137,18,0,0" TextWrapping="Wrap" Text="" VerticalAlignment="Top"/>
<TextBlock Name="Info_UserNameText" HorizontalAlignment="Left" Margin="137,59,0,0" TextWrapping="Wrap" Text="" VerticalAlignment="Top"/>
<TextBlock Name="Info_IPAddressText" HorizontalAlignment="Left" Margin="137,101,0,0" TextWrapping="Wrap" Text="" VerticalAlignment="Top"/>
</Grid>
</TabItem>
</TabControl>
</Grid>
答案 0 :(得分:1)
我的猜测是你需要将DataContext专门设置为Grid和ListBox。像这样:
WinUpdateDataGrid.DataContext = WindowsUpdate.updateClassList;
和
ThirdPartyListBox.DataContext = RegScan_ThirdParty.comparisonListWithState;
问题在于,如果两个函数CheckforWindowsUpdates_Click
和CheckforThirdPartyUpdatesButton_Click
在同一个代码隐藏文件中出现,它们将在Grid中设置相同的DataContext和绑定ItemsSource="{Binding}"
,ListBox将继承相同的DataContext。
答案 1 :(得分:0)
简短回答:{Binding}
是&#34;绑定到自身的快捷方式&#34; (在RelativeSource.Self的意义上)。而是{Binding}
is equivalent to {Binding Path=.}
,它绑定到当前来源。
详细说明:绑定包含源和路径。例如,您可以使用
对自身&#34;进行绑定<myUIControl myProperty="{Binding RelativeSource={RelativeSource Self}, Path=x}" />
然而,这会将源设置为控件本身,因此它将尝试访问UI控件的属性x
(而不是当前属性x
数据上下文)。从我如何理解你的问题,这不是你想要的;特别是,它不是{Binding}
所做的:{Binding}
保持源的原样(通常是某个父元素的DataContext
)并绑定到源本身(相当于{{1} }})。
您可能正在共享两个控件的当前源。我只是显式设置Path=.
数据源而不是快捷方法
<强>更新强>:
它实际上是在共享DataContext。您可以为Binding
创建两个公共属性,然后从那里执行DataContext
。不要忘记实现Binding
并在设置属性时调用实现。这样,对于其他开发人员来说,两个不同的控件实际上有两个INotifyPropertyChanged
更清晰,更易读。