Python 中的翻牌动画

问题描述 投票:0回答:1

我有两张静态图像,一张用于卡片的正面,一张用于背面。我想创建一个卡片翻转并显示背面的视频动画,类似于使用 CSS 和 JavaScript 实现的 this CodePen

我确信在 Python 和像 PIL、Pyglet 或 Pygame 这样的库中这是可能的(例如,在 PIL 中使用透视图),但我无法通过搜索

python pil|pyglet|pygame code flip card animation
找到它。这看起来很普遍,我认为以前有人需要过这个。

有人遇到过这个问题并且有代码可以使卡片翻转动画吗?

python animation graphics
1个回答
0
投票

你很幸运:)

我已经为你发布了这个要点: https://gist.github.com/iburakov/49b2934d0ff5bee17fd99df8b3c812a5

它正是使用 Ursina 来完成你所要求的,这是一个游戏引擎(而且是一个相当粗略的引擎!),这对于任务来说显然是一种矫枉过正,并且对性能不友好,但有它的优点:

  • 只需约 50 行代码!
  • 我已经启用了 mipmap 纹理过滤,因此它不会闪烁(在一个 线!)
  • 如果您决定向场景添加可见的卡片边框或运动模糊着色器等,它应该很容易扩展。

它还以无头模式(没有窗口)运行,并且作为中间结果,生成一系列对您来说可能更方便的 PNG。

输出示例

这是代码的副本,以防链接失效:

"""
Requirements:
- pip install ursina==6.1.2
- ffmpeg should be on path to render MP4 from PNGs
"""

import math
import time
from pathlib import Path

from ursina import Sprite, Texture, Ursina
from ursina.prefabs.video_recorder import VideoRecorder

# app = Ursina()  # use this in development to see rendered window
app = Ursina(development_mode=False, window_type="offscreen")

Texture.default_filtering = "mipmap"
side_a = Sprite(texture="_card_a.png")  # at origin, facing the camera
side_b = Sprite(texture="_card_b.png", rotation_y=180)


_total_frames = 60
rec = VideoRecorder(fps=30, max_duration=100000)  # we'll stop the recorder manually
rec_dir = Path("video_temp")  # recorder crashes if rec_dir is changed :/
rec.start_recording()


def update():
    frame = rec.i
    if frame > _total_frames:
        _finish()

    cos_arg = frame / _total_frames * math.pi
    angle_coef = math.cos(cos_arg) ** 2  # [0; 1]
    angle = angle_coef * 180
    side_a.rotation_y = angle - 180
    side_b.rotation_y = angle

    print(f"frame {frame}/{_total_frames} ({frame/_total_frames:.0%})")


def _finish():
    # first frame is empty for some reason :/
    (rec_dir / "untitled_video_0000.png").unlink()

    rec.stop_recording()
    # well, now we wait for ffmpeg to finish in an extremely sketchy way :/
    # no access to Popen result here
    time.sleep(10)

    exit(0)


app.run()
© www.soinside.com 2019 - 2024. All rights reserved.