高级渲染添加

This commit is contained in:
Rowland 2025-10-11 10:08:28 +08:00
parent 83fcb3ced4
commit ea8e340c33
5 changed files with 177 additions and 7 deletions

View File

@ -11,8 +11,5 @@
"enable_ssr": false, "enable_ssr": false,
"shadow_quality": "medium", "shadow_quality": "medium",
"ao_quality": "low" "ao_quality": "low"
}, }
"anti_aliasing": "4x",
"refresh_rate": "144Hz",
"async_reprojection": true
} }

View File

@ -45,6 +45,7 @@ class VRJoystickConfig:
self.teleport_arc_resolution = 50 # 抛物线精度 self.teleport_arc_resolution = 50 # 抛物线精度
self.teleport_initial_velocity = 10.0 # 传送初始速度 self.teleport_initial_velocity = 10.0 # 传送初始速度
self.min_teleport_distance = 1.0 # 最小传送距离 self.min_teleport_distance = 1.0 # 最小传送距离
self.player_height_offset = 1.7 # 玩家站立高度偏移(米)
# 反馈设置 # 反馈设置
self.haptic_feedback_enabled = True # 是否启用震动反馈 self.haptic_feedback_enabled = True # 是否启用震动反馈
@ -151,6 +152,15 @@ class VRJoystickConfig:
self.teleport_range = max(5.0, min(50.0, range_meters)) self.teleport_range = max(5.0, min(50.0, range_meters))
print(f"✓ 传送范围设置为: {self.teleport_range}") print(f"✓ 传送范围设置为: {self.teleport_range}")
def set_player_height(self, height_meters: float):
"""设置玩家站立高度偏移
Args:
height_meters: 站立高度偏移推荐范围1.5-2.0
"""
self.player_height_offset = max(1.0, min(2.5, height_meters))
print(f"✓ 玩家站立高度偏移设置为: {self.player_height_offset}")
def enable_haptic_feedback(self, enabled: bool): def enable_haptic_feedback(self, enabled: bool):
"""启用或禁用震动反馈 """启用或禁用震动反馈
@ -200,6 +210,7 @@ class VRJoystickConfig:
teleport_sys.arc_resolution = self.teleport_arc_resolution teleport_sys.arc_resolution = self.teleport_arc_resolution
teleport_sys.initial_velocity = self.teleport_initial_velocity teleport_sys.initial_velocity = self.teleport_initial_velocity
teleport_sys.min_teleport_distance = self.min_teleport_distance teleport_sys.min_teleport_distance = self.min_teleport_distance
teleport_sys.player_height_offset = self.player_height_offset
print("✅ 配置已成功应用到摇杆管理器") print("✅ 配置已成功应用到摇杆管理器")

View File

