internal static Rect GetLayoutRect()

in src/Microsoft.Xaml.Behaviors/Core/ExtendedVisualStateManager.cs [943:1011]


        internal static Rect GetLayoutRect(FrameworkElement element)
        {
            double actualWidth = element.ActualWidth;
            double actualHeight = element.ActualHeight;

            // Use RenderSize here because that works for SL Image and MediaElement - the other uses fo ActualWidth/Height are correct even for these element types
            if ((element is Image || element is MediaElement))
            {
                if (element.Parent is Canvas)
                {
                    actualWidth = double.IsNaN(element.Width) ? actualWidth : element.Width;
                    actualHeight = double.IsNaN(element.Height) ? actualHeight : element.Height;
                }
                else
                {
                    actualWidth = element.RenderSize.Width;
                    actualHeight = element.RenderSize.Height;
                }
            }

            actualWidth = element.Visibility == Visibility.Collapsed ? 0 : actualWidth;
            actualHeight = element.Visibility == Visibility.Collapsed ? 0 : actualHeight;
            Thickness margin = element.Margin;

            Rect slotRect = LayoutInformation.GetLayoutSlot(element);

            double left = 0.0;
            double top = 0.0;

            switch (element.HorizontalAlignment)
            {
                case HorizontalAlignment.Left:
                    left = slotRect.Left + margin.Left;
                    break;

                case HorizontalAlignment.Center:
                    left = ((((slotRect.Left + margin.Left) + slotRect.Right) - margin.Right) / 2.0) - (actualWidth / 2.0);
                    break;

                case HorizontalAlignment.Right:
                    left = (slotRect.Right - margin.Right) - actualWidth;
                    break;

                case HorizontalAlignment.Stretch:
                    left = Math.Max((double)(slotRect.Left + margin.Left), (double)(((((slotRect.Left + margin.Left) + slotRect.Right) - margin.Right) / 2.0) - (actualWidth / 2.0)));
                    break;
            }

            switch (element.VerticalAlignment)
            {
                case VerticalAlignment.Top:
                    top = slotRect.Top + margin.Top;
                    break;

                case VerticalAlignment.Center:
                    top = ((((slotRect.Top + margin.Top) + slotRect.Bottom) - margin.Bottom) / 2.0) - (actualHeight / 2.0);
                    break;

                case VerticalAlignment.Bottom:
                    top = (slotRect.Bottom - margin.Bottom) - actualHeight;
                    break;

                case VerticalAlignment.Stretch:
                    top = Math.Max((double)(slotRect.Top + margin.Top), (double)(((((slotRect.Top + margin.Top) + slotRect.Bottom) - margin.Bottom) / 2.0) - (actualHeight / 2.0)));
                    break;
            }

            return new Rect(left, top, actualWidth, actualHeight);
        }