c# - 如何在后面的代码中更改框架的背景颜色?
问题描述
我正在使用 xamarin 为 android、iOS 和 WP 创建一个应用程序。在我的一个页面中,我有一个frame
内部 adatatemplate
并且我无法在后面的代码中访问框架元素,所以我将框架的背景颜色绑定到一个变量。当用户点击一个按钮时,颜色应该会改变,但不会。
XAML:
<CollectionView x:Name="collectionView">
<CollectionView.EmptyView>
<Label Text="Não foram encontrados contactos com email" x:Name="SemContactos" IsVisible="False" AbsoluteLayout.LayoutBounds="0.5,0.5,100,100" AbsoluteLayout.LayoutFlags="PositionProportional"/>
</CollectionView.EmptyView>
<CollectionView.ItemsLayout>
<GridItemsLayout Orientation="Vertical" Span="2"/>
</CollectionView.ItemsLayout>
<CollectionView.ItemTemplate>
<DataTemplate x:Name="template">
<Grid Padding="5" x:Name="grid">
<Grid.RowDefinitions>
<RowDefinition Height="50"/>
<RowDefinition Height="25"/>
<RowDefinition Height="25"/>
</Grid.RowDefinitions>
<Grid.ColumnDefinitions>
<ColumnDefinition Width="70"/>
<ColumnDefinition Width="70"/>
</Grid.ColumnDefinitions>
<Frame BackgroundColor="{DynamicResource myResourceKey}"
OutlineColor="LightGray"
CornerRadius="3" Padding="0.5" Grid.RowSpan="3" Grid.ColumnSpan="5" x:Name="frameContacto">
<Frame.GestureRecognizers>
<TapGestureRecognizer Tapped="ContactoSelecionado" />
</Frame.GestureRecognizers>
<StackLayout Spacing="5">
<Image x:Name="imageX" Grid.RowSpan="2" Grid.ColumnSpan="2"
Source="{Binding Foto}"
Aspect="AspectFill"
HeightRequest="60"
WidthRequest="60"
HorizontalOptions="Center" />
<!--Source="{local:ImageResource KiaiDay.Images.user.png}"-->
<Label Grid.Row="2" Grid.ColumnSpan="2" Text="{Binding Nome}" FontAttributes="Bold" HorizontalOptions="Center" VerticalOptions="EndAndExpand" TextColor="Black"/>
<Label Grid.Row="3" Grid.ColumnSpan="2" Text="{Binding Email}" HorizontalOptions="Center" VerticalOptions="StartAndExpand"/>
</StackLayout>
</Frame>
</Grid>
</DataTemplate>
</CollectionView.ItemTemplate>
</CollectionView>
<StackLayout AbsoluteLayout.LayoutBounds=".5,1,.5,.1" AbsoluteLayout.LayoutFlags="All" x:Name="butoes" IsVisible="False">
<StackLayout Orientation="Horizontal" HorizontalOptions="CenterAndExpand" VerticalOptions="CenterAndExpand">
<Button Text="Seleccionar todos" WidthRequest="170" TextColor="White" BackgroundColor="#1E90FF" FontAttributes="Bold" CornerRadius="2" HeightRequest="40" HorizontalOptions="CenterAndExpand" VerticalOptions="CenterAndExpand" Clicked="SeleccionarTodos" x:Name="selTodos"/>
<Button Text="Convidar" WidthRequest="170" TextColor="White" BackgroundColor="#1E90FF" FontAttributes="Bold" CornerRadius="2" HeightRequest="40" HorizontalOptions="CenterAndExpand" VerticalOptions="CenterAndExpand"/>
</StackLayout>
</StackLayout>
和 C#
[XamlCompilation(XamlCompilationOptions.Compile)]
public partial class ConviteEmailPage: ContentPage {
Color corFrame = Color.White;
public ConviteEmailPage() {
this.Resources.Add("myResourceKey", corFrame);
InitializeComponent();
}
private void SeleccionarTodos(object sender, EventArgs e) {
if (selTodos.Text == "Desmarcar") selTodos.Text = "Seleccionar Todos";
else selTodos.Text = "Desmarcar";
corFrame = Color.LightGray;
}
解决方案
从代码来看,Frame的颜色在CollectionView.ItemTemplate
。如果想在Item中改变颜色,你应该改变模型的数据,而不是直接通过绑定的资源名称或x:名称来改变。
在模型中将MyColor
属性添加到模型Monkey
:
private string mycolor = "Accent";
public string MyColor
{
get
{
return mycolor;
}
set
{
if (mycolor != value)
{
mycolor = value;
OnPropertyChanged("MyColor");
}
}
}
如果要动态变化,还需要INotifyPropertyChanged
建模:
public event PropertyChangedEventHandler PropertyChanged;
protected virtual void OnPropertyChanged(string propertyName)
{
if (PropertyChanged != null)
{
PropertyChanged(this, new PropertyChangedEventArgs(propertyName));
}
}
MyColor
然后在Xaml中绑定:
<ContentPage.Resources>
<ResourceDictionary>
<CollectionViewDemos:StringToColorConverter x:Key="StringToColorConverter"/>
</ResourceDictionary>
</ContentPage.Resources>
Frame BackgroundColor="{Binding MyColor, Converter={StaticResource StringToColorConverter}}"
它还需要IValueConverter
从字符串转换颜色:
public class StringToColorConverter : IValueConverter
{
public object Convert(object value, Type targetType, object parameter, CultureInfo culture)
{
//throw new NotImplementedException();
string valueAsString = value.ToString();
switch (valueAsString)
{
case ("Red"):
{
return Color.Red;
}
case ("Accent"):
{
return Color.Accent;
}
default:
{
return Color.FromHex(value.ToString());
}
}
}
public object ConvertBack(object value, Type targetType, object parameter, CultureInfo culture)
{
throw new NotImplementedException();
}
}
最后,您可以在 CollectionView 时进行测试SelectedItem
<CollectionView ItemsSource="{Binding Monkeys}"
SelectionMode="Single"
SelectedItem="{Binding SelectedMonkey, Mode=TwoWay}">
添加selectedMonkey
到MonkeyList
模型。选中后,将颜色更改为红色,如下所示:
Monkey selectedMonkey;
public Monkey SelectedMonkey
{
get
{
return selectedMonkey;
}
set
{
if (selectedMonkey != value)
{
selectedMonkey.MyTextColor = "Red"; //Here is changing the color
selectedMonkey = value;
}
}
}
推荐阅读
- c++ - C ++:静态成员函数为具有私有构造函数的类返回自静态对象
- python - Python Pandas:尝试在 date_range 操作中加快每个日期的每行
- python - 如何使用 tf.keras 模型从 keras 模型复制结果(或找到差异)?
- java - 使用 CompletableFuture 的并发数据库调用
- asp.net-mvc - 如何从客户模型中选择所有下订单的客户orderby 购买数量
- replace - 使用带有特殊字符的 JREPL
- ubuntu-18.04 - ROS2 (ros-eloquent-desktop) - Ubuntu 18.04 - 无法纠正问题,你持有损坏的包
- user-interface - 将 FXML 中的扩展自定义类与自定义 ControllerFactory 一起使用
- javascript - 根据html5中相同形式的另一个字段中的数据设置输入的最大长度的方法?
- css - 使用 WayPoint 滚动时如何显示导航栏