Forum Cross Platform with Xamarin

Announcement:

The Xamarin Forums have officially moved to the new Microsoft Q&A experience. Microsoft Q&A is the home for technical questions and answers at across all products at Microsoft now including Xamarin!

To create new threads and ask questions head over to Microsoft Q&A for .NET and get involved today.

How do I override the Windows Phone accent color?

As the title says: I want to override the accent color but don't know how to.
I've managed to override the accent color on buttons but I can't get it to work for the Entry-control (TextBox), see attached file.

I've tried setting the following style in the WinPhone-projects App.xaml:

<Style TargetType="TextBox">
    <Setter Property="BorderBrush" Value="#de7635" />
    <Setter Property="SelectionBackground" Value="#de7635" />
    <Setter Property="SelectionForeground" Value="White" />
    <Setter Property="CaretBrush" Value="#de7635" />
    <Setter Property="Template">
        <Setter.Value>
            <ControlTemplate TargetType="TextBox">
                <Grid Background="Transparent">
                    <VisualStateManager.VisualStateGroups>
                        <VisualStateGroup x:Name="CommonStates">
                            <VisualState x:Name="Normal" />
                            <VisualState x:Name="MouseOver" />
                            <VisualState x:Name="Disabled" />
                            <VisualState x:Name="ReadOnly" />
                        </VisualStateGroup>
                        <VisualStateGroup x:Name="FocusStates">
                            <VisualState x:Name="Focused">
                                <Storyboard>
                                    <ObjectAnimationUsingKeyFrames Storyboard.TargetProperty="Background" Storyboard.TargetName="MainBorder">
                                        <DiscreteObjectKeyFrame KeyTime="0" Value="White"/>
                                    </ObjectAnimationUsingKeyFrames>
                                    <ObjectAnimationUsingKeyFrames Storyboard.TargetProperty="BorderBrush" Storyboard.TargetName="MainBorder">
                                        <DiscreteObjectKeyFrame KeyTime="0" Value="#de7635"/>
                                    </ObjectAnimationUsingKeyFrames>
                                </Storyboard>
                            </VisualState>
                            <VisualState x:Name="Unfocused" />
                        </VisualStateGroup>
                    </VisualStateManager.VisualStateGroups>
                    <Border x:Name="MainBorder" BorderBrush="{TemplateBinding BorderBrush}" BorderThickness="{TemplateBinding BorderThickness}" Background="{TemplateBinding Background}" Margin="{StaticResource PhoneTouchTargetOverhang}"/>
                    <Border x:Name="ReadonlyBorder" BorderBrush="{StaticResource PhoneDisabledBrush}" BorderThickness="{TemplateBinding BorderThickness}" Background="Transparent" Margin="{StaticResource PhoneTouchTargetOverhang}"     Visibility="Collapsed"/>
                    <Border BorderBrush="Transparent" BorderThickness="{TemplateBinding BorderThickness}" Background="Transparent" Margin="{StaticResource PhoneTouchTargetOverhang}">
                        <ContentControl x:Name="ContentElement" BorderThickness="0" HorizontalContentAlignment="Stretch" Margin="{StaticResource PhoneTextBoxInnerMargin}" Padding="{TemplateBinding Padding}" VerticalContentAlignment="Stretch"/>
                    </Border>
                <Grid>
            </ControlTemplate>
        </Setter.Value>
    </Setter>
</Style>

Answers

  • nrdybynaturenrdybynature SEMember

    Ok, so I managed to change the color of the border around the Entry-control and also change the color of the selected text background.
    I still haven't been able to change the color of the two "markers" that select the text.

    The solution to my problem was to create a custom renderer follwing the docs (they even use the Entry as an example, which was nice).

    The final product:

    Create a new class MyEntry.cs in the shared project:

    namespace nrdybynature.CustomRenderers {
        public class MyEntry : Entry { }
    }
    

    And a new class MyEntryRenderer_WinPhone.cs in the WinPhone proeject:

    [assembly: ExportRenderer(typeof(MyEntry), typeof(MyEntryRenderer_WinPhone))]
    namespace nrdybynature.WinPhone.CustomRenderers
    {
        public class MyEntryRenderer_WinPhone : EntryRenderer
        {
            private SolidColorBrush _myPrimaryColor = new SolidColorBrush(System.Windows.Media.Color.FromArgb(Convert.ToByte("FF", 16), Convert.ToByte("14", 16), Convert.ToByte("13", 16), Convert.ToByte("29", 16)));
            private SolidColorBrush _myAccentColor = new SolidColorBrush(System.Windows.Media.Color.FromArgb(Convert.ToByte("FF", 16), Convert.ToByte("de", 16), Convert.ToByte("76", 16), Convert.ToByte("35", 16)));
            protected override void OnElementChanged(ElementChangedEventArgs<Entry> e)
            {
                base.OnElementChanged(e);
                if (e.OldElement == null)
                {
                    // Check if the Entry is used for password
                    if (e.NewElement.IsPassword)
                    {
                        var nativePasswordTextBox = (PasswordBox)Control.Children[1];
                        nativePasswordTextBox.GotFocus += nativePasswordTextBox_GotFocus;
                        nativePasswordTextBox.LostFocus += nativePasswordTextBox_LostFocus;
    
                        nativePasswordTextBox.CaretBrush = _myPrimaryColor;
                        nativePasswordTextBox.SelectionBackground = _myPrimaryColor;
                    }
                    else
                    {
                        var nativePhoneTextBox = (PhoneTextBox)Control.Children[0];
                        nativePhoneTextBox.GotFocus += nativePhoneTextBox_GotFocus;
                        nativePhoneTextBox.LostFocus += nativePhoneTextBox_LostFocus;
    
                        nativePhoneTextBox.CaretBrush = _myPrimaryColor;
                        nativePhoneTextBox.SelectionBackground = _myPrimaryColor;
                    }
                }
            }
    
            private void nativePasswordTextBox_GotFocus(object sender, System.Windows.RoutedEventArgs e)
            {
                SetBorderColor(sender, _inloggadAccentColor, true);
            }
    
            private void nativePasswordTextBox_LostFocus(object sender, System.Windows.RoutedEventArgs e)
            {
                SetBorderColor(sender, new SolidColorBrush(Colors.Transparent), true);
            }
    
            void nativePhoneTextBox_GotFocus(object sender, System.Windows.RoutedEventArgs e)
            {
                SetBorderColor(sender, _inloggadAccentColor);
            }
    
            void nativePhoneTextBox_LostFocus(object sender, System.Windows.RoutedEventArgs e)
            {
                SetBorderColor(sender, new SolidColorBrush(Colors.Transparent));
            }
    
            private void SetBorderColor(object sender, SolidColorBrush color, bool isPassword = false)
            {
                if (isPassword)
                {
                    var textbox = (PasswordBox)sender;
                    textbox.BorderBrush = color;
                }
                else
                {
                    var textbox = (PhoneTextBox)sender;
                    textbox.BorderBrush = color;
                }
            }
        }
    }
    

    Since I don't want to make any changes to how Android and iOS renders it's controls I don't have to create custom renderers for those two.

    If you have any tips on improving my code or solution feel free to leave a comment.

    Also if you have any idea on how to change the color of the "markers" I'd appreciate it!

    Cheers.

  • nrdybynaturenrdybynature SEMember

    Just a note:

    My SetBorderColor(...) function from above could be simplified to:

    private void SetBorderColor(object sender, SolidColorBrush color)
    {
        var control = (Control)sender;
        control.BorderBrush = color;
    }
    
Sign In or Register to comment.