private static Storyboard CreateStoryboard(
            FrameworkElement target,
            DependencyProperty animatingDependencyProperty,
            string propertyPath,
            ref object toValue,
            TimeSpan durationTimeSpan,
            IEasingFunction easingFunction)
        {
            object fromValue = target.GetValue(animatingDependencyProperty);

            double fromDoubleValue;
            double toDoubleValue;

            DateTime fromDateTime;
            DateTime toDateTime;

            Storyboard storyBoard = new Storyboard();

            Storyboard.SetTarget(storyBoard, target);
            Storyboard.SetTargetProperty(storyBoard, new PropertyPath(propertyPath));

            if ((fromValue != null && toValue != null))
            {
                if (ValueHelper.TryConvert(fromValue, out fromDoubleValue) && ValueHelper.TryConvert(toValue, out toDoubleValue))
                {
                    DoubleAnimation doubleAnimation = new DoubleAnimation();
#if SILVERLIGHT
                    doubleAnimation.EasingFunction = easingFunction;
#endif
                    doubleAnimation.Duration = durationTimeSpan;
                    doubleAnimation.To       = ValueHelper.ToDouble(toValue);
                    toValue = doubleAnimation.To;

                    storyBoard.Children.Add(doubleAnimation);
                }
                else if (ValueHelper.TryConvert(fromValue, out fromDateTime) && ValueHelper.TryConvert(toValue, out toDateTime))
                {
                    ObjectAnimationUsingKeyFrames keyFrameAnimation = new ObjectAnimationUsingKeyFrames();
                    keyFrameAnimation.Duration = durationTimeSpan;

                    long intervals = (long)(durationTimeSpan.TotalSeconds * KeyFramesPerSecond);
                    if (intervals < 2L)
                    {
                        intervals = 2L;
                    }

                    IEnumerable <TimeSpan> timeSpanIntervals =
                        ValueHelper.GetTimeSpanIntervalsInclusive(durationTimeSpan, intervals);

                    IEnumerable <DateTime> dateTimeIntervals =
                        ValueHelper.GetDateTimesBetweenInclusive(fromDateTime, toDateTime, intervals);

                    IEnumerable <DiscreteObjectKeyFrame> keyFrames =
                        EnumerableFunctions.Zip(
                            dateTimeIntervals,
                            timeSpanIntervals,
                            (dateTime, timeSpan) => new DiscreteObjectKeyFrame()
                    {
                        Value = dateTime, KeyTime = timeSpan
                    });

                    foreach (DiscreteObjectKeyFrame keyFrame in keyFrames)
                    {
                        keyFrameAnimation.KeyFrames.Add(keyFrame);
                        toValue = keyFrame.Value;
                    }

                    storyBoard.Children.Add(keyFrameAnimation);
                }
            }

            if (storyBoard.Children.Count == 0)
            {
                ObjectAnimationUsingKeyFrames keyFrameAnimation = new ObjectAnimationUsingKeyFrames();
                DiscreteObjectKeyFrame        endFrame          = new DiscreteObjectKeyFrame()
                {
                    Value = toValue, KeyTime = new TimeSpan(0, 0, 0)
                };
                keyFrameAnimation.KeyFrames.Add(endFrame);

                storyBoard.Children.Add(keyFrameAnimation);
            }

            return(storyBoard);
        }
コード例 #2
0
        protected override Size MeasureOverride(Size availableSize)
        {
            double offset = 0.0;

            if (Children.Count > 0)
            {
                Size totalSize = new Size(double.PositiveInfinity, double.PositiveInfinity);
                foreach (UIElement child in this.Children)
                {
                    child.Measure(totalSize);
                }

                Func <UIElement, double> lengthSelector = null;
                Func <UIElement, double> offsetSelector = null;

                if (Orientation == Orientation.Horizontal)
                {
                    lengthSelector = child => GetCorrectedDesiredSize(child).Width;
                    offsetSelector = child => GetCorrectedDesiredSize(child).Height;
                }
                else
                {
                    lengthSelector = child => GetCorrectedDesiredSize(child).Height;
                    offsetSelector = child => GetCorrectedDesiredSize(child).Width;
                }

                IEnumerable <IGrouping <int, UIElement> > priorityGroups =
                    from child in Children.CastWrapper <UIElement>()
                    group child by GetPriority(child) into priorityGroup
                    select priorityGroup;

                ActualMinimumDistanceBetweenChildren =
                    (from priorityGroup in priorityGroups
                     let orderedElements =
                         (from element in priorityGroup
                          orderby GetCenterCoordinate(element) ascending
                          select element).ToList()
                         where orderedElements.Count >= 2
                         select
                             (EnumerableFunctions.Zip(
                                 orderedElements,
                                 orderedElements.Skip(1),
                                 (leftElement, rightElement) =>
                {
                    double halfLeftLength = lengthSelector(leftElement) / 2;
                    double leftCenterCoordinate = GetCenterCoordinate(leftElement);

                    double halfRightLength = lengthSelector(rightElement) / 2;
                    double rightCenterCoordinate = GetCenterCoordinate(rightElement);

                    return((rightCenterCoordinate - halfRightLength) - (leftCenterCoordinate + halfLeftLength));
                }))
                         .Min())
                    .MinOrNullable() ?? MinimumDistanceBetweenChildren;

                IEnumerable <int> priorities =
                    Children
                    .CastWrapper <UIElement>()
                    .Select(GetPriority).Distinct().OrderBy(priority => priority).ToList();

                PriorityOffsets = new Dictionary <int, double>();
                foreach (int priority in priorities)
                {
                    PriorityOffsets[priority] = 0.0;
                }

                IEnumerable <(int Previous, int Next)> priorityPairs =
                    EnumerableFunctions.Zip(priorities, priorities.Skip(1), (previous, next) => (previous, next));

                foreach (var(Previous, Next) in priorityPairs)
                {
                    IEnumerable <UIElement> currentPriorityChildren = Children.CastWrapper <UIElement>().Where(child => GetPriority(child) == Previous).ToList();

                    IEnumerable <Range <double> > currentPriorityRanges =
                        GetRanges(currentPriorityChildren, lengthSelector);

                    IEnumerable <UIElement> nextPriorityChildren = Children.CastWrapper <UIElement>().Where(child => GetPriority(child) == Next).ToList();

                    IEnumerable <Range <double> > nextPriorityRanges =
                        GetRanges(nextPriorityChildren, lengthSelector);

                    bool intersects =
                        (from currentPriorityRange in currentPriorityRanges
                         from nextPriorityRange in nextPriorityRanges
                         select currentPriorityRange.IntersectsWith(nextPriorityRange))
                        .Any(value => value);

                    if (intersects)
                    {
                        double maxCurrentPriorityChildOffset =
                            currentPriorityChildren
                            .Select(child => offsetSelector(child))
                            .MaxOrNullable() ?? 0.0;

                        offset += maxCurrentPriorityChildOffset + OffsetPadding;
                    }
                    PriorityOffsets[Next] = offset;
                }

                offset =
                    (Children
                     .CastWrapper <UIElement>()
                     .GroupBy(GetPriority)
                     .Select(
                         group =>
                         group
                         .Select(child => PriorityOffsets[group.Key] + offsetSelector(child))
                         .MaxOrNullable()))
                    .Where(num => num.HasValue)
                    .Select(num => num.Value)
                    .MaxOrNullable() ?? 0.0;
            }

            if (Orientation == Orientation.Horizontal)
            {
                return(new Size(0, offset));
            }
            else
            {
                return(new Size(offset, 0));
            }
        }