The official Microsoft article states:
Modify the default system styles
You should use the styles that come from the Windows Runtime default XAML resources when you can. When you have to define your own styles, try to base your styles on the default ones when possible (using based-on styles as explained earlier, or start by editing a copy of the original default style).
I understand that you can copy and paste the default style from MSDN in order to "start by editing a copy of the original". However, that strikes me as very ugly and inelegant, as I'm pasting in almost a 100 lines even if I just want to add one thing.
I like the idea of "using based-on styles" to include all of the default style by reference, but from what I can tell the original default styles supplied by Microsoft are implicit. Given that they have no key to reference them by, how can BasedOn be used?
You are right about that BasedOn won't work with default styles as they are implicit.
However, you don't have to include the full style code if you simply want to edit some properties.
For example, the Button below will inherit everything from the default style except the Background color being changed to Red.
<Page.Resources>
<Style x:Key="RedButtonStyle"
TargetType="Button">
<Setter Property="Background"
Value="Red" />
</Style>
</Page.Resources>
<Grid>
<Button Content="Red" Style="{StaticResource RedButtonStyle}" />
</Grid>
Related
I have a Style with target type Grid. I want all Entry child elements within a grid of this style to automatically acquire a particular style.
I've had a look at these:
Styling nested elements in WPF
Apply Style to all child-elements of specific type
The only solution appears to be setting Resources within the parent Style, so this is what I've done:
<Style x:Key="BuggyGrid" TargetType="Grid">
<!-- bunch of property setters -->
<Style.Resources>
<Style TargetType="Entry">
<Setter Property="FontFamily" Value="Arial" />
</Style>
</Style.Resources>
</Style>
However, I get a build error:
"No property, bindable property, or event found for 'Resources'".
Why do I get this error?
I'm using Xamarin.Forms 2.3.2.
The links you have referenced are specific to WPF XAML and do not apply to Xamarin.Forms XAML.
I'm not sure how you would achieve nested styles in Xamarin.Forms.
The only possibility is XamlCSS which I haven't personally used.
https://www.nuget.org/packages/XamlCSS.xamarinforms/2.0.0-pre1
I have a custom font in my assets folder and need to assign this font as the global font for the app. This is what I thought of but it's not working.
<FontFamily x:Key="MetricWebRegular">
ms-appx:///Assets/Fonts/MetricWeb-Regular.ttf#Metric Web
</FontFamily>
I'm calling this by adding it to a style setter in a textbox.
This is what I thought of but it's not working.
It's hard to know what is going wrong here, just base on your code, it should work. Firstly, I don't have your font resource, I downloaded one from Internet and tested like this:
<Application.Resources>
<FontFamily x:Key="MetricWebRegular">ms-appx:///Assets/Blambot-Custom.ttf#Blambot Custom</FontFamily>
</Application.Resources>
then use this resource in the style setter in a textbox:
<Page.Resources>
<Style x:Key="TextBoxStyle" TargetType="TextBox">
...
<Setter Property="FontFamily" Value="{StaticResource MetricWebRegular}" />
...
</Setter>
</Style>
</Page.Resources>
And my TextBox:
<TextBox Text="Hello 11111222333" FontSize="30" Style="{StaticResource TextBoxStyle}" />
It works perfectly:
Here is my font download Uri. I downloaded it and changed its name here so it will meet the format as yours.
So,
Make sure your font file has no problem.
ms-appx:///Assets/Fonts/MetricWeb-Regular.ttf#Metric Web this path means your font file is under the Fonts folder of the Assets folder, make sure the path is right.
If you want to use this resource, you need to use StaticResource and its key.
If you want to override the default font family, you can override the ContentControlThemeFontFamily resource like this:
<FontFamily x:Key="ContentControlThemeFontFamily">ms-appx:///Assets/Blambot-Custom.ttf#Blambot Custom</FontFamily>, the result of my layout is here:
If there is still problem, you can leave a comment to post the download url of your font file resource, so can we download it and have a test.
I have the next XAML:
<ContentPage ...>
<ContentPage.Resources>
<ResourceDictionary>
<Style x:Key="visualStyle" TargetType="VisualElement">
<Setter Property="BackgroundColor" Value="Red" />
</Style>
<Style x:Key="baseStyle" TargetType="View" BasedOn="{StaticResource visualStyle}">
...
</Style>
<Style x:Key="labelStyle" TargetType="Label" BasedOn="{StaticResource baseStyle}">
<Setter Property="TextColor" Value="Black" />
</Style>
</ResourceDictionary>
</ContentPage.Resources>
<ContentPage.Style>
<StaticResourceExtension Key="visualStyle" />
</ContentPage.Style>
...
</ContentPage>
When I try to set Style for entire ContentPage using visualStyle StaticResourceExtension I get the next annoing popup in Visual Studio:
Why is this happening and how to remove it? XAML is correct and is successfully parsed in runtime.
That's a very unusual syntax to be using. Markup extensions are almost always instantiated using moustache bracket syntax, so it doesn't surprise me that the Intellisense is getting confused.
I see why you are doing this though - you want to reference a resource that is defined within the Resources of the referencing element. But XAML wants to be able to parse that resource before encountering the reference.
There are a few options...
You could move the visualStyle resource to App.xaml and reference it from your page using normal attribute plus moustache bracket syntax.
You could reference it via DynamicResource instead, which should allow it to resolve properly. But this seems a little heavy-handed.
However, my preferred solution is the first one since this is likely an application-wide thematic style.
I see this part of your code, and wonder (since I'm too starting to learn Xamarin) couldn't it be that the StaticResourceExtension key attribute, must be used with the suffix x:?
<ContentPage.Style>
<StaticResourceExtension x:Key="visualStyle" />
<!-- INSTEAD OF <StaticResourceExtension Key="visualStyle" />-->
</ContentPage.Style>
I just came across this exception and found that the problem was that I was using the attributes the wrong way, so maybe that exception is Xamarin's way to tell us that we messed up on something, without saying explicitly on what.
I'm trying to override the padding property of a ListViewItemPresenter in Windows Store apps.
Everything works when I copy the complete generic ListView style, change the padding and apply that style as ItemContainerStyle to my ListView.
Now I need to do this for another ListView. How can I override just one property of the ListViewItemPresenter ControlTemplate without copying the complete style all over again?
The best solution I have found came from the link below. I copy-pasted the answer below.
The idea is to copy the full Windows 10 style into your dictionary and give it a key. You don't need to modify the style and you only have to copy it once. (Though once more than ideally you should have to.) Since it now has a key, you can create another style "BasedOn" that key and modify it.
[https://social.msdn.microsoft.com/Forums/en-US/d3c1f120-b11f-4d14-b45c-7bdf3e9233be/inheriting-a-default-application-style-xaml?forum=winappswithcsharp][1]
First, create the default style for the control in your App.xaml-level resource dictionary, but give it an x:Key
<Style x:Key="ButtonDefaultStyle" TargetType="Button">
...
</Style>
Then, create another style that inherits from this style.
<Style x:Key="MyButtonStyle" TargetType="Button" BasedOn="{StaticResource ButtonDefaultStyle}" />
</Style>
Default styles can be found here
[https://msdn.microsoft.com/en-us/library/windows/apps/mt299122.aspx]
or on your computer at a location like
C:\Program Files (x86)\Windows Kits\10\DesignTime\CommonConfiguration\Neutral\UAP\10.0.10586.0\Generic\generic.xaml
I am reading up about the ResourceDictionary and have come to a confusing point.
It appears I can only have 1 ResourceDictionary per XAML. So, if I wanted to use more than one, I can Merge the ResourceDictionaries.
If I can merge dictionaries then where should 'global' styles live? I could have an ApplicationResourceDictionary with all the styles which are to be consistent throughout my application OR, I could save this information into the App.xaml file. both appear to be valid options but I don't know if that is the case.
Is this about personal choice or is one better than the other? It would appear keeping them in ResourceDictionaries is better because all styles are together (within the dictionaries) instead of splitting some in XAML pages.
Our current solution has 100+ projects in it. Each needing access to a few Resource Dictionaries with global resources for themes and uniformity etc. What I do for it is have the resource dictionaries centrally located in one project the others reference, in this case we call it "infrastructure" then I supply the dictionaries to each proj directly via their own app.xaml with merged dictionaries like for example;
<Application.Resources>
<ResourceDictionary>
<ResourceDictionary.MergedDictionaries>
<ResourceDictionary Source="/Our.Client.Infrastructure;component/Resources/Styles/ResDictName1.xaml" />
<ResourceDictionary Source="/Our.Client.Infrastructure;component/Resources/Styles/ResDictName2.xaml" />
</ResourceDictionary.MergedDictionaries>
</ResourceDictionary>
</Application.Resources>
Which so far works splendidly, the way I make the styles apply global though is specifying them as such at the bottom of one of our custom Resource Dictionaries and remove the same declaration from the Default Resource Dictionaries. So for example if you find;
<Style BasedOn="{StaticResource DefaultButtonStyle}" TargetType="Button" />
in your Default CoreStyles.xaml or SdkStyles.xaml or whatever they may be, I just remove it, and move that declaration over to the bottom of our custom Resource Dictionary and change it accordingly like;
<Style BasedOn="{StaticResource OurSuperAwesomeCustomNewGlobalButtonStyle}" TargetType="Button" />
and voila... Any Button thereafter inherits our custom style by default instead of the original default template. The advantages of having just one or two Resource Dictionaries for your entire solution become clear real quick once you adopt it. That is, provided the template actually needs to be globally available. If you're using a template for something adhoc that only pertains to the view its used on, keep it in that view explicitly, no need to keep it somewhere else if nothing else needs it.
Hope this helps.