Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

How do I keep a constant FontSize in WPF Viewbox?

I have a Viewbox with a number of TextBlocks that are scaled and positioned perfectly by the ViewBox. Something like this:

<Viewbox Stretch="Uniform">
    <Canvas Width="100" Height="100">
        <Ellipse Width="100" Height="100" Stroke="Black"/>
        <TextBlock Width="100" TextAlignment="Center" FontSize="12">Top Center</TextBlock>
    </Canvas>
</Viewbox>

If the user resizes the Viewbox its contents are perfectly scaled to match. However I would like to keep the FontSize to 12 regardless of the actual size of the Viewbox.

How can I do this? Can I do this in XAML without attaching to an Resize event?

like image 346
Hallgrim Avatar asked Jan 06 '10 15:01

Hallgrim


Video Answer


1 Answers

ViewBox won't allow you to keep a constant font size, that's just not how it works. You need to put the text outside the view box for that to happen:

<Grid>
    <Viewbox Stretch="Uniform">
        <Canvas Width="100" Height="100">
            <Ellipse Width="100" Height="100" Stroke="Black"/>
        </Canvas>
    </Viewbox>
    <TextBlock TextAlignment="Center" FontSize="12">Top Center</TextBlock>
</Grid>

Note that I removed the Width property from the TextBlock, I just let it stretch for the width of the grid, letting the text alignment take care of the centering.

Or, you could get creative and bind the FontSize property to the ActualWidth of the ViewBox and having it scaled appropriately, for example:

Converter:

class ViewBoxConstantFontSizeConverter : IValueConverter
{
    public object Convert(object value, Type targetType, object parameter, CultureInfo culture)
    {
        if (!(value is double)) return null;
        double d = (double)value;
        return 100 / d * 12;
    }

    public object ConvertBack(object value, Type targetType, object parameter, CultureInfo culture)
    {
        throw new NotSupportedException();
    }
}

Usage:

<Window.Resources>
    ...
    <local:ViewBoxConstantFontSizeConverter x:Key="conv"/>
</Window.Resources>
...
<Viewbox Name="vb" Stretch="Uniform">
    <Canvas Width="100" Height="100">
        <Ellipse Width="100" Height="100" Stroke="Black"/>
        <TextBlock Width="100" TextAlignment="Center"
                   FontSize="{Binding ElementName=vb, 
                                      Path=ActualWidth, 
                                      Converter={StaticResource conv}}">
            Top Center
        </TextBlock>
    </Canvas>
</Viewbox>
like image 98
Aviad P. Avatar answered Sep 21 '22 09:09

Aviad P.