I am trying to match the default font of the ToggleSwitch Header property from the WPToolkit to a TextBlock. I've noticed that the default font of the ToggleSwitch header does not math the TextBlock. What can I use to apply the some text foreground to a TextBlock?
Have you looked at the existing Style template Setter for that property to see what it's using and just apply the same to the Style template for the other? So if for example we look at the template shared on MSDN for the default Style it shows on line 7;
<Setter Property="FontFamily" Value="{StaticResource ContentControlThemeFontFamily}" />
So you could either set it to that via the default template for TextBlock in the Resource Dictionary or say for example all your instances within a user control like;
<Blah.Resources>
<Style TargetType="TextBlock">
<Setter Property="FontFamily" Value="{StaticResource ContentControlThemeFontFamily}" />
</Style>
</Blah.Resources>
Hope this helps.
UPDATE NOTE: I apparently grabbed the default template of the windows store app Toggle instead of the Windows phone but the same question applies of checking whats in the default template and matching it to the other.
Related
I am trying to learn how to use Styles most effectively in WinUI 3 (from WindowsAppSDK 1.1.1) but I'm having difficulty getting simple inheritance to work.
Consider the NavigationViewItem class. I'd like to modify the default style to bind the FontSize and Height properties. The following works in my Page XAML:
<NavigationViewItem x:Uid="Shell_05" helpers:NavigationHelper.NavigateTo="ViewModels._05CreditViewModel"
FontSize="{Binding ViewModel.RootShellFontSize, ElementName=shellPage}"
Height="{Binding ViewModel.CurrentMenuItemHeight, ElementName=shellPage}">
<NavigationViewItem.Icon>
<BitmapIcon UriSource="\Images\credit.png"/>
</NavigationViewItem.Icon>
</NavigationViewItem>
But adding the two properties to a page resource does not (although the FontSize property works in each of the following. It's the Height that doesn't):
<Page.Resources>
<Style TargetType="NavigationViewItem" >
<Setter Property="FontSize" Value="{Binding ViewModel.RootShellFontSize, ElementName=shellPage}" />
<Setter Property="Height" Value="{Binding ViewModel.CurrentMenuItemHeight, ElementName=shellPage}" />
</Style>
</Page.Resources>
Neither does adding the style to a resource dictionary and merging. I've read over what I can find about inheriting styles and the BasedOn="" extension is an explicit way to derive from an existing style in WinUI versions prior to 2.6 (I think). Apparently, WinUI 3 does not require BasedOn. In any case, simply specifying TargetType="NavigationViewItem" doesn't work, but nor does
<Style TargetType="controls:NavigationViewItem" BasedOn="DefaultNavigationViewItemStyle">
The source code for v1.1.1 of the SDK declares a default style for the NavigationViewItem in generic.xaml, but there is no definition for DefaultNavigationViewItemStyle.
I also cannot derive from the default style using
<Style TargetType="controls:NavigationViewItem" BasedOn="{StaticResource {x:Type NavigationViewItem}}">
because x:Type is undefined.
I can do all of the bindings I want in code but I assume it's both clearer and more efficient to do it in XAML.
How do I inherit, derive from, or override a portion of the default style for a WinUI 3 control (not a custom control) in a desktop application, please?
Thanks for any help. Pointers to good XAML for WinUI 3 documentation (or books and articles) would also be greatly appreciated.
In your case the height is most probably not working since page.resources get compiled before object initialization and the height of the CurrentMenuItemHeight is 0. To solve it just set the mode to one way as such
{Binding ViewModel.CurrentMenuItemHeight,Mode=OneWay , ElementName=shellPage}
When you wish to use BasedOn, just say BasedOn={ThemeResource styleName}.
Just make sure the style is actually defined in Generic.xaml file which u can find in "C:\Users\AdminName.nuget\packages\microsoft.windowsappsdk\1.1.1\lib\uap10.0\Microsoft.UI\Themes"
So your final page.resources should be as such:
<Page.Resources>
<Style TargetType="NavigationViewItem" >
<Setter Property="FontSize" Value="{Binding ViewModel.RootShellFontSize, ElementName=shellPage}" />
<Setter Property="Height" Value="{Binding ViewModel.CurrentMenuItemHeight, Mode=OneWay, ElementName=shellPage}" />
</Style>
</Page.Resources>
But it would be much better to use x:Bind instead of Binding. You can view this page to learn more about it https://learn.microsoft.com/en-US/windows/uwp/data-binding/data-binding-in-depth
In WPF, if you want to base a style on the default style of a control, you would say:
<Style TargetType="customControls:ResponsiveGridView" BasedOn="{StaticResource {x:Type GridView}}">
However, x:Type is not supported on UAP - how do I do it then? I tried the following - none works (after defining XAML as an alias for the namespace where GridView is).
<Style TargetType="customControls:ResponsiveGridView" BasedOn="{StaticResource xaml:GridView}">
<Style TargetType="customControls:ResponsiveGridView" BasedOn="xaml:GridView">
None of this works - crashes on parsing the XAML.
Any more ideas?
You can still use "BasedOn" for inheritance of styles.
<Page.Resources>
<Style TargetType="Button" x:Key="MyOtherStyle">
<Setter Property="Background" Value="Red"></Setter>
</Style>
<Style TargetType="Button" BasedOn="{StaticResource MyOtherStyle}" >
<Setter Value="Green" Property="Foreground"></Setter>
</Style>
</Page.Resources>
Just define the resources like above. They'll be applied for every button on the page.
<Button Content="Hello"></Button>
To base on a default style of a control, you don't use "BasedOn". You implicitly base on the default style of a control by specifying the TargetType in the style.
To be more precise for your special case:
If you want to use an (implicit) style for your custom control that is based on a default style of a built-in control do the follwing:
Create a custom style that targets the built-in control type. Like this:
<Page.Resources>
<Style TargetType="Grid" x:Key="MyStyle1" >
<Setter Property="Background" Value="Green"></Setter>
</Style>
...
Then add another style that targets your custom control type an is based on your custom style for the built-in control. Like this:
...
<Style TargetType="local:MyCustomGrid" BasedOn="{StaticResource MyStyle1}">
<Setter Property="BorderBrush" Value="Black"></Setter>
<Setter Property="BorderThickness" Value="4"></Setter>
</Style>
</Page.Resources>
All your MyCustomGrid controls will implicitly get the style which is based on the default style.
All standard Grids will keep their default style, because they won't get the style implicitly, because you specified the x:key in the first style and therefore have to explicitly set the style of the grids. Does this clarify?
I'm trying implicitly apply a style for DataGrid and TextBlocks.
For TextBlock's ForeGround I need White color.
For DataGrid's rows I need Black Color.
Beside this I need White again for DataGrid's header columns.
When I globally apply an implicit style for on MainPage by
<UserControl>
<UserControl.Resorces>
<Style targetType="TextBlock">
<Setter Property="Foreground" Value="White"/>
</Style>
</UserControl.Resorces>
</UserControl>
Making TextBlock's Foreground White operation is done! But beside this all of elements
in DataGrid (By default content elements are textblock's I think) turn to White color.
It doesn't look good White on white as you guess :)
So how can I particularly specify DataGrid's elements Foreground to black?
I can do it by using same technic shown below ,but this is an expensive operation for each DataGrid. As a con more I want DataGrid's HeaderColumns white again.This operation make them all black.
Is there an explicit way such as we do in css styles?
Here is what I tried to achieve this goal by Control template. But no chance because of being DataGrid's ContentControl is dynamic.
<DataGrid>
<DataGrid.Resources>
<Style targetType="TextBlock">
<Setter Property="Foreground" Value="Black"/>
</Style>
<DataGrid.Resources>
In fact we use Telerik's RadGridView but I give a sdk's DataGrid example to make question more global.
<Style TargetType="sdk:DataGrid">
<Setter Property="Foreground" Value="Black"/>
<Setter Property="RowDetailsTemplate" Value="{StaticResource DataTemplate1}"/>
<Setter Property="Template" Value="{StaticResource ControlTemplate1}"/>
</Style>
<ControlTemplate x:Key="ControlTemplate1" TargetType="sdk:DataGrid">
<Grid/>
</ControlTemplate>
<DataTemplate x:Key="DataTemplate1">
<Grid/>
</DataTemplate>
Thanks in advance!
If it were me I would pull out the full control templates and style them accordingly instead of trying to just do adhoc setter changes to override bits of the original template. In Expression Blend right click, choose "Edit Template -> Edit A Copy" and break out the templates for your rows etc and apply those implicitly with StaticResource instead.
What is the correct way to apply styles on elements with a condition on their parent element's type, i. e. only if they are children of certain other elements?
In my case, I want to apply some exact button width and height, but only if those buttons are direct children of a stackpanel. Additionally, a second style should be applied to images within those buttons (glyphs).
How do I define a button style that only affects buttons on a stackpanel, but not those buttons placed directly on a grid?
Is it possible to add additional conditions such as only stackpanels with orientation="horizontal"?
Can I define "tree conditions" like only images on buttons on [horizontal] stackpanels?
As 90% of all buttons in my application are those on the stackpanels, so far I've applied the style to all buttons and images and overrode it where necessary. But this isn't the best solution, is it?
Preferably, the solution would deal with all the conditions in the style definition, so I won't have to explicitly assign that style to every single one of my stackpanels.
<StackPanel>
<StackPanel.Resources>
<Style x:Key="Rectangle1" TargetType="Rectangle">
<Setter Property="Stroke" Value="Black" />
<Setter Property="Fill" Value="White" />
</Style>
</StackPanel.Resources>
<UniformGrid Columns="10">
<UniformGrid.Resources>
<Style TargetType="Rectangle" BasedOn="{StaticResource Rectangle1}">
<Setter Property="Fill" Value="Red" />
</Style>
</UniformGrid.Resources>
</UniformGrid>
</StackPanel>
I have a question
I've created new win8 metro app and I don't get from where it is taking styles.
I've change in App.xaml name of styles file. My Style.xaml looks like this
<!-- Page layout roots typically use entrance animations and a theme-appropriate background color -->
<Style x:Key="LayoutRootStyle" TargetType="Panel">
<Setter Property="Background" Value="White"/>
<Setter Property="ChildrenTransitions">
<Setter.Value>
<TransitionCollection>
<EntranceThemeTransition/>
</TransitionCollection>
</Setter.Value>
</Setter>
</Style>
But still I got gold letters, my buttons change white when I'm hover it. Same like with default StandardStyles.xaml
What am I doing wrong ? Or it works just fine ?
The style you show would only affect the the panel that uses that style. If you put a button inside a the panel, the panel's style does not cascade to the button. The button has its own style, as you correctly deduced from standardstyles.xaml, that controls its appearance. If you want to change the style of the button, you need to create a new style or update the current style.
The problem is you gave your style a key using the x:Key attribute. Once a style has a key it will only be applied to controls that implicitly use that named style. If you remove the key, the style should be applied to all controls that match TargetType (in this case Panel).