更新godot ai 到最新版本
This commit is contained in:
@@ -352,6 +352,15 @@ static func coerce_with_context(value: Variant, ctx: Dictionary) -> Dictionary:
|
||||
return coerce_for_type(value, ctx.prop_type, ctx.prop_name)
|
||||
|
||||
|
||||
## A rotation slerp can consume: all components finite and unit length within
|
||||
## float32 precision. Guards the normalization path against a scaled result
|
||||
## that is zero, infinite, or NaN.
|
||||
static func _is_usable_rotation(quat: Quaternion) -> bool:
|
||||
if not is_finite(quat.x) or not is_finite(quat.y) or not is_finite(quat.z) or not is_finite(quat.w):
|
||||
return false
|
||||
return absf(quat.length() - 1.0) <= 0.001
|
||||
|
||||
|
||||
## Coerce a single value to the given Godot variant type. Returns
|
||||
## {"ok": coerced} or {"error": msg}. Unknown types pass through.
|
||||
static func coerce_for_type(value: Variant, prop_type: int, prop_name: String) -> Dictionary:
|
||||
@@ -386,6 +395,65 @@ static func coerce_for_type(value: Variant, prop_type: int, prop_name: String) -
|
||||
TYPE_BOOL:
|
||||
if value is int or value is float or value is bool:
|
||||
return {"ok": bool(value)}
|
||||
TYPE_VECTOR3I:
|
||||
var v3i = McpJsonValues.parse_vector3i(value)
|
||||
if v3i != null:
|
||||
return {"ok": v3i}
|
||||
return {"error": "Cannot coerce value to Vector3i for property '%s' (expected {x,y,z}, [x,y,z], or Vector3i; components must be finite and within int32 range)" % prop_name}
|
||||
TYPE_QUATERNION:
|
||||
var quat = McpJsonValues.parse_quaternion(value)
|
||||
if quat == null:
|
||||
return {"error": "Cannot coerce value to Quaternion for property '%s' (expected {x,y,z,w}, [x,y,z,w], or Quaternion; components must be finite)" % prop_name}
|
||||
## Rotation contract at the animation boundary: AnimationPlayer
|
||||
## slerps quaternions, and a non-unit one makes
|
||||
## value_track_interpolate emit a normalization error and return
|
||||
## identity. Normalize valid nonzero rotations so stored tracks are
|
||||
## usable; only an exactly zero-length quaternion is refused.
|
||||
## Scale by the largest component before measuring: components are
|
||||
## float32, so squaring one near the type's maximum overflows to
|
||||
## INF (normalized() then returns (0,0,0,0)), while squaring a tiny
|
||||
## nonzero one underflows to zero and misreads as zero-length.
|
||||
var largest := maxf(maxf(absf(quat.x), absf(quat.y)), maxf(absf(quat.z), absf(quat.w)))
|
||||
if largest == 0.0:
|
||||
return {"error": "Cannot coerce value to Quaternion for property '%s': zero-length quaternion is not a rotation" % prop_name}
|
||||
var normalized := Quaternion(
|
||||
quat.x / largest, quat.y / largest, quat.z / largest, quat.w / largest
|
||||
).normalized()
|
||||
## Validate the result instead of trusting the arithmetic: an
|
||||
## unusable rotation must fail here, not reach slerp as zero.
|
||||
if not _is_usable_rotation(normalized):
|
||||
return {"error": "Cannot coerce value to Quaternion for property '%s': components cannot be normalized to a usable rotation" % prop_name}
|
||||
return {"ok": normalized}
|
||||
TYPE_BASIS:
|
||||
var basis = McpJsonValues.parse_basis(value)
|
||||
if basis != null:
|
||||
return {"ok": basis}
|
||||
return {"error": "Cannot coerce value to Basis for property '%s' (expected {x,y,z} axis vectors, a 3x3 nested array, or Basis)" % prop_name}
|
||||
TYPE_TRANSFORM3D:
|
||||
var xform = McpJsonValues.parse_transform3d(value)
|
||||
if xform != null:
|
||||
return {"ok": xform}
|
||||
return {"error": "Cannot coerce value to Transform3D for property '%s' (expected {basis,origin}, {position,rotation_degrees?,scale?}, or Transform3D)" % prop_name}
|
||||
TYPE_RECT2:
|
||||
var rect = McpJsonValues.parse_rect2(value)
|
||||
if rect != null:
|
||||
return {"ok": rect}
|
||||
return {"error": "Cannot coerce value to Rect2 for property '%s' (expected {position,size}, [x,y,w,h], or Rect2)" % prop_name}
|
||||
TYPE_AABB:
|
||||
var aabb = McpJsonValues.parse_aabb(value)
|
||||
if aabb != null:
|
||||
return {"ok": aabb}
|
||||
return {"error": "Cannot coerce value to AABB for property '%s' (expected {position,size}, [x,y,z,w,h,d], or AABB)" % prop_name}
|
||||
TYPE_NODE_PATH:
|
||||
var node_path = McpJsonValues.parse_node_path(value)
|
||||
if node_path != null:
|
||||
return {"ok": node_path}
|
||||
return {"error": "Cannot coerce value to NodePath for property '%s' (expected a string path)" % prop_name}
|
||||
TYPE_STRING_NAME:
|
||||
var string_name = McpJsonValues.parse_string_name(value)
|
||||
if string_name != null:
|
||||
return {"ok": string_name}
|
||||
return {"error": "Cannot coerce value to StringName for property '%s' (expected a string)" % prop_name}
|
||||
return {"ok": value}
|
||||
|
||||
|
||||
|
||||
Reference in New Issue
Block a user