我试图用每个单独的用户控件创建一个listview。
MainPage.xaml:
<ListView Name="Shortcut_Holder"
ScrollViewer.VerticalScrollBarVisibility="Disabled"
ScrollViewer.HorizontalScrollBarVisibility="Disabled"
SelectionMode="Single"
SelectedIndex="-1"
HorizontalContentAlignment="Stretch"
ItemsSource="{Binding ShortcutList,
UpdateSourceTrigger=PropertyChanged,
ElementName=MainPage}">
<ListView.ItemsPanel>
<ItemsPanelTemplate>
<StackPanel Orientation="Horizontal" />
</ItemsPanelTemplate>
</ListView.ItemsPanel>
<ListView.ItemContainerStyle>
<Style TargetType="{x:Type ListViewItem}">
<Setter Property="Template">
<Setter.Value>
<ControlTemplate TargetType="{x:Type ListViewItem}">
<local:Exam_Folder />
</ControlTemplate>
</Setter.Value>
</Setter>
<Setter Property="HorizontalContentAlignment" Value="Stretch" />
</Style>
</ListView.ItemContainerStyle>
</ListView>
ShortcutList在页面的代码中绑定了自定义Usercontrol的ObservableCollection。该页面实现INotifyPropertyChange,并且在应用程序中的另一个事件上,将填充该集合。
MainPage.xaml.cs:
public ObservableCollection<Exam_Folder> ShortcutList
{
get => _shortcutlist;
set
{
_shortcutlist = value;
_shortcutdataview = new CollectionViewSource();
_shortcutdataview.Source = _shortcutlist;
NotifyPropertyChanged("ShortcutList");
}
}
private ObservableCollection<Exam_Folder> _shortcutlist { get; set; }
public ListCollectionView ShortCutDataView
{
get => (ListCollectionView)_shortcutdataview.View;
}
private CollectionViewSource _shortcutdataview { get; set; }
private void HandleExamListUpdate()
{
//Make shortcut list a new observable collection of
exam_folders
ShortcutList = new ObservableCollection<Exam_Folder>(CreateExamFolderUIList());
var view = (ListCollectionView)CollectionViewSource.GetDefaultView(ShortcutList);
view.CustomSort = new Exam_Folder_Comparer(((MainViewModel)DataContext).CurrentExamShortcutSort);
}
其中Exam_Folder是用户控件。我收到以下绑定错误:
System.Windows.Data Error: 4 : Cannot find source for binding with reference 'RelativeSource FindAncestor, AncestorType='System.Windows.Controls.ItemsControl', AncestorLevel='1''. BindingExpression:Path=HorizontalContentAlignment; DataItem=null; target element is 'ListViewItem' (Name=''); target property is 'HorizontalContentAlignment' (type 'HorizontalAlignment')
之后,应用程序崩溃。我对WPF还是很陌生,因此我尽力了。有什么想法吗?
编辑:
我现在将列表视图绑定到数据,而不是用户控件。我以为这可以解决我所遇到的错误,但是现在该错误有时会出现...我想说我有50%的时间运行该应用程序,但仍然崩溃了。
MainPage.xaml:
<!-- Listview ItemsSource needs to be bound to page since it's a collection of User Controls-->
<ListView Name="Shortcut_Holder"
ScrollViewer.VerticalScrollBarVisibility="Disabled"
ScrollViewer.HorizontalScrollBarVisibility="Disabled"
SelectionMode="Single"
SelectedIndex="-1"
SelectionChanged="Shortcut_Holder_SelectionChanged"
Background="Transparent"
BorderBrush="Transparent"
ItemsSource="{Binding ShortcutList,
UpdateSourceTrigger=PropertyChanged,
ElementName=MainPage}">
<ListView.Resources>
<Style TargetType="{x:Type ListViewItem}">
<Setter Property="Background" Value="Transparent" />
</Style>
</ListView.Resources>
<!-- How Listview items are laid out -->
<ListView.ItemsPanel>
<ItemsPanelTemplate>
<StackPanel Orientation="Horizontal" />
</ItemsPanelTemplate>
</ListView.ItemsPanel>
<!-- Data Template for each listview item-->
<ListView.ItemTemplate>
<DataTemplate>
<local:Exam_Folder DisplayText="{Binding Converter={local:ExamShortcutDisplayTextValueConverter}}" />
</DataTemplate>
</ListView.ItemTemplate>
<!-- Style for each listview item -->
<ListView.ItemContainerStyle>
<Style TargetType="{x:Type ListViewItem}">
<Setter Property="Padding" Value="0" />
<Setter Property="Background" Value="Transparent" />
<Setter Property="HorizontalContentAlignment" Value="Stretch" />
<Setter Property="Margin" Value="5,0,5,0" />
<Setter Property="Template">
<Setter.Value>
<ControlTemplate TargetType="{x:Type ListViewItem}">
<ContentPresenter />
</ControlTemplate>
</Setter.Value>
</Setter>
<!-- Change cursor style over each list item on mouse hover -->
<Style.Triggers>
<Trigger Property="IsMouseOver" Value="True">
<Setter Property="ForceCursor" Value="True" />
<Setter Property="Cursor" Value="Hand" />
</Trigger>
</Style.Triggers>
</Style>
</ListView.ItemContainerStyle>
</ListView>
MainPage.xaml.cs:
private void HandleExamListUpdate(bool RefreshList = true)
{
//Make shortcut list a new observable collection of exam_folders
if (ShortcutList == null || ShortcutList.Count == 0 || RefreshList)
ShortcutList = new ObservableCollection<ExamType>(Ioc.Get<ApplicationViewModel>().CurrentPatient.PatientExams);
var view = (ListCollectionView)CollectionViewSource.GetDefaultView(ShortcutList);
view.CustomSort = new Exam_Folder_Comparer(((MainViewModel)DataContext).CurrentExamShortcutSort);
//Calculate how many folders can be displayed given the width of the control
//If there has been no change in the amount of exam folders we need to display, no need to do anything else
//Have to do math on the overall top grid, bc the stackpanel that holds the folders would initially have its actualwidth skewed by the
//possible amount of controls in it.
int holdingnumber = (int)(Math.Ceiling((Top_View.ActualWidth - TopCol1.ActualWidth - TopCol3.ActualWidth) / WIDTH_PER_SHORTCUT));
//Apply filter based on the amount of controls we can hold
view.Filter = new Predicate<object>(o =>
{
if (ShortcutList.IndexOf((ExamType)o) < holdingnumber)
return true;
return false;
});
}
为了完整起见,这是我正在使用的Usercontrol的xaml:
<UserControl x:Class="Tomo_GUI.Exam_Folder"
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
xmlns:local="clr-namespace:Tomo_GUI"
xmlns:svgc="http://sharpvectors.codeplex.com/svgc/"
mc:Ignorable="d"
Background="Transparent"
d:DesignHeight="100" d:DesignWidth="120">
<Grid>
<Grid.RowDefinitions>
<RowDefinition Height="*" />
<RowDefinition Height="*" />
<RowDefinition Height="*" />
</Grid.RowDefinitions>
<svgc:SvgViewbox Grid.RowSpan="3">
<svgc:SvgViewbox.Style>
<Style TargetType="svgc:SvgViewbox">
<Setter Property="local:SvgcViewboxAttachedProperties.Source" Value="{Binding ImagePath,
RelativeSource={RelativeSource AncestorType={x:Type UserControl}}}" />
<Style.Triggers>
<DataTrigger Binding="{Binding IsMouseOver,
RelativeSource={RelativeSource AncestorType={x:Type UserControl}}}"
Value="True">
<Setter Property="local:SvgcViewboxAttachedProperties.Source" Value="\Images\TopView\Exam_File_Icon_Colored.svg" />
</DataTrigger>
</Style.Triggers>
</Style>
</svgc:SvgViewbox.Style>
</svgc:SvgViewbox>
<TextBlock FontSize="{StaticResource FontSizeRegularSmall}"
FontWeight="Black"
Grid.Row="1"
VerticalAlignment="Center"
HorizontalAlignment="Center"
Background="Transparent"
Text="{Binding DisplayText,
RelativeSource={RelativeSource AncestorType={x:Type UserControl}}}"
Name="BlockText">
</TextBlock>
</Grid>
现在,当最初加载集合时,有时会出现相同的错误;或者,如果我更改集合上的过滤器,有时会出现相同的错误。有什么想法会发生什么吗?
答案 0 :(得分:-1)
public class main
{
DataClass dc = new DataClass();
public void yourinitialmethod()
{
InitializeComponents();
this.DataContext = dc;
}
}
请勿在XAML中使用ElementName=...
,而最好使用全局(窗口)DataContext。
它的DataContext深度会自动持续到项目容器本身(在这种情况下不需要它)