UWP 切换开关仅切换视图中的其他项目
我知道这对您来说可能非常基础,但请原谅我,因为我是 UWP 的新手。
渲染的非常基本的对象列表,
<ListView Grid.Row="2" Grid.ColumnSpan="2" BorderBrush="#FF141EE4" Name="BillsList"
SelectionChanged="BillsList_SelectionChanged"
FontFamily="Arial"
FlowDirection="LeftToRight" Height="250" >
<ListView.ItemTemplate>
<DataTemplate>
<Grid Margin="2">
<Border BorderBrush="Black" BorderThickness="1">
<Grid>
<Grid.RowDefinitions>
<RowDefinition Height="Auto"/>
<RowDefinition Height="Auto"/>
<RowDefinition Height="Auto"/>
<RowDefinition Height="Auto"/>
<RowDefinition Height="Auto"/>
<RowDefinition Height="Auto"/>
</Grid.RowDefinitions>
<TextBlock Margin="5,0,0,0" Grid.Row="0" x:Name="BookTxt" TextWrapping="Wrap" Text="{Binding bilng_date, Converter={StaticResource billingDateFormatter }}" FontSize="16" Foreground="Black" FontFamily="Arial"/>
<TextBlock Grid.Row="0" Text="الدورة" FontSize="20" HorizontalAlignment="Right" VerticalAlignment="Center" Foreground="Black" FontFamily="Arial"/>
<TextBlock Margin="5,0,0,0" Grid.Row="1" x:Name="WalkTxt" TextWrapping="Wrap" Foreground="Black" FontSize="16" Text="{Binding cl_blnce}" FontFamily="Arial"/>
<TextBlock Grid.Row="1" Text="القيمة" FontSize="20" HorizontalAlignment="Right" VerticalAlignment="Center" Foreground="Black" FontFamily="Arial"/>
<TextBlock Margin="5,0,0,0" Grid.Row="2" x:Name="paymentTxt" TextWrapping="Wrap" Foreground="Black" FontSize="16" Text="{Binding payment_no}" FontFamily="Arial"/>
<TextBlock Grid.Row="2" Text="رقم الفاتورة" FontSize="20" HorizontalAlignment="Right" VerticalAlignment="Center" Foreground="Black" FontFamily="Arial"/>
<TextBlock Margin="5,0,0,0" Grid.Row="3" x:Name="CollectionState" Text="{Binding delivery_st , Converter={StaticResource AvailabilityToColorConverter}}" TextWrapping="Wrap" Foreground="Black" FontSize="16" FontFamily="Arial"/>
<TextBlock Grid.Row="3" Text="حاله الفاتوره" FontSize="20" HorizontalAlignment="Right" VerticalAlignment="Center" Foreground="Black" FontFamily="Arial"/>
<ToggleSwitch Grid.Row="4" IsOn="False" Toggled="AddToBillsList_Toggled" OffContent="إضافه لقائمه التحصيل" OnContent="حذف من قائمه التحصيل" Visibility="{Binding delivery_st, Converter={StaticResource AvailabilityToCollection}}" />
</Grid>
</Border>
</Grid>
</DataTemplate>
</ListView.ItemTemplate>
<ListView.ItemContainerStyle>
<Style TargetType="ListViewItem">
<Setter Property="HorizontalContentAlignment" Value="Stretch" />
<!--<Setter Property="Background" Value="LightGreen"/>-->
</Style>
</ListView.ItemContainerStyle>
</ListView>
我有使用 Listview AddToBillsList_Toggled 函数
private void AddToBillsList_Toggled(object sender, RoutedEventArgs e)
{
ToggleSwitch toggle = sender as ToggleSwitch;
if (toggle != null)
{
try
{
var dataContext = toggle.DataContext;
var dataItem = (HAND_MH_ST)dataContext;
if (toggle.IsOn == true)
{
dataItem.isselected = true;
statmentCount++;
cl_balance += float.Parse(dataItem.cl_blnce);
statmentsCount.Text = statmentCount.ToString();
statmentsAmount.Text = cl_balance.ToString();
Search_statmentsCount.Text = statmentCount.ToString();
Search_statmentsAmount.Text = cl_balance.ToString();
customersBills.Add(dataItem);
}
if (toggle.IsOn == false)
{
dataItem.isselected = false;
var idx2 = BillsList.SelectedIndex;
statmentCount--;
cl_balance -= float.Parse(dataItem.cl_blnce);
statmentsCount.Text = statmentCount.ToString();
statmentsAmount.Text = cl_balance.ToString();
customersBills.Remove(dataItem);
}
}
catch (Exception ex)
{
var dialog = new MessageDialog($@"{ex.Message}");
dialog.ShowAsync().AsTask().Wait();
}
}
}
一切进展顺利,
但是当我使用切换开关时,切换的项目被添加到另一个列表(我想要的),但我发现另一个项目被切换(仅在视图中) )并且当我滚动时不添加到其他列表。
因此,我对包含所有切换项目的其他列表采取的任何操作都进展顺利,但查看它的问题
无法找到为什么会发生这种行为来修复它
编辑
我在一个全新的应用程序中模拟了问题,如下所示
这是主页代码它在列表视图中生成 1000 个项目
代码
public class test
{
public int id { get; set; }
public string name { get; set; }
}
public sealed partial class MainPage : Page
{
public MainPage()
{
this.InitializeComponent();
this.Loaded += CreateData;
}
List<test> Holders = new List<test>();
public void CreateData(object sender, RoutedEventArgs e)
{
for (int i = 0; i < 1000; i++)
{
test obj = new test();
obj.id = i;
obj.name = "Toggle";
Holders.Add(obj);
}
ListObjects.ItemsSource = Holders;
}
private void ListObjects_SelectionChanged(object sender, SelectionChangedEventArgs e)
{
}
}
}
这是当我选择前 3 个元素时主页的视图
<Page
x:Class="App1.MainPage"
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
xmlns:local="using:App1"
xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
mc:Ignorable="d"
Background="Bisque">
<Grid>
<ListView Grid.Row="3" Grid.Column="0" Grid.ColumnSpan="3" BorderBrush="#FF141EE4" HorizontalAlignment="Stretch" VerticalAlignment="Stretch" Name="ListObjects"
SelectionChanged="ListObjects_SelectionChanged" FlowDirection="LeftToRight"
FontFamily="Arial"
Height="250"
>
<ListView.ItemTemplate>
<DataTemplate>
<Grid Margin="2">
<Border Margin="2" BorderBrush="Black" BorderThickness="1" >
<Grid>
<Grid.RowDefinitions>
<RowDefinition Height="Auto"/>
<RowDefinition Height="Auto"/>
</Grid.RowDefinitions>
<TextBlock Margin="5,0,0,0" Grid.Row="0" x:Name="SBookTxt" TextWrapping="Wrap" Text="{Binding name}" FontSize="16" Foreground="Black" FontFamily="Arial"/>
<ToggleSwitch Grid.Row="1" Name="SaddToBillsList" IsOn="False" OffContent="Removed" OnContent="Added" />
</Grid>
</Border>
</Grid>
</DataTemplate>
</ListView.ItemTemplate>
<ListView.ItemContainerStyle>
<Style TargetType="ListViewItem">
<Setter Property="HorizontalContentAlignment" Value="Stretch" />
<Setter Property="Background" Value="LightGreen"/>
</Style>
</ListView.ItemContainerStyle>
</ListView>
</Grid>
,例如一切正常
正常选择,
但是当我向下滚动时,我发现元素被切换,并真正切换了它们
,当我滚动回我在第一个位置选择的前 3 个项目时,我发现一个元素已被删除
I know this is maybe very basic to you, but excuse me as am new in UWP .
i has very basic List of objects rendered using Listview
<ListView Grid.Row="2" Grid.ColumnSpan="2" BorderBrush="#FF141EE4" Name="BillsList"
SelectionChanged="BillsList_SelectionChanged"
FontFamily="Arial"
FlowDirection="LeftToRight" Height="250" >
<ListView.ItemTemplate>
<DataTemplate>
<Grid Margin="2">
<Border BorderBrush="Black" BorderThickness="1">
<Grid>
<Grid.RowDefinitions>
<RowDefinition Height="Auto"/>
<RowDefinition Height="Auto"/>
<RowDefinition Height="Auto"/>
<RowDefinition Height="Auto"/>
<RowDefinition Height="Auto"/>
<RowDefinition Height="Auto"/>
</Grid.RowDefinitions>
<TextBlock Margin="5,0,0,0" Grid.Row="0" x:Name="BookTxt" TextWrapping="Wrap" Text="{Binding bilng_date, Converter={StaticResource billingDateFormatter }}" FontSize="16" Foreground="Black" FontFamily="Arial"/>
<TextBlock Grid.Row="0" Text="الدورة" FontSize="20" HorizontalAlignment="Right" VerticalAlignment="Center" Foreground="Black" FontFamily="Arial"/>
<TextBlock Margin="5,0,0,0" Grid.Row="1" x:Name="WalkTxt" TextWrapping="Wrap" Foreground="Black" FontSize="16" Text="{Binding cl_blnce}" FontFamily="Arial"/>
<TextBlock Grid.Row="1" Text="القيمة" FontSize="20" HorizontalAlignment="Right" VerticalAlignment="Center" Foreground="Black" FontFamily="Arial"/>
<TextBlock Margin="5,0,0,0" Grid.Row="2" x:Name="paymentTxt" TextWrapping="Wrap" Foreground="Black" FontSize="16" Text="{Binding payment_no}" FontFamily="Arial"/>
<TextBlock Grid.Row="2" Text="رقم الفاتورة" FontSize="20" HorizontalAlignment="Right" VerticalAlignment="Center" Foreground="Black" FontFamily="Arial"/>
<TextBlock Margin="5,0,0,0" Grid.Row="3" x:Name="CollectionState" Text="{Binding delivery_st , Converter={StaticResource AvailabilityToColorConverter}}" TextWrapping="Wrap" Foreground="Black" FontSize="16" FontFamily="Arial"/>
<TextBlock Grid.Row="3" Text="حاله الفاتوره" FontSize="20" HorizontalAlignment="Right" VerticalAlignment="Center" Foreground="Black" FontFamily="Arial"/>
<ToggleSwitch Grid.Row="4" IsOn="False" Toggled="AddToBillsList_Toggled" OffContent="إضافه لقائمه التحصيل" OnContent="حذف من قائمه التحصيل" Visibility="{Binding delivery_st, Converter={StaticResource AvailabilityToCollection}}" />
</Grid>
</Border>
</Grid>
</DataTemplate>
</ListView.ItemTemplate>
<ListView.ItemContainerStyle>
<Style TargetType="ListViewItem">
<Setter Property="HorizontalContentAlignment" Value="Stretch" />
<!--<Setter Property="Background" Value="LightGreen"/>-->
</Style>
</ListView.ItemContainerStyle>
</ListView>
the AddToBillsList_Toggled function
private void AddToBillsList_Toggled(object sender, RoutedEventArgs e)
{
ToggleSwitch toggle = sender as ToggleSwitch;
if (toggle != null)
{
try
{
var dataContext = toggle.DataContext;
var dataItem = (HAND_MH_ST)dataContext;
if (toggle.IsOn == true)
{
dataItem.isselected = true;
statmentCount++;
cl_balance += float.Parse(dataItem.cl_blnce);
statmentsCount.Text = statmentCount.ToString();
statmentsAmount.Text = cl_balance.ToString();
Search_statmentsCount.Text = statmentCount.ToString();
Search_statmentsAmount.Text = cl_balance.ToString();
customersBills.Add(dataItem);
}
if (toggle.IsOn == false)
{
dataItem.isselected = false;
var idx2 = BillsList.SelectedIndex;
statmentCount--;
cl_balance -= float.Parse(dataItem.cl_blnce);
statmentsCount.Text = statmentCount.ToString();
statmentsAmount.Text = cl_balance.ToString();
customersBills.Remove(dataItem);
}
}
catch (Exception ex)
{
var dialog = new MessageDialog($@"{ex.Message}");
dialog.ShowAsync().AsTask().Wait();
}
}
}
every things goes very well
but when I use toggle switch the item toggled is added to another list( which what I want ), but i find another items got toggled ( in view only) and not add to other list when I scroll .
so any action i took on other list that containes all toggled items goes very well, but view something wrong with it
cant find why such a behavior happened to fix it
Edit
I simulated the problem as follow in a completely new app
this is the mainpage code which generate 1000 items in the listview
the Code
public class test
{
public int id { get; set; }
public string name { get; set; }
}
public sealed partial class MainPage : Page
{
public MainPage()
{
this.InitializeComponent();
this.Loaded += CreateData;
}
List<test> Holders = new List<test>();
public void CreateData(object sender, RoutedEventArgs e)
{
for (int i = 0; i < 1000; i++)
{
test obj = new test();
obj.id = i;
obj.name = "Toggle";
Holders.Add(obj);
}
ListObjects.ItemsSource = Holders;
}
private void ListObjects_SelectionChanged(object sender, SelectionChangedEventArgs e)
{
}
}
}
here is the view of the main page
<Page
x:Class="App1.MainPage"
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
xmlns:local="using:App1"
xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
mc:Ignorable="d"
Background="Bisque">
<Grid>
<ListView Grid.Row="3" Grid.Column="0" Grid.ColumnSpan="3" BorderBrush="#FF141EE4" HorizontalAlignment="Stretch" VerticalAlignment="Stretch" Name="ListObjects"
SelectionChanged="ListObjects_SelectionChanged" FlowDirection="LeftToRight"
FontFamily="Arial"
Height="250"
>
<ListView.ItemTemplate>
<DataTemplate>
<Grid Margin="2">
<Border Margin="2" BorderBrush="Black" BorderThickness="1" >
<Grid>
<Grid.RowDefinitions>
<RowDefinition Height="Auto"/>
<RowDefinition Height="Auto"/>
</Grid.RowDefinitions>
<TextBlock Margin="5,0,0,0" Grid.Row="0" x:Name="SBookTxt" TextWrapping="Wrap" Text="{Binding name}" FontSize="16" Foreground="Black" FontFamily="Arial"/>
<ToggleSwitch Grid.Row="1" Name="SaddToBillsList" IsOn="False" OffContent="Removed" OnContent="Added" />
</Grid>
</Border>
</Grid>
</DataTemplate>
</ListView.ItemTemplate>
<ListView.ItemContainerStyle>
<Style TargetType="ListViewItem">
<Setter Property="HorizontalContentAlignment" Value="Stretch" />
<Setter Property="Background" Value="LightGreen"/>
</Style>
</ListView.ItemContainerStyle>
</ListView>
</Grid>
when i select the first 3 elements for example every thing is ok
but when i scroll down i found elements got toggled with really toggling them
Toggle Selected without really toggling them
and when i scroll back to the first 3 items i selected at first place i found one element removed
如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。
绑定邮箱获取回复消息
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
发布评论
评论(1)
此行为是由 UI虚拟化。当您显示大量项目时,它不会同时为 ListView 创建所有项目。有时它会重复使用旧物品。这可以提高性能。
第一种方法是您可以替换 ListView 的默认
ItemsStackPanel
。这将禁用UI虚拟化并且将避免这种行为。但你会损失一些性能。第二种方法是您需要将
ToggleSwitch
绑定到 ViewModel 内的 bool 值。使用绑定可以降低发生这种情况的可能性,但不能完全禁用这种行为。This behavior is caused by the UI virtualization. It will not create all the items at the same time for the ListView when you are showing large amount of items. And sometimes it will reuse the old items. This could improve the performance.
The first way to this is that you could replace the default
ItemsStackPanel
of the ListView. This will disable the UI virtualization and this behavior will be avoided. But you will lose some performance.The second way is that you need to bind the
ToggleSwitch
to a bool value inside the ViewModel. Using binding could reduce the probability of this happening but it can't completely disable this behavior.