You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Godot调用get_texture时报空实例错误,求问题原因分析

问题原因分析

错误提示的是在null实例上调用get_texture,并非selected_mesh为空,而是selected_mesh.get_surface_material(result.shape)返回了null,后续调用其get_texture方法才触发报错,核心原因有两个:

  • result.shape的含义误解:intersect_ray返回的result.shape是碰撞体的形状索引,而非MeshInstance的网格表面索引。如果你的碰撞体是MeshInstance的父节点(比如StaticBody),或者碰撞形状是手动添加的简化形状,这个索引和Mesh的表面索引完全不匹配,调用get_surface_material时会因索引无效返回null。
  • 目标表面无材质:即使索引正确,若MeshInstance对应表面未设置材质,get_surface_material也会返回null,进而导致调用get_texture失败。
修复方案

1. 正确获取命中的Mesh表面索引

用射线结果中的face_index(命中的三角面索引)推导对应的Mesh表面索引,替换原有的result.shape:

func _process(delta: float) -> void:
    var camera = get_parent().get_node("Camera")
    if camera != null:
        var from = camera.project_ray_origin(mouse_position)
        var to = from + camera.project_ray_normal(mouse_position) * raycast_length
        var space_state = get_world().direct_space_state
        var result = space_state.intersect_ray(from, to)
        if result:
            var children = result.collider.get_children()
            for child in children:
                if child is MeshInstance:
                    if selected_mesh != null:
                        selected_mesh.material_override = null
                    selected_mesh = child
                    selected_mesh.material_override = SpatialMaterial.new()
                    # 修复部分:正确获取表面索引
                    if result.has("face_index"):
                        var face_idx = result.face_index
                        var surface_idx = selected_mesh.mesh.get_surface_for_face(face_idx)
                        var original_material = selected_mesh.get_surface_material(surface_idx)
                        if original_material != null:
                            selected_mesh.material_override.albedo_texture = original_material.get_texture("albedo_texture")
                        else:
                            # 处理材质为空的情况
                            selected_mesh.material_override.albedo_texture = null
                else:
                    if selected_mesh != null:
                        selected_mesh.material_override = null
                        selected_mesh = null
        else:
            if selected_mesh != null:
                selected_mesh.material_override = null
                selected_mesh = null

2. 增加空值判断

在调用get_texture前,先检查get_surface_material的返回值是否有效,避免null报错。

3. 确保碰撞体与MeshInstance的关联

如果射线检测的目标是包含MeshInstance的父节点(比如StaticBody),建议直接将碰撞形状附加到MeshInstance上,或者在检测时优先判断result.collider是否为MeshInstance,减少索引不匹配的风险。


内容的提问来源于stack exchange,提问作者AbsolutePickle42

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.07.26 03:42:35