@ -913,6 +913,10 @@ class VRManager(DirectObject):
self.render_pipeline_enabled = True self.render_pipeline_enabled = True
print("✅ VR Pipeline控制器已初始化将在相机设置时创建完整管线") print("✅ VR Pipeline控制器已初始化将在相机设置时创建完整管线")
# 检查天空盒状态
self._check_skybox_status()
return True return True
except Exception as e: except Exception as e:
@ -942,6 +946,130 @@ class VRManager(DirectObject):
except Exception as e: except Exception as e:
print(f"⚠️ 应用RenderPipeline VR效果失败: {e}") print(f"⚠️ 应用RenderPipeline VR效果失败: {e}")
def _check_skybox_status(self):
"""检查并报告天空盒状态"""
try:
print("\n🌌 检查天空盒状态...")
# 方法1在render节点下搜索所有名字包含skybox的节点
skybox_nodes = self.world.render.findAllMatches("**/skybox*")
if skybox_nodes and skybox_nodes.getNumPaths() > 0:
print(f" ✓ 找到 {skybox_nodes.getNumPaths()} 个天空盒节点(使用名称搜索)")
for i in range(skybox_nodes.getNumPaths()):
skybox = skybox_nodes.getPath(i)
print(f" 天空盒 #{i+1}:")
print(f" 名称: {skybox.getName()}")
print(f" 位置: {skybox.getPos()}")
print(f" 缩放: {skybox.getScale()}")
print(f" 父节点: {skybox.getParent().getName()}")
# 检查是否有shader
if skybox.hasShader():
print(f" ✓ 已应用shader效果")
else:
print(f" ⚠️ 未应用shader效果")
# 检查bin设置
if skybox.hasBin():
print(f" Bin: {skybox.getBinName()}")
else:
print(" ⚠️ 未找到天空盒(名称搜索)")
# 方法2搜索所有GeomNode几何节点天空盒通常是一个大的几何体
print(" 搜索所有几何节点...")
all_geoms = self.world.render.findAllMatches("**/+GeomNode")
print(f" 找到 {all_geoms.getNumPaths()} 个几何节点")
# 查找大型几何体(缩放值很大,可能是天空盒)
skybox_candidates = []
for i in range(all_geoms.getNumPaths()):
geom_node = all_geoms.getPath(i)
scale = geom_node.getScale()
# 天空盒通常缩放很大如40000
if scale[0] > 1000 or scale[1] > 1000 or scale[2] > 1000:
print(f" ✓ 找到大型几何体(可能是天空盒):")
print(f" 名称: {geom_node.getName()}")
print(f" 缩放: {scale}")
print(f" 位置: {geom_node.getPos()}")
if geom_node.hasShader():
print(f" ✓ 已应用shader")
skybox_candidates.append(geom_node)
# 方法3检查render节点的所有直接子节点显示全部
print(" 检查render的所有直接子节点...")
render_children = self.world.render.getChildren()
print(f" render有 {render_children.getNumPaths()} 个直接子节点:")
for i in range(render_children.getNumPaths()):
child = render_children.getPath(i)
scale = child.getScale()
# 标记大型节点(可能是天空盒)
if scale[0] > 1000 or scale[1] > 1000 or scale[2] > 1000:
print(f" - {child.getName()} ⭐ (大型节点,缩放: {scale})")
else:
print(f" - {child.getName()}")
# 报告结果但不自动创建
if len(skybox_candidates) == 0:
print(" ⚠️ 未找到明显的天空盒(缩放>1000的几何体")
print(" 💡 RenderPipeline的天空盒可能在上述列表中但缩放值不同")
print(" 💡 或者可能RenderPipeline未在VR模式下自动创建天空盒")
else:
print(f" ✓ 找到 {len(skybox_candidates)} 个可能的天空盒")
print("🌌 天空盒状态检查完成\n")
except Exception as e:
print(f"⚠️ 天空盒状态检查失败: {e}")
import traceback
traceback.print_exc()
def _create_vr_skybox(self):
"""为VR创建天空盒"""
try:
print(" 🎨 创建VR天空盒...")
# 检查RenderPipeline是否可用
if hasattr(self.world, 'render_pipeline') and self.world.render_pipeline:
pipeline = self.world.render_pipeline
# 使用RenderPipeline的load_default_skybox方法
print(" 使用RenderPipeline方法创建天空盒...")
skybox = pipeline.common_resources.load_default_skybox()
if skybox:
# 设置天空盒属性
skybox.set_scale(40000) # 大型缩放
skybox.reparent_to(self.world.render)
skybox.set_bin("unsorted", 10000) # 最后渲染
# 应用天空盒shader效果
pipeline.set_effect(skybox, "effects/skybox.yaml", {
"render_shadow": False,
"render_envmap": False,
"render_voxelize": False,
"alpha_testing": False,
"normal_mapping": False,
"parallax_mapping": False
}, 1000)
print(f" ✅ VR天空盒已创建")
print(f" 名称: {skybox.getName()}")
print(f" 缩放: {skybox.getScale()}")
print(f" 位置: {skybox.getPos()}")
return skybox
else:
print(" ❌ 无法加载天空盒模型")
return None
else:
print(" ❌ RenderPipeline未初始化无法创建天空盒")
return None
except Exception as e:
print(f" ❌ 创建VR天空盒失败: {e}")
import traceback
traceback.print_exc()
return None
def _setup_vr_cameras(self): def _setup_vr_cameras(self):
"""设置VR相机 - 使用锚点层级系统""" """设置VR相机 - 使用锚点层级系统"""
try: try:

