ContentControl (CheckBox) does not inherit Foreground - xaml

It looks like the CheckBox control does not inherit its Foreground property:
<UserControl Foreground="Orange">
<StackPanel>
<!-- this shows as black - no inheritance -->
<CheckBox Content="foo" />
<!-- this shows as turquoise -->
<CheckBox Foreground="Turquoise" Content="bar" />
<!-- but this shows as orange - inheritance works here -->
<TextBlock Text="baz" />
</StackPanel>
</UserControl>
What's the reason for this, and what is the best workaround?
Edit #helb suggested the reason is the default style, which sets the Foreground to black. I don't think this explains it, though: if you override that style and remove the line - <Setter Property="Foreground" Value="#FF000000"/> - the behavior stays the same.

The best I could find is this, which may be an explanation:
Property value inheritance behavior is not globally enabled for all dependency properties, because the calculation time for inheritance does have some performance impact. Property value inheritance is typically only enabled for properties where a particular scenario suggests that property value inheritance is appropriate.
So maybe they decided not to apply Foreground inheritance to ContentControls, for performance reasons. Would be nice to be able to confirm this, though. (This answer claims to have used reflector to uncover an opaque hex value, in the internal DP registration, that may have something to do with it.)
This is one possible workaround (seems adequate, I guess):
<Style TargetType="CheckBox">
<Setter Property="Foreground" Value="{Binding RelativeSource={RelativeSource AncestorType=UserControl},Path=Foreground}" />
</Style>
Edit
More evidence for the "ContentControl doesn't inherit Foreground" theory: Button does not inherit; ComboBox does inherit.

Related

Is there a way to specify multiple LayoutFlags in XAML Xamarin?

I Have a label set to relative positioning and auto size as shown below
<Style TargetType="Label">
<Setter Property="BackgroundColor" Value="Transparent" />
//Something like below?
<Setter Property="AbsoluteLayout.LayoutFlags" Value="PositionProportional | SizeProportional" />
</Style>
....
<Label Text="0" AbsoluteLayout.LayoutBounds="0.5, 0.00499999999999998, AutoSize, AutoSize"/>
Is there a way to specify multiple LayoutFlags in XAML?
As I run the code on devices with higher resolution the relative position of the label is correct but the size (font) of the label does not increase, although it is set to AutoSize. I figured I also needed to specify a LayoutFlag for the Label that is SizeProportional as well as PositionProportional. But how to do it in XAML? Currently the fonts don't resize when the device is rotated to landscape orientation.
As you can read here :
AbsoluteLayout on Xamarin Documentation
Flags are also specified in the declaration of views in the layout
using the AbsoluteLayout.LayoutFlags property. Note that flags can be
combined in XAML using a comma-separated list.
So in your case, there is no point since you want to use the All value (using both Positionning and Sizing proportionnaly).
But I had to use something like this and it works just fine :
<StackLayout AbsoluteLayout.LayoutBounds="0,1,1,100"
AbsoluteLayout.LayoutFlags="XProportional,YProportional,WidthProportional">
</StackLayout>
Hope it will help people like who googled it and found this post :)

WP81 Create XAML style to target all pages in the app

I want to set the background image for all the pages in my windows phone 8.1 app (RT not Silverlight) by declaring a style that targets the page.
Like this:
<Style TargetType="Page">
<Setter Property="Background" Value="Red" />
</Style>
It seems to work in the designer, as I see the red background on all my pages. However when I actually run the app the background is missing (black, blank) not red.
Some of the pages in my app derive from a custom type (which derives from Page) and I know that TargetType doesn't inherit. So I added additional styles for these:
<Style TargetType="local:ViewBase">
<Setter Property="Background" Value="Red" />
</Style>
Again, in the designer I see the Red (tho strangely enough I also saw the red when I was only targeting Page). Upon launch again however, the background is not Red, but blank (black).
I could easily give it a key, or add the Background property to every page and bind it to a resource, but I thought the whole point of Implicit styles was to allow me to override every instance of the control...
Can I not target a Page for a default (implicit) style?
aha: https://social.msdn.microsoft.com/Forums/windowsapps/en-US/bb927601-2e3e-45ac-afe8-621df57b9738/why-does-style-targettypepage-not-work-in-an-application?forum=winappswithcsharp
looks like this is a known issue, boo I say! I'll set the background to a resource then.
Why don't you override brush in application resource
<SolidColorBrush x:Name="ApplicationPageBackgroundThemeBrush" Color="RED"/>

