Avalonia 11에서 새로운 컴포지션 렌더러 사용

13320 단어 avaloniauixamlcsharp
Avalonia 11 프리뷰가 방금 출시되었으며 새로운 기능과 성능 개선이 포함되어 있습니다.
성능 괴짜로서 제가 가장 많이 살펴보는 기능은 새로운 "컴포지션"렌더러입니다.

새로운 컴포지션 렌더러는 무엇입니까?



렌더러는 비주얼 그리기를 추적, 검증 및 트리거하는 역할을 하므로 앱의 성능과 효율성에 영향을 미치는 가장 중요한 구성 요소 중 하나입니다.
새로운 렌더러는 UI 및 렌더 스레드 분리를 통해 UWP와 유사한 컴포지션 시각적 트리를 구현합니다.
결과적으로 Avalonia 앱은 이제 더 효율적이고 더 적은 RAM을 사용하며 렌더링 스레드 전용 애니메이션을 허용합니다.

새로운 애니메이션 속으로



Avalonia 앱에서 레이아웃 변경이 발생하면 렌더러는 새로운 범위에 맞게 시각적 개체를 재정렬합니다.
새로운 Composition API를 사용하면 Avalonia 개발자는 이러한 레이아웃 변경이 발생할 때 매끄럽고 부드러운 애니메이션을 만들 수 있습니다.
애니메이션에는 명시적 및 암시적의 두 가지 종류가 있습니다. 첫 번째는 코드 숨김에서 수동으로 트리거되고 나중에는 시각적 변경 속성으로 트리거됩니다.

새로운 구성 API



이제 Avalonia의 모든 Visual에는 CompositionVisual , Size , Offset 등과 같은 모든 합성 속성을 보유하는 Opacity 대응 항목이 있습니다.
이전 애니메이션과 마찬가지로 이러한 속성에 애니메이션을 적용할 수 있습니다.

예를 들어, 다음은 컨트롤의 명시적인 슬라이딩 인 애니메이션의 예입니다.

// Get the new composition visual
CompositionVisual compositionVisual = ElementComposition.GetElementVisual(control);
Compositor compositor = compositionVisual.Compositor;
// "Offset" is a Vector3 property, so we create a Vector3KeyFrameAnimation
Vector3KeyFrameAnimation animation = compositor.CreateVector3KeyFrameAnimation();
// Change the offset of the visual slightly to the left when the animation beginning
animation.InsertKeyFrame(0f, compositionVisual.Offset with {X = compositionVisual.Offset.X - 20});
// Revert the offset to the original position (0,0,0) when the animation ends
animation.InsertKeyFrame(1f, compositionVisual.Offset);
animation.Duration = TimeSpan.FromMilliseconds(300);
// Start the new animation!
compositionVisual.StartAnimation("Offset", animation);


여기서 우리는 3-벡터인 Offset 속성에 애니메이션을 적용합니다. (x,y,z) . 수직으로 오프셋이 20인 애니메이션을 명시적으로 시작하면 슬라이딩 인 애니메이션을 만들 수 있습니다.



암시적 애니메이션



암시적 애니메이션은 여러분이 짐작한 대로 명시적 애니메이션과 반대이며 시각적 변화의 속성으로 트리거됩니다.
이러한 애니메이션은 한 번만 설정하면 속성이 변경될 때마다 효율적으로 트리거되므로 특히 유용합니다.

각각CompositionVisual에는 속성 이름(예: ImplicitAnimations 애니메이션 또는 애니메이션 그룹이 변경될 때 트리거됩니다.

간단한 예로 컨트롤의 위치 변경을 암시적으로 애니메이션하는 방법은 다음과 같습니다.

CompositionVisual compositionVisual = ElementComposition.GetElementVisual(control);
Compositor compositor = compositionVisual.Compositor;
Vector3KeyFrameAnimation offsetAnimation = compositor.CreateVector3KeyFrameAnimation();
offsetAnimation.Target = "Offset";
// Using the "this.FinalValue" to indicate the last value of the Offset property
offsetAnimation.InsertExpressionKeyFrame(1.0f, "this.FinalValue");
offsetAnimation.Duration = TimeSpan.FromMilliseconds(400);
// Create a new implicit animation collection and bind the offset animation
ImplicitAnimationCollection implicitAnimationCollection = compositor.CreateImplicitAnimationCollection();
implicitAnimationCollection["Offset"] = offsetAnimation;
compositionVisual.ImplicitAnimations = implicitAnimationCollection;


먼저 오프셋 애니메이션을 만들고 이전에 명시적으로 Offset 값을 설정했을 때와 달리 여기서는 마지막 프레임에서 Offset 값을 사용하기 위해 - this.FinalValue 식을 사용합니다.

그런 다음 Offset와 새로운 ImplicitAnimationCollection 사이에 매핑되는 새로운 "Offset"를 사용하여 애니메이션을 비주얼에 연결합니다.
그러면 offsetAnimation 속성이 변경될 때 컴포지터가 offsetAnimation를 시작하도록 지시합니다.
결과적으로 비주얼의 레이아웃 변경이 애니메이션화됩니다.


XAML과 어떻게 결합합니까?



XAML을 확장하려면 Offset 외부에 선언된 속성인 AttachedProperty 를 사용할 수 있지만 여전히 영향을 미칠 수 있습니다.

모든 Windows에 대해 멋진 확대 애니메이션을 만들고 싶다고 가정해 보겠습니다. 연결된 속성에 대한 새 "Extension"클래스를 만드는 것으로 시작하겠습니다.

public class WindowAnimation : AvaloniaObject
{
    public static readonly AttachedProperty<bool> EnableScaleShowAnimationProperty =
        AvaloniaProperty.RegisterAttached<WindowBase, bool>("EnableShowScaleAnimation",
            typeof(WindowAnimation));

    static WindowAnimation()
    {
        EnableScaleShowAnimationProperty.Changed.AddClassHandler<WindowBase>(OnEnableScaleShowAnimationChanged);
    }

    private static void OnEnableScaleShowAnimationChanged(WindowBase windowBase,
        AvaloniaPropertyChangedEventArgs eventArgs)
    {
        if (eventArgs.NewValue is true)
        {
            windowBase.Opened += OnOpened;
        }
        else
        {
            windowBase.Opened -= OnOpened;
        }
    }

    private static void OnOpened(object sender, EventArgs e)
    {
        if (sender is not WindowBase windowBase || !GetEnableScaleShowAnimation(windowBase))
            return;

        // Here we explicitly animate the "Scale" property
        // The implementation is the same as `Offset` at the beginning, but just with the Scale property
        windowBase.StartWindowScaleAnimation();
    }

    public static bool GetEnableScaleShowAnimation(WindowBase element)
    {
        return element.GetValue(EnableScaleShowAnimationProperty);
    }

    public static void SetEnableScaleShowAnimation(WindowBase element, bool value)
    {
        element.SetValue(EnableScaleShowAnimationProperty, value);
    }
}


그런 다음 Control에서 Style를 사용하여 모든 창에 쉽게 적용할 수 있습니다.

<Style Selector="Window">
    <Setter Property="animations:WindowAnimation.EnableScaleShowAnimation" Value="True"/>
</Style>




그리고 그게 다야!
이 게시물이 흥미로웠기를 바랍니다 :)

좋은 웹페이지 즐겨찾기