Wpf ComoBox Selected Item Alignment - c#

Hi i'm using Reuxables Free Theme Inc in my wpf application.
I added the theme to App.xaml this way:
<Application.Resources>
<ResourceDictionary>
<ResourceDictionary.MergedDictionaries>
<ResourceDictionary Source="/ReuxablesLegacy;component/inc.xaml" />
</ResourceDictionary.MergedDictionaries>
</ResourceDictionary>
</Application.Resources>
And in my Main.xaml i used a combobox by default its content aligned to the left:
I want to align the content of combobox to right.
When i tried HorizontalContentAlignment="Right" nothing changed.
I tried TextBlock.TextAlignment="Right" and the result is this:
This time comboboxitems are aligned to the right however selected item which is "1" in this picture, is still aligned to the left.
Whatever i tried i couldn't align the selected item to the right. What am I doing wrong?

If you look on the ComboBox Styles and Templates page on MSDN, you will find the default ControlTemplate for the ComboBox used in WPF. It's too large to display here, but if you look down the page, you'll see a TextBox control named PART_EditableTextBox which looks like this:
<TextBox x:Name="PART_EditableTextBox"
Style="{x:Null}"
Template="{StaticResource ComboBoxTextBox}"
HorizontalAlignment="Left"
VerticalAlignment="Bottom"
Margin="3,3,23,3"
Focusable="True"
Background="Transparent"
Visibility="Hidden"
IsReadOnly="{TemplateBinding IsReadOnly}" />
This is the control used for the selected value and as you can see, its HorizontalAlignment property is hard coded to "Left", so text in this TextBox will always align to the left.
Therefore, to align text to the right, you will need to define your own ControlTemplate for your ComboBox. You can find out how to do that in the Control Authoring Overview page on MSDN. Basically, you just need to copy the default ControlTemplate and replace the TextBox above with the TextBox below:
<TextBox x:Name="PART_EditableTextBox"
Style="{x:Null}"
Template="{StaticResource ComboBoxTextBox}"
HorizontalAlignment="{TemplateBinding HorizontalContentAlignment}"
VerticalAlignment="Bottom"
Margin="3,3,23,3"
Focusable="True"
Background="Transparent"
Visibility="Hidden"
IsReadOnly="{TemplateBinding IsReadOnly}" />
Once you have done this and applied your new ControlTemplate to the Template property of your ComboBox and set the HorizontalContentAlignment property to Right, then you should finally see your selected value text align to the right.

Related

How to set the background color of a label in WPF?

I have a label but setting the Background property not seem to do anything:
<Label Content="{Binding Name, Source={StaticResource LocStrings}}"
HorizontalAlignment="Left" Margin="4" Name="label2" Background="Blue"
VerticalAlignment="Top"/>
This does not show a blue background (while the property Background is recognized.
Also when using the Label.Background 'way' I do not see a blue background.
Update:
I used the following minimalistic code:
<Window xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
Title="TEST" SizeToContent="WidthAndHeight">
<Grid>
<Label Content="TEXT TO TEST" Foreground="Green" Background="Orange"/>
</Grid>
</Window>
What I see is the tekst in green but without any orange background.
<Label Content="{Binding Name, Source={StaticResource LocStrings}}"
HorizontalAlignment="Stretch" Margin="4" Name="label2" Background="Blue"
VerticalAlignment="Top"/>
Have you tried to just enter some text in the Content and checked the binding output, maybe there is something wrong with your binding. Because it works just fine here.
Note that I set HorizontalAlignment="Stretch" instead of left, which will make the label use all the horizontal avaliable space. If you don't have anything bound your label will be invisible in your case above, you may use this in combination with the output to figure out what's likely wrong with your binding as stated by others, like Sriram Sakthivel and PoweredByOrange. For helping you with that, we need a bit more information :)
Hope it helps,
Cheers,
Stian
Since you are binding to a string value so using a TextBlock instead of Label is worth here. A content model of Label may not be required in this scenario.
here is an example
<TextBlock Text="{Binding Name, Source={StaticResource LocStrings}}"
HorizontalAlignment="Left" Margin="4" Name="label2" Background="Blue"
VerticalAlignment="Top"/>
some other benefits of displaying text in a TextBlock instead of a Label
Unlike a Label a Textblock is derived directly from FrameworkElement instead of deriving from a Control thus making it lightweight.
A Label follows content model so the appearance may get affected by the content and its type and / or any style or template defined for the same.
read here for more Differences between Label and TextBlock

