2009-08-10 10 views
8

que una cuadrícula en mi control Silverlight, estoy añadiendo programáticamente un lienzo, y en el lienzo Estoy cargando y la visualización de la imagen.Cómo forzar ActualWidth y ActualHeight para actualizar (Silverlight)

También estoy añadiendo un giro a la lona. El problema es que, de manera predeterminada, CenterX y CenterY de la rotación se encuentran en la parte superior izquierda del lienzo. Lo que quiero es que la rotación ocurra alrededor del centro del lienzo.

Para ello, He tratado de establecer la centerx y centery de la rotación de las imágenes ActualWidth/2 y ActualHeight/2, sin embargo he descubierto que ActualWidth y ActualHeight no siempre se llenan, al menos no de inmediato . ¿Cómo puedo obligarlos a actualizarse?

Incluso utilizando el evento DownloadProgress en la imagen no parece garantizar la ActualWidth y ActualHeight están pobladas, y tampoco lo hace utilizando 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)); 

Respuesta

12

Para actualizar la ActualWidth y ActualHeight de un FrameworkElement que tendrá que llamar UpdateLayout.

+0

Eso funcionó para mí, gracias! –

+0

Funcionó para mí también. Gracias. – Jordan

3

Desafortunadamente, llamando UpdateLayout no siempre funciona bien dependiendo de su situación.

que he tenido mejor suerte haciendo algo como:

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

pero incluso eso no funciona demasiado a menudo.

0

método más confiable que he encontrado es utilizar DependencyPropertyDescriptorAddValueChanged oyentes de ActualWidth y ActualHeight en lugar de OnLayoutUpdated para conseguir tamaños de elementos después de rendir

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); 
} 

En lugar de utilizar StackPanel, rejilla, etc. utilización elemento de base que está en función de los tamaños relativos

+0

'DependencyPropertyDescriptor' no está disponible en Silverlight. – trm

+0

Puede intentar escuchar LayoutUpdated o crear algún retraso utilizando DispatcherTimer, pero probablemente no le garantice resultados –

Cuestiones relacionadas