#c# #xaml #windows-runtime #windows-phone-8.1
#c# #xaml #windows-среда выполнения #windows-phone-8.1
Вопрос:
У меня возникли проблемы с прокруткой списков просмотра в моем приложении Windows Phone 8.1. Короткие списки прокручиваются просто отлично, прокручиваются плавно, однако, как только запускается виртуализация, весь ListView слегка «колеблется» влево, но достаточно заметно, чтобы раздражать.
Я пытался удалить все переходы безрезультатно, а также загружать элементы постепенно, но безуспешно. Установка панели элементов на StackPanel (удаление виртуализации) устраняет проблему, но не является предпочтительной.
Мои listviews привязаны к свойству в DefaultViewModel, которое поставляется с базовым шаблоном страницы.
Что я делаю не так и что заставляет мои просмотры списков демонстрировать такое поведение?
XAML:
<ListView x:Name="searchResultsList" IsItemClickEnabled="True" ItemClick="ListView_ItemClick" ItemsSource="{Binding searchResults}">
<ListView.ItemContainerStyle>
<Style TargetType="ListViewItem">
<Setter Property="HorizontalContentAlignment" Value="Stretch"/>
<Setter Property="Margin" Value="0,0,0,20" />
</Style>
</ListView.ItemContainerStyle>
<ListView.ItemTemplate>
<DataTemplate>
<Grid>
<Grid.ColumnDefinitions>
<ColumnDefinition Width="80" />
<ColumnDefinition Width="10" />
<ColumnDefinition Width="*" />
</Grid.ColumnDefinitions>
<Border Width="80" Height="80">
<Image Source="{Binding Image}" />
</Border>
<StackPanel Grid.Column="2">
<TextBlock Text="{Binding PodcastTitle}" TextWrapping="WrapWholeWords" FontSize="{StaticResource TextStyleExtraLargeFontSize}" />
<TextBlock Text="{Binding LastUpdated, Converter={StaticResource dateConverter}}" Style="{ThemeResource ListViewItemSubheaderTextBlockStyle}" />
<TextBlock Text="{Binding PodcastArtist}" TextWrapping="WrapWholeWords" Style="{ThemeResource ListViewItemContentTextBlockStyle}" />
</StackPanel>
</Grid>
</DataTemplate>
</ListView.ItemTemplate>
</ListView>
Комментарии:
1. Так что «колебания» — это то, что нужно было поискать в Google… Я не мог понять, как описать это явление …!
2. @FactorMystic Здесь то же самое. Я не знал, что искать. Я думаю, именно по этой причине этот вопрос не привлекает достаточного внимания.
Ответ №1:
Похоже, это проблема с ОС, о чем свидетельствует эта тема на форумах MS: http://social.msdn.microsoft.com/Forums/en-US/9a363d33-5760-4d38-9c81-84259c4edcbe/listview-jiggles-horizontally-when-large-item-about-to-scroll-in-or-out-in-windows-phone-81-preview?forum=WindowsPhonePreviewSDKamp;prof=required.
Проблема действительно заключается в виртуализации, с элементами, которые не имеют фиксированной ширины. Использование звезды в качестве ширины или растягивание горизонтального выравнивания не будет работать, поэтому единственным решением, учитывающим ориентацию и разрешение, было привязать ширину к свойству ActualWidth контейнера ListView:
<Grid x:name="contentRoot" Margin="19,9.5,19,0">
<ListView>
<ListView.ItemTemplate>
<DataTemplate>
<Grid Width={Binding ActualWidth, ElementName=contentRoot} />
</DataTemplate>
</ListView.ItemTemplate>
</ListView>
</Grid>
Комментарии:
1. Это приведет к тому, что мой первый элемент в списке не будет отображаться, какие-либо предложения?
2. Использовал его для UserControl, и все было хорошо, но вдруг я заметил, что эта привязанная ширина не соответствует ширине корня при изменениях времени выполнения, таких как рейтинг устройства. Корневые полосы отображаются в альбомной ориентации, а элементы списка — нет. Могу ли я что-нибудь с этим сделать?
3. Как насчет того, что ItemTemplate был определен выше, и у вас есть только ItemTemplateSelector. Я попробовал это, но, похоже, ItemTemplate не может привязываться к ширине сетки контейнера. Я застрял здесь.
4.
<ListView Grid.Row="1" x:Name="ListViewEvents" Loaded="OnListViewEventsLoaded" ItemsSource="{Binding xx}" ItemTemplateSelector="{StaticResource xx}" ItemContainerStyle="{StaticResource xx}" IsItemClickEnabled="True">
Вот так, как же тогда использовать этот метод? Спасибо!
Ответ №2:
Первый элемент в listview не отображается, потому что ActualWidth сетки равен 0 в первую секунду при загрузке страницы. Это решение, которое работает для меня:
<Grid x:Name="contentRoot" Margin="20">
<ListView>
<ListView.ItemTemplate>
<DataTemplate>
<Grid MinWidth="{Binding ActualWidth, ElementName=contentRoot}" />
</DataTemplate>
</ListView.ItemTemplate>
</ListView>
</Grid>
Ответ №3:
Это действительно досадная ошибка. Я не могу понять, почему это не исправлено с годами.
Imho растягивание элементов в списке с вертикальной прокруткой является очень простой функцией и должно работать на 100%.
Возможный обходной путь также сокращен, что также должно учитывать изменения размера :
public class StrechItemsListView : ListView
{
public StrechItemsListView()
{
SizeChanged = StrechItemsListView_SizeChanged;
}
private void StrechItemsListView_SizeChanged(object sender, SizeChangedEventArgs e)
{
if (ItemsPanelRoot != null)
{
ItemsPanelRoot.Width = e.NewSize.Width;
}
}
}
Изменение xaml только на пользовательский тип listview требует меньше работы и чище, Чем редактирование каждой таблицы данных и т. Д. Только мои 2 цента.
Комментарии:
1. Спасибо, это помогло! Просто и быстро!
Ответ №4:
Моя практика, похоже, работает. По крайней WP8.1
мере.
Просто установите ItemsPanelTemplate
в <ListView></ListView>
блоке явно, но не используйте
Style="{StaticResource ListViewStyle1}"
или что-то еще.
Пример кода:
<ListView ItemsSource="{Binding RadioList}" ScrollViewer.HorizontalScrollBarVisibility="Hidden" ScrollViewer.HorizontalScrollMode="Disabled"
ScrollViewer.VerticalScrollBarVisibility="Hidden" ScrollViewer.VerticalScrollMode="Auto">
<ListView.ItemTemplate>
<DataTemplate>
<Grid Margin="10,3,10,0">
<TextBlock Text="{Binding RadioName}" FontSize="15" VerticalAlignment="Center" HorizontalAlignment="Center"/>
</Grid>
</DataTemplate>
</ListView.ItemTemplate>
<ListView.ItemContainerStyle>
<Style TargetType="ListViewItem">
<Setter Property="HorizontalContentAlignment" Value="Stretch"/>
</Style>
</ListView.ItemContainerStyle>
<ListView.ItemsPanel>
<ItemsPanelTemplate>
<VirtualizingStackPanel Orientation="Vertical" Width="{Binding PhoneWidth}"/>
</ItemsPanelTemplate>
</ListView.ItemsPanel>
</ListView>
Параметры HorizontalContentAlignment
и Width
VirtualizingStackPanel
используются для центрирования содержимого в ListView
.Вы можете свободно перемещать эти настройки.Я не знаю почему, но это работает.
Ответ №5:
Это было исправлено в Windows 10 для приложений Windows 8.1