如何强制更新 ActualWidth 和 ActualHeight (silverlight)

发布于 2024-08-01 15:17:25 字数 1202 浏览 5 评论 0原文

我的 silverlight 控件上有一个网格,我以编程方式添加画布,并在画布中加载并显示图像。

我还在画布上添加了旋转。 问题是默认情况下旋转的 CenterX 和 CenterY 位于画布的左上角。 我想要的是围绕画布中心进行旋转。

为此,我尝试将旋转的 CenterX 和 CenterY 设置为图像 ActualWidth / 2 和 ActualHeight / 2,但是我发现 ActualWidthActualHeight 并不总是填充,至少不会立即填充。 我怎样才能强制他们更新?

即使在图像上使用 DownloadProgress 事件似乎也不能保证填充 ActualWidth 和 ActualHeight,使用 this.Dispatcher.BeginInvoke() 也不能保证填充 ActualWidth 和 ActualHeight...

Image imgTest = new Image();
Canvas cnvTest = new Canvas();
Uri uriImage = new Uri("myurl", UriKind.RelativeOrAbsolute);
System.Windows.Media.Imaging.BitmapImage bmpDisplay = new System.Windows.Media.Imaging.BitmapImage(uriImage);

bmpDisplay.DownloadProgress += new EventHandler<System.Windows.Media.Imaging.DownloadProgressEventArgs>(this.GetActualDimensionsAfterDownload);

imgTest.Source = bmpDisplay;
imgTest.Stretch = Stretch.Uniform;
imgTest.HorizontalAlignment = HorizontalAlignment.Center;
imgTest.VerticalAlignment = VerticalAlignment.Center;

cnvTest.Children.Add(imgTest);

this.grdLayout.Children.Add(imgTest);
this.Dispatcher.BeginInvoke(new Action(GetActualDimensions)); 

I a grid on my silverlight control, I am programatically adding a canvas, and in the canvas I am loading and displaying Image.

I'm also adding a rotation to the canvas. The problem is that by default the CenterX and CenterY of the rotation is the top left of the canvas. What I want is the rotation to happen around the centre of the canvas.

To do this, I've tried setting the CenterX and CenterY of the Rotation to the Images ActualWidth / 2 and ActualHeight / 2, however I've discovered that ActualWidth and ActualHeight are not always populated, at least not right away. How can I force them to get updated?

Even using the DownloadProgress event on the image doesn't seem to guarantee the ActualWidth and ActualHeight are populated, and neither does using this.Dispatcher.BeginInvoke()...

Image imgTest = new Image();
Canvas cnvTest = new Canvas();
Uri uriImage = new Uri("myurl", UriKind.RelativeOrAbsolute);
System.Windows.Media.Imaging.BitmapImage bmpDisplay = new System.Windows.Media.Imaging.BitmapImage(uriImage);

bmpDisplay.DownloadProgress += new EventHandler<System.Windows.Media.Imaging.DownloadProgressEventArgs>(this.GetActualDimensionsAfterDownload);

imgTest.Source = bmpDisplay;
imgTest.Stretch = Stretch.Uniform;
imgTest.HorizontalAlignment = HorizontalAlignment.Center;
imgTest.VerticalAlignment = VerticalAlignment.Center;

cnvTest.Children.Add(imgTest);

this.grdLayout.Children.Add(imgTest);
this.Dispatcher.BeginInvoke(new Action(GetActualDimensions)); 

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(3

李不 2024-08-08 15:17:25

要更新 FrameworkElementActualWidthActualHeight,您必须调用 UpdateLayout

To update the ActualWidth and ActualHeight of a FrameworkElement you will have to call UpdateLayout.

生生漫 2024-08-08 15:17:25

不幸的是,根据您的情况,调用 updateLayout 并不总是有效。

我在做类似的事情时运气更好:

whateverUIElement.Dispatcher.BeginInvoke(()
  {
   //code that needs width/height here
  }
);

但即使这样也经常失败。

Unfortunately, calling updateLayout doesn't always work either depending on your situation.

I've had better luck doing something like:

whateverUIElement.Dispatcher.BeginInvoke(()
  {
   //code that needs width/height here
  }
);

but even that fails too often.

伤感在游骋 2024-08-08 15:17:25

我发现最可靠的方法是使用 DependencyPropertyDescriptor AddValueChanged 监听器 ActualWidthActualHeight 而不是 OnLayoutUpdated< /strong> 在渲染后获取元素大小

DependencyPropertyDescriptor descriptor = DependencyPropertyDescriptor.FromProperty(ActualWidthProperty, typeof(StackPanel));
if (descriptor != null)
{
    descriptor.AddValueChanged(uiPanelRoot, DrawPipelines_LayoutUpdated);
}

descriptor = DependencyPropertyDescriptor.FromProperty(ActualHeightProperty, typeof(StackPanel));
if (descriptor != null)
{
    descriptor.AddValueChanged(uiPanelRoot, DrawPipelines_LayoutUpdated);
}


void DrawPipelines_LayoutUpdated(object sender, EventArgs e)
{
    // Point point1 = elementInstrumentSampleVial.TranslatePoint(
    //                new Point(11.0, 15.0), uiGridMainInner);
}

而不是使用 StackPanel、Grid 等,而是使用您所依赖的相对大小的基本元素

Most reliable method I found is to use DependencyPropertyDescriptor AddValueChanged listeners of ActualWidth and ActualHeight instead of OnLayoutUpdated to get element sizes after rendering

DependencyPropertyDescriptor descriptor = DependencyPropertyDescriptor.FromProperty(ActualWidthProperty, typeof(StackPanel));
if (descriptor != null)
{
    descriptor.AddValueChanged(uiPanelRoot, DrawPipelines_LayoutUpdated);
}

descriptor = DependencyPropertyDescriptor.FromProperty(ActualHeightProperty, typeof(StackPanel));
if (descriptor != null)
{
    descriptor.AddValueChanged(uiPanelRoot, DrawPipelines_LayoutUpdated);
}


void DrawPipelines_LayoutUpdated(object sender, EventArgs e)
{
    // Point point1 = elementInstrumentSampleVial.TranslatePoint(
    //                new Point(11.0, 15.0), uiGridMainInner);
}

Instead of using StackPanel, Grid etc. use base element that you are depending on for relative sizes

~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文