From 7fd1d97099c15e36a652e6c86f38e7ef1da8b8c1 Mon Sep 17 00:00:00 2001 From: yvmou_ Date: Fri, 9 Oct 2026 15:03:52 +0800 Subject: [PATCH] =?UTF-8?q?=E5=87=86=E5=BF=83?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .workbuddy/memory/2026-10-09.md | 11 +++++++ character/player/player.tscn | 14 ++++++++ ui/crosshair.gd | 57 +++++++++++++++++++++++++++++++++ ui/crosshair.gd.uid | 1 + 4 files changed, 83 insertions(+) create mode 100644 .workbuddy/memory/2026-10-09.md create mode 100644 ui/crosshair.gd create mode 100644 ui/crosshair.gd.uid diff --git a/.workbuddy/memory/2026-10-09.md b/.workbuddy/memory/2026-10-09.md new file mode 100644 index 0000000..8de9873 --- /dev/null +++ b/.workbuddy/memory/2026-10-09.md @@ -0,0 +1,11 @@ +# 2026-10-09 + +## 简易准心(Crosshair) +- 新增 `ui/crosshair.gd`:`@tool extends Control`,用 `_draw()` 画十字(gap/length/thickness/dot 可导出调参),`mouse_filter = IGNORE`,监听 `NOTIFICATION_RESIZED` 重绘。 +- 挂载约定:`CanvasLayer > Crosshair(Control)`,Control 锚点为 Full Rect,中心即屏幕中心;推荐挂在 `CameraRig` 之下 —— 因为 `player.gd _ready()` 对非 authority 会 `camera_rig.queue_free()`,远端玩家准心随之一并释放,无需额外代码。 +- 项目 stretch 模式为 `canvas_items` + `expand`,CanvasLayer 会自动跟随缩放。 + +### 后续改动:只保留「点」 +- 最终形态:准心 = 屏幕中心一个点,无十字、无样式开关(`enum Style` 已移除)。 +- 导出参数:`dot_color` / `dot_radius`(默认 2.5) / `outline` / `outline_color` / `outline_width`。 +- `_draw()` 先画描边圆再画主体圆,保证浅背景可见。 diff --git a/character/player/player.tscn b/character/player/player.tscn index b8a7da4..8e026b7 100644 --- a/character/player/player.tscn +++ b/character/player/player.tscn @@ -1,6 +1,7 @@ [gd_scene format=3 uid="uid://bekuuw153mv03"] [ext_resource type="Script" uid="uid://f5ptp3is4agf" path="res://character/player/player.gd" id="1_gtsfv"] +[ext_resource type="Script" uid="uid://baid7qspg2mla" path="res://ui/crosshair.gd" id="2_vuhga"] [ext_resource type="PackedScene" uid="uid://css1vk3u8gt7o" path="res://character/player/assets/mouse.glb" id="2_wu8e1"] [ext_resource type="Script" uid="uid://roaqmma0vjon" path="res://character/player/player_animator.gd" id="3_g20gq"] [ext_resource type="SceneReplicationConfig" uid="uid://c4ubbxjfrrs47" path="res://character/player/player_sync.tres" id="3_wu8e1"] @@ -38,6 +39,19 @@ target_position = Vector3(0, 0.45, 0) [node name="InteractionPos" type="Marker3D" parent="CameraRig/Camera" unique_id=816323614] transform = Transform3D(1, 0, 0, 0, 1, 0, 0, 0, 1, 0, 0, -0.44393378) +[node name="HUD" type="CanvasLayer" parent="CameraRig" unique_id=2008353247] + +[node name="Crosshair" type="Control" parent="CameraRig/HUD" unique_id=1606201608] +layout_mode = 3 +anchors_preset = 15 +anchor_right = 1.0 +anchor_bottom = 1.0 +grow_horizontal = 2 +grow_vertical = 2 +size_flags_horizontal = 4 +size_flags_vertical = 4 +script = ExtResource("2_vuhga") + [node name="Body" type="Node3D" parent="." unique_id=394283421] [node name="mouse" parent="Body" unique_id=1995806863 instance=ExtResource("2_wu8e1")] diff --git a/ui/crosshair.gd b/ui/crosshair.gd new file mode 100644 index 0000000..096c234 --- /dev/null +++ b/ui/crosshair.gd @@ -0,0 +1,57 @@ +@tool +extends Control +## 简易准心:屏幕正中央的一个点,用 _draw() 实时绘制,不依赖任何贴图。 +## +## 挂法:CanvasLayer > Crosshair(Control),Control 的锚点设为「Full Rect」 +## (anchor 全 0/1),这样 size 就等于视口尺寸,中心即屏幕中心。 +## 因为是 CanvasLayer 子节点,在 window/stretch/mode=canvas_items 下会自动跟随缩放。 + +## 点的颜色 +@export var dot_color: Color = Color(1, 1, 1, 0.9): + set(v): + dot_color = v + queue_redraw() + +## 点的半径(像素) +@export_range(0.5, 12.0, 0.5) var dot_radius: float = 2.5: + set(v): + dot_radius = v + queue_redraw() + +## 是否给点画一圈描边(浅色背景上也看得清) +@export var outline: bool = true: + set(v): + outline = v + queue_redraw() + +## 描边颜色 +@export var outline_color: Color = Color(0, 0, 0, 0.6): + set(v): + outline_color = v + queue_redraw() + +## 描边宽度(像素) +@export_range(0.5, 4.0, 0.5) var outline_width: float = 1.0: + set(v): + outline_width = v + queue_redraw() + + +func _ready() -> void: + # 准心不吃鼠标事件,否则会挡住后面的 UI / 拖拽 + mouse_filter = Control.MOUSE_FILTER_IGNORE + queue_redraw() + + +func _notification(what: int) -> void: + # 窗口尺寸变化时重画(stretch 模式下实时跟着变) + if what == NOTIFICATION_RESIZED: + queue_redraw() + + +func _draw() -> void: + var c := size * 0.5 # 控件中心 = 屏幕中心 + + if outline and outline_width > 0.0: + draw_circle(c, dot_radius + outline_width, outline_color) + draw_circle(c, dot_radius, dot_color) diff --git a/ui/crosshair.gd.uid b/ui/crosshair.gd.uid new file mode 100644 index 0000000..5824880 --- /dev/null +++ b/ui/crosshair.gd.uid @@ -0,0 +1 @@ +uid://baid7qspg2mla