I am relatively new to the WPF scene, and am having a problem understanding how styles are reused amongst controls.
My example situation is this, I'm making a control that needs a Toggle button. I want this ToggleButton to look like the 'expand' Button on a TreeViewItem. How would apply the TreeViewItem's button style to my own button?
From my searching I have a feeling that it isn't possible without copying XAML, but I can't justify to myself why anyone would make a UI framework that limited.
Thanks in advance.
I'm not sure there's a way of retrieving the default style/template from something and applying it to another control in XAML, although you may be able to to it in code. Although that would pose the problem that you just want to get the button part of the template and it's easier (not to mention cleaner) just to write a new style rather than hacking around to get just that part of the template.
The problem with restyling buttons is that when pressed they will go back to their default pressed appearance, same for when they are hovered. What you want to do is change the ControlTemplate of the button.
When I was starting out in WPF I found this tutorial
to be quite a useful introduction to the process.
I'd recommend getting a copy of ShowMeTheTemplate to give you access to most of the default templates for controls as that will save a lot of the basic work and give you an insight into how the controls work.
When you've created your control template (or any style/template for that matter), you can store it in a resource dictionary and apply it to controls by referencing it from the relevant property using the StaticResource markup extension.
Example:
(In a resource dictionary, for example App.Resources):
<Style x:Key="myStyle" TargetType="Button">
<Setter Property="Width" Value="70" />
</Style>
Used in a button:
<Button Style="{StaticResource myStyle}" />
Hope this helps get you started.
Related
I made myself a TransparentButton style that makes the Button portion behave the way I want it to (mouseover, enabled, etc), but what I haven't been able to do is set the content correctly in the style. Currently, I manually set everything in <Button.Content> for every button, and clearly that stuff needs to go into the Style. I have set the ContentTemplate for the style to a StackPanel that just contains an Image and a Label. The problem is, I don't know how to specify in my <Button ...> markup the Label's text and the Image's Source. I figured that it had to do with TemplateBinding somehow, but I've been searching like crazy and can't seem to find the information.
So, in summary, I just want a consistent button style where the button content is just a StackPanel of an Image and a Label, and I want to be able to create it in my GUI with something simple like:
<Button Style={DynamicResource TransparentButton}"
Label="Click Me" Image="Images/MyImage.png" />
Any tips would be much appreciated! I hope I'm on the right track here...
In order to create custom properties like this, you'll need to make a CustomControl instead of just using a Button style.
This is fairly easy, though - just make a custom control that subclasses button, and adds your new properties (as dependency properties). This will make it stylable, but also provide you the ability to enforce that those properties are always available, with the syntax you're describing (other than changing <Button to <local:MyButton).
For details, see the Control Authoring Overview on MSDN.
I did some searching but it wasn't what I was looking for. So, does anyone know a way how to style the validation tooltip in Silverlight(the thing in the green border)?
alt text http://img689.imageshack.us/img689/222/validationtooltip.png
Any help would be greatly appreciated!
Best Regards,
~K
Unfortunately you can't easily provide a style for the validation tooltip without effectively styling the entire Textbox control. Blend makes this fairly easy if you are familiar with using that design tool. However if your a dyed in the wool coder like me then...
Goto this page on MSDN TextBox Styles and Templates
Copy the vsm namespace alias to your UserControl xaml
Copy the TextBox style into UserControls.Resources give it at an x:Key name (say MyTextBoxStyle")
Copy the ValidationToolTipTemplate from the web page to the UserControls.Resources, paste it above the TextBox style. It already has an x:Key name that the TextBox style will be referencing.
Add Style="{StaticResource MyTextBoxStyle}" to your TextBox in the data grid.
Now you play around with the validation elements of the templates to get your desired result.
The validation messages are displayed as a visual state. you can get to these (and edit them) as templates directly from blend.
So that when I apply additional typed styles in my application I don't have to do the BasedOn thing in order for them to be merged with my custom global style. You know, like happens with Microsoft's own styles. Essentially, I want to apply my style at number 9 instead of 8.
If that's relevant: I also want to completely ignore themes and anything else that might make my application appear differently on different machines.
Edit: I want to do this for controls that I didn't make, like, Button.
It sounds like what you want to do is create a different Generic.xaml (theme) Style for a control but that isn't something that's intended for built-in controls. You might be able to do something like create an alternate theme assembly with your Styles that you can fool WPF into loading (i.e. PresentationFramework.Aero.dll) or subclassing controls you want to replace templates on. Before going down that road you should really evaluate whether it's worth the time investment. Anything you might be able to get to work is going to add complexity and be a lot of extra work just to change your local default Style declarations from
<Style TargetType="{x:Type Button}" BasedOn="{StaticResource {x:Type Button}}">
to
<Style TargetType="{x:Type Button}">
As far as ignoring themes, there's not much you can control as far as the automatic selection process. The standard way to do it is to copy the default Style from a specific theme into your App.xaml as your application default Style and modify as necessary but that obviously creates the situation that you're trying to get away from.
If you set the OverridesDefaultStyle property to true in your custom Style, then the theme Styles (or default Styles) will be ignored. This effeictvely makes your Style the only Style used.
http://msdn.microsoft.com/en-us/library/system.windows.frameworkelement.overridesdefaultstyle.aspx
I am new to WPF and I have a doubt in modifying a control. I came to know that one can modify a control by changing its Control Template. i.e.,
<Button>
<Button.Template>
<ControlTemplate>
...
</ControlTemplate>
</Button.Template>
</Button>
Also we can edit a control utilizing the Content Model. i.e.,
<Button>
<Grid>
<CheckBox>
</CheckBox>
<RadioButton>
</RadioButton>
...
</Grid>
</Button>
What is the difference between these two techniques. Which one is the correct way to customize a control in WPF. Please help me in understanding this better.
The primary difference between these two things, is that the ControlTemplate defines the look of the control. It is not actually placing content inside of it. At some location inside the content control, there should be some form of ContentPresenter. The built in controls are capable of this because they are what is known as 'lookless controls', and any custom controls created should also be lookless. When a control is not templated in a lookless manner but instead has a static layout, then the confusion you have run into can occur.
As for the correct way to do things, it depends on what you are trying to achieve. If you are attempting to change the control, such as the look and feel or the behavior, then using a ControlTemplate, (or DataTemplate, depending on what you are templating), is definitely the way to go. A good example of this is the CheckBox, belive it or not, the CheckBox is actually a ToggleButton (more or less), that through templating displays the togleablity in a bullet. Here's another very good example of how you can use Templates to do some very nifty things.
ControlTemplates should also be applied through Styles, instead of directly set on an element.
If you aren't actually aiming to modify the behavior or look of the control then using the content model is the correct approach.
WPF does this better then Silverlight, though I don't know if there are improvements in SL3.
My rule of thumb is that if it's possible to get what I want without changing the control template then you shouldn't change the control template.
control templates are a way to change the look&feel of a control, for example making a round button of changing the check mark graphics of a checkbox.
adding controls inside a control is simpler, for example place an image inside a button.
Also remember, there is a lot of functionality in the control template, including padding, content alignment, disabled look and more, if you change the control template you will have to add support for all of those features.
Template can be placed into a resource and re-used for another button.
Changing content directly is not re-usable unless you make a UserControl out of it.
Which one you use depends on a concrete task and your personal preferences.
In Expression Blend you can create a font-size of say 18 and then create a "font-size resource".
Coming at this from HTML/CSS, I cannot think of when I would want to make a style for a "font-size" and one for a "font-style" and one for a "font-weight". Instead I want to make a font called "CompanyHeader" and have 10 different attributes set in it, e.g. font-weight, font-style, font-size, color,etc.
Why is this different in Expression Blend, XAML, what is the sense of making a style/resource for each attribute?
this graphic shows how you can click on a little button on each attribute to change it into a resource:
alt text http://tanguay.info/web/external/blendStyles.png
I have no experience with Blend, but styles in XAML can include more than one attribute, more then that, since unlike css you can only apply one style to an element you can't combine multiple one-attribute styles.
Here is an example for a style that set multiple properties:
<Page xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml">
<Page.Resources>
<Style x:Key="MyStyle" TargetType="{x:Type Label}">
<Setter Property="Width" Value="125"/>
<Setter Property="Height" Value="25"/>
<Setter Property="Background" Value="Red"/>
</Style>
</Page.Resources>
<Label Style="{StaticResource MyStyle}"/>
</Page>
Note that if I wanted to break the style into 3 smaller styles each setting one property I couldn't use them because the Label's Style property can only accept one style.
I think they likely allow for the creation of single resources for FontFamily, FontWeight, etc. to allow them to be used across many styles in the application. By placing a single property in a resource you can effect all styles using that resource at once. If you weren't using a resource but were attempting to use a consistent FontFamily across your whole application (or a portion of it) then you had to go through each style one at a time in order to update it.
In order to make a style with multiple properties in blend you can do the following:
Select the control you wish to style (the control's type will be used as the TargetType for the style)
From the menu select Object->Edit Style->Create Empty
Enter the Key you would like to assign to the style (this is the name that you will use to reference the style)
Go to the properties tab and begin to apply the look/feel that you want for that style
It allows you to reuse the font details at am more granular level than having to define all elements of the font definition. You might have several styles that all inherit from the same font-size definition. Your designer can then change the font-size and all the styles that use it then automatically have an updated appearance.
Each instance of a font will use its own resources, doesn't matter if multiple such defenitions refer to same font.
Using same font in two different styles will end-up with two instances of the font (when the styles are applied). Instade, you can defined the font as a style of its own and use the style with-in other styles. In this case, once runtime instance of the font resource is used by both styles.
If you have very complex resource dictionaries (say for example you are creating a theme), it is a good idea to define geanular assets (like a specific color brush or font) as independent resource (or named style) and use them in other complex styles to conserve system resources.
On your question on Blend, it simpley enforces this best practice.
This is possible by creating a helper class to use and wrap your styles. CompoundStyle mentioned here shows how to do it. There are multiple ways, but the easiest is to do the following:
<TextBlock Text="Test"
local:CompoundStyle.StyleKeys="headerStyle,textForMessageStyle,centeredStyle"/>
The blog post talks about Win8 and Windows Phone, but the same code works for WPF as well (minus the Utilies class which is not needed)
Hope that helps.