XAML WP8 and making a 'TextBlock' scroll down

Alright, so I have a XAML page with a TextBlock in a Windows Phone 8 application. My dilemma is this:
I pragmatically add more content (formatted lines with Inlines.Add(new Run...) to the TextBlock. The text block is currently filled from bottom to up because of the ScrollViewer in the sense that a line appears in the bottom after another. I would also be fine with them starting to appear from the top as long as the TextBlock would continue to scroll down (actually this might look better) once it is full. My TextBlock is inside a ScrollViewer as below:
<Popup x:Name="send_message_xaml" Grid.Row="1" VerticalOffset="0" Width="750" Height="auto">
<StackPanel Orientation="Vertical" Margin="0,0" Width="auto" Height="auto">
<ScrollViewer Height="345" HorizontalAlignment="Left" Margin="0,0,0,0" Name="scrollViewer1" VerticalAlignment="Bottom" Width="420" VerticalScrollBarVisibility="Auto">
<TextBlock x:Name="message_log" Margin="40,50,0,0" TextWrapping="Wrap" Width="420" VerticalAlignment="Top" FontSize="22"/>
</ScrollViewer>
<TextBox x:Name="message_to_send" InputScope="Chat" Width="480" KeyDown="message_to_send_KeyDown" Margin="15,0"/>
</StackPanel>
</Popup>
How can I get the textblock to scroll so that the newest appended message is always at the bottom? I found a bunch of these threads but none seem to solve my problem so far. Do I need to add some code somewhere with the appending?
You need to update the VerticalOffset based on the ScrollableHeight. When you add new inlines to the TextBlock, its height is going to change and that will notify the parent ScrollViewer. So, after you add new items to the inlines, run the Measure method and update the VerticalOffset.
Here is an example.

Why does the ScrollViewer property not affect a label?

I use a Label with the ScrollViewer property:
<Label ScrollViewer.HorizontalScrollBarVisibility="Auto"
ScrollViewer.VerticalScrollBarVisibility="Auto">
Here is many many many text.
</Label>
But no scrollbar appears. Even when using Visible instead of Auto.
What is wrong here?
You need to put the ScrollViewer around the label, it's a seperate control:
<ScrollViewer Width="50" Height="30" HorizontalScrollBarVisibility="Visible">
<Label>
Here is many many many text.
</Label>
</ScrollViewer>
Now I am wondering, why the Label can have ScrollViewer properties
when they are not affecting the label at all?
The ScrollViewer properties are attached properties. Attached properties often have default behavior that is independent from the elements they are applied to (e.g. ToolTipService properties are handled by the service, the elements themselves don't need to know anything about it), so they can always be set anywhere.
It's similar to the BorderBrush property that is on every control. A control usually passes this value along to a Border element that is within its template. Most control templates contain a Border, but many don't contain a ScrollViewer. You could write a Label template that includes one, though:
<Window.Resources>
<Style TargetType="Label">
<Setter Property="Template">
<Setter.Value>
<ControlTemplate TargetType="Label">
<Border BorderBrush="{TemplateBinding BorderBrush}"
BorderThickness="{TemplateBinding BorderThickness}">
<ScrollViewer>
<ContentPresenter HorizontalAlignment="{TemplateBinding HorizontalContentAlignment}"
VerticalAlignment="{TemplateBinding VerticalContentAlignment}"
RecognizesAccessKey="True" />
</ScrollViewer>
</Border>
</ControlTemplate>
</Setter.Value>
</Setter>
</Style>
</Window.Resources>
<Label ScrollViewer.HorizontalScrollBarVisibility="Visible"
ScrollViewer.VerticalScrollBarVisibility="Hidden"
Content="text" />
Notice that this works even though I haven't added TemplateBindings to the ScrollViewer. This is because ScrollViewer knows about its own attached properties and actually adds the bindings by default if it is inside a template.
As you can see from the template, a label is really nothing but a content presenter with RecognizesAccessKey set. This is so that users can use Alt keyboard shortcuts based on its text. Label also defines a Target property to define which element should be selected when the keyboard shortcut is pressed. Labels are meant to be short descriptive text next to input elements. In your case (displaying long text that needs scrolling), it is probably unnecessary. In fact, you can just place the text content directly within a ScrollViewer:
<ScrollViewer HorizontalScrollBarVisibility="Auto"
VerticalScrollBarVisibility="Auto">
Here is many many many text.
</ScrollViewer>
ScrollViewer attached property is there to control ScrollViewer which was defined within the control's Template (first example of such control which comes to mind is ListView). There is no ScrollViewer in Label's template, therefore setting this property on label has no effect.
Instead, you should simply wrap your Label with ScrollViewer, as was shown by JMK.
You need to add the lable inside the ScrollViewer and provide some Height and Width
<ScrollViewer HorizontalScrollBarVisibility="Visible" Height="40" Width="40" >
<Label>
Content
</Label>
</ScrollViewer>
You have to put ScrollViewer around the Label.
like--
<ScrollViewer HorizontalScrollBarVisibility="Visible">
<Label/>
</ScrollViewer>

How do I make the WPF TextBox border inside the ScrollViewer not disappear

in a WPF window I have a TextBox inside a ScrollViewer:
<ScrollViewer ScrollViewer.HorizontalScrollBarVisibility="Auto" ScrollViewer.VerticalScrollBarVisibility="Auto" ScrollViewer.CanContentScroll="True" MaxHeight="160" Grid.Column="1" Grid.Row="0">
<TextBox MinHeight="80" Name="generalLog"/>
</ScrollViewer>
With an empty text it looks like this.
When the text gets to long or contains too many lines, the scrollbars appear, as they should. But as the TextBox is wrapped inside the ScrollViewer, the TextBox gets bigger and its border (default style) gets hidden on the sides:
Link to Screenshot because I can't embed pictures
As you can see, the border is not visible on the left side.
Is there any way to make the ScrollViewer appear inside the TextBox? Or make the ScrollViewer have a border like the TextBox and hide the TextBox one, which would probably look the way I want.
Thanks so much.
Wrap the Scrollviewer with a border and set Textbox borderbrush="transparent" ?
<Border>
<ScrollViewer ScrollViewer.HorizontalScrollBarVisibility="Auto" ScrollViewer.VerticalScrollBarVisibility="Auto" ScrollViewer.CanContentScroll="True" MaxHeight="160" Grid.Column="1" Grid.Row="0">
<TextBox BorderBrush="transparent" MinHeight="80" Name="generalLog"/>
</ScrollViewer>
</Border>

WPF: Row of ToggleButtons with equal length?

I'm currently displaying RadioButtons in my application as rows of ToggleButtons (see my last question). However, I'd like the buttons to be of the same width - currently, every button is just as wide as it has to be.
Since I'm working with templates, I'd like to avoid specifying the width every time I use the control if possible - instead, the width of every button in the row should be equal to that of the widest button in that group.
Any ideas how to do this in XAML? :-)
Maybe using a UniformGrid and setting int the style the property HorizontalAlignement="Stretch" will help.
If you have access to all the toggle buttons (e.g. they aren't databound) then there is a neat trick you can do by binding the minwidth of each button to the width of the one next to it. With the final button being bound to the first:
<StackPanel Orientation="Horizontal">
<Button x:Name="Button1" Content="Long text" MinWidth="{Binding ElementName=Button2, Path=ActualWidth}"/>
<Button x:Name="Button2" Content="A" MinWidth="{Binding ElementName=Button3, Path=ActualWidth}"/>
<Button x:Name="Button3" Content="Extremely long text that should cause this button to be really wide" MinWidth="{Binding ElementName=Button1, Path=ActualWidth}"/>
</StackPanel>
in your resources section create a style that targets ToggleButtons and sets the width to whatever value you want.
<Window.Resources>
<Style TargetType="{x:Type ToggleButton}">
<Setter Property="Width" Value="50" />
</Style>
</Window.Resources>
Use a grid with a 1 button in each column and definethe widths like this

Categories

Resources