如何在 Xamarin Forms 中将 ListView 按钮的绑定上下文设置为父级的绑定上下文
Posted
技术标签:
【中文标题】如何在 Xamarin Forms 中将 ListView 按钮的绑定上下文设置为父级的绑定上下文【英文标题】:How to set Binding Context of ListView button to the binding context of parent in Xamarin Forms 【发布时间】:2017-03-15 06:20:49 【问题描述】:基本上,我有一个带有 DataTemplate Selector 的 ListView,它使用基于 ListView 项的特定 DataTemplate。
现在,在 DataTemplate 中 - 我有一个带有命令的按钮,该按钮应该绑定在父级(或 ListView)本身的 ViewModel 上。
请注意,我只想绑定按钮的 Command 属性,因为 Text 和其他属性需要绑定到按钮的当前绑定上下文。
DataTemplate 的 BindingContext 是 ListView 项 bindingContext(在本例中为消息模型),但我希望能够仅将数据模板中的特定按钮绑定到父 listView 的视图模型。
我该怎么做?
<?xml version="1.0" encoding="UTF-8"?>
<ContentPage
xmlns="http://xamarin.com/schemas/2014/forms"
xmlns:x="http://schemas.microsoft.com/winfx/2009/xaml"
x:Class="MobileMobile.Views.MobileMessageListView"
Title="Message List"
NavigationPage.BarBackgroundColor="#FF9100"
NavigationPage.BarTextColor="White"
xmlns:ViewSwitchers="clr-namespace:MobileMobile.ViewSwitchers;assembly=MobileMobile"
xmlns:ViewCells="clr-namespace:MobileMobile.ViewCells;assembly=MobileMobile"
xmlns:Extensions="clr-namespace:MobileMobile.Extensions;assembly=MobileMobile"
>
<ContentPage.Resources>
<ResourceDictionary>
<DataTemplate x:Key="botMessageDataTemplate">
<ViewCell>
<Button Text="Hello!" Command="Binding TestCommand, Source=???" CommandParameter="Hello"/>
</ViewCell>
</DataTemplate>
<ViewSwitchers:MobileMessageTemplateSwitcher x:Key="MobileMessageTemplateSwitcher" BotMessageDataTemplate="StaticResource botMessageDataTemplate" />
</ResourceDictionary>
</ContentPage.Resources>
<ContentPage.Content>
<Grid>
<Grid.RowDefinitions>
<RowDefinition Height="*" />
<RowDefinition Height="Auto" />
</Grid.RowDefinitions>
<Grid.ColumnDefinitions>
<ColumnDefinition Width="*" />
</Grid.ColumnDefinitions>
<StackLayout Grid.Row="0" Orientation="Vertical" x:Name="MainViewStack">
<ListView
CachingStrategy="RecycleElement"
BackgroundColor="Transparent"
ItemTemplate="StaticResource MobileMessageTemplateSwitcher"
IsPullToRefreshEnabled="true"
RefreshCommand="Binding RefreshCommand"
ItemsSource="Binding Messages"
HasUnevenRows="true"
IsRefreshing="Binding IsLoading, Mode=OneWay"
SeparatorVisibility="None">
<ListView.Footer/>
</ListView>
</StackLayout>
<StackLayout Grid.Row="1" Orientation="Horizontal" HeightRequest="50">
<Entry Text="Binding CurrentMessageText" Placeholder="Binding MessageTextPlaceHolder" HorizontalOptions="FillAndExpand"/>
<Button Text="SEND" Command="Binding SendMessageCommand"/>
</StackLayout>
</Grid>
</ContentPage.Content>
</ContentPage>
【问题讨论】:
【参考方案1】:试试这个:
<Button
Text="Hello!"
Command="Binding Path=BindingContext. TestCommand, Source=x:Reference Name=MessageListPage"
CommandParameter="Hello" />
您必须为 Page 提供一个值为 MessageListPage
的 x:Name
属性,因此它与您的纯 MVVM 有点混乱,但由于 Xamarin XAML 不支持相对绑定(据我所知.. ) 这是要走的路。
【讨论】:
感谢您的尝试!但是我遇到了 x:Reference 错误:找不到 x:Reference 的 MarkupExtension 这很奇怪,它应该可以工作。您可以尝试此解决方法来解决您遇到的错误:forums.xamarin.com/discussion/comment/191390/#Comment_191390 你应该给你的 ListView 一个 x:Name 像: 您不需要将 x:name 引用添加到页面,而不是列表视图(根据之前的评论?) 别忘了写Name=
【参考方案2】:
不要将数据模板声明为内容字典中的静态资源,而是将数据模板放在列表本身的 itemtemplate 中。
我不能 100% 确定幕后发生的事情,但是当声明为静态资源时,数据模板似乎与页面的绑定上下文无关。这意味着当您离开并返回页面或更改列表视图的内容时,您可能会在呈现项目更新时遇到问题。
这将使您能够将按钮命令绑定到父级,但如果您离开并重新访问页面,也可以停止任何问题
<?xml version="1.0" encoding="UTF-8"?>
<ContentPage
xmlns="http://xamarin.com/schemas/2014/forms"
xmlns:x="http://schemas.microsoft.com/winfx/2009/xaml"
x:Class="MobileMobile.Views.MobileMessageListView"
Title="Message List"
NavigationPage.BarBackgroundColor="#FF9100"
NavigationPage.BarTextColor="White"
xmlns:ViewSwitchers="clr-namespace:MobileMobile.ViewSwitchers;assembly=MobileMobile"
xmlns:ViewCells="clr-namespace:MobileMobile.ViewCells;assembly=MobileMobile"
xmlns:Extensions="clr-namespace:MobileMobile.Extensions;assembly=MobileMobile"
x:Name="DeclareYourCodeBehindHereOrDeclareAViewModel"
>
<ContentPage.Resources>
<ResourceDictionary>
<ViewSwitchers:MobileMessageTemplateSwitcher x:Key="MobileMessageTemplateSwitcher" BotMessageDataTemplate="StaticResource botMessageDataTemplate" />
</ResourceDictionary>
</ContentPage.Resources>
<ContentPage.Content>
<Grid>
<Grid.RowDefinitions>
<RowDefinition Height="*" />
<RowDefinition Height="Auto" />
</Grid.RowDefinitions>
<Grid.ColumnDefinitions>
<ColumnDefinition Width="*" />
</Grid.ColumnDefinitions>
<StackLayout Grid.Row="0" Orientation="Vertical" x:Name="MainViewStack">
<ListView
CachingStrategy="RecycleElement"
BackgroundColor="Transparent"
IsPullToRefreshEnabled="true"
RefreshCommand="Binding RefreshCommand"
ItemsSource="Binding Messages"
HasUnevenRows="true"
IsRefreshing="Binding IsLoading, Mode=OneWay"
SeparatorVisibility="None">
<ListView.ItemTemplate>
<DataTemplate x:Key="botMessageDataTemplate">
<ViewCell>
<Button Text="Hello!" Command="Binding Source=x:Reference DeclareYourCodeBehindHereOrDeclareAViewModel, Path=BindingContext.CommandName" CommandParameter="Hello"/>
</ViewCell>
</DataTemplate>
</ListView.ItemTemplate>
<ListView.Footer/>
</ListView>
</StackLayout>
<StackLayout Grid.Row="1" Orientation="Horizontal" HeightRequest="50">
<Entry Text="Binding CurrentMessageText" Placeholder="Binding MessageTextPlaceHolder" HorizontalOptions="FillAndExpand"/>
<Button Text="SEND" Command="Binding SendMessageCommand"/>
</StackLayout>
</Grid>
</ContentPage.Content>
【讨论】:
以上是关于如何在 Xamarin Forms 中将 ListView 按钮的绑定上下文设置为父级的绑定上下文的主要内容,如果未能解决你的问题,请参考以下文章
在 Xamarin.Forms 中将 HeightRequest 设置回 Auto
在 Xamarin.Forms 上的 XAML 中将 BindingContext 设置为 ViewModel
在 Xamarin.Forms 中将默认的深色 Android 主题更改为白色?
使用 PlatformConfiguration (Xamarin.Forms 2.3.3) 在 UWP 中将工具栏移动到底部