C# 如何更改在ListView中用作ItemTemplate的UserControl的VisualState
我有一个用户控件,其中定义了一些可视状态:C# 如何更改在ListView中用作ItemTemplate的UserControl的VisualState,c#,windows,xaml,windows-phone-8.1,C#,Windows,Xaml,Windows Phone 8.1,我有一个用户控件,其中定义了一些可视状态: 我将它用作ListView的ItemTemplate。当选中ListView中的项时,我还想更改DataTemplate的VisualState。目前我有这样一种方法: private void list\u SelectionChanged(对象发送者,selectionchangedventargs e) { ListView ListView=发件人作为ListView; foreach(e.AddedItems中的变量项) VisualSt
我将它用作ListView的ItemTemplate。当选中ListView中的项时,我还想更改DataTemplate的VisualState。目前我有这样一种方法:
private void list\u SelectionChanged(对象发送者,selectionchangedventargs e)
{
ListView ListView=发件人作为ListView;
foreach(e.AddedItems中的变量项)
VisualStateManager.GoToState((listView.ContainerFromItem(item)作为ListViewItem)。ContentTemplateRoot作为myControl,“Selected”,false);
}
它似乎可以工作,但在某些情况下,(listView.ContainerFromItem(item)as ListViewItem
为空,因此引发异常
是否有其他/更好的方法来更改所用数据模板的VisualState?项容器(即
ListViewItem
)是null
是因为ListView
的默认面板ItemsStackPanel
是一个基于像素的UI虚拟化面板,它仅在项目位于或接近当前视口时才渲染项目
由于您在代码中设置了所选项目,这些项目可能不会被呈现,它们的容器将返回为null
一个简单的修复方法是用一个普通的StackPanel
替换ItemsStackPanel
,但是这样做会破坏内置的虚拟化
这是另一个不修改面板的解决方案
首先,仍然需要现有代码,您只需要执行null检查,如果项目容器为null,则什么也不做
然后,您需要订阅ListView
的ContainerContentChangeing
事件。这会在项目容器加载时触发。因此,基本上,您会检查此处加载的项目是否为所选项目之一。如果是,则更改其视觉状态。类似于下面的内容-
private void MyListView_ContainerContentChanging(ListViewBase sender, ContainerContentChangingEventArgs args)
{
if (this.MyListView.SelectedItems.Contains(args.Item))
{
// get the container
var container = (ListViewItem)args.ItemContainer;
// do your visual state change here, when the container was previously null
}
}
因此,您希望listview项设置的visualstate也被UserControl中的VSM自动继承以反映它吗?只是为了确保我理解。@ChrisW。是的,没错。例如,我的UserControl中有一个TextBlock,而visual state manager更改了它的前景色。选择列表项后,我希望它触发。a你不能说在哪种情况下它不起作用?如果你发现了,你很可能能够修复它。如果你提供一些示例解决方案,我可以检查它。此外,我会使用
(cast)
,而不是,因为我观察到问题所在(并非总是如此)当我不是通过触摸屏幕来选择项目,而是从代码中选择项目时-例如,通过将它们添加到SelectedItems或setting IsSelected。我明天将尝试构建一个示例并给您一个提示。您的列表视图是否需要虚拟化?它是否需要处理大量数据?看起来像是一堆很好的信息,这将我会解释一切的。我会稍后再试,然后返回结果。这肯定是问题所在,现在一切正常。谢谢你的帮助。