WPF Calculated FontSize Inside ViewBox - c#

I have faced a problem and tried the internet and threads here to find a solution but haven't found yet.
I am a beginner in programming any help will be appreciated.
I have a window which will be displayed on the secondary screen and a TextBlock wrapped in a viewbox and the text is binded and will be populated dymnamically on runtime on the second screen. The fontsize is also Binded and can be changed by the user.
This is working perfectly well.
The Problem Is That when the user increases fontsize to a higher value the text looks good if the text is short but if the text is very very large the text looks ugly sometimes becomes unreadable.
I have tried the ViewBox's Sretch direction and stretch but haven't found a better way to solve my problem but manually if there is very very long text and the text is unreadable reducing the fontsize makes text readable.
How may i be helped. One solution I have in mind is to calculate the fontsize maybe on height and width of parent grid such that when the text is very long the calculation reduces the fontsize to where it becomes readable.
here is my sample Xaml
<Grid>
<Viewbox Stretch="Fill"
StretchDirection="DownOnly">
<TextBlock Text="{Binding}"
Width="{Binding}"
FontSize="{Binding}"
TextWrapping="Wrap">
</TextBlock>
</Viewbox>
</Grid>
Here is the Ugly Behavior when text is very long and fontsize is set highly
Expected behavior. Here the fontsize is manually set lower

Okay I found a work around the problem. If anyone has another solution it will be welcomed.
I wrapped the textblock inside a border and removed binding of the width of the textblock and I will be increasing and decreasing the width. If font size increases I will decrease the width by a ratio in the ViewModel and vice versa.
<Grid>
<Viewbox >
<Border>
<TextBlock Text="{Binding}"
Width="{Binding}"
FontSize="{Binding}"
TextWrapping="Wrap">
</TextBlock>
</Border>
</Viewbox>

Related

How to create a layout with fixed width and flexible height in wpf?

I want to create a layout(or panel) for tooltip that has a flexible height with fixed width like the image that I mentioned
But in my xaml code both height and width is fixed !
<TextBox Name="mytxt" TextChanged="mytxt_TextChanged" Height="102"
SpellCheck.IsEnabled="True" >
<TextBox.ToolTip>
<ToolTip Background="#e74c3c">
<StackPanel >
<Label Content="This is a error test for textbox with flat red background color"/>
</StackPanel>
</ToolTip>
</TextBox.ToolTip>
</TextBox>
Posting my comment as an answer since it solved your issue:
It looks like using the Label could be the issue. Replace the Label with a TextBlock. Then define the TextWrapping property to true. Set a fixed width and that will give you the desired behavior you are looking for.

Limiting the width of the TextBlock in a WPF ListView

I have a ListView and in it's ItemTemplate there's a TextBlock (inside a Grid) which often has long lines of text. The problem is if the text is too long it increases the width of the ListViewItem rather than wrapping the text. How can I limit the width of the TextBlock so that it will not exceed the width of the ListView?
I don't want to hardocde the width to a constant value.
I tried setting the ScrollViewer.HorizontalScrollBarVisibility property to Disabled and setting TextWrapping="Wrap" on the TextBlock, but that didn't do the trick.
When I debug the application the Live Property Explorer shows that even though the ScrollViewer.HorizontalScrollBarVisibility is disabled it's still horizontally scrollable (the IScrollProvider.HorizontallyScrollable property is true).
Any idea how I can limit the textblock size properly?
Played with it a little and this gave me the expected result:
<ListView x:Name="listView"
HorizontalAlignment="Stretch"
ScrollViewer.HorizontalScrollBarVisibility="Disabled" >
<ListView.ItemTemplate>
<DataTemplate>
<TextBlock Text="{Binding Path=.}" TextWrapping="Wrap"></TextBlock>
</DataTemplate>
</ListView.ItemTemplate>
</ListView>
Hope it works for you too!.
If you don't want to hard code the MaxWidth for the text block, just give a relative width to it based on the ListView width.

How to change control alignment depending on available space?

Imagine this. I've got a Border which contains some custom wpf control, lets call it MyControl. This Border stretches itself when window is resized (to fill available space). MyControl size is fixed. Now, I want my control to have HorizontalAlignment="Center" when it fits the available space, and HorizontalAlignment="Left" when it doesn't. I'm having trouble figuring out how to implement such behaviour though.
I guess, i can subscribe to Border's SizeChanged event and change alignment in code-behind depending on ActualWidths of Border and MyControl, but isn't there an easier way? Can this be achieved by databinding or by attached behaviour?
It will automatically behave like that if you set the control's Width and Height to fixed values and HorizontalAlignment and VerticalAlignment to Stretch instead of Center:
<Border BorderBrush="Red" BorderThickness="5">
<my:MyControl Width="200" Height="150"
HorizontalAlignment="Stretch" VerticalAlignment="Stretch"/>
</Border>

Canvas overrides the TextAlignment value of TextBlock inside it

I am trying to configure the TextAlignment of a TextBlock that is a child of a Canvas. I realized that in a grid the TextAlignment works, but when in a Canvas you can't configure it as Center.
I really hope someone could help and shed some light on this topic.
A relatively easy solution is to wrap your TextBlock in a StackPanel with a width, and set the TextBlock's HorizontalAlignment to Center. This will center the text in the StackPanel.
The Width is the important part. Without the Width, the TextBlock wouldn't know how much room it has, and therefore how to center itself.
The Canvas will always give it's child elements their "desired size". So if your TextBlock needs to be 100 pixels wide to display it's text, then the Canvas will give it exactly 100 pixels. A Grid on the other hand, can give the TextBlock more or less space depending on what column/row the TextBlock is in.
For single lines of text (i.e. no new lines), the only time TextAlignment comes into play is when the TextBlock is given more (or less if TextWrapping is enabled) space than it needs.
For multiple lines of text (or in the case of text wrapping a single line), then the TextAlignment will align it's text withing the bounds of the TextBlock.
Since a Canvas will never force a TextBlock to wrap, the only time TextAlignment comes into play there is with multiple lines of text.
<Canvas Width="300" Height="50">
<TextBlock Canvas.Top="0" TextAlignment="Center">
This will not center
</TextBlock>
<TextBlock Canvas.Top="25" TextAlignment="Center">
This will center the shorter<LineBreak />lines of text
</TextBlock>
</Canvas>

I'm using a WPF TextBlock but then text gets cut off when it's too long. Is there an AutoScroll feature?

My TextBlock has for example 50x50 pixels to display text, however if there is more text, I want a user to be able to scroll. Is there an autoscroll feature for this control?
Should I use a different control better suited for this task?
Here's a couple of pics to illustrate the problem:
This one works fine because the text fits in snugly:
This one doesn't seem correct. Text is cut off.
Just in case someone comes into the same problem. Just wrap the textBlock with a control. Works like a charm!
<ScrollViewer Background="Black">
<TextBlock x:Name="textBlockBackStory"
FontSize="12"
Foreground="Orange"
TextWrapping="Wrap"
Background="Black"
TextDecorations="None">
Backstory here.
</TextBlock>
</ScrollViewer>
You can put your textblock inside a ViewBox, so the font will adjust to display the entire text.

Categories

Resources