Exemple #1
0
        /// <summary>
        /// Provides the behavior for the "Arrange" pass of layout.
        /// </summary>
        /// <param name="finalSize">The final area within the parent that this element should use to arrange itself and its children.</param>
        /// <returns>The actual size used.</returns>
        /// <remarks>
        /// Using the WPF paramater name finalSize instead of Silverlight's finalSize for clarity
        /// </remarks>
        protected override Size ArrangeOverride(Size finalSize)
        {
            FrameworkElement child = Child;

            if ((null == _transformRoot) || (null == child))
            {
                // No child, use whatever was given
                return(finalSize);
            }

            DiagnosticWriteLine("ArrangeOverride < " + finalSize);
            // Determine the largest available size after the transformation
            Size finalSizeTransformed = ComputeLargestTransformedSize(finalSize);

            if (IsSizeSmaller(finalSizeTransformed, _transformRoot.DesiredSize))
            {
                // Some elements do not like being given less space than they asked for (ex: TextBlock)
                // Bump the working size up to do the right thing by them
                DiagnosticWriteLine("  Replacing finalSizeTransformed with larger _transformRoot.DesiredSize");
                finalSizeTransformed = _transformRoot.DesiredSize;
            }
            DiagnosticWriteLine("  finalSizeTransformed = " + finalSizeTransformed);

            // Transform the working size to find its width/height
            Rect transformedRect = RectTransform(new Rect(0, 0, finalSizeTransformed.Width, finalSizeTransformed.Height), _transformation);
            // Create the Arrange rect to center the transformed content
            Rect finalRect = new Rect(
                -transformedRect.Left + ((finalSize.Width - transformedRect.Width) / 2),
                -transformedRect.Top + ((finalSize.Height - transformedRect.Height) / 2),
                finalSizeTransformed.Width,
                finalSizeTransformed.Height);

            // Perform an Arrange on _transformRoot (containing Child)
            DiagnosticWriteLine("  _transformRoot.Arrange < " + finalRect);
            _transformRoot.Arrange(finalRect);
            DiagnosticWriteLine("  Child.RenderSize = " + child.RenderSize);

            // This is the first opportunity under Silverlight to find out the Child's true DesiredSize
            if (IsSizeSmaller(finalSizeTransformed, child.RenderSize) && (Size.Empty == _childActualSize))
            {
                // Unfortunately, all the work so far is invalid because the wrong DesiredSize was used
                DiagnosticWriteLine("  finalSizeTransformed smaller than Child.RenderSize");
                // Make a note of the actual DesiredSize
                _childActualSize = new Size(child.ActualWidth, child.ActualHeight);
                DiagnosticWriteLine("  _childActualSize = " + _childActualSize);
                // Force a new measure/arrange pass
                InvalidateMeasure();
            }
            else
            {
                // Clear the "need to measure/arrange again" flag
                _childActualSize = Size.Empty;
            }
            DiagnosticWriteLine("  _transformRoot.RenderSize = " + _transformRoot.RenderSize);

            // Return result to perform the transformation
            DiagnosticWriteLine("ArrangeOverride > " + finalSize);
            return(finalSize);
        }