WPF comboBox Arrow Button - wpf

I'm doing a wpf project and inside my application i have a combobox.Can i know any simple way to change the dropDown arrow color? I found the resource here, but its too complicate. Anyone can help me out?
p/s: i'm a newbie
combobox example:

Because the arrow is just linked to a system resource, I believe there's no way to change it other than redoing the entire template like you see in your linked article. It seems complicated, but it's not so bad, especially if you have Blend (just because Blend makes it easy to pull out the current template to edit it).

<Setter Property="Template">
<Setter.Value>
<ControlTemplate TargetType="ComboBox">
<Path x:Name="Arrow" Fill="White"/>
</ControlTemplate>
</Setter.Value>
</Setter>

Related

VisualBrush using MediaElement in a Style

I have a UserControl that converts a text to a shape. I can then Stroke it or Fill it with a Brush. When I try to use a Visual Brush with a MediaElement (video) as the Source I am running into problems. When I do it directly in the XAML as below:
<custom:ExtendedTextBlock Text="Video Filled Text" FontFamily="Arial Black" FontSize="60">
<custom:ExtendedTextBlock.Fill>
<VisualBrush>
<VisualBrush.Visual>
<MediaElement Source="assets\1267066.mp4" Width="596" Height="366" LoadedBehavior="Play" Stretch="UniformToFill" MediaEnded="MediaElement_MediaEnded" MediaFailed="MediaElement_MediaFailed" MediaOpened="MediaElement_MediaOpened" />
</VisualBrush.Visual>
</VisualBrush>
</custom:ExtendedTextBlock.Fill>
</custom:ExtendedTextBlock>
It works great. The problem appears when I try to create a Style using the same information:
<Style x:Key="VideoFill" TargetType="{x:Type custom:ExtendedTextBlock}">
<Setter Property="StrokeThickness" Value="2" />
<Setter Property="Stroke" Value="Black" />
<Setter Property="Fill">
<Setter.Value>
<VisualBrush>
<VisualBrush.Visual>
<MediaElement Source="assets/1267066.mp4" Width="596" Height="366" LoadedBehavior="Play" LoadedBehavior="Play" Stretch="UniformToFill" MediaEnded="MediaElement_MediaEnded" MediaFailed="MediaElement_MediaFailed" MediaOpened="MediaElement_MediaOpened" />
</VisualBrush.Visual>
</VisualBrush>
</Setter.Value>
</Setter>
</Style>
I get no fill. No MediaOpened is thrown, no MediaFailed is thrown. It just doesn't render the fill. Using this same method with a SolidColorBrush, LinearGradientBrush, ImageBrush all works perfectly. Can anyone tell me what is going on here?
I've seen all sorts of examples of MediaElement not playing nicely with other WPF components, I don't think the dev team did their integration testing quite as comprehensively with that one as perhaps they did with other things. This particular case appears to be a bug I've seen crop up a few times where an element used in a style is created and then destroyed several times during initialization. MediaElement seems to be doing some type of deferred processing, gets confused and winds up thinking that it's no longer being used. The solution, believe it or not, is to simply set UnloadedBehavior="Play" as well.
Personally though I tend to avoid letting the XAML framework control things like this. My own approach with MediaPlayer is to make each instance a static resource, set both LoadedBehavior and UnloadedBehavior to "Manual" and control playback manually with a Blend behavior containing dependency properties that I bind back to my view models. This provides all the advantages of complete code-driven control of the media element without breaking MVVM and without having to cross your fingers and hope that the framework behaves itself.

Styling a control template in Silverlight 5

