Javascript 将SVG动画转换为webm或mov

Javascript 将SVG动画转换为webm或mov,javascript,animation,svg,video,webm,Javascript,Animation,Svg,Video,Webm,我正在寻找一种可靠且易于执行的方法,将纯SVG动画转换为视频格式,最好是webm或mov。 这里可以找到有问题的动画-这是我个人的工作,也是学习如何处理SVG的结果: 令我惊讶的是,我最初的搜索只得到了不完整的答案,结果往往各不相同。在进一步研究后,我发现了一篇博客文章,它使用创建了一个SVG动画的webm 有没有一种方法可以将上述脚本应用到我的动画中,从而得到一个webm。如果仔细查看该示例中的代码,您会发现视频是通过将每个帧逐个绘制到连接到MediaRecorder的画布上创建的 因此,您

我正在寻找一种可靠且易于执行的方法,将纯SVG动画转换为视频格式,最好是webmmov。 这里可以找到有问题的动画-这是我个人的工作,也是学习如何处理SVG的结果:

令我惊讶的是,我最初的搜索只得到了不完整的答案,结果往往各不相同。在进一步研究后,我发现了一篇博客文章,它使用创建了一个SVG动画的
webm


有没有一种方法可以将上述脚本应用到我的动画中,从而得到一个
webm

如果仔细查看该示例中的代码,您会发现视频是通过将每个帧逐个绘制到连接到
MediaRecorder
画布上创建的

因此,您需要执行相同的操作:暂停每一帧的动画,将该帧绘制到
画布上
,为下一帧稍微移动动画,然后重复

在链接的示例中,有用于将SVG绘制到画布上的代码,因此棘手的部分是在任何给定时间暂停动画以生成帧,因为您的动画都是CSS。可以通过暂停动画(
动画播放状态:暂停
)并调整
动画延迟
)来完成此操作。以下是一个例子:

因此,您可以在代码中执行类似的操作:

//Loop through all animated elements, and update their animation-delay.
//Together with "animation-play-state: paused", this freezes the animation at the specified time.
function freeze(time) {
    animed.forEach(x => {
        const css = x.style;

        if(!x.__originalDelay) {
            const delay = css.animationDelay;
            x.__originalDelay = delay.match(/\d/) ? delay : '0s';
        }

        css.animationPlayState = 'paused';
        css.animationDelay = `calc(${x.__originalDelay} - ${time}ms)`;
    });
}
更新的演示:

更新:更好的Firefox支持,以及使用


如果仔细查看该示例中的代码,您将看到视频是通过将每个帧逐个绘制到连接到
MediaRecorder
画布上创建的

因此,您需要执行相同的操作:暂停每一帧的动画,将该帧绘制到
画布上
,为下一帧稍微移动动画,然后重复

在链接的示例中,有用于将SVG绘制到画布上的代码,因此棘手的部分是在任何给定时间暂停动画以生成帧,因为您的动画都是CSS。可以通过暂停动画(
动画播放状态:暂停
)并调整
动画延迟
)来完成此操作。以下是一个例子:

因此,您可以在代码中执行类似的操作:

//Loop through all animated elements, and update their animation-delay.
//Together with "animation-play-state: paused", this freezes the animation at the specified time.
function freeze(time) {
    animed.forEach(x => {
        const css = x.style;

        if(!x.__originalDelay) {
            const delay = css.animationDelay;
            x.__originalDelay = delay.match(/\d/) ? delay : '0s';
        }

        css.animationPlayState = 'paused';
        css.animationDelay = `calc(${x.__originalDelay} - ${time}ms)`;
    });
}
更新的演示:

更新:更好的Firefox支持,以及使用


这并不是一个真正的动画,因为它会自己运行。看看函数
drawFrame()
:它只是在最后一帧的录制完成后绘制一个新帧。从它自己运行的意义上讲,这并不是真正的动画。查看函数
drawFrame()
:它只是在最后一帧的录制完成后绘制一个新帧。这看起来很有用。在演示中很难看到视频的质量。这段视频是实时拍摄的,所以如果你能足够快地更新画布,一切都会好起来。如果没有,你会得到丢失的帧或减慢的视频,这取决于你的设置。这看起来很有用。在演示中很难看到视频的质量。这段视频是实时拍摄的,所以如果你能足够快地更新画布,一切都会好起来。如果没有,你会得到丢失的帧或减慢的视频,这取决于你的设置。