带标记形状的BooleanSpriteCutter / FragmentManager英文手册第2部分(关于脚本)

本文档介绍了 BooleanSpriteCutterWithTaggedShapes 脚本和 Fragment Manager 脚本。
注意:第 1 部分在此处 BooleanSpriteCutterWithTaggedShapes / FragmentManager English Manual Part 1(About Sample Project)

BooleanSpriteCutterWithTaggedShapes 概述

BooleanSpriteCutterWithTaggedShapes 是一个 Node2D 脚本,它针对指定组中的 Sprite2D 节点(以及可选的重新切割片段),使用来自另一个组的“遮罩形状节点”来切割相交区域,通过沃罗诺伊分割(Voronoi partitioning)和布尔运算将其碎片化,并生成 RigidBody2D 碎片。
碎片被分类为内部(在遮罩内)和外部(剩余部分),您可以分别为每种类型配置力、物理、材质等。


功能

  • 通过组批量处理多个目标精灵(一次切割多个)
  • 从另一个组收集遮罩形状(顺序处理多个遮罩)
  • 内部/外部**力(方向/强度/扭矩)**的独立设置
  • 碎片物理设置模式:手动 / 继承自 Sprite / 继承自 Shape / 继承自指定节点
  • 碎片生成父节点模式:自身 / 指定节点 / 所有者的父节点 / 所有者的子节点 / 管理器
  • 支持重新切割(再次碎片化),内部/外部有独立的允许标志
  • 支持边缘线(Line2D)和材质继承/覆盖

前置条件和需求

项目 内容
所需插件 res://addons/gdDelaunay/Delaunay.gd 必须存在(已 preload
目标 target_sprite_group 中的 Sprite2D(需要纹理)/ 可重新切割的 RigidBody2D 碎片
遮罩 shape_node_group 中的形状节点(支持的类型如下)
相交 仅当遮罩 AABB 与目标 AABB 相交且存在多边形相交时才进行切割
注意 对于精灵基础多边形,仅使用 opaque_to_polygons() 的第一个元素(具有多个不透明岛屿的材质可能与预期行为不同)

设置

  1. 在场景中放置一个 Node2D 并附加此脚本。
  2. 将您要破碎的 Sprite2D 添加到 target_sprite_group(默认:SpriteGroup)。
  3. 将遮罩节点添加到 shape_node_group(默认:CutterShapeGroup)。
  • 示例:Polygon2D / CollisionPolygon2D / CollisionShape2D(凸/凹/圆/矩形)
  1. 在检查器中配置参数(最小要求:alpha_thresholdsimplify_tolerancevoronoi_seed_count)。
  2. 在所需时刻调用 call_cut()
  • 示例:输入、按钮、碰撞事件、动画事件等。

生成的节点规范

