English 中文(简体)
How do I measure the size of a TextBlock in WPF before it is rendered?
原标题:

I have a WPF DataTemplate with two TextBlock controls (stacked) and then some other elements underneath. Due to some complicated layout code, I need to know the height of the two TextBlock elements so that I can draw some fancy connector lines, and line up other controls, etc.

If I know the text that s going into the TextBlocks, and I know the font, etc., is there some way I can compute or measure the height of these TextBlocks without actually rendering them?

最佳回答

I think it should be sufficient to call the UIElement.Measure(Size) method and subsequently check the UIElement.DesiredSize property. For more information, check the provided MSDN links.

问题回答

The call to UIElement.Measure(Size), takes as a parameter Size. The second call UIElement.DesiredSize returns whatever Size you passed into the Measure method.

I think this is the case because UIElement (TextBlock in this case) is NOT a child of any control (yet) and therefore DesiredSize has no reason to be anything different.

I appreciate that this is a rather old question, but I have found that using the following code

        TextBlock textBlock = new TextBlock();
        textBlock.Text = "NR valve";
        Size msrSize = new Size(100, 200);
        textBlock.Measure(msrSize);
        Size dsrdSize = textBlock.DesiredSize;

dsrdSize is returned as {47.05,15.96}. The trick seems to be making the msrSize larger than the expected actual size. msrSize seems to act as a limit for the DesiredSize() result. For example, using msrSize = new Size(10, 10), results in a dsrdSize of {10,10} here. Hope this helps someone.

public static Size ShapeMeasure(TextBlock tb) {
    // Measured Size is bounded to be less than maxSize
    Size maxSize = new Size(
         double.PositiveInfinity, 
         double.PositiveInfinity);
    tb.Measure(maxSize);
    return tb.DesiredSize;
}

public static Testit() 
{
    TextBlock textBlock = new TextBlock();
    textBlock.Text = "NR valve";

    Size text size = ShapeMeasure(textBlock);
}

And since Measure is defined in UIElement you can measure the shape of any UIElement derived object including TextBlock:

public static Size ShapeMeasure(UIElement e) {
// Measured Size is bounded to be less than maxSize
Size maxSize = new Size(
     double.PositiveInfinity, 
     double.PositiveInfinity);
e.Measure(maxSize);
return e.DesiredSize;
}




相关问题
WPF convert 2d mouse click into 3d space

I have several geometry meshes in my Viewport3D, these have bounds of (w:1800, h:500, d:25). When a user clicks in the middle of the mesh, I want the Point3D of (900, 500, 25)... How can I achieve ...

Editing a xaml icons or images

Is it possible to edit a xaml icons or images in the expression design or using other tools? Is it possible to import a xaml images (that e.g you have exported) in the expression designer for editing?...

WPF: writing smoke tests using ViewModels

I am considering to write smoke tests for our WPF application. The question that I am faced is: should we use UI automation( or some other technology that creates a UI script), or is it good enough to ...

WPF - MVVM - NHibernate Validation

Im facing a bit of an issue when trying to validate a decimal property on domain object which is bound to a textbox on the view through the viewmodel. I am using NHibernate to decorate my property on ...

How do WPF Markup Extensions raise compile errors?

Certain markup extensions raise compile errors. For example StaticExtension (x:Static) raises a compile error if the referenced class cannot be found. Anyone know the mechanism for this? Is it baked ...

WPF design-time context menu

I am trying to create a custom wpf control, I m wondering how I can add some design-time features. I ve googled and can t seem to get to my goal. So here s my simple question, how can I add an entry ...

How to combine DataTrigger and EventTrigger?

NOTE I have asked the related question (with an accepted answer): How to combine DataTrigger and Trigger? I think I need to combine an EventTrigger and a DataTrigger to achieve what I m after: when ...

热门标签