在Lit Virtualizer中控制流体动画是否可能。

huangapple go评论65阅读模式
英文:

It it possible to control a fluid animation in Lit Virtualizer

问题

我正在使用 Lit 实现一个无限滚动的轮播图。
我想通过按键事件来控制轮播图。
在长时间按住按键时(或进行节流处理),我希望动画能够流畅,并停在特定位置。

是否可以使用一些 CSS 来对虚拟化器中的项目进行动画处理,而不必使用 window.scrollTo API?

我尝试使用 virtualizer.element(n).scrollIntoView,但没有得到期望的结果。

英文:

I am implementing a Infinte Scroll Carousel with Lit.
I want to control the carousel with key events.
On long key press (or throttled) I want the animation te be fluid and stop at a specific place.

Is it possible to animate the items in virtalizer with some CSS and avoid using window.scrollTo API?

I tried to use virtualizer.element(n).scrollIntoView but did not get the desired result

答案1

得分: 1

根据Brendan的答案建议,基本的方法如下:

  • 创建一个明确定义大小的overflow: hidden容器
  • 在容器内放置一个虚拟化器
  • 使用CSS(动画,或者转换+过渡等)根据用户与您提供的任何工具的交互来定位容器内的整个虚拟化器

我怀疑您已经尝试过这样做,并发现当您尝试导航到最初呈现的项目之外时,虚拟化器不会自动重新呈现。这是因为虚拟化器依赖于scroll事件来触发其更新周期,而由于您没有使用原生滚动,因此您无法获取这些事件。

但是,通过在动画/过渡进行时触发模拟的scroll事件来获得所需的效果非常容易。您可以高效地使用requestAnimationFrame()来实现这一点。

这里有一个在Lit playground中的示例(有趣的部分在transition-scroller.ts文件中):

https://lit.dev/playground/#gist=26a7de1c61a886625f691cc9484cab7c

英文:

As Brendan's answer suggests, the basic approach would be to:

  • Create an explicitly sized, overflow: hidden container
  • Put a virtualizer inside that container
  • Use CSS (animations, or transforms + transitions, etc.) to position the entire virtualizer within the container based on user interactions with whatever affordances you provide

I suspect you tried this and found that the virtualizer did not automatically re-render when you tried to navigate past the initially rendered items. That's because virtualizer relies on scroll events to trigger its update cycle, and since you're not using native scrolling you aren't getting those events.

However, it's pretty easy to get the effect you want by firing simulated scroll events while your animation / transition is in progress. You can use requestAnimiationFrame() to do this efficiently.

Here's an example in the Lit playground (the interesting bits are in the transition-scroller.ts file):

https://lit.dev/playground/#gist=26a7de1c61a886625f691cc9484cab7c

答案2

得分: 0

我会假设您在README中使用了scrollIntoView()behavior: 'smooth'选项:

virtualizer.element(42).scrollIntoView({
  block: 'center',
  behavior: 'smooth',
});

因为Virtualizer通过直接操作其light-DOM子元素的绝对位置(也就是渲染的项目)来工作,它对计算样式或ResizeObserver的观察的使用,这是它识别由于可能的可见性更改而需要重新校准的时刻的方式,可能会与某些动画方法冲突,如果这些方法直接应用于CSS中的子元素。

然而,如果您能够将CSS动画/过渡应用于包含元素,即<lit-virtualizer>自定义元素本身或virtualize()指令的包含元素(如果使用了该指令),则可能能够创建您想要的效果。

在这个视频中,我正在对Virtualizer进行非常广泛的概述,但在链接的特定时间5:24处,我试图在视觉上展示Virtualizer基本上只是一个假装包含所有子元素的大容器,如果您可以控制视口中该容器的位置,那么该容器元素的CSS动画过渡应该能够按预期工作。

https://www.youtube.com/watch?v=ay8ImAgO9ik&amp;t=324s

如果scroller: true,那么情况会更复杂,因为内部使用了一个单独的容器元素。

如果您有更多关于您的用例的详细信息可以分享,我会有兴趣进一步审查它,您可以将其作为问题提交到https://github.com/lit/lit/issues。

英文:

I will assume you used scrollIntoView() with the behavior: &#39;smooth&#39; option from the README:

virtualizer.element(42).scrollIntoView({
  block: &#39;center&#39;,
  behavior: &#39;smooth&#39;,
});

Because Virtualizer works by directly manipulating the absolute positions of its light-DOM child elements aka rendered items, its use of computed styles or observances by the ResizeObserver, which are how it identifies moments to recalibrate due to possible visibility changes, may conflict with some animation approaches if they were applied directly to children in CSS.

However, if you are able to apply your CSS animation/transitions to the containing element, i.e. the &lt;lit-virtualizer&gt; custom element itself or the containing element of the virtualize() directive if that was used, you may be able to create the effect you want.

In this video I am doing a very broad overview of Virtualizer, but at the specific time in the link 5:24 I am trying to show visually that Virtualizer is basically just a big container that pretends to hold all the children and if you can control the position of that container in the viewport then CSS animations transitions for that container element should function as expected.

https://www.youtube.com/watch?v=ay8ImAgO9ik&amp;t=324s

If scroller: true then it is trickier as a separate container element is used inside.

If you have more details you can share about your use case, I'd be interested in reviewing it further as an issue at https://github.com/lit/lit/issues

huangapple
  • 本文由 发表于 2023年7月13日 23:10:04
  • 转载请务必保留本文链接:https://go.coder-hub.com/76680937.html
匿名

发表评论

匿名网友

:?: :razz: :sad: :evil: :!: :smile: :oops: :grin: :eek: :shock: :???: :cool: :lol: :mad: :twisted: :roll: :wink: :idea: :arrow: :neutral: :cry: :mrgreen:

确定