View File

@ -74,6 +74,29 @@ class VRGBufferStage:
self.target.prepare_render(vr_camera) self.target.prepare_render(vr_camera)
self._camera = vr_camera self._camera = vr_camera
# 🌌 关键修复确保VR相机能看到天空盒
# RenderPipeline的天空盒在render节点下使用unsorted bin和shader effects
if self.target._source_region:
# 确保DisplayRegion支持所有bin排序
self.target._source_region.setSort(20) # 设置合理的sort值
print(f" ✓ DisplayRegion sort已设置")
# 🔑 关键设置VR相机的initial state为render的state
# 这样VR相机才能继承RenderPipeline应用在render节点上的所有shader effects包括天空盒shader
if vr_camera and vr_camera.node():
# 使用Panda3D的内置render节点通过builtins
try:
from panda3d.core import NodePath
import builtins
if hasattr(builtins, 'render'):
render = builtins.render
vr_camera.node().setInitialState(render.getState())
print(f" ✓ VR相机initial state已设置为render的state")
else:
print(f" ⚠️ builtins.render不存在跳过initial state设置")
except Exception as e:
print(f" ⚠️ 设置VR相机initial state失败: {e}")
# 设置正常的背景色(与主窗口一致的天空色) # 设置正常的背景色(与主窗口一致的天空色)
if self.target.internal_buffer: if self.target.internal_buffer:
buffer = self.target.internal_buffer buffer = self.target.internal_buffer

View File

@ -38,6 +38,7 @@ class VRTeleportSystem(DirectObject):
self.gravity = -9.8 # 重力系数 self.gravity = -9.8 # 重力系数
self.initial_velocity = 10.0 # 初始速度 self.initial_velocity = 10.0 # 初始速度
self.min_teleport_distance = 1.0 # 最小传送距离 self.min_teleport_distance = 1.0 # 最小传送距离
self.player_height_offset = 1.7 # 玩家站立高度偏移(米)
# 可视化元素 # 可视化元素
self.teleport_arc_node = None # 抛物线节点 self.teleport_arc_node = None # 抛物线节点
@ -359,13 +360,23 @@ class VRTeleportSystem(DirectObject):
# 计算传送偏移 # 计算传送偏移
if self.vr_manager.tracking_space: if self.vr_manager.tracking_space:
current_pos = self.vr_manager.tracking_space.getPos() current_pos = self.vr_manager.tracking_space.getPos()
target_offset = self.teleport_target_pos - self.active_controller.get_world_position()
new_pos = current_pos + target_offset # 计算水平偏移只考虑XY平面
controller_pos = self.active_controller.get_world_position()
horizontal_offset = Vec3(
self.teleport_target_pos.x - controller_pos.x,
self.teleport_target_pos.y - controller_pos.y,
0
)
# 计算新位置:保持水平偏移,设置固定站立高度
new_pos = current_pos + horizontal_offset
new_pos.z = self.teleport_target_pos.z + self.player_height_offset
# 执行传送 # 执行传送
self.vr_manager.tracking_space.setPos(new_pos) self.vr_manager.tracking_space.setPos(new_pos)
print(f"✅ 传送成功: {current_pos}{new_pos}") print(f"✅ 传送成功: {current_pos}{new_pos} (高度偏移: {self.player_height_offset}m)")
# 停止预览 # 停止预览
self.stop_teleport_preview() self.stop_teleport_preview()