Xamarin ControlTemplate 触发器应用于模板内的内部控件
Xamarin ControlTemplate Trigger applied to inner control within template
Coming from my original post, I was trying to create a custom control and build a control template for it much like in WPF, but it failed on triggers. I was provided a link that indicated that Control Templates are not allowed on all controls, but only certain ones via another Stack Overflow link provided by Raimo 关于我的另一个问题。
现在进入第 2 部分。我已将控件从“Entry”类型更改为“ContentView”类型,以便可以应用控件模板。所以这是唯一改变的地方
namespace MyAndroidApp
{
public class MyTextboxEntry : ContentView
{
public MyTextboxEntry()
{}
public static readonly BindableProperty IsRequiredProperty
= BindableProperty.Create(nameof(IsRequired), typeof(bool),
typeof(MyTextboxEntry), false, BindingMode.TwoWay);
public bool IsRequired
{
get { return (bool)GetValue(IsRequiredProperty); }
set { SetValue(IsRequiredProperty, value); }
}
}
}
命名空间引用..
xmlns:myCtrls="clr-namespace:MyAndroidApp"
现在,转到控件模板。我实际上在控件中定义了多个部分,但为了简单的上下文在这里缩写了。
<ControlTemplate x:Key="CT_MyTextboxEntry" >
<!-- Having a grid as an outer wrapper for multiple internal controls... -->
<Grid HorizontalOptions="StartAndExpand" x:Name="UpdateThisGridControl" >
<Grid.ColumnDefinitions>
<ColumnDefinition Width="150*" />
<ColumnDefinition Width="50" />
<ColumnDefinition Width="16" />
</Grid.ColumnDefinitions>
<Entry Text="Sample" Grid.Column="0" />
<Label Text="junk" Grid.Column="1" />
<Image Source="Sample.jpg" Grid.Column="2" />
<Grid.Triggers>
<Trigger TargetType="myCtrls:MyTextboxEntry" Property="IsRequired" Value="True">
<Setter Property="BackgroundColor" Value="Red"/>
</Trigger>
</Grid.Triggers>
</Grid>
</ControlTemplate>
而页面中控件的最终实例要显示通过
<myCtrls:MyTextboxEntry ControlTemplate="{StaticResource CT_MyTextboxEntry}" />
所以,我的失败在 Grid.Triggers 部分。此处的目的是使用新条目控件(基于 ContentView)的可绑定 属性 以及“IsRequired”的正确 BindableProperty 声明,但要设置 GRID 的背景颜色。
在 WPF 中,您可以说在这里使用这个东西的触发器,但是在控件模板中更新这个其他控件,如“x:Name”引用所引用的那样,我将其作为“UpdateThisGridControl”就地使用。
如果我禁用 [Grid.Triggers] 部分,控件和模板将按预期显示。一旦我启用触发器,它就会失败
"bindable" not an instance of AssociatedType
但是,如果您考虑到条目 ContentView 具有背景色 属性 并且 Grid 控件也是如此,为什么在尝试通过触发器设置时它会阻塞。
如何从自定义控件为 属性 执行此类绑定以更新特定控件模板中的 属性?
如果您使用 Grid.Triggers
,您应该像下面的代码一样在 Trigger
选项卡中设置 TargetType="Grid"
。
<ControlTemplate x:Key="CT_MyTextboxEntry" >
<!-- Having a grid as an outer wrapper for multiple internal controls... -->
<Grid HorizontalOptions="StartAndExpand" x:Name="UpdateThisGridControl" IsEnabled="True" >
<Grid.ColumnDefinitions>
<ColumnDefinition Width="150*" />
<ColumnDefinition Width="50" />
<ColumnDefinition Width="16" />
</Grid.ColumnDefinitions>
<Entry Text="Sample" Grid.Column="0" />
<Label Text="junk" Grid.Column="1" />
<Image Source="Sample.jpg" Grid.Column="2" />
<!-- For testing, I set the value of `Property` is `IsEnabled`, it worked as normal -->
<Grid.Triggers>
<Trigger TargetType="Grid" Property="IsEnabled" Value="True">
<Setter Property="BackgroundColor" Value="Red"/>
</Trigger>
</Grid.Triggers>
</Grid>
</ControlTemplate>
但是你想为Trigger
设置TargetType="myCtrls:MyTextboxEntry"
,你可以尝试使用Style为myCtrls:MyTextboxEntry
实现。
<ContentPage.Resources>
<ResourceDictionary>
<Style TargetType="myCtrls:MyTextboxEntry">
<Style.Triggers>
<Trigger TargetType="myCtrls:MyTextboxEntry"
Property="IsRequired" Value="True">
<Setter Property="BackgroundColor" Value="Red" />
<!-- Multiple setters elements are allowed -->
</Trigger>
</Style.Triggers>
</Style>
</ResourceDictionary>
<ControlTemplate x:Key="CT_MyTextboxEntry" >
<!-- Having a grid as an outer wrapper for multiple internal controls... -->
<Grid HorizontalOptions="StartAndExpand" x:Name="UpdateThisGridControl" >
<Grid.ColumnDefinitions>
<ColumnDefinition Width="150*" />
<ColumnDefinition Width="50" />
<ColumnDefinition Width="16" />
</Grid.ColumnDefinitions>
<Entry Text="Sample" Grid.Column="0" />
<Label Text="junk" Grid.Column="1" />
<Image Source="Sample.jpg" Grid.Column="2" />
<!-- <Grid.Triggers>
<Trigger TargetType="Grid" Property="IsEnabled" Value="True">
<Setter Property="BackgroundColor" Value="Red"/>
</Trigger>
</Grid.Triggers> -->
</Grid>
</ControlTemplate>
</ContentPage.Resources>
<StackLayout>
<myCtrls:MyTextboxEntry ControlTemplate="{StaticResource CT_MyTextboxEntry}" IsRequired="True" />
</StackLayout>
这是 运行 屏幕截图。
Coming from my original post, I was trying to create a custom control and build a control template for it much like in WPF, but it failed on triggers. I was provided a link that indicated that Control Templates are not allowed on all controls, but only certain ones via another Stack Overflow link provided by Raimo 关于我的另一个问题。
现在进入第 2 部分。我已将控件从“Entry”类型更改为“ContentView”类型,以便可以应用控件模板。所以这是唯一改变的地方
namespace MyAndroidApp
{
public class MyTextboxEntry : ContentView
{
public MyTextboxEntry()
{}
public static readonly BindableProperty IsRequiredProperty
= BindableProperty.Create(nameof(IsRequired), typeof(bool),
typeof(MyTextboxEntry), false, BindingMode.TwoWay);
public bool IsRequired
{
get { return (bool)GetValue(IsRequiredProperty); }
set { SetValue(IsRequiredProperty, value); }
}
}
}
命名空间引用..
xmlns:myCtrls="clr-namespace:MyAndroidApp"
现在,转到控件模板。我实际上在控件中定义了多个部分,但为了简单的上下文在这里缩写了。
<ControlTemplate x:Key="CT_MyTextboxEntry" >
<!-- Having a grid as an outer wrapper for multiple internal controls... -->
<Grid HorizontalOptions="StartAndExpand" x:Name="UpdateThisGridControl" >
<Grid.ColumnDefinitions>
<ColumnDefinition Width="150*" />
<ColumnDefinition Width="50" />
<ColumnDefinition Width="16" />
</Grid.ColumnDefinitions>
<Entry Text="Sample" Grid.Column="0" />
<Label Text="junk" Grid.Column="1" />
<Image Source="Sample.jpg" Grid.Column="2" />
<Grid.Triggers>
<Trigger TargetType="myCtrls:MyTextboxEntry" Property="IsRequired" Value="True">
<Setter Property="BackgroundColor" Value="Red"/>
</Trigger>
</Grid.Triggers>
</Grid>
</ControlTemplate>
而页面中控件的最终实例要显示通过
<myCtrls:MyTextboxEntry ControlTemplate="{StaticResource CT_MyTextboxEntry}" />
所以,我的失败在 Grid.Triggers 部分。此处的目的是使用新条目控件(基于 ContentView)的可绑定 属性 以及“IsRequired”的正确 BindableProperty 声明,但要设置 GRID 的背景颜色。
在 WPF 中,您可以说在这里使用这个东西的触发器,但是在控件模板中更新这个其他控件,如“x:Name”引用所引用的那样,我将其作为“UpdateThisGridControl”就地使用。
如果我禁用 [Grid.Triggers] 部分,控件和模板将按预期显示。一旦我启用触发器,它就会失败
"bindable" not an instance of AssociatedType
但是,如果您考虑到条目 ContentView 具有背景色 属性 并且 Grid 控件也是如此,为什么在尝试通过触发器设置时它会阻塞。
如何从自定义控件为 属性 执行此类绑定以更新特定控件模板中的 属性?
如果您使用 Grid.Triggers
,您应该像下面的代码一样在 Trigger
选项卡中设置 TargetType="Grid"
。
<ControlTemplate x:Key="CT_MyTextboxEntry" >
<!-- Having a grid as an outer wrapper for multiple internal controls... -->
<Grid HorizontalOptions="StartAndExpand" x:Name="UpdateThisGridControl" IsEnabled="True" >
<Grid.ColumnDefinitions>
<ColumnDefinition Width="150*" />
<ColumnDefinition Width="50" />
<ColumnDefinition Width="16" />
</Grid.ColumnDefinitions>
<Entry Text="Sample" Grid.Column="0" />
<Label Text="junk" Grid.Column="1" />
<Image Source="Sample.jpg" Grid.Column="2" />
<!-- For testing, I set the value of `Property` is `IsEnabled`, it worked as normal -->
<Grid.Triggers>
<Trigger TargetType="Grid" Property="IsEnabled" Value="True">
<Setter Property="BackgroundColor" Value="Red"/>
</Trigger>
</Grid.Triggers>
</Grid>
</ControlTemplate>
但是你想为Trigger
设置TargetType="myCtrls:MyTextboxEntry"
,你可以尝试使用Style为myCtrls:MyTextboxEntry
实现。
<ContentPage.Resources>
<ResourceDictionary>
<Style TargetType="myCtrls:MyTextboxEntry">
<Style.Triggers>
<Trigger TargetType="myCtrls:MyTextboxEntry"
Property="IsRequired" Value="True">
<Setter Property="BackgroundColor" Value="Red" />
<!-- Multiple setters elements are allowed -->
</Trigger>
</Style.Triggers>
</Style>
</ResourceDictionary>
<ControlTemplate x:Key="CT_MyTextboxEntry" >
<!-- Having a grid as an outer wrapper for multiple internal controls... -->
<Grid HorizontalOptions="StartAndExpand" x:Name="UpdateThisGridControl" >
<Grid.ColumnDefinitions>
<ColumnDefinition Width="150*" />
<ColumnDefinition Width="50" />
<ColumnDefinition Width="16" />
</Grid.ColumnDefinitions>
<Entry Text="Sample" Grid.Column="0" />
<Label Text="junk" Grid.Column="1" />
<Image Source="Sample.jpg" Grid.Column="2" />
<!-- <Grid.Triggers>
<Trigger TargetType="Grid" Property="IsEnabled" Value="True">
<Setter Property="BackgroundColor" Value="Red"/>
</Trigger>
</Grid.Triggers> -->
</Grid>
</ControlTemplate>
</ContentPage.Resources>
<StackLayout>
<myCtrls:MyTextboxEntry ControlTemplate="{StaticResource CT_MyTextboxEntry}" IsRequired="True" />
</StackLayout>
这是 运行 屏幕截图。