private async void StartExpressionAnimation() { // 將 containerVisual 與 spriteVisual 新增至 DemoPage5 中 var containerVisual = compositor.CreateContainerVisual(); var spriteVisual = compositor.CreateSpriteVisual(); containerVisual.Children.InsertAtTop(spriteVisual); ElementCompositionPreview.SetElementChildVisual(this, containerVisual); // 讀圖 var targetBrush = await GenerateCompositionBrush(); // 將圖片讀進 spriteVisual spriteVisual.Brush = targetBrush; spriteVisual.Size = new Vector2(300f, 300f); // 取得 ScrollViewer PropertySet CompositionPropertySet scrollProperties = ElementCompositionPreview.GetScrollViewerManipulationPropertySet(TargetScrollViewer); // Expression animation 規則 // 捲軸向下垂直捲動的距離 > TopBreak 時,物件垂直位移為 [0] // 上述條件不符時,物件垂直位移為 [TopBreak] - [捲軸向下垂直捲動的距離] // ***捲軸向下垂直捲動距離為負數,越往下捲越小 // 故以 [-ScrollManipulation.Translation.Y] 表示 [捲軸向下垂直捲動的距離] const float topBreak = 500; var expressionAnimation = compositor.CreateExpressionAnimation(); expressionAnimation.SetScalarParameter("TopBreak", topBreak); expressionAnimation.SetReferenceParameter("ScrollManipulation", scrollProperties); expressionAnimation.Expression = "-ScrollManipulation.Translation.Y > TopBreak ? 0 : TopBreak - (-ScrollManipulation.Translation.Y)"; spriteVisual.StartAnimation("Offset.Y", expressionAnimation); }
private void _scrollViewer_Loaded(object sender, RoutedEventArgs e) { _itemsPresenter = _scrollViewer.Content as ItemsPresenter; //_header = _scrollViewer.FindDescendantByName("Header") as ContentControl; //Binding headerbinding = new Binding(); //headerbinding.Source = this; //headerbinding.Mode = BindingMode.OneWay; //headerbinding.Path = new PropertyPath("Header"); //_header.SetBinding(ContentControl.ContentProperty, headerbinding); //Binding headerTemplatebinding = new Binding(); //headerTemplatebinding.Source = this; //headerTemplatebinding.Mode = BindingMode.OneWay; //headerTemplatebinding.Path = new PropertyPath("HeaderTemplate"); //_header.SetBinding(ContentControl.ContentTemplateProperty, headerTemplatebinding); _scrollerViewerManipulation = ElementCompositionPreview.GetScrollViewerManipulationPropertySet(_scrollViewer); _compositor = _scrollerViewerManipulation.Compositor; if (_frozenColumnsHeader != null) { _offsetAnimation = _compositor.CreateExpressionAnimation("-min(0,ScrollManipulation.Translation.X)"); _offsetAnimation.SetReferenceParameter("ScrollManipulation", _scrollerViewerManipulation); _scrollContentVisual = ElementCompositionPreview.GetElementVisual(_frozenColumnsHeader); _scrollContentVisual.StartAnimation("Offset.X", _offsetAnimation); } }
private void Page_Loaded(object sender, RoutedEventArgs e) { clampTeacherCount.Translation = new Vector3(0, -100, 0); clampSendButton.Translation = new Vector3(0, -100, 0); var propSet = ElementCompositionPreview.GetScrollViewerManipulationPropertySet(scrollRoot); var compositor = propSet.Compositor; var props = compositor.CreatePropertySet(); props.InsertScalar("progress", 0); props.InsertScalar("clampSize", ClampBreakPoint); var propScroll = propSet.GetSpecializedReference <ManipulationPropertySetReferenceNode>(); var propGet = props.GetReference(); var progressionNode = propGet.GetScalarProperty("progress"); var clampSizeNode = propGet.GetScalarProperty("clampSize"); ExpressionNode progressAnim = ExpressionFunctions.Clamp(-propScroll.Translation.Y / clampSizeNode, 0, 1); props.StartAnimation("progress", progressAnim); ExpressionNode opacityNode = ExpressionFunctions.Lerp(0, 1, progressionNode); ElementCompositionPreview.GetElementVisual(fadeBlackHeader).StartAnimation("Opacity", opacityNode); }
private void MainPage_Loaded(object sender, RoutedEventArgs e) { //Only run this code if the app is running on Windows 10 1511 or later because API not supported on earlier versions of Windows if (ApiInformation.IsApiContractPresent("Windows.Foundation.UniversalApiContract", 2)) { // Get a referece to a "propertyset" that contains the following keys // Translation (Vector3) // CenterPoint (Vector3) // Scale (Vector3) // Matrix (Matrix4x4) // that represent the state of the scrollview at any moment (i.e. as the user manipulates the scrollviewer with mouse, touch, touchpad) CompositionPropertySet scrollerManipProps = ElementCompositionPreview.GetScrollViewerManipulationPropertySet(myScroller); Compositor compositor = scrollerManipProps.Compositor; // Create the expression ExpressionAnimation expression = compositor.CreateExpressionAnimation("scroller.Translation.Y * parallaxFactor"); // wire the ParallaxMultiplier constant into the expression expression.SetScalarParameter("parallaxFactor", 0.3f); // set "dynamic" reference parameter that will be used to evaluate the current position of the scrollbar every frame expression.SetReferenceParameter("scroller", scrollerManipProps); // Get the background image and start animating it's offset using the expression Visual backgroundVisual = ElementCompositionPreview.GetElementVisual(background); backgroundVisual.StartAnimation("Offset.Y", expression); } }
private void AssignParallax() { if (ParallaxContent == null) { return; } if (AssociatedObject == null) { return; } var scroller = AssociatedObject as ScrollViewer; if (scroller == null) { scroller = AssociatedObject.GetChildOfType <ScrollViewer>(); } if (scroller == null) { return; } CompositionPropertySet scrollerViewerManipulation = ElementCompositionPreview.GetScrollViewerManipulationPropertySet(scroller); Compositor compositor = scrollerViewerManipulation.Compositor; ExpressionAnimation expression = compositor.CreateExpressionAnimation("ScrollManipululation.Translation.Y * ParallaxMultiplier"); expression.SetScalarParameter("ParallaxMultiplier", (float)ParallaxMultiplier); expression.SetReferenceParameter("ScrollManipululation", scrollerViewerManipulation); Visual textVisual = ElementCompositionPreview.GetElementVisual(ParallaxContent); textVisual.StartAnimation("Offset.Y", expression); }
private void Image_ImageOpened(object sender, RoutedEventArgs e) { TitleGridMargin.X = Image.ActualWidth + 48; Col1.Width = new GridLength(Image.ActualWidth); ToolbarTitle.Margin = new Thickness(Image.ActualWidth * 80 / 200 + 32, 8, 0, 8); var scrollviewer = SongList.GetScrollViewer(); var _scrollerPropertySet = ElementCompositionPreview.GetScrollViewerManipulationPropertySet(scrollviewer); var _compositor = _scrollerPropertySet.Compositor; var moving = 80f; // Get references to our property sets for use with ExpressionNodes var scrollingProperties = _scrollerPropertySet.GetSpecializedReference <ManipulationPropertySetReferenceNode>(); var horiMovingAni = EF.Clamp(-scrollingProperties.Translation.Y / moving, 0, 1); horiMovingAni = EF.Lerp(0, (float)((80f / ImageGrid.ActualHeight * ImageGrid.ActualWidth) - ImageGrid.ActualWidth), horiMovingAni); var scaleAnimation = EF.Clamp(-scrollingProperties.Translation.Y / moving, 0, 1); var textScaleAnimation = EF.Lerp(1, (float)(ToolbarTitle.ActualHeight / TitleText.ActualHeight), scaleAnimation); var titleVisual = ElementCompositionPreview.GetElementVisual(Title); titleVisual.StopAnimation("offset.X"); titleVisual.StartAnimation("Offset.X", horiMovingAni); }
private void Page_Loaded(object sender, RoutedEventArgs e) { //This whole thing is pure black magic. Literally undebugable. scrollerPropertySet = ElementCompositionPreview.GetScrollViewerManipulationPropertySet(ItemDetailScroller); Compositor compositor = scrollerPropertySet.Compositor; string progress = "Clamp(Abs(america.Translation.Y) / 232.0, 0.0, 1.0)"; // Shift the header by 50 pixels when scrolling down var offsetExpression = compositor.CreateExpressionAnimation($"-america.Translation.Y - {progress} * 232"); offsetExpression.SetReferenceParameter("america", scrollerPropertySet); // Shift the option button by 244 pixel (?) when scrolling down var itemoptionsvisual = ElementCompositionPreview.GetElementVisual(ItemOptions); itemoptionsvisual.StartAnimation("offset.Y", offsetExpression); var episodelistconfvisual = ElementCompositionPreview.GetElementVisual(EpisodesListConfiguration); episodelistconfvisual.StartAnimation("offset.Y", offsetExpression); // add a patch background. var backgroundadder = ElementCompositionPreview.GetElementVisual(backgroundadded); string _backExpression = "Clamp(Abs(america.Translation.Y) / 276.0, 0.0, 1.0)"; var _backoffset = compositor.CreateExpressionAnimation($"({progress} * 232) - ({_backExpression} * 276)"); _backoffset.SetReferenceParameter("america", scrollerPropertySet); backgroundadder.StopAnimation("offset.Y"); backgroundadder.StartAnimation("offset.Y", _backoffset); }
private void Page_Loaded(object sender, RoutedEventArgs e) { _scrollerPropertySet = ElementCompositionPreview.GetScrollViewerManipulationPropertySet(SCRpost); _compositor = _scrollerPropertySet.Compositor; _props = _compositor.CreatePropertySet(); _props.InsertScalar("progress", 0); _props.InsertScalar("clampSize", 150); _props.InsertScalar("scaleFactor", 0.7f); var progressAnimation = _compositor.CreateExpressionAnimation("Clamp(-scrollingProperties.Translation.Y/150,0,1)"); progressAnimation.SetReferenceParameter("scrollingProperties", _scrollerPropertySet); _props.StartAnimation("progress", progressAnimation); Visual headerVisual = ElementCompositionPreview.GetElementVisual(Header); /* * var headerScaleAnimation = _compositor.CreateExpressionAnimation("Lerp(1,1.25f,Clamp(scrollingProperties.Translation.Y/50,0,1))"); * headerScaleAnimation.SetReferenceParameter("scrollingProperties", _scrollerPropertySet); * headerVisual.StartAnimation("Scale.X", headerScaleAnimation); * headerVisual.StartAnimation("Scale.Y", headerScaleAnimation); * headerVisual.CenterPoint= new Vector3((float)(Header.ActualWidth / 2), (float)Header.ActualHeight, 0);*/ var headerOffsetAnimation = _compositor.CreateExpressionAnimation("-150*props.progress"); headerOffsetAnimation.SetReferenceParameter("props", _props); headerVisual.StartAnimation("Offset.Y", headerOffsetAnimation); Visual photoVisual = ElementCompositionPreview.GetElementVisual(RECTback); var photoOpacityAnimation = _compositor.CreateExpressionAnimation("1-props.progress"); photoOpacityAnimation.SetReferenceParameter("props", _props); photoVisual.StartAnimation("Opacity", photoOpacityAnimation); Visual overlayVisual = ElementCompositionPreview.GetElementVisual(OverlayRectangle); var overlayOpacityAnimation = _compositor.CreateExpressionAnimation("props.progress"); overlayOpacityAnimation.SetReferenceParameter("props", _props); overlayVisual.StartAnimation("Opacity", overlayOpacityAnimation); Visual blurbVisual = ElementCompositionPreview.GetElementVisual(Blurb); var textOpacityAnimation = _compositor.CreateExpressionAnimation("Clamp(1-(props.progress*2),0,1)"); textOpacityAnimation.SetReferenceParameter("props", _props); var scaleAnimation = _compositor.CreateExpressionAnimation("Lerp(1,0.7f,props.progress)"); scaleAnimation.SetReferenceParameter("props", _props); blurbVisual.StartAnimation("Opacity", textOpacityAnimation); blurbVisual.StartAnimation("Scale.X", scaleAnimation); blurbVisual.StartAnimation("Scale.Y", scaleAnimation); Visual titleVisual = ElementCompositionPreview.GetElementVisual(TitleBlock); Visual buttonVisual = ElementCompositionPreview.GetElementVisual(ButtonPanel); var contentOffsetAnimation = _compositor.CreateExpressionAnimation("(props.progress)*120"); var titleScaleAnimation = _compositor.CreateExpressionAnimation("Lerp(1,1.05f,props.progress)"); contentOffsetAnimation.SetReferenceParameter("props", _props); titleScaleAnimation.SetReferenceParameter("props", _props); titleVisual.StartAnimation("Offset.Y", contentOffsetAnimation); titleVisual.StartAnimation("Scale.X", titleScaleAnimation); titleVisual.StartAnimation("Scale.Y", titleScaleAnimation); var buttonOffsetAnimation = _compositor.CreateExpressionAnimation("(props.progress*30)"); buttonOffsetAnimation.SetReferenceParameter("props", _props); buttonVisual.StartAnimation("Offset.Y", buttonOffsetAnimation); }
private void Header_Loaded(object sender, RoutedEventArgs e) { var scrollviewer = MainScroller; _scrollerPropertySet = ElementCompositionPreview.GetScrollViewerManipulationPropertySet(scrollviewer); _compositor = _scrollerPropertySet.Compositor; _props = _compositor.CreatePropertySet(); _props.InsertScalar("progress", 0); // Get references to our property sets for use with ExpressionNodes var scrollingProperties = _scrollerPropertySet.GetSpecializedReference <ManipulationPropertySetReferenceNode>(); var props = _props.GetReference(); var progressNode = props.GetScalarProperty("progress"); // Create and start an ExpressionAnimation to track scroll progress over the desired distance ExpressionNode progressAnimation = EF.Clamp(-scrollingProperties.Translation.Y / ((float)Header.Height), 0, 1); _props.StartAnimation("progress", progressAnimation); var headerbgVisual = ElementCompositionPreview.GetElementVisual(HeaderBG); var bgblurOpacityAnimation = EF.Clamp(progressNode, 0, 1); headerbgVisual.StartAnimation("Opacity", bgblurOpacityAnimation); }
// Init map private void InitializeMap() { var space = (ActualHeight * 40) / 100; MapPresenter.Height = ActualHeight; MapPresenter.Margin = new Thickness(0, -(space / 2), 0, -(space / 2)); if (ApiInformation.IsApiContractPresent("Windows.Foundation.UniversalApiContract", 2)) { var scrollingHost = NearbyList.Descendants <ScrollViewer>().FirstOrDefault() as ScrollViewer; var scrollerViewerManipulation = ElementCompositionPreview.GetScrollViewerManipulationPropertySet(scrollingHost); var compositor = scrollerViewerManipulation.Compositor; var expression = compositor.CreateExpressionAnimation("-(ScrollManipulation.Translation.Y / 2)"); expression.SetScalarParameter("ParallaxMultiplier", (float)(space / 2)); expression.SetReferenceParameter("ScrollManipulation", scrollerViewerManipulation); var heroVisual = ElementCompositionPreview.GetElementVisual(MapPresenter); heroVisual.CenterPoint = new Vector3((float)(MapPresenter.ActualWidth / 2), (float)MapPresenter.ActualHeight, 0); heroVisual.StartAnimation("Offset.Y", expression); } mMap.Style = MapStyle.Road; mMap.ZoomLevel = 10; userPos = new MapIcon(); userPos.ZIndex = 0; userPos.Image = RandomAccessStreamReference.CreateFromUri(new Uri("ms-appx:///Assets/Icons/userPos32.png")); userPos.Visible = false; mMap.MapElements.Add(userPos); FindLocation(); }
/// <summary> /// Creates and starts an animation on the target element that binds either the X or Y axis of the source <see cref="ScrollViewer"/> /// </summary> /// <param name="scroller">The source <see cref="ScrollViewer"/> control to use</param> /// <param name="target">The target <see cref="UIElement"/> that will be animated</param> /// <param name="sourceAxis">The scrolling axis of the source <see cref="ScrollViewer"/></param> /// <param name="targetAxis">The optional scrolling axis of the target element, if <see langword="null"/> the source axis will be used</param> /// <param name="property">The target <see cref="Visual"/> property to animate.</param> /// <returns>An <see cref="ExpressionAnimation"/> instance that represents an already running animation.</returns> public static ExpressionAnimation StartExpressionAnimation( this ScrollViewer scroller, UIElement target, Axis sourceAxis, Axis targetAxis, VisualProperty property = VisualProperty.Translation) { CompositionPropertySet scrollSet = ElementCompositionPreview.GetScrollViewerManipulationPropertySet(scroller); ExpressionAnimation animation = scrollSet.Compositor.CreateExpressionAnimation($"{nameof(scroller)}.{nameof(UIElement.Translation)}.{sourceAxis}"); animation.SetReferenceParameter(nameof(scroller), scrollSet); Visual visual = ElementCompositionPreview.GetElementVisual(target); switch (property) { case VisualProperty.Translation: ElementCompositionPreview.SetIsTranslationEnabled(target, true); visual.StartAnimation($"{nameof(Matrix4x4.Translation)}.{targetAxis}", animation); break; case VisualProperty.Offset: visual.StartAnimation($"{nameof(Visual.Offset)}.{targetAxis}", animation); break; default: throw new ArgumentException($"Invalid target property: {property}", nameof(property)); } return(animation); }
private void AttachParallaxEffect(UIElement element) { if (element != null && this.AssociatedObject != null) { var scrollViewer = this.AssociatedObject as ScrollViewer; if (scrollViewer == null) { // Attempt to see if this is attached to a scroll-based control like a ListView or GridView. scrollViewer = this.AssociatedObject.FindDescendant <ScrollViewer>(); if (scrollViewer == null) { throw new InvalidOperationException( "The associated object or one of it's child elements must be of type ScrollViewer."); } } var compositionPropertySet = ElementCompositionPreview.GetScrollViewerManipulationPropertySet(scrollViewer); var compositor = compositionPropertySet.Compositor; var animationExpression = compositor.CreateExpressionAnimation( "ScrollViewer.Translation.Y * Multiplier"); animationExpression.SetScalarParameter("Multiplier", (float)this.ParallaxMultiplier); animationExpression.SetReferenceParameter("ScrollViewer", compositionPropertySet); var visual = ElementCompositionPreview.GetElementVisual(element); visual.StartAnimation("Offset.Y", animationExpression); } }
private void MainPage_Loaded(object sender, RoutedEventArgs e) { // Hide the refresh indicator (SV1 is the outer ScrollViewer) SV1.ChangeView(null, 100, null); ScrollViewer childScrollView = GetChildElement <ScrollViewer>(lv); if (childScrollView != null) { CompositionPropertySet scrollingProperties = ElementCompositionPreview.GetScrollViewerManipulationPropertySet(childScrollView); Compositor comp = scrollingProperties.Compositor; // // Set up the animation on the content of the main scroller. Animation will show a peek // of the refresh indicator when the child listview is bouncing. // MyPanel tempGrid = GetChildElement <MyPanel>(SV1); Visual elementVisual = ElementCompositionPreview.GetElementVisual(tempGrid); ExpressionAnimation elementAnimation = comp.CreateExpressionAnimation(@" max(scrollingProperties.Translation.Y, 0)"); elementAnimation.SetReferenceParameter("scrollingProperties", scrollingProperties); elementVisual.StartAnimation("Offset.Y", elementAnimation); // // Setup the animation to negate the bounce on the listView's scroller // Visual childVisual = ElementCompositionPreview.GetElementVisual(childScrollView); ExpressionAnimation childAnimation = comp.CreateExpressionAnimation(@" -max(scrollingProperties.Translation.Y, 0)"); childAnimation.SetReferenceParameter("scrollingProperties", scrollingProperties); childVisual.StartAnimation("Offset.Y", childAnimation); } }
private void HeaderUpdated() { FlipView.Height = Image.ActualHeight; var height = FlipView.ActualHeight - HeaderText.ActualHeight + 1; CompositionPropertySet scrollerPropertySet = ElementCompositionPreview.GetScrollViewerManipulationPropertySet(MainScrollViewer); Compositor compositor = scrollerPropertySet.Compositor; // Get the visual that represents our HeaderTextBlock // And define the progress animation string var headerVisual = ElementCompositionPreview.GetElementVisual(ScrollHeader); String progress = $"Clamp(Abs(scroller.Translation.Y) / {height}, 0.0, 1.0)"; var textExpression = compositor.CreateExpressionAnimation("Lerp(1.5, 1, " + progress + ")"); textExpression.SetReferenceParameter("scroller", scrollerPropertySet); var offsetExpression = compositor.CreateExpressionAnimation($"-scroller.Translation.Y - {progress} * {height}"); offsetExpression.SetReferenceParameter("scroller", scrollerPropertySet); headerVisual.StartAnimation("Offset.Y", offsetExpression); Visual textVisual = ElementCompositionPreview.GetElementVisual(HeaderText); Vector3 finalOffset = new Vector3(0, 0, 0); var headerOffsetAnimation = compositor.CreateExpressionAnimation($"Lerp(Vector3(0,0,0), finalOffset, {progress})"); headerOffsetAnimation.SetReferenceParameter("scroller", scrollerPropertySet); headerOffsetAnimation.SetVector3Parameter("finalOffset", finalOffset); textVisual.StartAnimation(nameof(Visual.Offset), headerOffsetAnimation); var opacityExpression = compositor.CreateExpressionAnimation($"{progress}"); opacityExpression.SetReferenceParameter("scroller", scrollerPropertySet); textVisual.StartAnimation("opacity", opacityExpression); }
private void OnLoaded(object sender, RoutedEventArgs routedEventArgs) { ComparisonFiltersList.SelectedIndex = (int)_viewModel.ComparisonFilter; var index = (int)_viewModel.StatusFilter; index = index > 4 ? index - 1 : index; StatusFiltersList.SelectedIndex = index - 1; SortOptionsList.SelectedIndex = (int)_viewModel.ComparisonSorting; FilterStatusComboBox.SelectedIndex = (int)_viewModel.StatusFilterTarget; // Get scrollviewer _myScrollViewer = GridView.GetFirstDescendantOfType <ScrollViewer>(); _scrollProperties = ElementCompositionPreview.GetScrollViewerManipulationPropertySet(_myScrollViewer); // Setup the expression var scrollPropSet = _scrollProperties.GetSpecializedReference <ManipulationPropertySetReferenceNode>(); var startOffset = ExpressionValues.Constant.CreateConstantScalar("startOffset", 0.0f); var parallaxValue = 0.7f; var parallax = (scrollPropSet.Translation.Y + startOffset); _parallaxExpression = parallax * parallaxValue - parallax / 1.11f; _lastColumns = (int)(GridView.ActualWidth / 380.0f); _isWide = Root.ActualWidth > 1205; UpdateVisualStates(); _viewModel.CurrentItems.CollectionChanged += async(o, args) => { await Task.Delay(500); _myScrollViewer.ChangeView(null, _myScrollViewer.VerticalOffset + 4, null); }; }
private void ApplyAnimations() { var compositor = ElementCompositionPreview.GetElementVisual(this).Compositor; var scrollerPropertySet = ElementCompositionPreview.GetScrollViewerManipulationPropertySet(scrollViewer); var anim = compositor.CreateScalarKeyFrameAnimation(); anim.InsertKeyFrame(0.0f, -340.0f); anim.InsertKeyFrame(1.0f, 0.0f); anim.Duration = TimeSpan.FromSeconds(0.250); ElementCompositionPreview.GetElementVisual(headerOffset).StartAnimation("Offset.Y", anim); brush.BlurAmountExpression = compositor.CreateExpressionWrapper("Clamp(scroller.Translation.Y * parallaxFactor, 0, 360/10)") .Parameter("scroller", scrollerPropertySet) .Parameter("parallaxFactor", -0.05f) .Expression; compositor.CreateExpressionWrapper("Clamp(scroller.Translation.Y * parallaxFactor, -360/2, 0)") .Parameter("scroller", scrollerPropertySet) .Parameter("parallaxFactor", 0.25f) .Start(header, "Offset.Y"); compositor.CreateExpressionWrapper("Lerp(0, -300, scroller.Translation.Y * parallaxFactor / -340.0)") .Parameter("scroller", scrollerPropertySet) .Parameter("parallaxFactor", 0.5f) .Start(pictureContainer, "Offset.Y"); }
private void ListView_SizeChanged(object sender, SizeChangedEventArgs e) { var ListViewheight = (sender as FrameworkElement).ActualHeight; if (ListViewheight == _listviewheight) { return; } _listviewheight = ListViewheight; CompositionPropertySet scrollerPropertySet = ElementCompositionPreview.GetScrollViewerManipulationPropertySet(pagescroll); Compositor compositor = scrollerPropertySet.Compositor; string progress = $"Clamp(Floor(Abs(doe.Translation.Y) / {_listviewheight}), 0.0, 1.0)"; // Shift the header by 50 pixels when scrolling down var offsetExpression = compositor.CreateExpressionAnimation($"-doe.Translation.Y + ({progress}*(doe.Translation.Y + {_listviewheight})) "); offsetExpression.SetReferenceParameter("doe", scrollerPropertySet); // Shift the option button by 244 pixel (?) when scrolling down var flTextBoxVisual = ElementCompositionPreview.GetElementVisual(fromLibraryTextBox); flTextBoxVisual.StopAnimation("offset.Y"); flTextBoxVisual.StartAnimation("offset.Y", offsetExpression); }
private void OnLoaded(object sender, RoutedEventArgs e) { var scrollViewer = ScrollingHost as ScrollViewer; if (scrollViewer == null && ScrollingHost != null) { scrollViewer = ScrollingHost.Descendants <ScrollViewer>().FirstOrDefault() as ScrollViewer; } if (scrollViewer == null) { return; } var props = ElementCompositionPreview.GetScrollViewerManipulationPropertySet(scrollViewer); if (props == null) { return; } if (VerticalAlignment == VerticalAlignment.Top) { _animation = _compositor.CreateExpressionAnimation("Max(Scroll.Translation.Y, 0)"); _animation.SetReferenceParameter("Scroll", props); _visual.StopAnimation("Size.Y"); _visual.StartAnimation("Size.Y", _animation); } }
private void InitComposition() { // Get our Compositor as well as the ScrollViewer that corresponds to // to our ListView. Then get the CompositionPropertySet that corresponds // to the ScrollViewer. var compositor = ElementCompositionPreview.GetElementVisual(this).Compositor; var scrollViewer = MainListView.GetChildOfType <ScrollViewer>(); var scrollerPropertySet = ElementCompositionPreview.GetScrollViewerManipulationPropertySet(scrollViewer); // Construct our parallax expression using the property set we got from the // ScrollViewer. Also we make sure to clamp the result so that the image doesn't // go off the screen/window. var expression = compositor.CreateExpressionAnimation("Clamp(scroller.Translation.Y * parallaxFactor, -608, 999)"); expression.SetScalarParameter("parallaxFactor", 0.3f); expression.SetReferenceParameter("scroller", scrollerPropertySet); // Assign our expression to the visual that represents our BackgroundImage. var backgroundVisual = ElementCompositionPreview.GetElementVisual(BackgroundImage); backgroundVisual.StartAnimation("Offset.Y", expression); // Get the visual that represents our HeaderTextBlock and also set up part // of our expression. var textVisual = ElementCompositionPreview.GetElementVisual(HeaderTextBlock); String progress = "Clamp(visual.Offset.Y / -100.0, 0.0, 1.0)"; // Create the expression and add in our progress string. var textExpression = compositor.CreateExpressionAnimation("Lerp(Vector3(0, 200, 0), Vector3(0, 0, 0), " + progress + ")"); textExpression.SetReferenceParameter("visual", backgroundVisual); // Assign our expression to the text visual. textVisual.StartAnimation("Offset", textExpression); }
private void LoadNowPlayingListAnimation() { _nowPlayingScrollViewer = NowPlayingList.GetScrollViewer(); _nowPlayingScrollViewer.DirectManipulationStarted += OnNowPlayingListManipulationStarted; _nowPlayingScrollViewer.DirectManipulationCompleted += OnNowPlayingListManipulationCompleted; _nowPlayingManipulation = ElementCompositionPreview.GetScrollViewerManipulationPropertySet(_nowPlayingScrollViewer); _nowPlayingCompositor = _nowPlayingManipulation.Compositor; _nowPlayingOpacityAnimation = _nowPlayingCompositor.CreateExpressionAnimation("min(max(0, -ScrollManipulation.Translation.X*4) / Divider, 1)"); _nowPlayingOpacityAnimation.SetScalarParameter("Divider", 95.0f); _nowPlayingOpacityAnimation.SetReferenceParameter("ScrollManipulation", _nowPlayingManipulation); _nowPlayingRefreshBorderOffsetAnimation = _nowPlayingCompositor.CreateExpressionAnimation(" ControlWidth+(max(min(0, ScrollManipulation.Translation.X*4) / Divider, -1)) * MaxOffsetX"); _nowPlayingRefreshBorderOffsetAnimation.SetScalarParameter("Divider", 95.0f); _nowPlayingRefreshBorderOffsetAnimation.SetScalarParameter("MaxOffsetX", 95.0f); _nowPlayingRefreshBorderOffsetAnimation.SetScalarParameter("ControlWidth", (float)(ActualWidth)); _nowPlayingRefreshBorderOffsetAnimation.SetReferenceParameter("ScrollManipulation", _nowPlayingManipulation); _nowPlayingBorderOffsetAnimation = _nowPlayingCompositor.CreateExpressionAnimation("(max(min(0, ScrollManipulation.Translation.X) / Divider, -1)) * MaxOffsetX"); _nowPlayingBorderOffsetAnimation.SetScalarParameter("Divider", 95.0f); _nowPlayingBorderOffsetAnimation.SetScalarParameter("MaxOffsetX", 95.0f); _nowPlayingBorderOffsetAnimation.SetReferenceParameter("ScrollManipulation", _nowPlayingManipulation); _nowPlayingResetAnimation = _nowPlayingCompositor.CreateScalarKeyFrameAnimation(); _nowPlayingResetAnimation.InsertKeyFrame(1.0f, 0.0f); _nowPlayingReleaseBorderVisual = ElementCompositionPreview.GetElementVisual(NowPlayingReleaseBorder); var border = (Border)VisualTreeHelper.GetChild(NowPlayingList, 0); _nowPlayingBorderVisual = ElementCompositionPreview.GetElementVisual(border); PrepareNowPlayingListExpressionAnimationsOnScroll(); }
private void AddPullRefreshEvents() { scrollViewer.DirectManipulationStarted += OnDirectManipulationStarted; scrollViewer.DirectManipulationCompleted += OnDirectManipulationCompleted; _scrollerViewerManipulation = ElementCompositionPreview.GetScrollViewerManipulationPropertySet(scrollViewer); var compositor = _scrollerViewerManipulation.Compositor; _rotationAnimation = compositor.CreateExpressionAnimation("min(max(0, ScrollManipulation.Translation.Y) * Multiplier, MaxDegree)"); _rotationAnimation.SetScalarParameter("Multiplier", 10.0f); _rotationAnimation.SetScalarParameter("MaxDegree", 400.0f); _rotationAnimation.SetReferenceParameter("ScrollManipulation", _scrollerViewerManipulation); _opacityAnimation = compositor.CreateExpressionAnimation("min(max(0, ScrollManipulation.Translation.Y) / Divider, 1)"); _opacityAnimation.SetScalarParameter("Divider", 30.0f); _opacityAnimation.SetReferenceParameter("ScrollManipulation", _scrollerViewerManipulation); _offsetAnimation = compositor.CreateExpressionAnimation("(min(max(0, ScrollManipulation.Translation.Y) / Divider, 1)) * MaxOffsetY"); _offsetAnimation.SetScalarParameter("Divider", 30.0f); _offsetAnimation.SetScalarParameter("MaxOffsetY", REFRESH_ICON_MAX_OFFSET_Y); _offsetAnimation.SetReferenceParameter("ScrollManipulation", _scrollerViewerManipulation); _refreshIconVisual = ElementCompositionPreview.GetElementVisual(RefreshIcon); _refreshIconVisual.CenterPoint = new Vector3(Convert.ToSingle(RefreshIcon.Width / 2), Convert.ToSingle(RefreshIcon.Height / 2), 0); _refreshSymbleVisual = ElementCompositionPreview.GetElementVisual(RefreshSymble); _refreshSymbleVisual.CenterPoint = new Vector3(Convert.ToSingle(RefreshSymble.Width / 2), Convert.ToSingle(RefreshSymble.Height / 2), 0); // Kick off the animations. OnRefreshComplete(); }
private void GridView_Loaded(object sender, RoutedEventArgs e) { var scroll = List.Descendants <ScrollViewer>().FirstOrDefault() as ScrollViewer; if (scroll != null) { _scrollingHost = scroll; _scrollingHost.ChangeView(null, 0, null, true); scroll.ViewChanged += Scroll_ViewChanged; Scroll_ViewChanged(scroll, null); _scrollingHost.Padding = new Thickness(0, Math.Max(0, BackgroundPanel.Margin.Top - _scrollingHost.VerticalOffset), 0, 0); var brush = App.Current.Resources["SystemControlBackgroundChromeMediumLowBrush"] as SolidColorBrush; var props = ElementCompositionPreview.GetScrollViewerManipulationPropertySet(scroll); if (_background == null) { _background = ElementCompositionPreview.GetElementVisual(BackgroundPanel).Compositor.CreateSpriteVisual(); ElementCompositionPreview.SetElementChildVisual(BackgroundPanel, _background); } _background.Brush = _background.Compositor.CreateColorBrush(brush.Color); _background.Size = new System.Numerics.Vector2((float)BackgroundPanel.ActualWidth, (float)BackgroundPanel.ActualHeight); _background.Clip = _background.Compositor.CreateInsetClip(); _groupHeader = ElementCompositionPreview.GetElementVisual(GroupHeader); _expression = _expression ?? _background.Compositor.CreateExpressionAnimation("Max(Maximum, Scrolling.Translation.Y)"); _expression.SetReferenceParameter("Scrolling", props); _expression.SetScalarParameter("Maximum", -(float)BackgroundPanel.Margin.Top + 1); _background.StopAnimation("Offset.Y"); _background.StartAnimation("Offset.Y", _expression); _expressionHeader = _expressionHeader ?? _background.Compositor.CreateExpressionAnimation("Max(0, Maximum - Scrolling.Translation.Y)"); _expressionHeader.SetReferenceParameter("Scrolling", props); _expressionHeader.SetScalarParameter("Maximum", -(float)BackgroundPanel.Margin.Top); _groupHeader.StopAnimation("Offset.Y"); _groupHeader.StartAnimation("Offset.Y", _expressionHeader); _expressionClip = _expressionClip ?? _background.Compositor.CreateExpressionAnimation("Min(0, Maximum - Scrolling.Translation.Y)"); _expressionClip.SetReferenceParameter("Scrolling", props); _expressionClip.SetScalarParameter("Maximum", -(float)BackgroundPanel.Margin.Top + 1); _background.Clip.StopAnimation("Offset.Y"); _background.Clip.StartAnimation("Offset.Y", _expressionClip); } var panel = List.ItemsPanelRoot as ItemsWrapGrid; if (panel != null) { panel.SizeChanged += (s, args) => { Scroll_ViewChanged(scroll, null); }; } }
/// <summary> /// Uses Composition API to get the UIElement and sets an ExpressionAnimation /// The ExpressionAnimation uses the height of the UIElement to calculate an opacity value /// for the Header as it is scrolling off-screen. The opacity reaches 0 when the Header /// is entirely scrolled off. /// </summary> /// <returns><c>true</c> if the assignment was successfull; otherwise, <c>false</c>.</returns> private bool AssignFadeAnimation() { // Confirm that Windows.UI.Xaml.Hosting.ElementCompositionPreview is available (Windows 10 10586 or later). if (!ApiInformation.IsMethodPresent("Windows.UI.Xaml.Hosting.ElementCompositionPreview", nameof(ElementCompositionPreview.GetScrollViewerManipulationPropertySet))) { // Just return true since it's not supported return(true); } if (AssociatedObject == null) { return(false); } var scroller = AssociatedObject as ScrollViewer ?? AssociatedObject.FindDescendant <ScrollViewer>(); if (scroller == null) { return(false); } // Implicit operation: Find the Header object of the control if it uses ListViewBase if (HeaderElement == null) { var listElement = AssociatedObject as Windows.UI.Xaml.Controls.ListViewBase ?? AssociatedObject.FindDescendant <Windows.UI.Xaml.Controls.ListViewBase>(); if (listElement != null) { HeaderElement = listElement.Header as UIElement; } } // If no header is set or detected, return. if (HeaderElement == null || HeaderElement.RenderSize.Height == 0d) { return(false); } // Get the ScrollViewer's ManipulationPropertySet var scrollViewerManipulationPropSet = ElementCompositionPreview.GetScrollViewerManipulationPropertySet(scroller); var compositor = scrollViewerManipulationPropSet.Compositor; // Use the ScrollViewer's Y offset and the header's height to calculate the opacity percentage. Clamp it between 0% and 100% var opacityExpression = compositor.CreateExpressionAnimation("Clamp(1 - (-ScrollManipulationPropSet.Translation.Y / HeaderHeight), 0, 1)"); // Get the ScrollViewerManipulation Reference opacityExpression.SetReferenceParameter("ScrollManipulationPropSet", scrollViewerManipulationPropSet); // Pass in the height of the header as a Scalar opacityExpression.SetScalarParameter("HeaderHeight", (float)HeaderElement.RenderSize.Height); // Begin animating var targetElement = ElementCompositionPreview.GetElementVisual(HeaderElement); targetElement.StartAnimation("Opacity", opacityExpression); return(true); }
/// <summary> /// Sets up the composition animations that position the Refresh Indicator and main content /// based on the overpan amount. /// </summary> private void UpdateCompositionAnimations() { if (m_root != null && m_scroller != null && m_scrollerContent != null && m_refreshIndicatorContainer != null) { if (m_scrollerContentAnimation == null) { CompositionPropertySet scrollingProperties = ElementCompositionPreview.GetScrollViewerManipulationPropertySet(m_scroller); Compositor compositor = scrollingProperties.Compositor; // Ensure that the maximum overpan amount corresponds to the Refresh Indicator's height. m_scrollerContentVisual = ElementCompositionPreview.GetElementVisual(m_scrollerContent); m_scrollerContentAnimation = compositor.CreateExpressionAnimation(@"overpanMultiplier * max(0, scrollingProperties.Translation.Y)"); m_scrollerContentAnimation.SetReferenceParameter("scrollingProperties", scrollingProperties); // Ensure that the Refresh Indicator is positioned on top of the main content. m_refreshIndicatorContainerVisual = ElementCompositionPreview.GetElementVisual(m_refreshIndicatorContainer); m_refreshIndicatorContainerAnimation = compositor.CreateExpressionAnimation(@"-refreshIndicatorContainerHeight"); // Create RefreshPropertySet and populate it with the PullRatio and PullProgress variables that vary from 0 to 1. this.RefreshPropertySet = compositor.CreatePropertySet(); m_pullRatioAnimation = compositor.CreateExpressionAnimation(@"clamp(max(0, scrollingProperties.Translation.Y) / maxOverpan + staticRatio, 0, 1)"); m_pullRatioAnimation.SetReferenceParameter("scrollingProperties", scrollingProperties); this.RefreshPropertySet.InsertScalar("PullRatio", 0); m_pullProgressAnimation = compositor.CreateExpressionAnimation(@"clamp(max(0, scrollingProperties.Translation.Y) / thresholdOverpan + staticProgress, 0, 1)"); m_pullProgressAnimation.SetReferenceParameter("scrollingProperties", scrollingProperties); this.RefreshPropertySet.InsertScalar("PullProgress", 0); } m_scrollerContentAnimation.SetScalarParameter("overpanMultiplier", (float)(m_refreshIndicatorContainer.ActualHeight / m_scroller.ActualHeight / MAX_SCROLLVIEWER_OVERPAN_RATIO - 1.0f / m_scroller.ZoomFactor)); m_scrollerContentVisual.StartAnimation("Offset.Y", m_scrollerContentAnimation); m_refreshIndicatorContainerAnimation.SetScalarParameter("refreshIndicatorContainerHeight", (float)m_refreshIndicatorContainer.ActualHeight); m_refreshIndicatorContainerVisual.StartAnimation("Offset.Y", m_refreshIndicatorContainerAnimation); float maxOverpan = (float)(m_scroller.ActualHeight * MAX_SCROLLVIEWER_OVERPAN_RATIO); m_pullRatioAnimation.SetScalarParameter("maxOverpan", maxOverpan); float staticRatio = (m_isAutoRefreshing || m_isSuppressingOverpan || m_scrollerContent.ManipulationMode == ManipulationModes.None) ? (float)DEFAULT_REFRESH_INDICATOR_THRESHOLD_RATIO : 0.0f; m_pullRatioAnimation.SetScalarParameter("staticRatio", staticRatio); this.RefreshPropertySet.StartAnimation("PullRatio", m_pullRatioAnimation); float thresholdOverpan = (float)(double.IsNaN(this.PullThreshold) ? (m_scroller.ActualHeight * MAX_SCROLLVIEWER_OVERPAN_RATIO * DEFAULT_REFRESH_INDICATOR_THRESHOLD_RATIO) : this.PullThreshold); m_pullProgressAnimation.SetScalarParameter("thresholdOverpan", thresholdOverpan); float staticProgress = (m_refreshActivated || m_isAutoRefreshing || m_isSuppressingOverpan || m_scrollerContent.ManipulationMode == ManipulationModes.None) ? 1.0f : 0.0f; m_pullProgressAnimation.SetScalarParameter("staticProgress", staticProgress); this.RefreshPropertySet.StartAnimation("PullProgress", m_pullProgressAnimation); } }
/// <summary> /// Uses Composition API to get the UIElement and sets an ExpressionAnimation /// The ExpressionAnimation uses the height of the UIElement to calculate an opacity value /// for the Header as it is scrolling off-screen. The opacity reaches 0 when the Header /// is entirely scrolled off. /// </summary> /// <returns><c>true</c> if the assignment was successful; otherwise, <c>false</c>.</returns> private bool AssignFadeAnimation() { // Confirm that Windows.UI.Xaml.Hosting.ElementCompositionPreview is available (Windows 10 10586 or later). if (!ApiInformation.IsMethodPresent("Windows.UI.Xaml.Hosting.ElementCompositionPreview", nameof(ElementCompositionPreview.GetScrollViewerManipulationPropertySet))) { // Just return true since it's not supported return(true); } if (AssociatedObject == null) { return(false); } var scroller = AssociatedObject as ScrollViewer ?? AssociatedObject.FindDescendant <ScrollViewer>(); if (scroller == null) { return(false); } var listView = AssociatedObject as Windows.UI.Xaml.Controls.ListViewBase ?? AssociatedObject.FindDescendant <Windows.UI.Xaml.Controls.ListViewBase>(); if (listView != null && listView.ItemsPanelRoot != null) { Canvas.SetZIndex(listView.ItemsPanelRoot, -1); } // Implicit operation: Find the Header object of the control if it uses ListViewBase if (HeaderElement == null && listView != null) { HeaderElement = listView.Header as UIElement; } // If no header is set or detected, return. if (HeaderElement == null || HeaderElement.RenderSize.Height == 0d) { return(false); } // Get the ScrollViewer's ManipulationPropertySet var scrollViewerManipulationPropSet = ElementCompositionPreview.GetScrollViewerManipulationPropertySet(scroller); var scrollPropSet = scrollViewerManipulationPropSet.GetSpecializedReference <ManipulationPropertySetReferenceNode>(); // Use the ScrollViewer's Y offset and the header's height to calculate the opacity percentage. Clamp it between 0% and 100% var headerHeight = (float)HeaderElement.RenderSize.Height; var opacityExpression = ExpressionFunctions.Clamp(1 - (-scrollPropSet.Translation.Y / headerHeight), 0, 1); // Begin animating var targetElement = ElementCompositionPreview.GetElementVisual(HeaderElement); targetElement.StartAnimation("Opacity", opacityExpression); return(true); }
static public void StopElementAtOffset(this ScrollViewer scrollViewer, UIElement element, float offset) { var compositor = Window.Current.Compositor; var propertySet = ElementCompositionPreview.GetScrollViewerManipulationPropertySet(scrollViewer); ElementCompositionPreview.SetIsTranslationEnabled(element, true); compositor.CreateExpressionWrapper("Max(0, -scroller.Translation.Y-offset)") .Parameter("scroller", propertySet) .Parameter("offset", offset) .Start(element, "Translation.Y"); }
public static ExpressionAnimation StartExpressionAnimation( [NotNull] this ScrollViewer scroller, [NotNull] UIElement target, Axis sourceXY, Axis?targetXY = null, bool invertSourceAxis = false) { CompositionPropertySet scrollSet = ElementCompositionPreview.GetScrollViewerManipulationPropertySet(scroller); string sign = invertSourceAxis ? "-" : string.Empty; ExpressionAnimation animation = scrollSet.Compositor.CreateExpressionAnimation($"{sign}scroll.Translation.{sourceXY}"); animation.SetReferenceParameter("scroll", scrollSet); target.GetVisual().StartAnimation($"Offset.{targetXY ?? sourceXY}", animation); return(animation); }
private ExpressionAnimation CreateExpression() { var compositor = ElementCompositionPreview.GetElementVisual(this).Compositor; var scrollViewer = gridView.GetChildOfType <ScrollViewer>(); var scrollerPropertySet = ElementCompositionPreview.GetScrollViewerManipulationPropertySet(scrollViewer); var _expression = compositor.CreateExpressionAnimation("Vector3(0, (-scroller.Translation.Y - container.Offset.Y + 300) * 0.05, 0)"); _expression.SetReferenceParameter("scroller", scrollerPropertySet); return(_expression); }
public void StartAnimation(bool update = false) { if (update || expression == null || visual == null) { visual = ElementCompositionPreview.GetElementVisual(VisualElement); //if (0 <= VisualElement.Margin.Top && VisualElement.Margin.Top <= ScrollViewer.ActualHeight) //{ // min = (float)-VisualElement.Margin.Top; // max = (float)ScrollViewer.ActualHeight + min; //} //else if (VisualElement.Margin.Top < 0) //{ //} //else if (VisualElement.Margin.Top > ScrollViewer.ActualHeight) //{ //} if (scrollViewerManipProps == null) { scrollViewerManipProps = ElementCompositionPreview.GetScrollViewerManipulationPropertySet(ScrollViewer); } Compositor compositor = scrollViewerManipProps.Compositor; // Create the expression //expression = compositor.CreateExpressionAnimation("min(max((ScrollViewerManipProps.Translation.Y + VerticalOffset), MinValue), MaxValue)"); ////Expression = compositor.CreateExpressionAnimation("ScrollViewerManipProps.Translation.Y +VerticalOffset"); //expression.SetScalarParameter("MinValue", min); //expression.SetScalarParameter("MaxValue", max); //expression.SetScalarParameter("VerticalOffset", (float)ScrollViewer.VerticalOffset); expression = compositor.CreateExpressionAnimation("ScrollViewerManipProps.Translation.Y + VerticalOffset"); ////Expression = compositor.CreateExpressionAnimation("ScrollViewerManipProps.Translation.Y +VerticalOffset"); //expression.SetScalarParameter("MinValue", min); //expression.SetScalarParameter("MaxValue", max); VerticalOffset = ScrollViewer.VerticalOffset; expression.SetScalarParameter("VerticalOffset", (float)ScrollViewer.VerticalOffset); // set "dynamic" reference parameter that will be used to evaluate the current position of the scrollbar every frame expression.SetReferenceParameter("ScrollViewerManipProps", scrollViewerManipProps); } visual.StartAnimation("Offset.Y", expression); IsActive = true; //Windows.UI.Xaml.Media.CompositionTarget.Rendering -= OnCompositionTargetRendering; //Windows.UI.Xaml.Media.CompositionTarget.Rendering += OnCompositionTargetRendering; }
private void Page_Loaded(object sender, RoutedEventArgs e) { var scrollviewer = MyList.GetScrollViewer(); CompositionPropertySet scrollerViewerManipulation = ElementCompositionPreview.GetScrollViewerManipulationPropertySet(scrollviewer); Compositor compositor = scrollerViewerManipulation.Compositor; ExpressionAnimation expression = compositor.CreateExpressionAnimation("ScrollManipululation.Translation.Y * ParallaxMultiplier"); expression.SetScalarParameter("ParallaxMultiplier", 0.3f); expression.SetReferenceParameter("ScrollManipululation", scrollerViewerManipulation); Visual textVisual = ElementCompositionPreview.GetElementVisual(header); textVisual.StartAnimation("Offset.Y", expression); }