生成的对象 结构 元数据 / 组 备注
内部碎片 RigidBody2D(子节点:Polygon2D + CollisionPolygon2D + 可选的 Line2D META_IS_FRAGMENT=true / META_FRAGMENT_TYPE="inside" / META_FRAGMENT_SOURCE_SPRITE=源 Sprite / 添加到 target_sprite_group 如果 unfreeze_delay>0,碎片将暂时冻结,然后在计时器结束后解冻并施加力
外部碎片 同上 META_FRAGMENT_TYPE="outside" 应用外部力/物理/材质设置
Sprite2D 隐藏 META_ALREADY_CUT=true 防止对同一精灵进行双重切割
重新切割源(碎片) queue_free() - 在重新切割期间,原始碎片被替换

使用示例

目标(用例) 设置 结果 备注
仅切割被遮罩触碰的区域 将遮罩形状添加到 shape_node_groupcall_cut() 仅相交的精灵生成碎片 多个遮罩按顺序处理
将内部碎片向右抛出 inside_force_direction_mode=FixedVectorinside_force_fixed_vector=(1,0) 内部碎片沿恒定方向飞行 强度为 inside_force_base_strength
从爆炸中心径向散射 *_force_direction_mode=ExplosionFromPoint,设置 *_explosion_center_node 碎片向外散射 您可以通过 call_cut(force_config) 覆盖中心
较大的碎片获得更强的力/旋转 use_area_scaling_for_impulse=true / use_area_scaling_for_torque=true 力和扭矩按面积比例缩放 area_ratio_min/max 限制
将碎片组织到特定节点下 fragment_parent_mode=SpecifiedNode(设置 fragment_parent_node 碎片分组在指定节点下 您也可以选择 Manager
重新切割(完成切割) allow_recutted_inside_fragments=true(和/或外部) 下次 call_cut() 也包括碎片 碎片添加到 target_sprite_group
切割后禁用附近碰撞 disable_related_collisions_on_cut=true 禁用原始精灵周围的碰撞 生成的碎片(META_IS_FRAGMENT)被排除

属性列表

基础

属性 类型 / 默认值 描述(行为/计算/备注)
target_sprite_group String / "SpriteGroup" 收集切割目标的组名(Sprite2D 和允许的碎片)
shape_node_group String / "CutterShapeGroup" 收集遮罩形状节点的组名
alpha_threshold float / 0.1 BitMap.create_from_image_alpha 的不透明阈值(alpha >= 阈值即为不透明)
simplify_tolerance float / 2.0 opaque_to_polygons() 的简化容差(越高越轻量但粗糙)
voronoi_seed_count int / 10 沃罗诺伊种子数量(碎片越多,计算越重)
density float / 1.0 质量系数:mass = area_world * density
unfreeze_delay float / 0.0 解冻生成身体前的延迟秒数(>0 产生暂时暂停效果)
circle_approx_segments int / 32 CircleShape2D 近似为多边形的段数
debug_log bool / false 如果为 true,则打印处理日志(通常保持 false)

沃罗诺伊种子分布

属性 类型 / 默认值 描述
voronoi_seed_density_mode enum / Uniform Uniform / TowardMaskCenter / TowardSpriteCenter / TowardNodeCenter
voronoi_seed_density_power float / 2.0 居中偏置的强度(pow(t, power)
voronoi_seed_center_node NodePath / 空 TowardNodeCenter 的中心(Node2D.global_position

力设置(内部)

属性 类型 / 默认值 描述
inside_force_base_strength float / 1000.0 内部碎片的基础冲量强度
inside_force_strength_jitter_ratio float / 0.0 强度抖动(±比例;方向固定)
inside_force_direction_mode enum / FixedVector FixedVector / ExplosionFromPoint
inside_force_fixed_vector Vector2 / (1,0) FixedVector 的方向(内部归一化)
inside_explosion_center_node NodePath / 空 ExplosionFromPoint 的爆炸中心 Node2D
inside_torque_impulse float / 0.0 施加给内部碎片的扭矩

力设置(外部)

属性 类型 / 默认值 描述
outside_force_base_strength float / 600.0 外部碎片的基础冲量强度
outside_force_strength_jitter_ratio float / 0.0 强度抖动(±比例)
outside_force_direction_mode enum / FixedVector FixedVector / ExplosionFromPoint
outside_force_fixed_vector Vector2 / (0,-1) FixedVector 的方向
outside_explosion_center_node NodePath / 空 爆炸中心
outside_torque_impulse float / 0.0 施加给外部碎片的扭矩

大小缩放

属性 类型 / 默认值 描述
use_area_scaling_for_impulse bool / true 按面积比例缩放冲量
use_area_scaling_for_torque bool / true 按面积比例缩放扭矩
area_ratio_min float / 0.2 面积比例的最小限制
area_ratio_max float / 3.0 面积比例的最大限制
impulse_area_exponent float / 0.5 impulse_scale = pow(area_ratio, exponent)
torque_area_exponent float / 1.0 torque_scale = pow(area_ratio, exponent)

材质设置(通用 / 内部 / 外部)

属性 类型 / 默认值 描述
fragment_inherit_material bool / true 继承原始材质(通用默认值)
fragment_use_custom_material bool / false 强制应用通用自定义材质
fragment_custom_material Material / null 通用自定义材质
inside_fragment_inherit_material bool / true 仅内部:是否继承
inside_fragment_use_custom_material bool / false 仅内部:使用自定义材质
inside_fragment_custom_material Material / null 仅内部材质
outside_fragment_inherit_material bool / true 仅外部:是否继承
outside_fragment_use_custom_material bool / false 仅外部:使用自定义材质
outside_fragment_custom_material Material / null 仅外部材质

边缘线设置

属性 类型 / 默认值 描述
draw_edge_line bool / true 使用 Line2D 绘制碎片边缘
edge_line_width float / 2.0 线宽
edge_line_color_inside Color / 白色 内部线条颜色
edge_line_color_outside Color / 白色 外部线条颜色

重新切割设置

属性 类型 / 默认值 描述
allow_recutted_inside_fragments bool / false 在下一次切割中将内部碎片作为目标
allow_recutted_outside_fragments bool / false 在下一次切割中将外部碎片作为目标

禁用原始碰撞

属性 类型 / 默认值 描述
disable_related_collisions_on_cut bool / false 扫描并禁用原始精灵周围的碰撞(排除生成的碎片)

碎片父节点(生成目标)

属性 类型 / 默认值 描述
fragment_parent_mode enum / Self Self / SpecifiedNode / OwnerParent / OwnerChild / Manager
fragment_parent_node NodePath / 空 SpecifiedNode 的生成目标
备注 - OwnerChild 在重新切割时应用回退(所有者是碎片)

碎片物理(内部)

属性 类型 / 默认值 描述
inside_fragment_physics_mode enum / FromSprite Manual / FromSprite / FromShape / FromSpecified
inside_fragment_physics_reference_node NodePath / 空 FromSpecified 的参考节点
inside_fragment_gravity_scale_manual float / 1.0 手动:重力比例
inside_fragment_collision_layer_manual int(flags) / 1 手动:碰撞层
inside_fragment_collision_mask_manual int(flags) / 1 手动:碰撞掩码
inside_fragment_linear_damp_manual float / 0.0 手动:线性阻尼
inside_fragment_angular_damp_manual float / 0.0 手动:角阻尼
inside_fragment_physics_material_manual PhysicsMaterial / null 手动:摩擦/弹跳
inside_fragment_lock_rotation_manual bool / false 手动:锁定旋转

碎片物理(外部)

属性 类型 / 默认值 描述
outside_fragment_physics_mode enum / FromSprite Manual / FromSprite / FromShape / FromSpecified
outside_fragment_physics_reference_node NodePath / 空 FromSpecified 的参考节点
outside_fragment_gravity_scale_manual float / 1.0 手动:重力比例
outside_fragment_collision_layer_manual int(flags) / 1 手动:碰撞层
outside_fragment_collision_mask_manual int(flags) / 1 手动:碰撞掩码
outside_fragment_linear_damp_manual float / 0.0 手动:线性阻尼
outside_fragment_angular_damp_manual float / 0.0 手动:角阻尼
outside_fragment_physics_material_manual PhysicsMaterial / null 手动:摩擦/弹跳
outside_fragment_lock_rotation_manual bool / false 手动:锁定旋转

管理器集成

属性 类型 / 默认值 描述
manager_mode enum / Autoload None / Autoload / SpecifiedNode
manager_autoload_name String / "FragmentManagerSingleton" Autoload 名称(引用 /root/<name>
manager_node NodePath / 空 SpecifiedNode 的引用目标
行为 - 在生成碎片时,调用已解析的 Manager 上的 register_fragment(body)(仅当该方法存在时)

运行时覆盖 (call_cut(force_config))

通过 call_cut()force_config 参数,您可以仅在该次调用中覆盖检查器中的力设置。

目标 示例值
内部/外部 base_strength 1400.0
内部/外部 strength_jitter_ratio 0.15
内部/外部 direction_mode FORCE_DIR_FIXED_VECTORFORCE_DIR_EXPLOSION
内部/外部 fixed_vector Vector2(1, 0)
内部/外部 explosion_center Vector2(100, 200)(世界坐标)
内部/外部 torque_impulse 3.0

FragmentManager 概述

FragmentManager 是一个 Node2D 脚本,用于管理由 Cutter 生成的 RigidBody2D 碎片。碎片通过 register_fragment() 注册,它可以管理数量限制、TTL(生存时间)、静止冻结和可选的屏幕外删除,内部/外部有独立的策略。

功能

  • 内部/外部独立的管理策略(限制、TTL、冻结、屏幕外删除)
  • 通过 WeakRef 持有引用;如果碎片离开树结构,引用将自动清理
  • 可选地在冻结时禁用碰撞(将层/掩码设置为 0)
  • 屏幕外检查从视口 Camera2D 计算视图矩形(如果不可用则跳过)

前置条件和需求

  • 假设使用 Godot 4.x 2D 节点结构。
  • 管理的对象是传递给 register_fragment(body)RigidBody2D
  • body 必须具有 Cutter 设置的 META_FRAGMENT_TYPE"inside" / "outside")。
  • 要排除某些碎片的管理,请设置 META_FRAGMENT_NO_MANAGE=true

设置

  1. 将此脚本附加到 fragment_manager.tscn 的根节点。
  2. fragment_manager.tscn 注册为 Autoload,使其保持在 /root 下。
  3. 确保 Cutter 在生成碎片时调用 FragmentManager.register_fragment(body)
  • 如果 Cutter 已经实现了“在生成时调用 register_fragment”,请确保 Autoload 名称和引用匹配。

生成/管理的数据

  • 此节点保持为 Node2D,并在内部维护两个列表:
    • _fragments_inside
    • _fragments_outside
  • 注册的碎片接收元数据:
    • _boolean_fragment(碎片标志)
    • _fragment_spawn_msec(生成时间,毫秒)
    • _fragment_last_active_msec(最后活跃时间,毫秒)
  • 如果 inside_fragment_group_name / outside_fragment_group_name 非空,碎片在注册时将被添加到这些组。

使用示例

目标(用例) 设置 结果 备注
防止碎片过多 设置 inside_max_fragments / outside_max_fragments 超过限制时删除旧碎片 如果 <= 0,则无限制
随时间自然消失 *_enable_ttl=true,设置 *_ttl_seconds TTL 后删除 注册时记录生成时间
静止后停止物理 *_enable_freeze_on_settled=true 低速持续后冻结 还可以选择禁用碰撞
收集屏幕外的碎片 *_delete_when_offscreen=true 在屏幕外停留一定时间后删除 如果无法获取相机,则跳过检查
保留特定碎片 body.set_meta("_fragment_no_manage", true) 管理器忽略该碎片 最好在生成后立即设置

属性列表 (FragmentManager)

属性 类型 / 默认值 描述(行为/计算/备注)
inside_fragment_group_name String / "FragmentGroupInside" 注册时添加到内部碎片的组名。如果为空,则不添加。
inside_max_fragments int / 300 内部碎片最大数量。如果 <= 0,则无限制。超出部分通过 queue_free() 按最旧顺序删除。
inside_enable_ttl bool / true 启用内部碎片的 TTL 删除。
inside_ttl_seconds float / 8.0 生存时间(秒)。当 now - spawn_msec >= 此值时删除。
inside_enable_freeze_on_settled bool / true 启用内部碎片的静止冻结。
inside_settled_linear_speed float / 15.0 线性速度阈值。高于此值视为“活跃”并更新最后活跃时间。
inside_settled_angular_speed float / 1.5 角速度阈值。高于此值视为“活跃”。
inside_settled_grace_seconds float / 0.6 如果低速状态持续此时间,则应用冻结。
inside_disable_collision_when_frozen bool / true 冻结时,将碰撞层/掩码设置为 0。不执行解冻恢复。
inside_delete_when_offscreen bool / false 启用内部碎片的屏幕外删除。
inside_offscreen_grace_seconds float / 1.0 如果屏幕外停留此时间,则删除。如果返回屏幕内,则更新最后活跃时间。
outside_fragment_group_name String / "FragmentGroupOutside" 注册时添加到外部碎片的组名。如果为空,则不添加。
outside_max_fragments int / 300 外部碎片最大数量。如果 <= 0,则无限制。超出部分按最旧顺序删除。
outside_enable_ttl bool / true 启用外部碎片的 TTL 删除。
outside_ttl_seconds float / 8.0 外部生存时间(秒)。过期时删除。
outside_enable_freeze_on_settled bool / true 启用外部碎片的静止冻结。
outside_settled_linear_speed float / 15.0 外部碎片的线性速度阈值。
outside_settled_angular_speed float / 1.5 外部碎片的角速度阈值。
outside_settled_grace_seconds float / 0.6 外部碎片的低速宽限期。
outside_disable_collision_when_frozen bool / true 冻结时,将碰撞层/掩码设置为 0。不恢复。
outside_delete_when_offscreen bool / false 启用外部碎片的屏幕外删除。
outside_offscreen_grace_seconds float / 1.0 外部碎片的屏幕外宽限期(秒)。
debug_log bool / false 如果为 true,则记录因限制/TTL/屏幕外等导致的删除。
1 个赞

这感觉是一种增强屏幕视觉表现力的非常好的方式。

1 个赞