Define a Thickness using resources

In a windows UWP app project, I am trying to define a Thickness by assigning to its Left, Top, Right and Bottom properties:
<Setter Property="Margin">
<Setter.Value>
<Thickness Left="{StaticResource SomeDouble}"
Top="0"
Right="0"
Bottom="0" />
</Setter.Value>
</Setter>
This answer seems to suggest that this is possible in WPF, however, in my UWP project (as well as in a WinRT app), I get the following error:
XAML Thickness type cannot be constructed.
In order to be constructed in XAML, a type cannot be abstract, interface, nested, generic
or a struct, and must have a public default constructor.
Is there a way to define the Thickness using resources?
You still can. Only to change System:Double to x:Double. e.g.
<x:Double x:Key="SomeDouble">12</x:Double>
Update
Interesting, with the above xaml the designer shows up fine but it doesn't compile... Yes it gives the exact same error like you showed.
So I guess you have to define the whole Thickness in xaml.
<Thickness x:Key="Thickness1">12,0,0,0</Thickness>
<Setter Property="Margin" Value="{StaticResource Thickness1}" />
I ran the project this time and yeah it worked. :)

Change the default page color on a window 8 store application

When I create a new page on a windows 8 store application it has default color which I want to change. If I remove all elements on the page and change the background color it has no effect. I've set the back ground to pink in my example below. How can I make this color take effect? (I've also removed everything out of App.xaml)
<common:LayoutAwarePage
x:Name="pageRoot"
x:Class="DemoWindows8StoreApp.BasicPage3"
DataContext="{Binding DefaultViewModel, RelativeSource={RelativeSource Self}}"
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
xmlns:local="using:DemoWindows8StoreApp"
xmlns:common="using:DemoWindows8StoreApp.Common"
xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
Background="Pink"
mc:Ignorable="d">
It's best to follow the default templates in that rather than setting the Background of the Page, but of the root element (usually a Grid), I'm not 100% sure why a Background on that page doesn't work (I suspect the control template).
UPDATE 1
According to Control.Background
Each control might apply this property differently based on its visual
template. This property only affects a control whose template uses the
Background property as a parameter. On other controls, this property
has no effect. For more info about visual templates, see the Template
property.
So there might be possible that Page's template doesn't use Background property as a parameter.
Remove nothing from the project to change the color. Go to Common\StandardStyles.xaml. Search for "LayoutRootStyle". You will find style for Panel. Change Background there. Please note this will be affected to all the pages in the project. If you want different color for different page then you can create separate style for each page.
<Style x:Key="LayoutRootStyle" TargetType="Panel">
<Setter Property="Background" Value="Pink"/>
<Setter Property="ChildrenTransitions">
<Setter.Value>
<TransitionCollection>
<EntranceThemeTransition/>
</TransitionCollection>
</Setter.Value>
</Setter>
</Style>

How to override TextBlock IsHitTestVisible across Silverlight app

I'll save my why did they do it this way rants for elsewhere, so...
I'm trying to prevent TextBlocks from getting focus across my Silverlight app. It seems like adding a setter for this property on any TextBlock within my application's base page class (Page-inheriting) makes some sense, but 1) I'm probably wrong and 2) I can't seem to quite get it right.
I've tried variations on adding code like this:
this.Style.Setters.Add(new Setter(TextBlock.IsHitTestVisibleProperty, false));
to the constructor of my app's base Page class (inherits directly from Page) or in a page Loaded event handler. But most variations on that theme don't seem to work (generally seeming as though all the right members don't yet exist or XamlParseExceptions.
It's probably absurdly simple, but so is my brain, apparently. Any ideas?
You could just use an implicit style
<Style TargetType="TextBlock">
<Setter Property="IsHitTestVisible" Value="False" />
</Style>
Generally, styles are merged at the top level of the App.xaml file if in separate resource dictionaries or you could simply add your style there. I'm pretty new to Silverlight myself, so I'm only reporting what I've seen.
Assuming you have an empty App.xaml starting out, it may look something like this:
<Application
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
x:Class="YourApp.App"
mc:Ignorable="d">
<Application.Resources>
<ResourceDictionary>
<Style TargetType="TextBlock">
<Setter Property="IsHitTestVisible" Value="False" />
</Style>
</ResourceDictionary>
</Application.Resources>
</Application>
This is pretty simple to test, you could add a Foreground color setter and see if all of your TextBlocks pick up the style.