我有一个多平台的Xamarin项目,它有一个MainPage(称为OVerviewPage),它有多个FlexLayouts,每个FlexLayouts都绑定到不同的BindableLayout. ItemSource。每个FlexLayouts的BindableLayout.ItemTemplate都是一个ContentView,每个FlexLayouts的格式都类似,但每个FlexLayouts都有一个不同的ViewModel. Model。每个ContentView都有自己的<Frame.GestureRecognizers>TapGestureRocgnizer,调用在代码后面处理的Tapped事件。这些Flexlayouts Package 在ScrollView中,ScrollView也 Package 在RefreshView中。目的是让用户单击其中一个,以便将ContentViews带到详细信息页面。问题是RefreshView在Windows桌面上为UWP编译时会导致冲突。问题是,在向下滚动列表并且用户单击ContentView之后,将调用不同ContentView的TappedEvent处理程序,而不是用户实际单击的那个。实际上,当表单首次加载时,屏幕上可见3个ContentView,当其他人滚动到并驻留在前3个中的一个的位置时,只有前3个中的一个的点击事件会响应单击,这取决于用户单击的屏幕上的位置。当我在xaml中注解RefreshView时,单击按预期工作。我知道RefreshView不是为桌面设备设计的,我试图使用以下命令禁用它:if(Device.Idiom == DeviceIdiom.Desktop){refreshview.IsEnabled = false},但这不起作用。仅仅因为它在xaml中被标识这一事实就导致了冲突。有几个注意事项:这个页面是Shell应用程序的主页,任何解决方案都需要考虑到这一点。我也愿意接受大多数解决方案。提前感谢
我的概述页面:(仅相关代码)
<RefreshView IsRefreshing="{Binding IsRefreshing, Mode=OneWay}"
RefreshColor="Teal"
Command="{Binding RefreshCommand}">
<ScrollView>
<StackLayout Margin="10,0,10,0">
<FlexLayout Direction="Column"
Wrap="NoWrap"
AlignItems="Stretch"
AlignContent="Center"
BindableLayout.ItemsSource="{Binding TrackWarrants}"
BindableLayout.ItemTemplate="{StaticResource TrackWarrantTemplate}"
BindableLayout.EmptyViewTemplate="{StaticResource EmptyWarrantTemplate}"/>
<!--Form As-->
<FlexLayout Direction="Column"
Wrap="NoWrap"
AlignItems="Stretch"
AlignContent="Center"
BindableLayout.ItemsSource="{Binding FormAs}"
BindableLayout.ItemTemplate="{StaticResource FormATemplate}"
BindableLayout.EmptyViewTemplate="{StaticResource EmptyFormATemplate}"/>
<!--Form Bs-->
<FlexLayout Direction="Column"
Wrap="NoWrap"
AlignItems="Stretch"
AlignContent="Center"
BindableLayout.ItemsSource="{Binding FormBs}"
BindableLayout.ItemTemplate="{StaticResource FormBTemplate}"
BindableLayout.EmptyViewTemplate="{StaticResource EmptyFormBTemplate}"/>
<!--Form Cs-->
<FlexLayout Direction="Column"
Wrap="NoWrap"
AlignItems="Stretch"
AlignContent="Center"
BindableLayout.ItemsSource="{Binding FormCs}"
BindableLayout.ItemTemplate="{StaticResource FormCTemplate}"
BindableLayout.EmptyViewTemplate="{StaticResource EmptyFormCTemplate}"/>
ContentViews代码:(仅1,例如,除数据放置外,它们都相同)
<ContentView.Content>
<Frame>
<Frame.GestureRecognizers>
<TapGestureRecognizer CommandParameter="{Binding}" Tapped="FormA_Tapped" />
</Frame.GestureRecognizers>
<Grid >
<Grid.ColumnDefinitions>
<ColumnDefinition Width="30"/>
<ColumnDefinition Width="70"/>
<ColumnDefinition Width="25"/>
<ColumnDefinition Width="25"/>
<ColumnDefinition Width="25"/>
<ColumnDefinition Width="30"/>
<ColumnDefinition Width="95"/>
</Grid.ColumnDefinitions>
<Grid.RowDefinitions>
<RowDefinition Height="25"/>
<RowDefinition Height="25"/>
<RowDefinition Height="Auto"/>
<RowDefinition Height="20"/>
</Grid.RowDefinitions>
<StackLayout Grid.Column="0" Grid.Row="0" Grid.RowSpan="2" Grid.ColumnSpan="2" HorizontalOptions="StartAndExpand" VerticalOptions="Start"
Orientation="Horizontal" WidthRequest="130" >
<Label FontFamily="Material" FontSize="Large" Text="{Binding Icon}" HorizontalOptions="Start" VerticalOptions="Start"
Grid.Column="0" Grid.Row="0" Grid.RowSpan="2">
<Label.Triggers>
<DataTrigger TargetType="Label" Binding="{Binding Source={x:Reference Reject},Path=Text}" Value="True">
<Setter Property="TextColor" Value="Black"/>
</DataTrigger>
</Label.Triggers>
</Label>
<Label FontSize="Medium" FontAttributes="Bold" HorizontalOptions="Start"
VerticalOptions="Start" x:Name="FormID">
<Label.FormattedText>
<FormattedString>
<Span Text="{Binding FormNumber}"/>
<Span Text="-"/>
<Span Text="{Binding LineNo}"/>
</FormattedString>
</Label.FormattedText>
<Label.Triggers>
<DataTrigger TargetType="Label" Binding="{Binding Source={x:Reference Reject},Path=Text}" Value="True">
<Setter Property="TextColor" Value="Black"/>
</DataTrigger>
</Label.Triggers>
</Label>
<StackLayout.Triggers>
<DataTrigger TargetType="StackLayout" Binding="{Binding Source={x:Reference Reject},Path=Text}" Value="True">
<Setter Property="BackgroundColor" Value="Salmon"/>
</DataTrigger>
</StackLayout.Triggers>
</StackLayout>
<Label Text="{Binding Territory}"
FontSize="Small"
VerticalOptions="Center"
HorizontalOptions="Start"
Grid.Column="0"
Grid.Row="3" Grid.ColumnSpan="6" />
<Label FontFamily="Material"
FontSize="Small"
Text="{x:Static md:MaterialDesignIcons.MyLocation}"
HorizontalOptions="Center"
Grid.Column="2"
Grid.Row="0" />
<Label Text="{Binding From}"
FontSize="Small"
Grid.Column="3"
Grid.Row="0" Grid.ColumnSpan="4" />
<Label FontFamily="Material"
FontSize="Small"
Text="{x:Static md:MaterialDesignIcons.LocationOn}"
HorizontalOptions="Center"
Grid.Column="2"
Grid.Row="1" />
<Label Text="{Binding End}"
FontSize="Small"
Grid.Column="3"
Grid.Row="1" Grid.ColumnSpan="4" />
<Label FontSize="Small"
FontAttributes="Bold"
HorizontalOptions="StartAndExpand"
Grid.Column="1"
Grid.Row="2"
Grid.ColumnSpan="5">
<Label.FormattedText>
<FormattedString>
<Span Text="Speed: "/>
<Span Text="{Binding Speed}"/>
</FormattedString>
</Label.FormattedText>
</Label>
<Label x:Name="Reject" Text="{Binding Rejected}"
FontSize="Small"
Grid.Column="0"
Grid.Row="3" IsVisible="False" />
<Label x:Name="status" Text="{Binding StatusID}"
FontSize="Small"
Grid.Column="0"
Grid.Row="3" IsVisible="False" ></Label>
</Grid>
</Frame>
</ContentView.Content>
ContentView的相关代码:
public FormACard()
{
InitializeComponent();
formaviewmodel = new FormAViewModel();
BindingContext = formaviewmodel;
}
private async void FormA_Tapped(object sender, EventArgs e)
{
var user = App.LoggedInUser.UserName;
var ea = e as TappedEventArgs;
if (ea.Parameter != null)
{
var forminfo = JsonConvert.SerializeObject(ea.Parameter);
string _forminfo = Uri.EscapeDataString(forminfo);
FormA forma = (FormA)ea.Parameter;
bool rejectAck = forma.RejectionAcked;
bool rejected = forma.Rejected;
string requestor = forma.RequestedBy;
if (!rejectAck && rejected && requestor == user)
{
await Shell.Current.GoToAsync($"{nameof(RejectACK)}?{nameof(RejectACK.Contentx)}={_forminfo}");
}
else
{
await Shell.Current.GoToAsync($"viewforma?Content={_forminfo}");
}
}
}
顺便说一句-如果这看起来很熟悉,我在信息较少的时候在另一个线程中发布了这个问题。我关闭了另一个线程,并用新鲜的信息打开了这个线程。
1条答案
按热度按时间ylamdve61#
问题是,在向下滚动列表并且用户单击ContentView之后,将调用另一个ContentView的TappedEvent处理程序,而不是用户实际单击的那个。
关于“Xamarin RefreshView导致UWP上的Tapped Event冲突”,我在GitHub上找到了这个:[Bug] Wrong behavior using BindableLayout wrapped by a RefreshView。链接提到:
基于您的repro测试了这个。发现它与BindableLayout无关:你可以完全消除它,只是直接创建20帧,它会导致同样的错误行为。(UWP RefreshContainer)被使用-点击事件被分派到错误的UI控件和/或滚动偏移未被正确考虑。目前不确定这是XF错误还是UWP RefreshContainer中的问题,即使我没有找到匹配的问题(经过短暂的搜索)。
如果
RefreshView
不影响你整个程序的运行,你可以删除它。否则你可以等待bug被修复。希望它能帮助你。