1

我在 Silverlight 中创建了一个无穷无尽的“地球旋转”动画,它为两张图片制作了动画。如果我只用两张图片做动画,动画会占用2-5%的CPU。这对我来说似乎没问题,也很正常。如果我添加一些简单的叠加效果(其中包含渐变的弧线),CPU 使用率会上升到 25%-30%,这太多了。

这是代码。我添加了注释,“错误代码”开始和结束的地方。

我的问题是:我怎样才能优化这个动画?为什么叠加渐变对 CPU 的要求如此之高?

<UserControl
    xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
    xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
    xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
    xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
    xmlns:ed="http://schemas.microsoft.com/expression/2010/drawing"
    mc:Ignorable="d"
    x:Class="SpinningGlobe.MainControl"
    d:DesignWidth="640" d:DesignHeight="480" Height="450" Width="450">

    <UserControl.Resources>
        <Storyboard x:Name="Vordergrund_Story"  RepeatBehavior="Forever">
            <DoubleAnimationUsingKeyFrames Storyboard.TargetProperty="(UIElement.RenderTransform).(CompositeTransform.TranslateX)" Storyboard.TargetName="Vordergrund">
                <EasingDoubleKeyFrame KeyTime="0" Value="0"/>
                <EasingDoubleKeyFrame KeyTime="0:01:59" Value="877"/>
            </DoubleAnimationUsingKeyFrames>
            <DoubleAnimationUsingKeyFrames Storyboard.TargetProperty="(UIElement.RenderTransform).(CompositeTransform.TranslateX)" Storyboard.TargetName="Hintergrund">
                <EasingDoubleKeyFrame KeyTime="0" Value="0"/>
                <EasingDoubleKeyFrame KeyTime="0:01:59" Value="-877"/>
            </DoubleAnimationUsingKeyFrames>
        </Storyboard>
    </UserControl.Resources>

    <!-- 1754 -->
    <Grid x:Name="LayoutRoot" Background="Transparent" Height="450" Width="450">
        <!-- Dunkle Weltkarte nach links-->
        <Canvas x:Name="Hintergrund" Margin="-507,10,-370,10" RenderTransformOrigin="0.5,0.5" d:IsLocked="True">
            <Canvas.RenderTransform>
                <CompositeTransform/>
            </Canvas.RenderTransform>
            <Image Margin="0,10,0,10" Source="WELT_DUNKEL.png" Stretch="None" HorizontalAlignment="Left"/>
            <Image Margin="877,10,0,10" Source="WELT_DUNKEL.png" Stretch="None" HorizontalAlignment="Left"/>
        </Canvas>
        <!-- Helle Weltkarte nach rechts-->
        <Canvas x:Name="Vordergrund" Margin="-1247,10,0,10" d:IsLocked="True">
            <Canvas.RenderTransform>
                <CompositeTransform/>
            </Canvas.RenderTransform>
            <Image Margin="0,10,0,10" Source="WELT_HELL.png" Stretch="None" HorizontalAlignment="Left"/>
            <Image Margin="877,10,0,10" Source="WELT_HELL.png" Stretch="None" HorizontalAlignment="Left"/>
        </Canvas>


        <!-- HERE STARTS THE HEAVY CPU USAGE-->


        <!-- Äusserer, weisser "Wolkenring"-->
        <ed:Arc ArcThickness="225" ArcThicknessUnit="Pixel" EndAngle="360" HorizontalAlignment="Left" Height="450" Margin="0,0,0,0" Stretch="None" Stroke="Transparent" StartAngle="0" UseLayoutRounding="False" VerticalAlignment="Top" Width="450">
            <ed:Arc.Fill>
                <RadialGradientBrush>
                    <GradientStop Color="Transparent" Offset="0.935"/>
                    <GradientStop Color="#5BFFFFFF" Offset="1"/>
                </RadialGradientBrush>
            </ed:Arc.Fill>
        </ed:Arc>
        <!-- Äusserer, weisser "Wolkenring", aber nur 1 Pixel breit, so das nach aussen eine schärfere Abgrenzung stattfindet-->
        <ed:Arc ArcThickness="1" ArcThicknessUnit="Pixel" EndAngle="360" HorizontalAlignment="Left" Height="450" Margin="0,0,0,0" Stretch="None" Stroke="Transparent" StartAngle="0" UseLayoutRounding="False" VerticalAlignment="Top" Width="450" d:IsLocked="True">
            <ed:Arc.Fill>
                <RadialGradientBrush>
                    <GradientStop Color="Transparent" Offset="0.935"/>
                    <GradientStop Color="#5BFFFFFF" Offset="1"/>
                </RadialGradientBrush>
            </ed:Arc.Fill>
        </ed:Arc>

        <ed:Arc ArcThickness="300" ArcThicknessUnit="Pixel" EndAngle="360" HorizontalAlignment="Left" Height="900" Margin="-450,-230,0,-220" Stretch="None" Stroke="Transparent" StartAngle="0" UseLayoutRounding="False" VerticalAlignment="Top" Width="900" Opacity="0.82" d:IsLocked="True">
            <ed:Arc.Fill>
                <RadialGradientBrush>
                    <GradientStop Color="#00000000" Offset="0.625"/>
                    <GradientStop Offset="0.884" Color="Black"/>
                </RadialGradientBrush>
            </ed:Arc.Fill>
        </ed:Arc>
        <ed:Arc ArcThickness="300" ArcThicknessUnit="Pixel" EndAngle="360" HorizontalAlignment="Left" Height="900" Margin="-120,-230,-330,-220" Stretch="None" Stroke="Transparent" StartAngle="0" UseLayoutRounding="False" VerticalAlignment="Top" Width="900" Opacity="0.82" d:IsLocked="True">
            <ed:Arc.Fill>
                <RadialGradientBrush>
                    <GradientStop Color="#00FFFFFF" Offset="0.6"/>
                    <GradientStop Offset="0.884" Color="#A3FFFFFF"/>
                </RadialGradientBrush>
            </ed:Arc.Fill>
        </ed:Arc>


        <!-- HERE ENDS THE HEAVY CPU USAGE-->

        <!-- Maskierung in Form einer Elipse (Aufheben, um alles zu sehen!)-->
        <Grid.Clip>
            <EllipseGeometry RadiusX="225" RadiusY="225" Center="225,225"/>
        </Grid.Clip>

    </Grid>

</UserControl> 

CPU 重动画的图像

4

1 回答 1

1

我只是想留下一些话,我对问题的解决方案是什么,我的想法。首先,我无法识别 XAML 中的任何错误或明显错误。

我不知道为什么,但是任何在动画中填充渐变的“弧”都会大大增加 CPU 负载。所以我不建议这样做。我个人的想法是,silverlight 只是不适合长或更长的动画。这一切都与简短的 UI 魔术有关。

我的解决方案是,我将动画中的每个框架元素渲染为 PNG 并将其用作图片,然后放在动画上。例如,右侧的黑色阴影是带有渐变的银色弧线,现在是纯 PNG。看起来一样。不需要CPU。

我真的很喜欢silverlight,但这种行为让我有些失望。

于 2013-10-22T16:51:47.693 回答