我有一个视图模型来管理对话框类型的视图,允许过滤列表(如果需要)和选择项目.无论我是否将IsSynchronizedWithCurrentItem设置为true,代码都能正常工作.我的理解是这个属性在ListView中默认是不正确的,所以我想更好地理解这个属性.
这是视图的xaml中的绑定设置(在没有synch属性设置的情况下也可以正常工作):
<ListView
ItemsSource="{Binding Projects.View}"
IsSynchronizedWithCurrentItem="True"
SelectedItem="{Binding SelectedProject, Mode=TwoWay}"
>
Run Code Online (Sandbox Code Playgroud)
视图模型Projects实际上是一个由私有ObservableCollection支持的CollectionViewSource.我想我从Josh Smith的一个示例项目中琢磨了这个想法,但老实说我现在不记得了.以下是与xaml绑定相关的VM的相关部分:
private ObservableCollection<ProjectViewModel> _projectsInternal { get; set; }
public CollectionViewSource Projects { get; set; }
private void _populateProjectListings(IEnumerable<Project> openProjects) {
var listing = (from p in openProjects
orderby p.Code.ToString()
select new ProjectViewModel(p)).ToList();
foreach (var pvm in listing)
pvm.PropertyChanged += _onProjectViewModelPropertyChanged;
_projectsInternal = new ObservableCollection<ProjectViewModel>(listing);
Projects = new CollectionViewSource {Source = _projectsInternal};
}
/// <summary>Property that is updated via the binding to the view</summary>
public ProjectViewModel SelectedProject { get; set; …Run Code Online (Sandbox Code Playgroud) 我正在尝试从MSDN创建类似官方DataGrid.ItemsSource的属性:
public IEnumerable ItemsSource { get; set; }
Run Code Online (Sandbox Code Playgroud)
这在任何派生类中提供任何类型的支持.有了这个,我可以设置类似的东西
var list = new List<ObservableCollection<KeyValuePair<decimal, bool>>>();
MyDataGrid.ItemsSource = list;
Run Code Online (Sandbox Code Playgroud)
但是当我尝试在没有Type T的情况下创建IEnumerable的属性时,就像MSDN所说的那样,我在VisualStudio上遇到错误:
Using the generic type 'System.Collections.Generic.IEnumerable<T>' requires 1 type arguments
Run Code Online (Sandbox Code Playgroud)
那么,有什么不对?
我一直用WPF DataGrids加载时间很长,我在网上找不到任何类似的报道,所以我怀疑我做错了什么.现在我很确定,因为添加布局复杂性会大大降低执行速度.在一个非常简单的布局中,DataGrid立即填充,而下面的代码大约需要3秒才能执行.
在以下代码中,加载150行和11列需要约3秒,即使每个单元格未绑定到任何属性且AutoGenerateColumns = False也是如此.(我有一个两核,2.6GHz处理器,有足够的RAM).
如果在布局中设置ItemsSource属性,则会发生瓶颈,如下所示:
<Window x:Class="datagridtest.MainWindow"
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
Title="MainWindow" Height="350" Width="525">
<Border Background="LightSteelBlue" CornerRadius="10" Margin="10">
<ScrollViewer Margin="10" HorizontalScrollBarVisibility="Auto">
<Grid Margin="10,50,0,0">
<Grid.RowDefinitions>
<RowDefinition Height="Auto" />
<RowDefinition Height="auto" />
<RowDefinition Height="auto" />
</Grid.RowDefinitions>
<Expander IsExpanded="True" Name="expander1" Grid.Row="0">
<Grid>
<DataGrid VirtualizingStackPanel.IsVirtualizing="True" AutoGenerateColumns="false" Name="dg" Height="auto" CanUserReorderColumns="False" CanUserResizeColumns="False" CanUserResizeRows="False" CanUserSortColumns="False">
<DataGrid.Columns>
<DataGridTextColumn >
<DataGridTextColumn.Header >
<TextBlock Width="140" HorizontalAlignment="Center" TextAlignment="Center">untitled<LineBreak/>column</TextBlock>
</DataGridTextColumn.Header>
</DataGridTextColumn>
<DataGridTextColumn >
<DataGridTextColumn.Header >
<TextBlock Width="140" HorizontalAlignment="Center" TextAlignment="Center">untitled<LineBreak/>column</TextBlock>
</DataGridTextColumn.Header>
</DataGridTextColumn>
<DataGridTextColumn >
<DataGridTextColumn.Header >
<TextBlock Width="140" HorizontalAlignment="Center" TextAlignment="Center">untitled<LineBreak/>column</TextBlock>
</DataGridTextColumn.Header>
</DataGridTextColumn>
<DataGridTextColumn > …Run Code Online (Sandbox Code Playgroud) 我写了简单的代码
public ObservableCollection<string> Names …
public Window1()
{
PutInDataIntoNames();
InitializeComponent();
this.listBox1.ItemsSource = Names;
}
Run Code Online (Sandbox Code Playgroud)
并在xaml
<Grid>
<ListBox Margin="10,11,10,16"
Name="listBox1"
Background="Black"
Foreground="Orange"
/>
</Grid>
Run Code Online (Sandbox Code Playgroud)
然后我想在xaml中设置ItemsSource属性.为了做到这一点,我写了以下内容:
ItemsSource="{Binding Path=Names}"
Run Code Online (Sandbox Code Playgroud)
不幸的是,它不起作用.你能解释为什么以及如何做到这一点吗?
快速问题......
我有一个ListBox与它的ItemsSource属性绑定到一个集合属性在视图模型,如下所示:
<ListBox Name="CollectionsListBox" ItemsSource="{Binding Activity.Timesheets}" />
Run Code Online (Sandbox Code Playgroud)
我Button在同一视图中也有两个对象.现在的问题是...我可以改变CollectionsListBox ItemsSource Binding从Activity.Timesheets到Activity.Attachments只使用XAML?
如果失败了,从viewmodel使用Command对象?
编辑>>>
我找到了一个简单的解决方案,使用RadioButtons代替Button了霍华德答案中的s:
<ListBox Name="CollectionsListBox">
<ListBox.Style>
<Style>
<Style.Triggers>
<DataTrigger Binding="{Binding ElementName=TimesheetsButton,Path=IsChecked}" Value="True">
<Setter Property="ListBox.ItemsSource" Value="{Binding Activity.Timesheets}" />
<Setter Property="ListBox.ItemContainerStyle" Value="{StaticResource TimesheetStyle}" />
</DataTrigger>
<DataTrigger Binding="{Binding ElementName=AttachmentsButton,Path=IsChecked}" Value="True">
<Setter Property="ListBox.ItemsSource" Value="{Binding Activity.Attachments}" />
<Setter Property="ListBox.ItemContainerStyle" Value="{StaticResource AttachmentStyle}" />
</DataTrigger>
</Style.Triggers>
</Style>
</ListBox.Style>
</ListBox>
Run Code Online (Sandbox Code Playgroud)
非常感谢您的帮助.
我已经在这方面工作了几天,但似乎无法想出一个解决方案
我有一个计时器上的代码,DataGrid每隔几秒刷新一次
我尝试了很多刷新选项,但最终他们都失去了用户的注意力,有时也失去了 SelectedItem
继承我的代码:
AddHandler bw.RunWorkerCompleted, Function(sender As Object, e As ComponentModel.RunWorkerCompletedEventArgs)
Dim lst = e.Result
Dim lst2 = CType(lst, List(Of Object)).OfType(Of INotifyPropertyChanged)()
'If Items.Count = 0 Then
Dim a = SelectedItem
Collection.Clear()
Collection.AddRange(lst2)
SelectedItem = a
'ItemsSource = lst
'End If
'For Each rw In lst
' Dim mtch = Collection.Where(Function(x) x.GetHashCode = rw.GetHashCode)
'Next
Run Code Online (Sandbox Code Playgroud)
我留下了评论,所以你可以看到我尝试的不同方法
结果:
如果我直接设置ItemsSource,结果(如注释),那么SelectedItem和Keyboard.FocusedElement保持稳定,直到上面的代码中结束,但是这个代码的结束和下一个节拍,他们都变成了介于两者之间Nothing
如果我一起去,ObservableCollection那么SelectedItem一旦我清除了收集Keyboard.FocusedElement就失去了,并且只在蜱之间的某个时间丢失.尽管可以使用临时支持变量在此处保留SelectedItem
所以关键是我们如何在保持(最重要的)键盘焦点的同时刷新数据库中的项目
是的,我知道ObservableCollections不会被"重置".事实上,我真的不想使用它.它只有一个保持 …
CanUserAddRows="True"只有"工作"时,有已经在数据ItemsSource的DataGrid.如果恰好在原始项目列表中没有行,则即使我已设置,DataGrid也不会显示placeholder用于输入新项目的行CanUserAddRows="True".为什么?!
提前谢谢,Trindaz
我DataSet有义务Window.DataContext; 我还有一个DataGrid:
<DataGrid ItemsSource={Binding Tables[Items]}>
<DataGrid.Columns>
<DataGridTextBoxColumn Header={Binding Path=DataContext.Tables[Names]/Test, RelativeSource={RelativeSource FindAncestor, AncestorType={x:Type Window}}} />
</DataGrid.Columns>
</DataGrid>
Run Code Online (Sandbox Code Playgroud)
基本上,我正在尝试将该列的Header绑定到DataTable"Names",列"Test",第一行.
但是,我无法做到对.请注意,我可以在DataGrid外部绑定它.Grid的ItemsSource更改了数据上下文,我不知道如何在外部引用原始DataContext.
似乎绑定成功了; 但问题是Window.DataContext中Tables [Names]的当前项(第一行)丢失了.
如果我使DataSet静态并通过{x:Static local:dataset}访问它,那么事情就可以了.但我不能使用静态数据集,因为会有多个实例(多用户).
有谁能指出我正确的方向?
我在WPF应用程序中有一个DataGrid,它将自己绑定到一个ObservableCollection对象,一切正常.现在,如果我在运行时修改数据网格中的单元格并删除内容,请将单元格留空.observableCollection的对应值不会被修改,它将是旧值.但是当我退出包含datagrid的窗口并重新启动窗口时,它会抛出一个XamlParseException,说:"设置属性'System.Windows.Controls.ItemsControl.ItemsSource'引发异常"
StackTrace:
at System.Windows.Markup.XamlReader.RewrapException(Exception e, IXamlLineInfo lineInfo, Uri baseUri)
at System.Windows.Markup.WpfXamlLoader.Load(XamlReader xamlReader, IXamlObjectWriterFactory writerFactory, Boolean skipJournaledProperties, Object rootObject, XamlObjectWriterSettings settings, Uri baseUri)
at System.Windows.Markup.WpfXamlLoader.LoadBaml(XamlReader xamlReader, Boolean skipJournaledProperties, Object rootObject, XamlAccessLevel accessLevel, Uri baseUri)
at System.Windows.Markup.XamlReader.LoadBaml(Stream stream, ParserContext parserContext, Object parent, Boolean closeStream)
at System.Windows.Application.LoadComponent(Object component, Uri resourceLocator)
at VO3.Start.InitializeComponent() in c:\VO\Trunk\VO3\Start.xaml:line 1
at VO3.Start..ctor() in C:\VO\Trunk\VO3\Start.xaml.cs:line 103
InnerException: System.InvalidOperationException
Message='DeferRefresh' is not allowed during an AddNew or EditItem transaction.
Source=PresentationFramework
StackTrace:
at System.Windows.Data.CollectionView.DeferRefresh()
at System.Windows.Controls.ItemCollection.SetCollectionView(CollectionView view)
at System.Windows.Controls.ItemCollection.SetItemsSource(IEnumerable value)
at …Run Code Online (Sandbox Code Playgroud) 它看起来WFP DataGridComboBoxColumn正在为此列中的所有单元格使用单个ItemsSource.我有一个案例,其中ComboBox项依赖于同一行中的另一个单元格.我设法在PreparingCellForEdit事件中填充ItemsSource.但是,它不能按预期工作.最初,此列中的所有单元格都是空的.一旦我为这个列的ComboBox填充ItemsSource,所有相关的单元格(具有相同的项目源)都显示值.但是,如果我单击其他类型的单元格(填充了不同的项目源),则所有值都将消失,新类型单元格将显示值.您只能为列使用一组Items Source?我不敢相信这是真的.我错过了什么吗?任何解决方法?
itemssource ×10
wpf ×10
datagrid ×6
data-binding ×3
listbox ×2
binding ×1
c# ×1
combobox ×1
exception ×1
focus ×1
ienumerable ×1
performance ×1
properties ×1
refresh ×1
row ×1
selecteditem ×1