小更新
This commit is contained in:
parent
93aa31c38e
commit
bc848b8526
|
|
@ -1,4 +1,4 @@
|
|||
[gd_scene load_steps=39 format=4 uid="uid://bj2318o3y68x2"]
|
||||
[gd_scene load_steps=40 format=4 uid="uid://bj2318o3y68x2"]
|
||||
|
||||
[ext_resource type="Script" uid="uid://ds6jy3s0hhmwt" path="res://_game/DemoScript.gd" id="1_2tycc"]
|
||||
[ext_resource type="PackedScene" uid="uid://1l06de041i40" path="res://_levels/l_level_1.tscn" id="1_p0ota"]
|
||||
|
|
@ -7,6 +7,7 @@
|
|||
[ext_resource type="PackedScene" uid="uid://b5nx4dntm0gyn" path="res://_props/door_manager/event_trigger_door.tscn" id="4_p0ota"]
|
||||
[ext_resource type="Script" uid="uid://b4menkyub4ce7" path="res://addons/reedscene/prop/PropComponent.gd" id="5_gslp7"]
|
||||
[ext_resource type="Script" uid="uid://7lml6d1t5xtq" path="res://addons/reedscene/prop/PropState.gd" id="6_6jw57"]
|
||||
[ext_resource type="Script" uid="uid://bh066o84byplh" path="res://addons/reedscene/scene/ReedSceneID.gd" id="6_hc6q0"]
|
||||
[ext_resource type="Script" uid="uid://cdvgq0xqdbagk" path="res://addons/reedscene/prop/ReedPropEffect.gd" id="7_2t6pm"]
|
||||
[ext_resource type="Script" uid="uid://fxpk2ot6otfh" path="res://addons/reedscene/act/Act.gd" id="7_xotud"]
|
||||
[ext_resource type="Script" uid="uid://baqgorvlumyju" path="res://addons/reedscene/act/SingleAct.gd" id="8_2tycc"]
|
||||
|
|
@ -50,12 +51,12 @@ script = ExtResource("8_2tycc")
|
|||
state_id = 1
|
||||
metadata/_custom_type_script = "uid://baqgorvlumyju"
|
||||
|
||||
[sub_resource type="Resource" id="Resource_xiw5v"]
|
||||
[sub_resource type="Resource" id="Resource_cqglw"]
|
||||
script = ExtResource("8_2tycc")
|
||||
state_id = 1
|
||||
metadata/_custom_type_script = "uid://baqgorvlumyju"
|
||||
|
||||
[sub_resource type="Resource" id="Resource_cqglw"]
|
||||
[sub_resource type="Resource" id="Resource_xiw5v"]
|
||||
script = ExtResource("8_2tycc")
|
||||
state_id = 1
|
||||
metadata/_custom_type_script = "uid://baqgorvlumyju"
|
||||
|
|
@ -164,6 +165,11 @@ collision_mask = 4
|
|||
script = ExtResource("13_2tycc")
|
||||
metadata/_custom_type_script = "uid://5e157vdk6175"
|
||||
|
||||
[node name="ReedSceneID" type="Node" parent="ReedScene"]
|
||||
script = ExtResource("6_hc6q0")
|
||||
scene_id = 10000
|
||||
metadata/_custom_type_script = "uid://bh066o84byplh"
|
||||
|
||||
[node name="SceneManager" type="Node" parent="ReedScene" node_paths=PackedStringArray("TransitionNode")]
|
||||
script = ExtResource("15_hc6q0")
|
||||
TransitionNode = NodePath("Transition")
|
||||
|
|
|
|||
|
|
@ -0,0 +1,10 @@
|
|||
[gd_resource type="Resource" script_class="SceneIDDatabase" load_steps=2 format=3 uid="uid://4c26uejocdos"]
|
||||
|
||||
[ext_resource type="Script" uid="uid://delj6tsrxv8s3" path="res://addons/reedscene/scene/SceneIDDatabase.gd" id="1_47k6c"]
|
||||
|
||||
[resource]
|
||||
script = ExtResource("1_47k6c")
|
||||
next_id = 10001
|
||||
scene_map = {
|
||||
"res://_game/LevelDemonstration.tscn": 10000
|
||||
}
|
||||
|
|
@ -0,0 +1,27 @@
|
|||
@tool
|
||||
extends Control
|
||||
|
||||
@onready var tree: Tree = %Tree
|
||||
|
||||
func _ready():
|
||||
_setup_tree()
|
||||
_fill_dummy_data()
|
||||
|
||||
func _setup_tree():
|
||||
tree.clear()
|
||||
tree.columns = 3
|
||||
tree.set_column_title(0, "ID")
|
||||
tree.set_column_title(1, "Scene Path")
|
||||
tree.set_column_title(2, "Action")
|
||||
|
||||
func _fill_dummy_data():
|
||||
var root := tree.create_item()
|
||||
|
||||
_add_row(root, 10001, "res://levels/level_1.tscn")
|
||||
_add_row(root, 10002, "res://levels/level_2.tscn")
|
||||
|
||||
func _add_row(root: TreeItem, id: int, path: String):
|
||||
var item := tree.create_item(root)
|
||||
item.set_text(0, str(id))
|
||||
item.set_text(1, path)
|
||||
item.set_text(2, "Open")
|
||||
|
|
@ -0,0 +1 @@
|
|||
uid://bi8dmt4ypmbhq
|
||||
|
|
@ -0,0 +1,17 @@
|
|||
[gd_scene load_steps=2 format=3 uid="uid://detpkhtovi6bp"]
|
||||
|
||||
[ext_resource type="Script" uid="uid://bi8dmt4ypmbhq" path="res://addons/reedscene/dock/scene_id_main_screen.gd" id="1_jm7r3"]
|
||||
|
||||
[node name="SceneIdMainScreen" type="CenterContainer"]
|
||||
anchors_preset = 15
|
||||
anchor_right = 1.0
|
||||
anchor_bottom = 1.0
|
||||
grow_horizontal = 2
|
||||
grow_vertical = 2
|
||||
script = ExtResource("1_jm7r3")
|
||||
|
||||
[node name="Tree" type="Tree" parent="."]
|
||||
unique_name_in_owner = true
|
||||
layout_mode = 2
|
||||
columns = 3
|
||||
hide_root = true
|
||||
|
|
@ -1,14 +1,69 @@
|
|||
@tool
|
||||
extends EditorPlugin
|
||||
|
||||
var inspector_plugin
|
||||
var inspector_plugins: Array[EditorInspectorPlugin] = []
|
||||
|
||||
const AUTOLOAD_REED_SCENE_NAME: StringName = "ReedSceneSystem"
|
||||
const AUTOLOAD_REED_SCENE_PATH:= "res://addons/reedscene/scene/SceneRegistry.gd"
|
||||
|
||||
var toolbar_button: Button
|
||||
var scene_id_window: Window
|
||||
var main_screen: Control
|
||||
|
||||
func _enter_tree() -> void:
|
||||
inspector_plugin = preload("res://addons/reedscene/act/ActManagerInspector.gd").new()
|
||||
# ✅ 注入 EditorInterface
|
||||
inspector_plugin.editor_interface = get_editor_interface()
|
||||
add_inspector_plugin(inspector_plugin)
|
||||
_load_mainscreen()
|
||||
|
||||
if not ProjectSettings.has_setting("autoload/%s" % AUTOLOAD_REED_SCENE_NAME):
|
||||
add_autoload_singleton(AUTOLOAD_REED_SCENE_NAME, AUTOLOAD_REED_SCENE_PATH)
|
||||
|
||||
# Inspector 1:你已有的
|
||||
var act_inspector := preload(
|
||||
"res://addons/reedscene/act/ActManagerInspector.gd"
|
||||
).new()
|
||||
act_inspector.editor_interface = get_editor_interface()
|
||||
add_inspector_plugin(act_inspector)
|
||||
inspector_plugins.append(act_inspector)
|
||||
|
||||
# Inspector 2:新的(比如 ReedSceneID)
|
||||
var scene_id_inspector := preload(
|
||||
"res://addons/reedscene/scene/ReedSceneIDInspector.gd"
|
||||
).new()
|
||||
add_inspector_plugin(scene_id_inspector)
|
||||
inspector_plugins.append(scene_id_inspector)
|
||||
|
||||
func _exit_tree() -> void:
|
||||
if inspector_plugin:
|
||||
remove_inspector_plugin(inspector_plugin)
|
||||
_unload_mainscreen()
|
||||
|
||||
##自动删除单例
|
||||
if ProjectSettings.has_setting("autoload/%s" % AUTOLOAD_REED_SCENE_NAME):
|
||||
remove_autoload_singleton(AUTOLOAD_REED_SCENE_NAME)
|
||||
|
||||
# 移除 InspectorPlugin
|
||||
for plugin in inspector_plugins:
|
||||
remove_inspector_plugin(plugin)
|
||||
inspector_plugins.clear()
|
||||
|
||||
##加載主界面
|
||||
func _load_mainscreen() -> void:
|
||||
main_screen = preload("res://addons/reedscene/dock/scene_id_main_screen.tscn").instantiate()
|
||||
EditorInterface.get_editor_main_screen().add_child(main_screen)
|
||||
main_screen.visible = false
|
||||
|
||||
##卸載主界面
|
||||
func _unload_mainscreen() -> void:
|
||||
if main_screen:
|
||||
main_screen.queue_free()
|
||||
main_screen = null
|
||||
|
||||
func _has_main_screen() -> bool:
|
||||
return true
|
||||
|
||||
func _make_visible(visible: bool) -> void:
|
||||
if main_screen:
|
||||
main_screen.visible = visible
|
||||
|
||||
func _get_plugin_name() -> String:
|
||||
return "Reed Scene"
|
||||
|
||||
func _get_plugin_icon() -> Texture2D:
|
||||
return EditorInterface.get_editor_theme().get_icon("Node", "EditorIcons")
|
||||
|
|
|
|||
|
|
@ -0,0 +1,8 @@
|
|||
@tool
|
||||
extends Node
|
||||
class_name ReedSceneID
|
||||
|
||||
@export var scene_id: int = -1
|
||||
|
||||
func has_id() -> bool:
|
||||
return scene_id >= 0
|
||||
|
|
@ -0,0 +1 @@
|
|||
uid://bh066o84byplh
|
||||
|
|
@ -0,0 +1,39 @@
|
|||
@tool
|
||||
extends RefCounted
|
||||
class_name ReedSceneIDEditorSystem
|
||||
|
||||
const DB_PATH := "res://addons/reedscene/demo/data_base/GLOBAL_SCENE_ID.tres"
|
||||
|
||||
static func _load_db_readonly() -> SceneIDDatabase:
|
||||
# 忽略缓存,避免拿到同一个共享实例(更稳)
|
||||
return ResourceLoader.load(DB_PATH, "", ResourceLoader.CACHE_MODE_IGNORE)
|
||||
|
||||
static func _clone_db_to_new(db_ro: SceneIDDatabase) -> SceneIDDatabase:
|
||||
var db := SceneIDDatabase.new()
|
||||
if db_ro:
|
||||
db.next_id = db_ro.next_id
|
||||
# 深拷贝 Dictionary,彻底断开只读引用链
|
||||
db.scene_map = db_ro.scene_map.duplicate(true)
|
||||
return db
|
||||
|
||||
static func request_id_for_scene(scene_path: String) -> int:
|
||||
var db_ro := _load_db_readonly()
|
||||
if db_ro == null:
|
||||
push_error("[ReedSceneIDEditorSystem] Database not found: " + DB_PATH)
|
||||
return -1
|
||||
|
||||
var db := _clone_db_to_new(db_ro)
|
||||
|
||||
if db.scene_map.has(scene_path):
|
||||
return int(db.scene_map[scene_path])
|
||||
|
||||
var new_id := db.next_id
|
||||
db.next_id += 1
|
||||
db.scene_map[scene_path] = new_id
|
||||
|
||||
var err := ResourceSaver.save(db, DB_PATH)
|
||||
if err != OK:
|
||||
push_error("[ReedSceneIDEditorSystem] Failed to save DB (%s), err=%d" % [DB_PATH, err])
|
||||
return -1
|
||||
|
||||
return new_id
|
||||
|
|
@ -0,0 +1 @@
|
|||
uid://b86r8tai4kygo
|
||||
|
|
@ -0,0 +1,31 @@
|
|||
@tool
|
||||
extends EditorInspectorPlugin
|
||||
|
||||
func _can_handle(object) -> bool:
|
||||
return object is ReedSceneID
|
||||
|
||||
func _parse_begin(object):
|
||||
var button := Button.new()
|
||||
button.text = "Request Scene ID"
|
||||
button.pressed.connect(func():
|
||||
_request_id(object)
|
||||
)
|
||||
add_custom_control(button)
|
||||
|
||||
func _request_id(id_comp: ReedSceneID):
|
||||
var scene := id_comp.get_owner()
|
||||
if scene == null:
|
||||
push_error("[ReedSceneID] Cannot find owning scene")
|
||||
return
|
||||
|
||||
var scene_path := scene.scene_file_path
|
||||
if scene_path == "":
|
||||
push_error("[ReedSceneID] Scene must be saved before requesting ID")
|
||||
return
|
||||
|
||||
var id := ReedSceneIDEditorSystem.request_id_for_scene(scene_path)
|
||||
if id < 0:
|
||||
return
|
||||
|
||||
id_comp.scene_id = id
|
||||
id_comp.notify_property_list_changed()
|
||||
|
|
@ -0,0 +1 @@
|
|||
uid://h6liq147is5g
|
||||
|
|
@ -0,0 +1,7 @@
|
|||
extends Resource
|
||||
class_name SceneIDDatabase
|
||||
|
||||
@export var next_id: int = 10000
|
||||
|
||||
# scene_path (String) -> scene_id (int)
|
||||
@export var scene_map: Dictionary = {}
|
||||
|
|
@ -0,0 +1 @@
|
|||
uid://delj6tsrxv8s3
|
||||
|
|
@ -0,0 +1,103 @@
|
|||
# id (int) -> WeakRef(ReedScene)
|
||||
var _by_id: Dictionary = {}
|
||||
|
||||
signal registered(id: int, node: ReedScene)
|
||||
signal unregistered(id: int)
|
||||
signal conflict(id: int, existing: ReedScene, incoming: ReedScene)
|
||||
|
||||
# -------------------------
|
||||
# 注册
|
||||
# -------------------------
|
||||
func register(id: int, node: ReedScene) -> bool:
|
||||
if id < 0:
|
||||
push_error("[SceneRegistry] register(): invalid id (<0): %d" % id)
|
||||
return false
|
||||
|
||||
if node == null:
|
||||
push_error("[SceneRegistry] register(): node is null for id=%d" % id)
|
||||
return false
|
||||
|
||||
_cleanup_dead(id)
|
||||
|
||||
if _by_id.has(id):
|
||||
var existing: ReedScene = _by_id[id].get_ref()
|
||||
if existing == node:
|
||||
return true # 重复注册同一个实例,忽略
|
||||
|
||||
emit_signal("conflict", id, existing, node)
|
||||
push_error(
|
||||
"[SceneRegistry] Duplicate id=%d existing=%s incoming=%s"
|
||||
% [id, existing, node]
|
||||
)
|
||||
return false
|
||||
|
||||
_by_id[id] = weakref(node)
|
||||
emit_signal("registered", id, node)
|
||||
return true
|
||||
|
||||
# -------------------------
|
||||
# 注销
|
||||
# -------------------------
|
||||
func unregister(id: int, node: ReedScene = null) -> void:
|
||||
if not _by_id.has(id):
|
||||
return
|
||||
|
||||
var existing: ReedScene = _by_id[id].get_ref()
|
||||
if node != null and existing != node:
|
||||
# 防止误删
|
||||
return
|
||||
|
||||
_by_id.erase(id)
|
||||
emit_signal("unregistered", id)
|
||||
|
||||
# -------------------------
|
||||
# 查询
|
||||
# -------------------------
|
||||
func get_scene(id: int) -> ReedScene:
|
||||
_cleanup_dead(id)
|
||||
var ref: WeakRef = _by_id.get(id)
|
||||
return ref.get_ref() if ref else null
|
||||
|
||||
func has(id: int) -> bool:
|
||||
return get_scene(id) != null
|
||||
|
||||
# -------------------------
|
||||
# 调用
|
||||
# -------------------------
|
||||
func call_scene(id: int, method: String, args: Array = []) -> Variant:
|
||||
var n := get_scene(id)
|
||||
if n == null:
|
||||
push_warning("[SceneRegistry] call_scene(): id not found: %d" % id)
|
||||
return null
|
||||
|
||||
if not n.has_method(method):
|
||||
push_warning(
|
||||
"[SceneRegistry] call_scene(): id=%d has no method '%s'"
|
||||
% [id, method]
|
||||
)
|
||||
return null
|
||||
|
||||
return n.callv(method, args)
|
||||
|
||||
# -------------------------
|
||||
# 列表
|
||||
# -------------------------
|
||||
func list_ids() -> PackedInt32Array:
|
||||
for id in _by_id.keys():
|
||||
_cleanup_dead(id)
|
||||
|
||||
var result := PackedInt32Array()
|
||||
for id in _by_id.keys():
|
||||
result.append(id)
|
||||
return result
|
||||
|
||||
# -------------------------
|
||||
# 内部:清理死引用
|
||||
# -------------------------
|
||||
func _cleanup_dead(id: int) -> void:
|
||||
if not _by_id.has(id):
|
||||
return
|
||||
|
||||
var ref: WeakRef = _by_id[id]
|
||||
if ref == null or ref.get_ref() == null:
|
||||
_by_id.erase(id)
|
||||
|
|
@ -0,0 +1 @@
|
|||
uid://iau86ajv4jv
|
||||
|
|
@ -22,6 +22,7 @@ CameraSystem="*res://_shared/CameraSystem.tscn"
|
|||
RoomSystem="*res://_shared/room_system.gd"
|
||||
GlobalEvent="*res://_shared/global_event.gd"
|
||||
ReedVFX="*res://addons/reedfx/vfx/ReedVFXSystem.tscn"
|
||||
ReedSceneSystem="*res://addons/reedscene/scene/SceneRegistry.gd"
|
||||
|
||||
[display]
|
||||
|
||||
|
|
|
|||
Loading…
Reference in New Issue