From 63e87e86d563c273c292ce333d24d956c9427009 Mon Sep 17 00:00:00 2001 From: 2ndbeam <2ndbeam@disroot.org> Date: Thu, 31 Jul 2025 15:33:31 +0300 Subject: [PATCH] Untested PickupableItem --- base/assets/resources/items/auto_weapon.tres | 10 +++++++ base/assets/resources/items/weapon_base.tres | 10 +++++++ .../interactive/interactive_object.tscn | 7 ++++- base/scenes/interactive/pickupable_item.tscn | 21 +++++++++++++ base/scenes/player.tscn | 30 +++++++++---------- base/scenes/rooms/test.tscn | 13 +++++++- .../interactive/base_pickupable_resource.gd | 13 ++++++++ .../base_pickupable_resource.gd.uid | 1 + .../scripts/interactive/interactive_object.gd | 26 ++++++++++++++++ .../interactive/interactive_object.gd.uid | 1 + base/scripts/interactive/pickupable_item.gd | 13 ++++++++ .../interactive/pickupable_item.gd.uid | 1 + .../interactive/weapon_pickupable_resource.gd | 27 +++++++++++++++++ .../weapon_pickupable_resource.gd.uid | 1 + base/scripts/interactive_object.gd.uid | 1 + base/scripts/player/player.gd | 2 ++ base/scripts/player/weapon_container.gd | 10 +++++++ base/scripts/player/weapon_slot.gd | 28 +++++++++++++++++ base/scripts/weapons/weapon_base.gd | 2 ++ 19 files changed, 200 insertions(+), 17 deletions(-) create mode 100644 base/assets/resources/items/auto_weapon.tres create mode 100644 base/assets/resources/items/weapon_base.tres create mode 100644 base/scenes/interactive/pickupable_item.tscn create mode 100644 base/scripts/interactive/base_pickupable_resource.gd create mode 100644 base/scripts/interactive/base_pickupable_resource.gd.uid create mode 100644 base/scripts/interactive/interactive_object.gd create mode 100644 base/scripts/interactive/interactive_object.gd.uid create mode 100644 base/scripts/interactive/pickupable_item.gd create mode 100644 base/scripts/interactive/pickupable_item.gd.uid create mode 100644 base/scripts/interactive/weapon_pickupable_resource.gd create mode 100644 base/scripts/interactive/weapon_pickupable_resource.gd.uid create mode 100644 base/scripts/interactive_object.gd.uid diff --git a/base/assets/resources/items/auto_weapon.tres b/base/assets/resources/items/auto_weapon.tres new file mode 100644 index 0000000..f133aea --- /dev/null +++ b/base/assets/resources/items/auto_weapon.tres @@ -0,0 +1,10 @@ +[gd_resource type="Resource" script_class="WeaponPickupableResource" load_steps=3 format=3 uid="uid://cdsrjmq8xd5b0"] + +[ext_resource type="Script" uid="uid://dob8q3jclxrtd" path="res://base/scripts/interactive/weapon_pickupable_resource.gd" id="1_7xmtm"] +[ext_resource type="PackedScene" uid="uid://cig5dryfni4f8" path="res://base/scenes/weapons/auto_weapon_test.tscn" id="2_qbjol"] + +[resource] +script = ExtResource("1_7xmtm") +weapon = ExtResource("2_qbjol") +id = &"auto_weapon_test" +metadata/_custom_type_script = "uid://dob8q3jclxrtd" diff --git a/base/assets/resources/items/weapon_base.tres b/base/assets/resources/items/weapon_base.tres new file mode 100644 index 0000000..9d23c26 --- /dev/null +++ b/base/assets/resources/items/weapon_base.tres @@ -0,0 +1,10 @@ +[gd_resource type="Resource" script_class="WeaponPickupableResource" load_steps=3 format=3 uid="uid://b1pqbhcv5ixmy"] + +[ext_resource type="Script" uid="uid://dob8q3jclxrtd" path="res://base/scripts/interactive/weapon_pickupable_resource.gd" id="1_fp2lr"] +[ext_resource type="PackedScene" uid="uid://bb6ovrbusyxpi" path="res://base/scenes/weapons/weapon_base.tscn" id="2_fp2lr"] + +[resource] +script = ExtResource("1_fp2lr") +weapon = ExtResource("2_fp2lr") +id = &"weapon_base" +metadata/_custom_type_script = "uid://dob8q3jclxrtd" diff --git a/base/scenes/interactive/interactive_object.tscn b/base/scenes/interactive/interactive_object.tscn index ca5b9de..2c0bf80 100644 --- a/base/scenes/interactive/interactive_object.tscn +++ b/base/scenes/interactive/interactive_object.tscn @@ -1,6 +1,7 @@ -[gd_scene load_steps=3 format=3 uid="uid://ddjjrkernsobh"] +[gd_scene load_steps=4 format=3 uid="uid://ddjjrkernsobh"] [ext_resource type="Texture2D" uid="uid://bdgoa18kfhlwo" path="res://base/assets/sprites/interactive/interactive.png" id="1_yf10f"] +[ext_resource type="Script" uid="uid://fva8kqc3mk86" path="res://base/scripts/interactive_object.gd" id="2_cdwk3"] [sub_resource type="SphereShape3D" id="SphereShape3D_cdwk3"] @@ -9,8 +10,12 @@ pixel_size = 0.0313 billboard = 1 texture_filter = 0 texture = ExtResource("1_yf10f") +script = ExtResource("2_cdwk3") [node name="Area3D" type="Area3D" parent="."] [node name="CollisionShape3D" type="CollisionShape3D" parent="Area3D"] shape = SubResource("SphereShape3D_cdwk3") + +[connection signal="body_entered" from="Area3D" to="." method="_on_body_entered"] +[connection signal="body_exited" from="Area3D" to="." method="_on_body_exited"] diff --git a/base/scenes/interactive/pickupable_item.tscn b/base/scenes/interactive/pickupable_item.tscn new file mode 100644 index 0000000..8b3070e --- /dev/null +++ b/base/scenes/interactive/pickupable_item.tscn @@ -0,0 +1,21 @@ +[gd_scene load_steps=4 format=3 uid="uid://c4wpq5gxkbor7"] + +[ext_resource type="Texture2D" uid="uid://bdgoa18kfhlwo" path="res://base/assets/sprites/interactive/interactive.png" id="1_2373a"] +[ext_resource type="Script" uid="uid://v2v4keo0ydlc" path="res://base/scripts/interactive/pickupable_item.gd" id="2_2373a"] + +[sub_resource type="SphereShape3D" id="SphereShape3D_cdwk3"] + +[node name="PickupableItem" type="Sprite3D"] +pixel_size = 0.0313 +billboard = 1 +texture_filter = 0 +texture = ExtResource("1_2373a") +script = ExtResource("2_2373a") + +[node name="Area3D" type="Area3D" parent="."] + +[node name="CollisionShape3D" type="CollisionShape3D" parent="Area3D"] +shape = SubResource("SphereShape3D_cdwk3") + +[connection signal="body_entered" from="Area3D" to="." method="_on_body_entered"] +[connection signal="body_exited" from="Area3D" to="." method="_on_body_exited"] diff --git a/base/scenes/player.tscn b/base/scenes/player.tscn index 6a4ec4f..279f6d1 100644 --- a/base/scenes/player.tscn +++ b/base/scenes/player.tscn @@ -9,6 +9,21 @@ [sub_resource type="CapsuleShape3D" id="CapsuleShape3D_jjqxs"] +[sub_resource type="Animation" id="Animation_gt0rj"] +length = 0.001 +tracks/0/type = "value" +tracks/0/imported = false +tracks/0/enabled = true +tracks/0/path = NodePath("HUD/Weapon:position") +tracks/0/interp = 1 +tracks/0/loop_wrap = true +tracks/0/keys = { +"times": PackedFloat32Array(0), +"transitions": PackedFloat32Array(1), +"update": 0, +"values": [Vector2(0, 0)] +} + [sub_resource type="Animation" id="Animation_8sdfx"] resource_name = "default" length = 1.33334 @@ -27,21 +42,6 @@ tracks/0/keys = { "values": [Vector2(0, 0), Vector2(16, 32), Vector2(0, 0), Vector2(32, 32), Vector2(0, 0)] } -[sub_resource type="Animation" id="Animation_gt0rj"] -length = 0.001 -tracks/0/type = "value" -tracks/0/imported = false -tracks/0/enabled = true -tracks/0/path = NodePath("HUD/Weapon:position") -tracks/0/interp = 1 -tracks/0/loop_wrap = true -tracks/0/keys = { -"times": PackedFloat32Array(0), -"transitions": PackedFloat32Array(1), -"update": 0, -"values": [Vector2(0, 0)] -} - [sub_resource type="Animation" id="Animation_juj2l"] resource_name = "static" step = 0.0 diff --git a/base/scenes/rooms/test.tscn b/base/scenes/rooms/test.tscn index 6a29623..a96c1ca 100644 --- a/base/scenes/rooms/test.tscn +++ b/base/scenes/rooms/test.tscn @@ -1,4 +1,7 @@ -[gd_scene format=3 uid="uid://bgnb01j1nphhi"] +[gd_scene load_steps=3 format=3 uid="uid://bgnb01j1nphhi"] + +[ext_resource type="PackedScene" uid="uid://c4wpq5gxkbor7" path="res://base/scenes/interactive/pickupable_item.tscn" id="1_1whpt"] +[ext_resource type="Resource" uid="uid://b1pqbhcv5ixmy" path="res://base/assets/resources/items/weapon_base.tres" id="2_ayew2"] [node name="Test Room" type="Node3D"] @@ -41,3 +44,11 @@ size = Vector3(0.2, 4, 4) [node name="SpotLight3D" type="SpotLight3D" parent="."] transform = Transform3D(1, 0, 0, 0, -4.37114e-08, 1, 0, -1, -4.37114e-08, 0, 2.6, 0) spot_angle = 90.0 + +[node name="PickupableItem" parent="." instance=ExtResource("1_1whpt")] +transform = Transform3D(1, 0, 0, 0, 1, 0, 0, 0, 1, -0.992068, -0.47008, -0.800458) +content = ExtResource("2_ayew2") + +[node name="PickupableItem2" parent="." instance=ExtResource("1_1whpt")] +transform = Transform3D(1, 0, 0, 0, 1, 0, 0, 0, 1, 0.700438, -0.47008, -0.800458) +content = ExtResource("2_ayew2") diff --git a/base/scripts/interactive/base_pickupable_resource.gd b/base/scripts/interactive/base_pickupable_resource.gd new file mode 100644 index 0000000..428b0d3 --- /dev/null +++ b/base/scripts/interactive/base_pickupable_resource.gd @@ -0,0 +1,13 @@ +extends Resource + +class_name BasePickupableResource + +## Item ID, make sure it's unique +@export var id: StringName + +## Texture that will be used in node sprite +@export var texture: Texture2D + +## Emitted when item picked up. Returns if PickupableItem should be freed +func _apply(_player: Player) -> bool: + return true diff --git a/base/scripts/interactive/base_pickupable_resource.gd.uid b/base/scripts/interactive/base_pickupable_resource.gd.uid new file mode 100644 index 0000000..8de29d0 --- /dev/null +++ b/base/scripts/interactive/base_pickupable_resource.gd.uid @@ -0,0 +1 @@ +uid://cfovybsk5c606 diff --git a/base/scripts/interactive/interactive_object.gd b/base/scripts/interactive/interactive_object.gd new file mode 100644 index 0000000..f81577d --- /dev/null +++ b/base/scripts/interactive/interactive_object.gd @@ -0,0 +1,26 @@ +extends Sprite3D + +class_name InteractiveObject + +var player: Player = null + +func _ready() -> void: + pass + +func _process(_delta: float) -> void: + if player == null: + return + if Input.is_action_just_pressed('interact'): + _interact(player) + +func _on_body_entered(body: Node3D) -> void: + if body is Player: + player = body + +func _on_body_exited(body: Node3D) -> void: + if body is Player: + player = null + +## Invoked when interact action was used when player is in object's area +func _interact(_player: Player) -> void: + pass diff --git a/base/scripts/interactive/interactive_object.gd.uid b/base/scripts/interactive/interactive_object.gd.uid new file mode 100644 index 0000000..0a89033 --- /dev/null +++ b/base/scripts/interactive/interactive_object.gd.uid @@ -0,0 +1 @@ +uid://junnt60g6c7x diff --git a/base/scripts/interactive/pickupable_item.gd b/base/scripts/interactive/pickupable_item.gd new file mode 100644 index 0000000..1abcbc5 --- /dev/null +++ b/base/scripts/interactive/pickupable_item.gd @@ -0,0 +1,13 @@ +extends InteractiveObject + +class_name PickupableItem + +@export var content: BasePickupableResource + +func _ready() -> void: + if content.texture != null: + texture = content.texture + +func _interact(_player: Player) -> void: + if content._apply(_player): + queue_free() diff --git a/base/scripts/interactive/pickupable_item.gd.uid b/base/scripts/interactive/pickupable_item.gd.uid new file mode 100644 index 0000000..1532bbb --- /dev/null +++ b/base/scripts/interactive/pickupable_item.gd.uid @@ -0,0 +1 @@ +uid://v2v4keo0ydlc diff --git a/base/scripts/interactive/weapon_pickupable_resource.gd b/base/scripts/interactive/weapon_pickupable_resource.gd new file mode 100644 index 0000000..c6bd77b --- /dev/null +++ b/base/scripts/interactive/weapon_pickupable_resource.gd @@ -0,0 +1,27 @@ +extends BasePickupableResource + +class_name WeaponPickupableResource + +## Weapon that will be added on interaction +@export var weapon: PackedScene + +func _apply(player: Player) -> bool: + var slot = player.weapons.first_free_slot() + + # TODO: Implement proper swapping behavior when old or new weapon uses several slots + if slot == null: + slot = player.weapons.current_slot + + var set_data = slot.set_weapon(weapon) + set_data.old_weapon.id = id + + if slot == player.weapons.current_slot: + player.weapons.refresh_current_slot() + + return update_by_id(set_data.new_weapon) + +# TODO: implement proper updating +func update_by_id(new_id: StringName) -> bool: + id = new_id + + return id == "" diff --git a/base/scripts/interactive/weapon_pickupable_resource.gd.uid b/base/scripts/interactive/weapon_pickupable_resource.gd.uid new file mode 100644 index 0000000..7a84fca --- /dev/null +++ b/base/scripts/interactive/weapon_pickupable_resource.gd.uid @@ -0,0 +1 @@ +uid://dob8q3jclxrtd diff --git a/base/scripts/interactive_object.gd.uid b/base/scripts/interactive_object.gd.uid new file mode 100644 index 0000000..d69e7fa --- /dev/null +++ b/base/scripts/interactive_object.gd.uid @@ -0,0 +1 @@ +uid://fva8kqc3mk86 diff --git a/base/scripts/player/player.gd b/base/scripts/player/player.gd index 5364d73..e909f2c 100644 --- a/base/scripts/player/player.gd +++ b/base/scripts/player/player.gd @@ -1,5 +1,7 @@ extends CharacterBody3D +class_name Player + @export var speed = 100.0 @export var fall_acceleration = 75.0 @export var vertical_sensivity = 0.005 diff --git a/base/scripts/player/weapon_container.gd b/base/scripts/player/weapon_container.gd index 92c5cd8..3e53281 100644 --- a/base/scripts/player/weapon_container.gd +++ b/base/scripts/player/weapon_container.gd @@ -27,3 +27,13 @@ func select_slot(index: int): current_slot = slots[index] current_weapon = current_slot.weapon slot_selected.emit() + +func first_free_slot() -> WeaponSlot: + for slot in slots: + if not slot.has_weapon: + return slot + return null + +func refresh_current_slot() -> void: + var index = slots.find(current_slot) + select_slot(index) diff --git a/base/scripts/player/weapon_slot.gd b/base/scripts/player/weapon_slot.gd index 11e3bc6..e1de34f 100644 --- a/base/scripts/player/weapon_slot.gd +++ b/base/scripts/player/weapon_slot.gd @@ -5,6 +5,17 @@ class_name WeaponSlot var has_weapon = false var weapon: Weapon +## Contains data about swapped weapons +class WeaponSetData: + ## New Weapon node, may be null + var new_weapon: Weapon + ## Old weapon id, may be empty string + var old_weapon: StringName + + func _init(_new_weapon: Weapon, _old_weapon: StringName): + new_weapon = _new_weapon + old_weapon = _old_weapon + func _ready(): has_weapon = get_child_count() > 0 @@ -12,3 +23,20 @@ func _ready(): var child = get_child(0) assert(child is Weapon) weapon = child as Weapon + +func set_weapon(new_weapon: PackedScene) -> WeaponSetData: + var weapon_inst = null + if new_weapon != null: + weapon_inst = new_weapon.instantiate() as Weapon + add_child(weapon_inst) + + var old_weapon_id = drop_weapon() + return WeaponSetData.new(weapon_inst, old_weapon_id) + +func drop_weapon() -> StringName: + var id = "" + if has_weapon: + id = weapon.id + weapon.queue_free() + _ready() + return id diff --git a/base/scripts/weapons/weapon_base.gd b/base/scripts/weapons/weapon_base.gd index 226ef40..6d4527a 100644 --- a/base/scripts/weapons/weapon_base.gd +++ b/base/scripts/weapons/weapon_base.gd @@ -6,6 +6,8 @@ signal fired() signal fire_failed() signal fire_allowed() +var id: StringName + @onready var barrel = $"Barrel" @export var uses_hands: Array[CommandQueue.Side]