I'm looking at using the Silverlight Menu Control from Codeplex. It's functionally very good but I'd like to restyle the appearance. Is it possible to do this without just making a new copy of the template and changing a few properties? Here's an example from the generic "theme" that comes with the control:
<Style TargetType="GenericControl:MenuBar">
<Setter Property="Template">
<Setter.Value>
<ControlTemplate TargetType="GenericControl:MenuBar">
<Canvas x:Name="LayoutRootMB">
<StackPanel Height="25"
x:Name="baseRectMB"
Canvas.Left="0"
Canvas.Top="0"
HorizontalAlignment="Left"
Orientation="Horizontal" />
</Canvas>
</ControlTemplate>
</Setter.Value>
</Setter>
</Style>
I'd like to change, say, HorizontalAlignment to Stretch (for the sake of argument -- never mind if it'll actually accomplish anything useful). Is there any way to tell XAML (in XAML, not in C#) that I want to do something to baseRectMB?
baseRectMB is named in a TemplatePartAttribute on class MenuBar.
I assume I can simply copy the existing template and alter it, though I haven't gotten that working yet either.

Setting ALL colors on WPF ComboBox using styles?

I asked this question a few days ago and got some answers, non of which really helped me with the problem, so I am trying a fresh approach.
I want to be able to set the colors (foreground, background, and border) of the textbox used by a comboBox so that it can have a number of different values, based on a trigger. With a textbox, this is easy, just use setters on those properties and you are done.
So given that I have a trigger as follows:
<Trigger Property="someProperty" Value="true">
<!-- Insert Setters Here -->
<Setter Property="Foreground"
Value="Red" />
</Trigger>
What Setters would I insert into the above to change the 3 aforementioned colors of the textbox used by the combobox? For each trigger, assume that every color will change. It appears that Foreground works except for disabled.
I am under the impression that changing the colors based on an "IsEnabled" trigger (when false) can be tricky, but not sure why. But I need to support that and a number of other triggers based on custom attached properties or validations.
For the background, I have tried a whole bunch of options including ComboBox.Background, TextElement.Background, Panel.Background, etc., but all I get is a plain white background.
One other thing occurred to me is that if those should work, there may be some resource library in the calling tree that may be setting the background color in a way that won't allow me to change it, but, if so, how would I be able to find out?
Thank you!
As I told you in your last (now duplicated) question, you will need to define a new ControlTemplate to achieve your goal.
For future reference:
Asking duplicate questions on StackOverflow is not approved by the community, especially if you are asking a duplicate of your own question. If you do not understand your answer(s) or do not feel that they answer your question adequately, you should ask the answer author(s) to explain it further in that question.
Now I'll get off my soap box and get you further on your way to achieving your goal. As I said, you will need to define a new ControlTemplate... there is no way around this. The reason for this is simple - you want to add Triggers to affect the XAML controls that are defined inside the default ControlTemplate, but you have no other way to do this from XAML.
So, how do we define a new ControlTemplate? It's quite simple really: we just define some XAML in the Template property that describes the way that we want the control to look and behave. Please refer to the link that I provided you with for help with this in your last post. Additionally, here is a very simplified example:
<Style TargetType="{x:Type ComboBox}">
<Setter Property="Template">
<Setter.Value>
<ControlTemplate TargetType="{x:Type ComboBox}">
<Border Name="Border" CornerRadius="2" Padding="2">
<ScrollViewer Margin="0" HorizontalScrollBarVisibility="Disabled"
VerticalScrollBarVisibility="Auto">
<ItemsPresenter />
</ScrollViewer>
</Border>
<ControlTemplate.Triggers>
<Trigger Property="IsEnabled" Value="False">
<Setter TargetName="Border" Property="Background" Value="Red"/>
</Trigger>
</ControlTemplate.Triggers>
</ControlTemplate>
</Setter.Value>
</Setter>
</Style>
Apply this Style to a ComboBox with the IsEnabled property set to False and you will see that it is red. Now you're probably thinking 'that doesn't look like a ComboBox' and you'd be right. That's because I just replaced all of the XAML from the default ComboBox ControlTemplate with a little bit that slightly resembles just the drop down section for simplicity.
Your job now is to define your own ControlTemplate that replicates the default XAML and adds the relevant Triggers that I have shown you in this and your last post. In the example, notice how the Trigger.TargetName is set to Border, which is the name of the internal Border control used. You will need to do this for each element that you want to colour.
Here is a link to the default ControlTemplate for the ComboBox control. When you see how large it is, you will understand why I didn't use it in the example.
ComboBox Styles and Templates

Xaml Grid Styling

New to WPF, I'm having some trouble creating a styles in my code, I was able to make some buttons styles by drawing rectangles and making them into buttons, this opened a template editor so I was able to do it.
Now I'm wanting to create a template for a repeating stackpanel/grid layout, and I wrote it by hand this time, but I am getting an error that says the "template is not a valid member"
This is the kind of thing I was trying to create, but the Property="Template" bit is underlined in red. Can somebody explain to me the reason behind this? How do I create or initialize the template?
<Style x:Key="LaneStyle" TargetType="{x:Type Grid}">
<Setter Property="Width" Value="760"/>
<Setter Property="Template">
<Setter.Value>
<ControlTemplate TargetType="{x:Type Grid}">
<!-- Things here -->
</ControlTemplate>
</Setter.Value>
</Setter>
</Style>
If someone could direct me to a tutorial on styles/templates that would be nice as well, haven't been able to find one that explained it in more detail.
Grid is not a control, therefore you cannot apply a ControlTemplate to it. If you're looking for a "repeater" kind of thing, you should be using an ItemsControl.
The best way to create templates/styles is by using Microsoft Blend 3.0/4.0
Over there one can easily find out what's the progress after doing each change.
In your case, a grid cannot be styled as it is a container not a control. If you wish to customize some control need to modify the control template of the control.

How to display a MessageBox when wrong input is given and reverting the old value of TextBox using MVVM in WPF

I have been using WPF and its built in validation controls for quiet sometime. I was going through an excellent article in codeproject whose link is given below
http://www.codeproject.com/KB/WPF/wpfvalidation.aspx
I am having a requirement from one of our clients which I have not been able to chieve using MVVM in WPF.
The problem is as follows :
There is a TextBox which accepts only numbers.
When the user enters any value other than numbers I have to display an error to him. The error should
highlight the TextBox, provide a ToolTip
display an error in MessageBox
revert the TextBox to its previous value
For example when the TextBox is loaded, it might have an initial value say 10
. Then the user enters some wrong value say "aa".
Now I have to display a MessageBox saying "Wrong value" and then revert the value back to 10.
There are lot of articles and ways to display error in WPF say by using ErrorTemplate and so on.
<Style TargetType="{x:Type TextBox}">
<Setter Property="Validation.ErrorTemplate">
<Setter.Value>
<ControlTemplate>
<DockPanel LastChildFill="True">
<TextBlock DockPanel.Dock="Right"
Foreground="Orange"
FontSize="12pt">
!!!!
</TextBlock>
<Border BorderBrush="Green" BorderThickness="1">
<AdornedElementPlaceholder />
</Border>
</DockPanel>
</ControlTemplate>
</Setter.Value>
</Setter>
<Style.Triggers>
<Trigger Property="Validation.HasError" Value="true">
<Setter Property="ToolTip"
Value="{Binding RelativeSource={RelativeSource Self},
Path=(Validation.Errors)[0].ErrorContent}">
</Setter>
</Trigger>
</Style.Triggers>
</Style>
But how do I revert the value and display a MessageBox. I know it can be displayed using an event in code-behind file but I dont want to write any logic in my code behind file. I want to achieve this functionality using MVVM
A sample illustration will be really helpful!!
the answer to your 2nd question: build a messageboxservice and just call it from your viewmodel. you can find mvvm messageboxservices in all wpf frameworks. look at cinch for example.
the undo redo thing, hmm its built in in wpf, so strg+z will work. but i dont know yet how to get it work with mvvm :)
Hey people finally I solved the problem. Its based on this
StackOverFLow Solution
The solution is very simple. I call the Validator on losing focus from TextBox. The validator return me a Validation Result.Based on the result I can take some action.
I used attached behaviour for this. I have written a trigger which checks if Validation.HasError is true or not. If it is true, then it assigns some dummy value to my attached property. While assigning I will have TextBoxBase under my control. Using this I just call the Undo() function and it solves my problem.

Resources