#wpf #data-binding
#wpf #привязка данных
Вопрос:
Если у меня есть несортированная коллекция, есть ли простой способ связать и отсортировать ее. Я хотел бы сделать это в XAML (без Linq, без C #)
Если мой DataContext имеет свойство, скажем, myItems, его легко привязать к нему:
<ListBox ItemsSource={Binding MyItems}/>
Тем не менее, я бы хотел также отсортировать ее. Решением должно быть использование CollectionViewSource, но у меня это не работает:
<ListBox>
<ListBox.ItemsSource>
<Binding>
<Binding.Source>
<CollectionViewSource Source={Binding MyItems}/>
</Binding.Source>
</Binding>
</ListBox.ItemsSource>
</ListBox>
На этом этапе мой ListBox теряет свои элементы.
Я упускаю что-то очевидное?
Ответ №1:
Вы можете определить CollectionViewSource
как ресурс и обеспечить желаемую сортировку…
<Window.Resources>
<CollectionViewSource x:Key="cvs" Source="{Binding MyItems}">
<CollectionViewSource.SortDescriptions>
<scm:SortDescription PropertyName="MyItemName" Direction="Ascending"/>
</CollectionViewSource.SortDescriptions>
</CollectionViewSource>
</Window.Resources>
<Grid>
<ListBox ItemsSource="{Binding Source={StaticResource cvs}}"/>
</Grid>
scm
Пространство имен является xmlns:scm="clr-namespace:System.ComponentModel;assembly=WindowsBase"
Комментарии:
1. Спасибо за предложение. Однако мой listbox находится в DataTemplate, поэтому я не могу использовать ресурс. Почему он работает как ресурс, а не как источник привязки?
2. Ах, в вашем первоначальном ответе не было SortDescriptions , поэтому я ответил с ним, и вы отредактировали, чтобы включить
Ответ №2:
Создайте CollectionViewSource в CodeBehind, который считывается из myItems, и привяжите к нему свой ListBox
<ListBox ItemsSource="{Binding MyCollectionViewSource"} />
Комментарии:
1. В -1 OP конкретно указано, что они хотят избежать C # (код позади)
2. Не заслуживает значения -1. Конечно, в OP это сказано, но будущие пользователи, ищущие ответы на этот вопрос, могут посчитать вклад @Rachel ценным.
3. @Robaticus Все становятся не в форме при значении -1. Поскольку в OP явно указано, что C # не должен использоваться; линия должна быть где-то нарисована. Если OP явно не вызывал нежелание использовать C #, ответ был бы прекрасным. Попытка сохранить ответы относительно вопроса — это все.
4. @Aaron Я предположил, что OP не хочет никакого дополнительного кода для выполнения сортировки, такого как код за представлением или конвертер. Я все еще думаю, что лучше изменить источник ваших данных, чтобы он указывал на
CollectionViewSource
, а не непосредственно на список, если вы собираетесь его сортировать. При желании позже это также позволило бы использовать другие параметры сортировки.5. Я полностью согласен. Я возвращаю CollectionViewSource из моей ViewModel точно так, как вы рекомендовали. Явно укажите тот факт, что вы отметили ссылку OP на C # при редактировании, и я могу удалить значение -1. Опять же, это не говорит о том, что вы ошибаетесь… просто немного не по теме.
Ответ №3:
Ни один из других ответов фактически не касается сортировки. Они оба правы насчет CollectionViewSource
, но вы можете использовать это для выполнения сортировки с помощью CollectionViewSource.SortDescription
. Взято из здесь и изменено:
<Window.Resources>
<src:MyItems x:Key="MyItems"/>
<CollectionViewSource Source="{StaticResource MyItems}" x:Key="cvs">
<CollectionViewSource.SortDescriptions>
<scm:SortDescription PropertyName="CityName"/>
</CollectionViewSource.SortDescriptions>
</CollectionViewSource>
</Window.Resources>
<ListBox ItemsSource="{Binding Source={StaticResource cvs}}"
DisplayMemberPath="CityName" Name="lb">
<ListBox.GroupStyle>
<x:Static Member="GroupStyle.Default"/>
</ListBox.GroupStyle>
</ListBox>
В этом примере CityName
это будет свойство каждого элемента в MyItems
, используемое для выполнения сортировки
Комментарии:
1. ummm…my в ответе говорится о SortDescriptions.
2. @Aaron — этого не произошло, когда я впервые загрузил страницу. Вы отредактировали, чтобы включить. Конечно, правки в течение первых нескольких минут публикации не отображаются как правки, поэтому я не могу это доказать.