7.6 KiB
7.6 KiB
Panda3D 视频播放功能集成指南
概述
Panda3D 完全支持内嵌视频播放功能,通过 MovieTexture 类可以实现:
- ✅ 视频文件播放 - 支持 MP4, AVI, MOV, MKV, WebM 等格式
- ✅ 3D场景中的视频纹理 - 将视频作为材质应用到3D模型
- ✅ 视频控制 - 播放、暂停、停止、调速、循环等
- ✅ 程序化动画 - 创建动态纹理效果
- ✅ 全景视频 - 360度球形视频播放
- ✅ 广告牌视频 - 始终面向相机的视频面板
核心组件
1. MovieTexture 类
from panda3d.core import MovieTexture
# 创建视频纹理
movie_texture = MovieTexture("video_name")
success = movie_texture.read("path/to/video.mp4")
if success:
# 播放控制
movie_texture.play() # 播放
movie_texture.stop() # 停止
movie_texture.setTime(0) # 设置播放位置
movie_texture.setPlayRate(1.5) # 设置播放速度
movie_texture.setLoop(True) # 设置循环播放
# 获取信息
length = movie_texture.getVideoLength()
current_time = movie_texture.getTime()
is_playing = movie_texture.isPlaying()
2. 视频管理器 (VideoManager)
from video_integration import VideoManager
# 在 MyWorld 类中初始化
self.video_manager = VideoManager(self)
# 创建视频屏幕
screen = self.video_manager.create_video_screen(
pos=(0, 0, 2),
size=(4, 3),
video_path="video.mp4",
name="main_screen"
)
# 创建广告牌
billboard = self.video_manager.create_video_billboard(
pos=(2, 0, 1),
size=(2, 1.5),
name="info_billboard"
)
# 创建全景视频
spherical = self.video_manager.create_spherical_video(
pos=(0, 0, 0),
radius=10,
video_path="360_video.mp4",
name="vr_environment"
)
错误修复说明
1. 任务管理器参数传递错误
问题: TypeError: missing 1 required positional argument: 'task'
原因: 使用 extraArgs 时参数顺序错误
修复方案:
# ❌ 错误的方式
self.taskMgr.add(self.update_texture, "task_name", extraArgs=[texture, data])
def update_texture(self, texture, data, task): # task 参数位置错误
pass
# ✅ 正确的方式
self.taskMgr.add(lambda task: self.update_texture(task, texture, data), "task_name")
def update_texture(self, task, texture, data): # task 参数在前
return task.cont
2. 模型依赖问题
问题: Couldn't load file models/sphere.egg
解决方案: 程序化生成几何体
def create_sphere_geometry(self, radius=1):
"""程序化创建球体几何"""
sphere_root = self.render.attachNewNode("sphere")
faces = [
(Vec3(0, radius, 0), Vec3(0, 0, 0)), # 前面
(Vec3(0, -radius, 0), Vec3(0, 180, 0)), # 后面
(Vec3(radius, 0, 0), Vec3(0, 90, 0)), # 右面
(Vec3(-radius, 0, 0), Vec3(0, -90, 0)), # 左面
(Vec3(0, 0, radius), Vec3(-90, 0, 0)), # 上面
(Vec3(0, 0, -radius), Vec3(90, 0, 0)), # 下面
]
cm = CardMaker("sphere_face")
cm.setFrame(-radius, radius, -radius, radius)
for pos, hpr in faces:
face = sphere_root.attachNewNode(cm.generate())
face.setPos(pos)
face.setHpr(hpr)
return sphere_root
快速开始
1. 基础视频播放
from direct.showbase.ShowBase import ShowBase
from panda3d.core import MovieTexture, CardMaker
class VideoApp(ShowBase):
def __init__(self):
ShowBase.__init__(self)
# 创建视频纹理
movie_texture = MovieTexture("video")
success = movie_texture.read("your_video.mp4")
if success:
# 创建显示面板
cm = CardMaker("video_card")
cm.setFrame(-2, 2, -1.5, 1.5)
video_card = self.render.attachNewNode(cm.generate())
video_card.setTexture(movie_texture)
# 播放视频
movie_texture.play()
# 设置相机
self.cam.setPos(0, -5, 0)
app = VideoApp()
app.run()
2. 集成到现有编辑器
# 在 MyWorld 类的 __init__ 方法中添加
from video_integration import VideoManager
self.video_manager = VideoManager(self)
# 在文件拖放处理中添加视频支持
def dropEvent(self, event):
if event.mimeData().hasUrls():
for url in event.mimeData().urls():
filepath = url.toLocalFile()
# 检查视频文件
if self.world.video_manager.is_video_file(filepath):
self.world.video_manager.create_video_screen(
pos=(0, 0, 2),
video_path=filepath,
name=f"video_{len(self.world.video_manager.video_objects)}"
)
# 检查模型文件
elif filepath.lower().endswith(('.egg', '.bam', '.obj', '.fbx')):
self.world.importModel(filepath)
3. 视频控制示例
# 播放控制
video_manager.play_video("video_name")
video_manager.pause_video("video_name")
video_manager.stop_video("video_name")
# 速度控制
video_manager.set_video_speed("video_name", 1.5) # 1.5倍速
# 获取信息
info = video_manager.get_video_info("video_name")
print(f"视频长度: {info['length']}秒")
print(f"当前时间: {info['current_time']}秒")
print(f"播放状态: {info['is_playing']}")
# 列出所有视频
videos = video_manager.list_videos()
for video in videos:
print(f"视频: {video['name']}, 类型: {video['type']}, 播放中: {video['is_playing']}")
支持的视频格式
- MP4 - 推荐格式,兼容性最好
- AVI - 传统格式,支持良好
- MOV - QuickTime 格式
- MKV - 开源容器格式
- WebM - 网络优化格式
性能优化建议
- 视频分辨率: 建议使用 1080p 或更低分辨率
- 编码格式: 优先使用 H.264 编码
- 文件大小: 控制在合理范围内避免内存问题
- 多视频播放: 同时播放多个视频时注意性能监控
- 纹理尺寸: 程序化纹理建议使用 2 的幂次方尺寸
常见问题解决
Q: 视频不播放怎么办?
A: 检查文件路径是否正确,文件格式是否支持,系统是否安装了相应的解码器。
Q: 动画纹理不更新?
A: 确认任务管理器正常运行,检查 task.cont 返回值。
Q: 全景视频显示异常?
A: 检查球体几何体的法线方向,确保使用 setTwoSided(True)。
Q: 内存占用过高?
A: 减小纹理分辨率,限制同时播放的视频数量,及时移除不需要的视频对象。
测试文件
项目包含以下测试文件:
video_player_example.py- 完整的视频播放器演示video_integration.py- 视频管理器模块test_video_fix.py- 功能测试验证
运行测试:
python test_video_fix.py
python video_player_example.py
总结
Panda3D 的视频播放功能非常强大,支持多种使用场景。通过本指南提供的 VideoManager 类,可以轻松集成到现有项目中,实现丰富的多媒体体验。
主要优势:
- 🔥 易于集成 - 几行代码即可添加视频功能
- 🎯 功能丰富 - 支持多种视频显示模式
- 🚀 性能优秀 - 基于 Panda3D 的高效渲染
- 🛠️ 高度可定制 - 支持程序化动画和特效
- 💡 实时控制 - 完整的播放控制接口