根据绑定属性在xamarin中切换模板(不是ItemTemplate) [英] Switch templates in xamarin based of bound property (NOT ItemTemplate)
问题描述
我有一个包含一些数据的模型,一个字段可以具有三个(枚举)值之一.
Socket,Tcp,乌德普
还有一个显示一些细节的视图.
我希望在视图中显示的详细信息根据模型中此属性的值而有所不同.
我已经阅读了有关列表和选择器的ItemTemplates的所有内容,并且我想做一些类似的操作,但只将单个视图绑定到一个属性.
如果 Socket
=>显示此视图else =>显示其他视图.
两个视图都具有相同的视图模型.
查看
< ContentView.Resources>< local:SocketServerSocketView x:Key =" ServerSocket"/>< local:SocketServerTcpUdpView x:Key ="ServerTcpUdp";/></ContentView.Resources>...< ContentView Grid.Column ="2"保证金="12".>< ContentView.Content>< local:SocketServerTcpUdpView/></ContentView.Content>< ContentView.Style>< Style TargetType =" ContentView">< Style.Triggers>< DataTrigger TargetType ="{x:Type ContentView}"Binding =" {Binding Mode}"值="{绑定模型:NetworkMode.Socket}"< Setter Property =内容"值="{StaticResource ServerSocket}"/></DataTrigger></Style.Triggers></样式></ContentView.Style></ContentView>
因此,我开始(默认情况下)显示TCP版本,并希望在枚举值更改时将其动态切换为套接字模板.我在做什么错了?
我们可以参考
这是示例.
I have a Model that contains some data, and a field that can have one of three (enum) values.
Socket,
Tcp,
Udp
And a View that shows some details.
The details that I want shown in the view differ according to the value of this property in the model.
I have read all about ItemTemplates for Lists and Pickers, and I want to do something similar but just with a single view bound to a single property.
If Socket
=> Show this view
else => Show this other view.
Both views have the same viewmodel.
View
<ContentView.Resources>
<local:SocketServerSocketView x:Key="ServerSocket" />
<local:SocketServerTcpUdpView x:Key="ServerTcpUdp" />
</ContentView.Resources>
...
<ContentView Grid.Column="2" Margin="12" >
<ContentView.Content>
<local:SocketServerTcpUdpView />
</ContentView.Content>
<ContentView.Style>
<Style TargetType="ContentView">
<Style.Triggers>
<DataTrigger TargetType="{x:Type ContentView}" Binding="{Binding Mode}" Value="{Binding models:NetworkMode.Socket}">
<Setter Property="Content" Value="{StaticResource ServerSocket}" />
</DataTrigger>
</Style.Triggers>
</Style>
</ContentView.Style>
</ContentView>
So I start (by default) displaying the TCP version, and want to dynamically switch it out for the socket template when the value of the enum changes. What am I doing wrong?
We can refer to Data Triggers documents to know how to achieve that .
Create a sample ViewModel model only contains Model
property inside it .
public class ViewModel : INotifyPropertyChanged
{
public event PropertyChangedEventHandler PropertyChanged;
private int model;
public int Model
{
set
{
if (model != value)
{
model = value;
OnPropertyChanged("Model");
}
}
get
{
return model;
}
}
protected virtual void OnPropertyChanged(string propertyName)
{
PropertyChanged?.Invoke(this, new PropertyChangedEventArgs(propertyName));
}
}
Then we can create two sample ContentView
to replace SocketServerSocketView
and SocketServerTcpUdpView
as follow :
SocketServerTcpUdpView:
<?xml version="1.0" encoding="UTF-8"?>
<ContentView xmlns="http://xamarin.com/schemas/2014/forms"
xmlns:x="http://schemas.microsoft.com/winfx/2009/xaml"
xmlns:d="http://xamarin.com/schemas/2014/forms/design"
xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
mc:Ignorable="d"
x:Class="AppTriggerType.SocketServerTcpUdpView">
<ContentView.Content>
<StackLayout BackgroundColor="Azure">
<Label Text="SocketServer TcpUdpView!"
VerticalOptions="Center" />
</StackLayout>
</ContentView.Content>
</ContentView>
SocketServerSocketView:
<?xml version="1.0" encoding="UTF-8"?>
<ContentView xmlns="http://xamarin.com/schemas/2014/forms"
xmlns:x="http://schemas.microsoft.com/winfx/2009/xaml"
xmlns:d="http://xamarin.com/schemas/2014/forms/design"
xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
mc:Ignorable="d"
x:Class="AppTriggerType.SocketServerSocketView">
<ContentView.Content>
<StackLayout BackgroundColor="Beige" >
<Label Text="SocketServer SocketView!" />
</StackLayout>
</ContentView.Content>
</ContentView>
Now in Xaml of ContentPage
,we can defined as follow :
<?xml version="1.0" encoding="utf-8" ?>
<ContentPage xmlns="http://xamarin.com/schemas/2014/forms"
xmlns:x="http://schemas.microsoft.com/winfx/2009/xaml"
xmlns:d="http://xamarin.com/schemas/2014/forms/design"
xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
xmlns:local="clr-namespace:AppTriggerType"
mc:Ignorable="d"
x:Class="AppTriggerType.MainPage">
<ContentPage.Resources>
<local:SocketServerSocketView x:Key="ServerSocket" />
<local:SocketServerTcpUdpView x:Key="ServerTcpUdp" />
</ContentPage.Resources>
<StackLayout>
<!-- Place new controls here -->
<Label Text="Welcome to Xamarin.Forms!"
HorizontalOptions="Center"
VerticalOptions="Start" />
<Button Text="ServerSocket"
Clicked="Button_Clicked_ServerSocket"/>
<Button Text="ServerTcpUdp"
Clicked="Button_Clicked_ServerTcpUdp"/>
<ContentView x:Name="MyContentView"
Margin="12"
VerticalOptions="FillAndExpand">
<ContentView.Content>
<ContentView />
</ContentView.Content>
<ContentView.Triggers>
<DataTrigger TargetType="{x:Type ContentView}"
Binding="{Binding Source={x:Reference MyContentView}, Path=BindingContext.Model}"
Value="1">
<Setter Property="Content"
Value="{StaticResource ServerSocket}" />
</DataTrigger>
<DataTrigger TargetType="{x:Type ContentView}"
Binding="{Binding Source={x:Reference MyContentView}, Path=BindingContext.Model}"
Value="2">
<Setter Property="Content"
Value="{StaticResource ServerTcpUdp}" />
</DataTrigger>
</ContentView.Triggers>
</ContentView>
</StackLayout>
</ContentPage>
Last bind data for MyContentView
in ContentPage.xaml.cs :
public partial class MainPage : ContentPage
{
ViewModel viewModel = new ViewModel();
public MainPage()
{
InitializeComponent();
viewModel.Model = 1;
MyContentView.BindingContext = viewModel;
}
private void Button_Clicked_ServerSocket(object sender, EventArgs e)
{
viewModel.Model = 1;
}
private void Button_Clicked_ServerTcpUdp(object sender, EventArgs e)
{
viewModel.Model = 2;
}
}
Now we will see the effect as follow :
Here is the sample.
这篇关于根据绑定属性在xamarin中切换模板(不是ItemTemplate)的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!