equipped weapon; health; death; test enemy; weapon cooldown
This commit is contained in:
parent
5c4c0384ba
commit
27bd064c15
22 changed files with 521 additions and 92 deletions
|
@ -27,9 +27,15 @@ class Some extends Option:
|
||||||
func _init(val: Variant) -> void:
|
func _init(val: Variant) -> void:
|
||||||
value = val
|
value = val
|
||||||
|
|
||||||
func chain(fn: Callable) -> Option:
|
func and_then(fn: Callable) -> Option:
|
||||||
return fn.call(value)
|
return fn.call(value)
|
||||||
|
|
||||||
|
func and_other(other: Option) -> Option:
|
||||||
|
return other
|
||||||
|
|
||||||
|
func contains(target_value: Variant) -> bool:
|
||||||
|
return value == target_value
|
||||||
|
|
||||||
func filter(fn: Callable) -> Option:
|
func filter(fn: Callable) -> Option:
|
||||||
if fn.call(value): return self
|
if fn.call(value): return self
|
||||||
else: return Option.none
|
else: return Option.none
|
||||||
|
@ -42,24 +48,49 @@ class Some extends Option:
|
||||||
func map(fn: Callable) -> Option:
|
func map(fn: Callable) -> Option:
|
||||||
return Option.some(fn.call(value))
|
return Option.some(fn.call(value))
|
||||||
|
|
||||||
|
func ok_or(_err: Variant) -> Result:
|
||||||
|
return Result.ok(value)
|
||||||
|
|
||||||
|
func ok_or_else(fn: Callable) -> Result:
|
||||||
|
return Result.ok(value)
|
||||||
|
|
||||||
|
func or_other(option: Option) -> Option:
|
||||||
|
return self
|
||||||
|
|
||||||
|
func inspect(fn: Callable) -> Option:
|
||||||
|
fn.call(value)
|
||||||
|
return self
|
||||||
|
|
||||||
func is_some() -> bool:
|
func is_some() -> bool:
|
||||||
return true
|
return true
|
||||||
|
|
||||||
func is_none() -> bool:
|
func is_none() -> bool:
|
||||||
return false
|
return false
|
||||||
|
|
||||||
func or_default(_default_value: Variant) -> Variant:
|
|
||||||
return value
|
|
||||||
|
|
||||||
func or_else(_fn: Callable) -> Variant:
|
|
||||||
return value
|
|
||||||
|
|
||||||
func unwrap() -> Variant:
|
func unwrap() -> Variant:
|
||||||
return value
|
return value
|
||||||
|
|
||||||
class None extends Option:
|
func unwrap_or(_default_value: Variant) -> Variant:
|
||||||
func chain(_fn: Callable) -> Option:
|
return value
|
||||||
|
|
||||||
|
func unwrap_or_else(_fn: Callable) -> Variant:
|
||||||
|
return value
|
||||||
|
|
||||||
|
func xor_other(other: Option) -> Option:
|
||||||
|
if other.is_none():
|
||||||
return self
|
return self
|
||||||
|
else:
|
||||||
|
return Option.none
|
||||||
|
|
||||||
|
class None extends Option:
|
||||||
|
func and_then(_fn: Callable) -> Option:
|
||||||
|
return self
|
||||||
|
|
||||||
|
func and_other(other: Option) -> Option:
|
||||||
|
return self
|
||||||
|
|
||||||
|
func contains(value: Variant) -> bool:
|
||||||
|
return false
|
||||||
|
|
||||||
func filter(_f: Callable) -> Option:
|
func filter(_f: Callable) -> Option:
|
||||||
return self
|
return self
|
||||||
|
@ -70,18 +101,36 @@ class None extends Option:
|
||||||
func map(_fn: Callable) -> Option:
|
func map(_fn: Callable) -> Option:
|
||||||
return self
|
return self
|
||||||
|
|
||||||
|
func ok_or(err: Variant) -> Result:
|
||||||
|
return Result.err(err)
|
||||||
|
|
||||||
|
func ok_or_else(fn: Callable) -> Result:
|
||||||
|
return Result.err(fn.call())
|
||||||
|
|
||||||
|
func or_other(option: Option) -> Option:
|
||||||
|
return option
|
||||||
|
|
||||||
|
func inspect(_fn: Callable) -> Option:
|
||||||
|
return self
|
||||||
|
|
||||||
func is_some() -> bool:
|
func is_some() -> bool:
|
||||||
return false
|
return false
|
||||||
|
|
||||||
func is_none() -> bool:
|
func is_none() -> bool:
|
||||||
return true
|
return true
|
||||||
|
|
||||||
func or_default(default_value: Variant) -> Variant:
|
|
||||||
return default_value
|
|
||||||
|
|
||||||
func or_else(fn: Callable) -> Variant:
|
|
||||||
return fn.call()
|
|
||||||
|
|
||||||
func unwrap() -> Variant:
|
func unwrap() -> Variant:
|
||||||
assert(false, "Called unwrap() on a None value")
|
assert(false, "Called unwrap() on a None value")
|
||||||
return null
|
return null
|
||||||
|
|
||||||
|
func unwrap_or(default_value: Variant) -> Variant:
|
||||||
|
return default_value
|
||||||
|
|
||||||
|
func unwrap_or_else(fn: Callable) -> Variant:
|
||||||
|
return fn.call()
|
||||||
|
|
||||||
|
func xor_other(other: Option) -> Option:
|
||||||
|
if other.is_some():
|
||||||
|
return other
|
||||||
|
else:
|
||||||
|
return self
|
||||||
|
|
BIN
godot/assets/mann.glb
Normal file
BIN
godot/assets/mann.glb
Normal file
Binary file not shown.
44
godot/assets/mann.glb.import
Normal file
44
godot/assets/mann.glb.import
Normal file
|
@ -0,0 +1,44 @@
|
||||||
|
[remap]
|
||||||
|
|
||||||
|
importer="scene"
|
||||||
|
importer_version=1
|
||||||
|
type="PackedScene"
|
||||||
|
uid="uid://cyrwuqefk3efr"
|
||||||
|
path="res://.godot/imported/mann.glb-288e378e28910734d9c899c96305cd64.scn"
|
||||||
|
|
||||||
|
[deps]
|
||||||
|
|
||||||
|
source_file="res://assets/mann.glb"
|
||||||
|
dest_files=["res://.godot/imported/mann.glb-288e378e28910734d9c899c96305cd64.scn"]
|
||||||
|
|
||||||
|
[params]
|
||||||
|
|
||||||
|
nodes/root_type=""
|
||||||
|
nodes/root_name=""
|
||||||
|
nodes/apply_root_scale=true
|
||||||
|
nodes/root_scale=0.008
|
||||||
|
nodes/import_as_skeleton_bones=false
|
||||||
|
nodes/use_node_type_suffixes=true
|
||||||
|
meshes/ensure_tangents=true
|
||||||
|
meshes/generate_lods=true
|
||||||
|
meshes/create_shadow_meshes=true
|
||||||
|
meshes/light_baking=1
|
||||||
|
meshes/lightmap_texel_size=0.2
|
||||||
|
meshes/force_disable_compression=false
|
||||||
|
skins/use_named_skins=true
|
||||||
|
animation/import=true
|
||||||
|
animation/fps=30
|
||||||
|
animation/trimming=false
|
||||||
|
animation/remove_immutable_tracks=true
|
||||||
|
animation/import_rest_as_RESET=false
|
||||||
|
import_script/path=""
|
||||||
|
_subresources={
|
||||||
|
"nodes": {
|
||||||
|
"PATH:AnimationPlayer": {
|
||||||
|
"import_tracks/position": 0,
|
||||||
|
"import_tracks/scale": 2
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
gltf/naming_version=1
|
||||||
|
gltf/embedded_image_handling=1
|
BIN
godot/assets/mann_0.png
Normal file
BIN
godot/assets/mann_0.png
Normal file
Binary file not shown.
After Width: | Height: | Size: 12 MiB |
38
godot/assets/mann_0.png.import
Normal file
38
godot/assets/mann_0.png.import
Normal file
|
@ -0,0 +1,38 @@
|
||||||
|
[remap]
|
||||||
|
|
||||||
|
importer="texture"
|
||||||
|
type="CompressedTexture2D"
|
||||||
|
uid="uid://c3upx1jyltix0"
|
||||||
|
path.s3tc="res://.godot/imported/mann_0.png-0eec56285f3b8080c8323d0defc178e9.s3tc.ctex"
|
||||||
|
metadata={
|
||||||
|
"imported_formats": ["s3tc_bptc"],
|
||||||
|
"vram_texture": true
|
||||||
|
}
|
||||||
|
generator_parameters={
|
||||||
|
"md5": "8af17aa62c9ee95592da5f3e6e42fcf1"
|
||||||
|
}
|
||||||
|
|
||||||
|
[deps]
|
||||||
|
|
||||||
|
source_file="res://assets/mann_0.png"
|
||||||
|
dest_files=["res://.godot/imported/mann_0.png-0eec56285f3b8080c8323d0defc178e9.s3tc.ctex"]
|
||||||
|
|
||||||
|
[params]
|
||||||
|
|
||||||
|
compress/mode=2
|
||||||
|
compress/high_quality=false
|
||||||
|
compress/lossy_quality=0.7
|
||||||
|
compress/hdr_compression=1
|
||||||
|
compress/normal_map=0
|
||||||
|
compress/channel_pack=0
|
||||||
|
mipmaps/generate=true
|
||||||
|
mipmaps/limit=-1
|
||||||
|
roughness/mode=0
|
||||||
|
roughness/src_normal=""
|
||||||
|
process/fix_alpha_border=true
|
||||||
|
process/premult_alpha=false
|
||||||
|
process/normal_map_invert_y=false
|
||||||
|
process/hdr_as_srgb=false
|
||||||
|
process/hdr_clamp_exposure=false
|
||||||
|
process/size_limit=0
|
||||||
|
detect_3d/compress_to=0
|
BIN
godot/assets/mann_1.png
Normal file
BIN
godot/assets/mann_1.png
Normal file
Binary file not shown.
After Width: | Height: | Size: 22 MiB |
38
godot/assets/mann_1.png.import
Normal file
38
godot/assets/mann_1.png.import
Normal file
|
@ -0,0 +1,38 @@
|
||||||
|
[remap]
|
||||||
|
|
||||||
|
importer="texture"
|
||||||
|
type="CompressedTexture2D"
|
||||||
|
uid="uid://b14nebibcf2g6"
|
||||||
|
path.s3tc="res://.godot/imported/mann_1.png-93592f6ed267c9cdc1a955fda87a4e91.s3tc.ctex"
|
||||||
|
metadata={
|
||||||
|
"imported_formats": ["s3tc_bptc"],
|
||||||
|
"vram_texture": true
|
||||||
|
}
|
||||||
|
generator_parameters={
|
||||||
|
"md5": "018299a57123ad32d2eaf390dda03ca7"
|
||||||
|
}
|
||||||
|
|
||||||
|
[deps]
|
||||||
|
|
||||||
|
source_file="res://assets/mann_1.png"
|
||||||
|
dest_files=["res://.godot/imported/mann_1.png-93592f6ed267c9cdc1a955fda87a4e91.s3tc.ctex"]
|
||||||
|
|
||||||
|
[params]
|
||||||
|
|
||||||
|
compress/mode=2
|
||||||
|
compress/high_quality=false
|
||||||
|
compress/lossy_quality=0.7
|
||||||
|
compress/hdr_compression=1
|
||||||
|
compress/normal_map=1
|
||||||
|
compress/channel_pack=0
|
||||||
|
mipmaps/generate=true
|
||||||
|
mipmaps/limit=-1
|
||||||
|
roughness/mode=1
|
||||||
|
roughness/src_normal="res://assets/mann_1.png"
|
||||||
|
process/fix_alpha_border=true
|
||||||
|
process/premult_alpha=false
|
||||||
|
process/normal_map_invert_y=false
|
||||||
|
process/hdr_as_srgb=false
|
||||||
|
process/hdr_clamp_exposure=false
|
||||||
|
process/size_limit=0
|
||||||
|
detect_3d/compress_to=0
|
85
godot/scenes/enemy.tscn
Normal file
85
godot/scenes/enemy.tscn
Normal file
|
@ -0,0 +1,85 @@
|
||||||
|
[gd_scene load_steps=10 format=3 uid="uid://c0cf6jkxasplk"]
|
||||||
|
|
||||||
|
[ext_resource type="PackedScene" uid="uid://cyrwuqefk3efr" path="res://assets/mann.glb" id="2_4ra3w"]
|
||||||
|
[ext_resource type="Script" uid="uid://d4anpy5efe22d" path="res://src/health.gd" id="2_md0e3"]
|
||||||
|
|
||||||
|
[sub_resource type="CapsuleShape3D" id="CapsuleShape3D_md0e3"]
|
||||||
|
|
||||||
|
[sub_resource type="AnimationNodeAnimation" id="AnimationNodeAnimation_md0e3"]
|
||||||
|
animation = &"HeadHit"
|
||||||
|
|
||||||
|
[sub_resource type="AnimationNodeAnimation" id="AnimationNodeAnimation_4ra3w"]
|
||||||
|
animation = &"DyingBackwards"
|
||||||
|
|
||||||
|
[sub_resource type="AnimationNodeAnimation" id="AnimationNodeAnimation_5uy6h"]
|
||||||
|
animation = &"T-Pose (No Animation)"
|
||||||
|
|
||||||
|
[sub_resource type="AnimationNodeOneShot" id="AnimationNodeOneShot_c4w8v"]
|
||||||
|
|
||||||
|
[sub_resource type="AnimationNodeTransition" id="AnimationNodeTransition_xwavj"]
|
||||||
|
input_0/name = "idle"
|
||||||
|
input_0/auto_advance = false
|
||||||
|
input_0/break_loop_at_end = false
|
||||||
|
input_0/reset = true
|
||||||
|
input_1/name = "dead"
|
||||||
|
input_1/auto_advance = false
|
||||||
|
input_1/break_loop_at_end = false
|
||||||
|
input_1/reset = true
|
||||||
|
|
||||||
|
[sub_resource type="AnimationNodeBlendTree" id="AnimationNodeBlendTree_nenq2"]
|
||||||
|
graph_offset = Vector2(-685.25, 50.2044)
|
||||||
|
nodes/Animation/node = SubResource("AnimationNodeAnimation_5uy6h")
|
||||||
|
nodes/Animation/position = Vector2(-220, 120)
|
||||||
|
"nodes/Animation 2/node" = SubResource("AnimationNodeAnimation_md0e3")
|
||||||
|
"nodes/Animation 2/position" = Vector2(-140, 320)
|
||||||
|
"nodes/Animation 3/node" = SubResource("AnimationNodeAnimation_4ra3w")
|
||||||
|
"nodes/Animation 3/position" = Vector2(60, 420)
|
||||||
|
nodes/Hit/node = SubResource("AnimationNodeOneShot_c4w8v")
|
||||||
|
nodes/Hit/position = Vector2(60, 120)
|
||||||
|
nodes/Transition/node = SubResource("AnimationNodeTransition_xwavj")
|
||||||
|
nodes/Transition/position = Vector2(260, 120)
|
||||||
|
nodes/output/position = Vector2(440, 120)
|
||||||
|
node_connections = [&"Hit", 0, &"Animation", &"Hit", 1, &"Animation 2", &"Transition", 0, &"Hit", &"Transition", 1, &"Animation 3", &"output", 0, &"Transition"]
|
||||||
|
|
||||||
|
[node name="Enemy" type="CharacterBody3D"]
|
||||||
|
transform = Transform3D(1.75, 0, 0, 0, 1.75, 0, 0, 0, 1.75, 0, 0, 0)
|
||||||
|
|
||||||
|
[node name="CollisionShape3D" type="CollisionShape3D" parent="."]
|
||||||
|
transform = Transform3D(1, 0, 0, 0, 1, 0, 0, 0, 1, 0, 1, 0)
|
||||||
|
shape = SubResource("CapsuleShape3D_md0e3")
|
||||||
|
|
||||||
|
[node name="Health" type="Node" parent="."]
|
||||||
|
script = ExtResource("2_md0e3")
|
||||||
|
max_health = 5
|
||||||
|
metadata/_custom_type_script = "uid://d4anpy5efe22d"
|
||||||
|
|
||||||
|
[node name="AnimationTree" type="AnimationTree" parent="."]
|
||||||
|
root_node = NodePath("../AuxScene")
|
||||||
|
tree_root = SubResource("AnimationNodeBlendTree_nenq2")
|
||||||
|
anim_player = NodePath("../AuxScene/AnimationPlayer")
|
||||||
|
parameters/Hit/active = false
|
||||||
|
parameters/Hit/internal_active = false
|
||||||
|
parameters/Hit/request = 0
|
||||||
|
parameters/Transition/current_state = "idle"
|
||||||
|
parameters/Transition/transition_request = ""
|
||||||
|
parameters/Transition/current_index = 0
|
||||||
|
|
||||||
|
[node name="AuxScene" parent="." instance=ExtResource("2_4ra3w")]
|
||||||
|
transform = Transform3D(1, 0, 0, 0, 1, 0, 0, 0, 1, 0, 0.708055, 0)
|
||||||
|
|
||||||
|
[node name="Skeleton3D" parent="AuxScene/Node" index="0"]
|
||||||
|
bones/14/rotation = Quaternion(-0.049153, -0.00278018, 0.056403, 0.997194)
|
||||||
|
bones/30/rotation = Quaternion(-0.00214526, -6.9426e-18, 1.71983e-18, 0.999998)
|
||||||
|
bones/33/rotation = Quaternion(0.0397321, 6.93342e-18, -2.75697e-19, 0.99921)
|
||||||
|
bones/39/rotation = Quaternion(0.0548733, -0.109425, -0.0279963, 0.992084)
|
||||||
|
bones/45/rotation = Quaternion(0.0420007, -5.82877e-19, -1.38655e-17, 0.999118)
|
||||||
|
bones/46/rotation = Quaternion(-0.00160061, -2.22129e-20, 1.38778e-17, 0.999999)
|
||||||
|
bones/50/rotation = Quaternion(-0.027251, 0, 0, 0.999629)
|
||||||
|
bones/52/rotation = Quaternion(0.0706924, 0.00317808, 0.0447985, 0.996487)
|
||||||
|
bones/56/rotation = Quaternion(0.0852392, 0.00496034, 0.0578828, 0.994665)
|
||||||
|
bones/61/rotation = Quaternion(-0.00265969, 1.04465e-05, -0.0039276, 0.999989)
|
||||||
|
|
||||||
|
[connection signal="damaged" from="Health" to="AnimationTree" method="set" binds= ["parameters/Hit/request", 1]]
|
||||||
|
[connection signal="died" from="Health" to="AnimationTree" method="set" binds= ["parameters/Transition/transition_request", "dead"]]
|
||||||
|
|
||||||
|
[editable path="AuxScene"]
|
|
@ -1,4 +1,4 @@
|
||||||
[gd_scene load_steps=15 format=3 uid="uid://dttyp3682enn7"]
|
[gd_scene load_steps=16 format=3 uid="uid://dttyp3682enn7"]
|
||||||
|
|
||||||
[ext_resource type="PackedScene" uid="uid://crbrniwi6kd3p" path="res://scenes/player.tscn" id="1_2q6dc"]
|
[ext_resource type="PackedScene" uid="uid://crbrniwi6kd3p" path="res://scenes/player.tscn" id="1_2q6dc"]
|
||||||
[ext_resource type="Script" uid="uid://csjccrhj5wnx7" path="res://addons/phantom_camera/scripts/phantom_camera/phantom_camera_3d.gd" id="2_klq6b"]
|
[ext_resource type="Script" uid="uid://csjccrhj5wnx7" path="res://addons/phantom_camera/scripts/phantom_camera/phantom_camera_3d.gd" id="2_klq6b"]
|
||||||
|
@ -9,6 +9,7 @@
|
||||||
[ext_resource type="Script" uid="uid://cdvtrsqkkxtdd" path="res://src/persistence.gd" id="4_mx8sn"]
|
[ext_resource type="Script" uid="uid://cdvtrsqkkxtdd" path="res://src/persistence.gd" id="4_mx8sn"]
|
||||||
[ext_resource type="Resource" uid="uid://cqfnwpmo4fyv4" path="res://resources/items/key.tres" id="7_8c41q"]
|
[ext_resource type="Resource" uid="uid://cqfnwpmo4fyv4" path="res://resources/items/key.tres" id="7_8c41q"]
|
||||||
[ext_resource type="PackedScene" uid="uid://cn7tgd4y67wnd" path="res://scenes/inventory.tscn" id="8_b121j"]
|
[ext_resource type="PackedScene" uid="uid://cn7tgd4y67wnd" path="res://scenes/inventory.tscn" id="8_b121j"]
|
||||||
|
[ext_resource type="PackedScene" uid="uid://c0cf6jkxasplk" path="res://scenes/enemy.tscn" id="10_olg7q"]
|
||||||
|
|
||||||
[sub_resource type="PlaneMesh" id="PlaneMesh_rd3vj"]
|
[sub_resource type="PlaneMesh" id="PlaneMesh_rd3vj"]
|
||||||
|
|
||||||
|
@ -113,6 +114,10 @@ text = "Load
|
||||||
[node name="Inventory" parent="CanvasLayer" instance=ExtResource("8_b121j")]
|
[node name="Inventory" parent="CanvasLayer" instance=ExtResource("8_b121j")]
|
||||||
visible = false
|
visible = false
|
||||||
|
|
||||||
|
[node name="Enemy" parent="." instance=ExtResource("10_olg7q")]
|
||||||
|
transform = Transform3D(1.75, 0, 0, 0, 1.75, 0, 0, 0, 1.75, 6, 0, 0)
|
||||||
|
|
||||||
|
[connection signal="opened" from="Door" to="Door" method="hide"]
|
||||||
[connection signal="interacted" from="Door/Interactable" to="Door" method="_on_interact"]
|
[connection signal="interacted" from="Door/Interactable" to="Door" method="_on_interact"]
|
||||||
[connection signal="pressed" from="CanvasLayer/Control/HBoxContainer/SaveButton" to="CanvasLayer/Control/Persistence" method="save" binds= ["save1.sav"]]
|
[connection signal="pressed" from="CanvasLayer/Control/HBoxContainer/SaveButton" to="CanvasLayer/Control/Persistence" method="save" binds= ["save1.sav"]]
|
||||||
[connection signal="pressed" from="CanvasLayer/Control/HBoxContainer/LoadButton" to="CanvasLayer/Control/Persistence" method="load" binds= ["save1.sav"]]
|
[connection signal="pressed" from="CanvasLayer/Control/HBoxContainer/LoadButton" to="CanvasLayer/Control/Persistence" method="load" binds= ["save1.sav"]]
|
||||||
|
|
31
godot/scenes/pistol.tscn
Normal file
31
godot/scenes/pistol.tscn
Normal file
|
@ -0,0 +1,31 @@
|
||||||
|
[gd_scene load_steps=4 format=3 uid="uid://isqkayrtr7t8"]
|
||||||
|
|
||||||
|
[ext_resource type="Script" uid="uid://bn7dr8s404qnf" path="res://src/usable.gd" id="1_1e3ry"]
|
||||||
|
[ext_resource type="PackedScene" uid="uid://5a023hrws3gx" path="res://assets/Glock 17 Gen 4/Main.glb" id="1_igbvm"]
|
||||||
|
[ext_resource type="Script" uid="uid://ddqif2gmm1ec2" path="res://src/damage_source.gd" id="2_buff3"]
|
||||||
|
|
||||||
|
[node name="Pistol" type="Node3D"]
|
||||||
|
script = ExtResource("1_1e3ry")
|
||||||
|
|
||||||
|
[node name="Main" parent="." instance=ExtResource("1_igbvm")]
|
||||||
|
|
||||||
|
[node name="RayCast3D" type="RayCast3D" parent="."]
|
||||||
|
transform = Transform3D(1, 0, 0, 0, 1, 0, 0, 0, 1, 0, 0.5, -1.25)
|
||||||
|
target_position = Vector3(0, 0, -100)
|
||||||
|
debug_shape_custom_color = Color(1, 0, 0, 1)
|
||||||
|
debug_shape_thickness = 1
|
||||||
|
|
||||||
|
[node name="DamageSource" type="Node" parent="." node_paths=PackedStringArray("raycast")]
|
||||||
|
script = ExtResource("2_buff3")
|
||||||
|
damage = 1
|
||||||
|
raycast = NodePath("../RayCast3D")
|
||||||
|
metadata/_custom_type_script = "uid://ddqif2gmm1ec2"
|
||||||
|
|
||||||
|
[node name="Timer" type="Timer" parent="."]
|
||||||
|
wait_time = 0.5
|
||||||
|
one_shot = true
|
||||||
|
|
||||||
|
[connection signal="used" from="." to="." method="disable"]
|
||||||
|
[connection signal="used" from="." to="DamageSource" method="try_damage"]
|
||||||
|
[connection signal="used" from="." to="Timer" method="start"]
|
||||||
|
[connection signal="timeout" from="Timer" to="." method="enable"]
|
|
@ -1,11 +1,13 @@
|
||||||
[gd_scene load_steps=44 format=3 uid="uid://crbrniwi6kd3p"]
|
[gd_scene load_steps=49 format=3 uid="uid://crbrniwi6kd3p"]
|
||||||
|
|
||||||
[ext_resource type="PackedScene" uid="uid://dpmbimh6m4ari" path="res://scenes/player_mesh.tscn" id="1_3vyb7"]
|
[ext_resource type="PackedScene" uid="uid://dpmbimh6m4ari" path="res://scenes/player_mesh.tscn" id="1_3vyb7"]
|
||||||
[ext_resource type="Script" uid="uid://d1drx1b1s1evy" path="res://src/player.gd" id="1_qhqgy"]
|
[ext_resource type="Script" uid="uid://50vv0ta67tgl" path="res://src/player.gd" id="1_qhqgy"]
|
||||||
[ext_resource type="Script" uid="uid://877g2wvcupw6" path="res://src/player_input.gd" id="3_dqkch"]
|
[ext_resource type="Script" uid="uid://877g2wvcupw6" path="res://src/player_input.gd" id="3_dqkch"]
|
||||||
[ext_resource type="Script" uid="uid://c3wlcxy4vnm2i" path="res://src/interactor.gd" id="4_dqkch"]
|
[ext_resource type="Script" uid="uid://c3wlcxy4vnm2i" path="res://src/interactor.gd" id="4_dqkch"]
|
||||||
[ext_resource type="Script" uid="uid://csjl56hf0fnoy" path="res://src/item_container.gd" id="5_qlg0r"]
|
[ext_resource type="Script" uid="uid://csjl56hf0fnoy" path="res://src/item_container.gd" id="5_qlg0r"]
|
||||||
[ext_resource type="Resource" uid="uid://bllq6ri54q3ne" path="res://resources/player_inventory.tres" id="6_tuyoq"]
|
[ext_resource type="Resource" uid="uid://bllq6ri54q3ne" path="res://resources/player_inventory.tres" id="6_tuyoq"]
|
||||||
|
[ext_resource type="PackedScene" uid="uid://isqkayrtr7t8" path="res://scenes/pistol.tscn" id="7_fjrip"]
|
||||||
|
[ext_resource type="Script" uid="uid://c710qg683rqbc" path="res://src/equipment.gd" id="7_ur7pv"]
|
||||||
|
|
||||||
[sub_resource type="SphereShape3D" id="SphereShape3D_qhqgy"]
|
[sub_resource type="SphereShape3D" id="SphereShape3D_qhqgy"]
|
||||||
|
|
||||||
|
@ -14,6 +16,27 @@
|
||||||
[sub_resource type="AnimationNodeAnimation" id="AnimationNodeAnimation_smehm"]
|
[sub_resource type="AnimationNodeAnimation" id="AnimationNodeAnimation_smehm"]
|
||||||
animation = &"Aim"
|
animation = &"Aim"
|
||||||
|
|
||||||
|
[sub_resource type="AnimationNodeAnimation" id="AnimationNodeAnimation_jej6c"]
|
||||||
|
animation = &"Fire"
|
||||||
|
|
||||||
|
[sub_resource type="AnimationNodeAnimation" id="AnimationNodeAnimation_f1ej7"]
|
||||||
|
animation = &"Aim"
|
||||||
|
|
||||||
|
[sub_resource type="AnimationNodeBlend2" id="AnimationNodeBlend2_oprun"]
|
||||||
|
filter_enabled = true
|
||||||
|
filters = ["AuxScene/Scene/Armature/Skeleton3D:mixamorigHead", "AuxScene/Scene/Armature/Skeleton3D:mixamorigHead001", "AuxScene/Scene/Armature/Skeleton3D:mixamorigHips", "AuxScene/Scene/Armature/Skeleton3D:mixamorigHips001", "AuxScene/Scene/Armature/Skeleton3D:mixamorigLeftArm", "AuxScene/Scene/Armature/Skeleton3D:mixamorigLeftFoot", "AuxScene/Scene/Armature/Skeleton3D:mixamorigLeftForeArm", "AuxScene/Scene/Armature/Skeleton3D:mixamorigLeftLeg", "AuxScene/Scene/Armature/Skeleton3D:mixamorigLeftLeg001", "AuxScene/Scene/Armature/Skeleton3D:mixamorigLeftShoulder", "AuxScene/Scene/Armature/Skeleton3D:mixamorigLeftShoulder001", "AuxScene/Scene/Armature/Skeleton3D:mixamorigLeftToeBase", "AuxScene/Scene/Armature/Skeleton3D:mixamorigLeftUpLeg", "AuxScene/Scene/Armature/Skeleton3D:mixamorigLeftUpLeg001", "AuxScene/Scene/Armature/Skeleton3D:mixamorigNeck", "AuxScene/Scene/Armature/Skeleton3D:mixamorigNeck001", "AuxScene/Scene/Armature/Skeleton3D:mixamorigRightArm", "AuxScene/Scene/Armature/Skeleton3D:mixamorigRightFoot", "AuxScene/Scene/Armature/Skeleton3D:mixamorigRightForeArm", "AuxScene/Scene/Armature/Skeleton3D:mixamorigRightLeg", "AuxScene/Scene/Armature/Skeleton3D:mixamorigRightLeg001", "AuxScene/Scene/Armature/Skeleton3D:mixamorigRightShoulder", "AuxScene/Scene/Armature/Skeleton3D:mixamorigRightShoulder001", "AuxScene/Scene/Armature/Skeleton3D:mixamorigRightToeBase", "AuxScene/Scene/Armature/Skeleton3D:mixamorigRightUpLeg", "AuxScene/Scene/Armature/Skeleton3D:mixamorigRightUpLeg001", "AuxScene/Scene/Armature/Skeleton3D:mixamorigSpine", "AuxScene/Scene/Armature/Skeleton3D:mixamorigSpine001", "AuxScene/Scene/Armature/Skeleton3D:mixamorigSpine1", "AuxScene/Scene/Armature/Skeleton3D:mixamorigSpine1001", "AuxScene/Scene/Armature/Skeleton3D:mixamorigSpine2", "AuxScene/Scene/Armature/Skeleton3D:mixamorigSpine2001"]
|
||||||
|
|
||||||
|
[sub_resource type="AnimationNodeBlendTree" id="AnimationNodeBlendTree_a8ls1"]
|
||||||
|
graph_offset = Vector2(-454.653, 56.3387)
|
||||||
|
nodes/Animation/node = SubResource("AnimationNodeAnimation_f1ej7")
|
||||||
|
nodes/Animation/position = Vector2(200, 340)
|
||||||
|
"nodes/Animation 2/node" = SubResource("AnimationNodeAnimation_jej6c")
|
||||||
|
"nodes/Animation 2/position" = Vector2(200, 160)
|
||||||
|
nodes/Blend2/node = SubResource("AnimationNodeBlend2_oprun")
|
||||||
|
nodes/Blend2/position = Vector2(380, 160)
|
||||||
|
nodes/output/position = Vector2(560, 160)
|
||||||
|
node_connections = [&"Blend2", 0, &"Animation 2", &"Blend2", 1, &"Animation", &"output", 0, &"Blend2"]
|
||||||
|
|
||||||
[sub_resource type="AnimationNodeAnimation" id="AnimationNodeAnimation_d2wvv"]
|
[sub_resource type="AnimationNodeAnimation" id="AnimationNodeAnimation_d2wvv"]
|
||||||
animation = &"Run"
|
animation = &"Run"
|
||||||
|
|
||||||
|
@ -35,9 +58,6 @@ nodes/Blend2/position = Vector2(60, 140)
|
||||||
nodes/output/position = Vector2(300, 140)
|
nodes/output/position = Vector2(300, 140)
|
||||||
node_connections = [&"Blend2", 0, &"Animation", &"Blend2", 1, &"Animation 2", &"output", 0, &"Blend2"]
|
node_connections = [&"Blend2", 0, &"Animation", &"Blend2", 1, &"Animation 2", &"output", 0, &"Blend2"]
|
||||||
|
|
||||||
[sub_resource type="AnimationNodeAnimation" id="AnimationNodeAnimation_ur7pv"]
|
|
||||||
animation = &"Fire"
|
|
||||||
|
|
||||||
[sub_resource type="AnimationNodeAnimation" id="AnimationNodeAnimation_y4r1p"]
|
[sub_resource type="AnimationNodeAnimation" id="AnimationNodeAnimation_y4r1p"]
|
||||||
animation = &"PistolIdle"
|
animation = &"PistolIdle"
|
||||||
|
|
||||||
|
@ -76,14 +96,6 @@ advance_expression = "not velocity"
|
||||||
advance_mode = 2
|
advance_mode = 2
|
||||||
advance_expression = "is_weapon_ready"
|
advance_expression = "is_weapon_ready"
|
||||||
|
|
||||||
[sub_resource type="AnimationNodeStateMachineTransition" id="AnimationNodeStateMachineTransition_a8ls1"]
|
|
||||||
advance_mode = 2
|
|
||||||
advance_expression = "is_firing"
|
|
||||||
|
|
||||||
[sub_resource type="AnimationNodeStateMachineTransition" id="AnimationNodeStateMachineTransition_qfm1y"]
|
|
||||||
switch_mode = 2
|
|
||||||
advance_mode = 2
|
|
||||||
|
|
||||||
[sub_resource type="AnimationNodeStateMachineTransition" id="AnimationNodeStateMachineTransition_fulsm"]
|
[sub_resource type="AnimationNodeStateMachineTransition" id="AnimationNodeStateMachineTransition_fulsm"]
|
||||||
advance_mode = 2
|
advance_mode = 2
|
||||||
advance_expression = "not is_weapon_ready"
|
advance_expression = "not is_weapon_ready"
|
||||||
|
@ -96,19 +108,30 @@ advance_expression = "is_running"
|
||||||
advance_mode = 2
|
advance_mode = 2
|
||||||
advance_expression = "not is_running"
|
advance_expression = "not is_running"
|
||||||
|
|
||||||
|
[sub_resource type="AnimationNodeStateMachineTransition" id="AnimationNodeStateMachineTransition_a8ls1"]
|
||||||
|
advance_mode = 2
|
||||||
|
advance_expression = "is_firing
|
||||||
|
"
|
||||||
|
|
||||||
|
[sub_resource type="AnimationNodeStateMachineTransition" id="AnimationNodeStateMachineTransition_qfm1y"]
|
||||||
|
break_loop_at_end = true
|
||||||
|
switch_mode = 2
|
||||||
|
advance_mode = 2
|
||||||
|
|
||||||
[sub_resource type="AnimationNodeStateMachine" id="AnimationNodeStateMachine_d2wvv"]
|
[sub_resource type="AnimationNodeStateMachine" id="AnimationNodeStateMachine_d2wvv"]
|
||||||
states/Aim/node = SubResource("AnimationNodeAnimation_smehm")
|
states/Aim/node = SubResource("AnimationNodeAnimation_smehm")
|
||||||
states/Aim/position = Vector2(327, 194)
|
states/Aim/position = Vector2(327, 194)
|
||||||
states/BlendTree/node = SubResource("AnimationNodeBlendTree_f1ej7")
|
states/BlendTree/node = SubResource("AnimationNodeBlendTree_f1ej7")
|
||||||
states/BlendTree/position = Vector2(653, 100)
|
states/BlendTree/position = Vector2(653, 100)
|
||||||
|
"states/BlendTree 2/node" = SubResource("AnimationNodeBlendTree_a8ls1")
|
||||||
|
"states/BlendTree 2/position" = Vector2(488, 194)
|
||||||
states/End/position = Vector2(890, 40)
|
states/End/position = Vector2(890, 40)
|
||||||
states/Fire/node = SubResource("AnimationNodeAnimation_ur7pv")
|
|
||||||
states/Fire/position = Vector2(462, 194)
|
|
||||||
states/PistolIdle/node = SubResource("AnimationNodeAnimation_y4r1p")
|
states/PistolIdle/node = SubResource("AnimationNodeAnimation_y4r1p")
|
||||||
states/PistolIdle/position = Vector2(327, 100)
|
states/PistolIdle/position = Vector2(327, 100)
|
||||||
states/Walk/node = SubResource("AnimationNodeBlendTree_ur7pv")
|
states/Walk/node = SubResource("AnimationNodeBlendTree_ur7pv")
|
||||||
states/Walk/position = Vector2(488, 100)
|
states/Walk/position = Vector2(488, 100)
|
||||||
transitions = ["Start", "PistolIdle", SubResource("AnimationNodeStateMachineTransition_ur7pv"), "PistolIdle", "Walk", SubResource("AnimationNodeStateMachineTransition_y4r1p"), "Walk", "PistolIdle", SubResource("AnimationNodeStateMachineTransition_d2wvv"), "PistolIdle", "Aim", SubResource("AnimationNodeStateMachineTransition_oprun"), "Aim", "Fire", SubResource("AnimationNodeStateMachineTransition_a8ls1"), "Fire", "Aim", SubResource("AnimationNodeStateMachineTransition_qfm1y"), "Aim", "PistolIdle", SubResource("AnimationNodeStateMachineTransition_fulsm"), "Walk", "BlendTree", SubResource("AnimationNodeStateMachineTransition_4r5pv"), "BlendTree", "Walk", SubResource("AnimationNodeStateMachineTransition_60mlk")]
|
transitions = ["Start", "PistolIdle", SubResource("AnimationNodeStateMachineTransition_ur7pv"), "PistolIdle", "Walk", SubResource("AnimationNodeStateMachineTransition_y4r1p"), "Walk", "PistolIdle", SubResource("AnimationNodeStateMachineTransition_d2wvv"), "PistolIdle", "Aim", SubResource("AnimationNodeStateMachineTransition_oprun"), "Aim", "PistolIdle", SubResource("AnimationNodeStateMachineTransition_fulsm"), "Walk", "BlendTree", SubResource("AnimationNodeStateMachineTransition_4r5pv"), "BlendTree", "Walk", SubResource("AnimationNodeStateMachineTransition_60mlk"), "Aim", "BlendTree 2", SubResource("AnimationNodeStateMachineTransition_a8ls1"), "BlendTree 2", "Aim", SubResource("AnimationNodeStateMachineTransition_qfm1y")]
|
||||||
|
graph_offset = Vector2(-75, 65)
|
||||||
|
|
||||||
[sub_resource type="AnimationNodeAnimation" id="AnimationNodeAnimation_qhqgy"]
|
[sub_resource type="AnimationNodeAnimation" id="AnimationNodeAnimation_qhqgy"]
|
||||||
animation = &"Idle"
|
animation = &"Idle"
|
||||||
|
@ -170,12 +193,31 @@ states/Unarmed/node = SubResource("AnimationNodeStateMachine_ur7pv")
|
||||||
states/Unarmed/position = Vector2(356, 50)
|
states/Unarmed/position = Vector2(356, 50)
|
||||||
transitions = ["Start", "Unarmed", SubResource("AnimationNodeStateMachineTransition_qlg0r"), "Start", "Handgun", SubResource("AnimationNodeStateMachineTransition_3v2ag"), "Handgun", "Unarmed", SubResource("AnimationNodeStateMachineTransition_jej6c"), "Unarmed", "Handgun", SubResource("AnimationNodeStateMachineTransition_f1ej7")]
|
transitions = ["Start", "Unarmed", SubResource("AnimationNodeStateMachineTransition_qlg0r"), "Start", "Handgun", SubResource("AnimationNodeStateMachineTransition_3v2ag"), "Handgun", "Unarmed", SubResource("AnimationNodeStateMachineTransition_jej6c"), "Unarmed", "Handgun", SubResource("AnimationNodeStateMachineTransition_f1ej7")]
|
||||||
|
|
||||||
[node name="Player" type="CharacterBody3D" groups=["persist"]]
|
[node name="Player" type="CharacterBody3D" node_paths=PackedStringArray("input", "interactor", "equipment") groups=["persist"]]
|
||||||
script = ExtResource("1_qhqgy")
|
script = ExtResource("1_qhqgy")
|
||||||
|
input = NodePath("Input")
|
||||||
|
interactor = NodePath("Interactor")
|
||||||
|
equipment = NodePath("Weapon")
|
||||||
|
|
||||||
[node name="Input" type="Node" parent="."]
|
[node name="Input" type="Node" parent="."]
|
||||||
script = ExtResource("3_dqkch")
|
script = ExtResource("3_dqkch")
|
||||||
|
|
||||||
|
[node name="Inventory" type="Node" parent="."]
|
||||||
|
script = ExtResource("5_qlg0r")
|
||||||
|
inventory = ExtResource("6_tuyoq")
|
||||||
|
|
||||||
|
[node name="Weapon" type="BoneAttachment3D" parent="." node_paths=PackedStringArray("initial_equipment")]
|
||||||
|
transform = Transform3D(0.00876506, 0.0120414, 0.00178277, 0.00882159, -0.00779736, 0.00929411, 0.00838767, -0.00438243, -0.0116379, -0.128585, 1.36723, 0.500051)
|
||||||
|
bone_name = "mixamorigRightHandMiddle1"
|
||||||
|
bone_idx = 24
|
||||||
|
use_external_skeleton = true
|
||||||
|
external_skeleton = NodePath("../Mesh/AuxScene/Scene/Armature/Skeleton3D")
|
||||||
|
script = ExtResource("7_ur7pv")
|
||||||
|
initial_equipment = NodePath("Pistol")
|
||||||
|
|
||||||
|
[node name="Pistol" parent="Weapon" instance=ExtResource("7_fjrip")]
|
||||||
|
transform = Transform3D(-0.948472, 9.81445, -1.66645, -5.38265, -1.91379, -8.20758, -8.37422, 0.118531, 5.46429, 3.16379, 3.48907, 1.04434)
|
||||||
|
|
||||||
[node name="Interactor" type="Node3D" parent="." node_paths=PackedStringArray("area", "root_node")]
|
[node name="Interactor" type="Node3D" parent="." node_paths=PackedStringArray("area", "root_node")]
|
||||||
script = ExtResource("4_dqkch")
|
script = ExtResource("4_dqkch")
|
||||||
area = NodePath("Area3D")
|
area = NodePath("Area3D")
|
||||||
|
@ -200,10 +242,7 @@ tree_root = SubResource("AnimationNodeStateMachine_y4r1p")
|
||||||
advance_expression_base_node = NodePath("..")
|
advance_expression_base_node = NodePath("..")
|
||||||
anim_player = NodePath("../Mesh/AnimationPlayer")
|
anim_player = NodePath("../Mesh/AnimationPlayer")
|
||||||
parameters/Handgun/BlendTree/Blend2/blend_amount = 1.0
|
parameters/Handgun/BlendTree/Blend2/blend_amount = 1.0
|
||||||
|
"parameters/Handgun/BlendTree 2/Blend2/blend_amount" = 1.0
|
||||||
parameters/Handgun/Walk/Blend2/blend_amount = 1.0
|
parameters/Handgun/Walk/Blend2/blend_amount = 1.0
|
||||||
|
|
||||||
[node name="ItemContainer" type="Node" parent="."]
|
|
||||||
script = ExtResource("5_qlg0r")
|
|
||||||
inventory = ExtResource("6_tuyoq")
|
|
||||||
|
|
||||||
[editable path="Mesh"]
|
[editable path="Mesh"]
|
||||||
|
|
25
godot/src/damage_source.gd
Normal file
25
godot/src/damage_source.gd
Normal file
|
@ -0,0 +1,25 @@
|
||||||
|
class_name DamageSource extends Node
|
||||||
|
|
||||||
|
@export var damage: int
|
||||||
|
@export var raycast: RayCast3D
|
||||||
|
|
||||||
|
func _ready() -> void:
|
||||||
|
raycast.enabled = false
|
||||||
|
|
||||||
|
func raycast_to_target() -> Option:
|
||||||
|
raycast.force_raycast_update()
|
||||||
|
if raycast.is_colliding():
|
||||||
|
return Option.some(raycast.get_collider())
|
||||||
|
else:
|
||||||
|
return Option.none
|
||||||
|
|
||||||
|
func try_damage() -> void:
|
||||||
|
match raycast_to_target():
|
||||||
|
var option when option.is_some():
|
||||||
|
var value = option.unwrap()
|
||||||
|
match NodeExt.find_child_variant(value, Health):
|
||||||
|
var node when node.is_some():
|
||||||
|
var health: Health = node.unwrap()
|
||||||
|
health.apply_damage(damage)
|
||||||
|
_: pass
|
||||||
|
_: pass
|
1
godot/src/damage_source.gd.uid
Normal file
1
godot/src/damage_source.gd.uid
Normal file
|
@ -0,0 +1 @@
|
||||||
|
uid://ddqif2gmm1ec2
|
25
godot/src/equipment.gd
Normal file
25
godot/src/equipment.gd
Normal file
|
@ -0,0 +1,25 @@
|
||||||
|
class_name Equipment extends Node
|
||||||
|
|
||||||
|
signal unequipped(item: Item)
|
||||||
|
signal equipped(item: Item)
|
||||||
|
|
||||||
|
@export var initial_equipment: Usable
|
||||||
|
var current_item: Option = Option.none
|
||||||
|
|
||||||
|
func _ready() -> void:
|
||||||
|
current_item = Option.from(initial_equipment)
|
||||||
|
|
||||||
|
func unequip():
|
||||||
|
if current_item.is_some():
|
||||||
|
var item = current_item.unwrap()
|
||||||
|
current_item = Option.none
|
||||||
|
unequipped.emit(item)
|
||||||
|
|
||||||
|
func equip(item: Item):
|
||||||
|
unequip()
|
||||||
|
if item != null:
|
||||||
|
current_item = Option.some(item)
|
||||||
|
equipped.emit(item)
|
||||||
|
|
||||||
|
func use():
|
||||||
|
current_item.inspect(func(x: Variant) -> void: x.use())
|
1
godot/src/equipment.gd.uid
Normal file
1
godot/src/equipment.gd.uid
Normal file
|
@ -0,0 +1 @@
|
||||||
|
uid://c710qg683rqbc
|
26
godot/src/health.gd
Normal file
26
godot/src/health.gd
Normal file
|
@ -0,0 +1,26 @@
|
||||||
|
class_name Health extends Node
|
||||||
|
|
||||||
|
signal died
|
||||||
|
signal damaged
|
||||||
|
|
||||||
|
@export var max_health: int
|
||||||
|
@export var current_value: int
|
||||||
|
@export var heal_on_spawn: bool = true
|
||||||
|
|
||||||
|
var dead: bool = false
|
||||||
|
|
||||||
|
func _ready() -> void:
|
||||||
|
if heal_on_spawn:
|
||||||
|
current_value = max_health
|
||||||
|
|
||||||
|
func apply_damage(value: int):
|
||||||
|
if dead: return
|
||||||
|
current_value = max(current_value - value, 0)
|
||||||
|
if current_value <= 0:
|
||||||
|
dead = true
|
||||||
|
died.emit()
|
||||||
|
else:
|
||||||
|
damaged.emit()
|
||||||
|
|
||||||
|
func apply_healing(value: int):
|
||||||
|
current_value = min(current_value + value, max_health)
|
1
godot/src/health.gd.uid
Normal file
1
godot/src/health.gd.uid
Normal file
|
@ -0,0 +1 @@
|
||||||
|
uid://d4anpy5efe22d
|
|
@ -3,8 +3,9 @@ class_name Player extends CharacterBody3D
|
||||||
@export var walk_speed: float = 4.0
|
@export var walk_speed: float = 4.0
|
||||||
@export var run_speed: float = 6.0
|
@export var run_speed: float = 6.0
|
||||||
|
|
||||||
@onready var input = $Input
|
@export var input: PlayerInput
|
||||||
@onready var interactor = $Interactor
|
@export var interactor: Interactor
|
||||||
|
@export var equipment: Equipment
|
||||||
|
|
||||||
var is_running: bool:
|
var is_running: bool:
|
||||||
get: return velocity and input.is_running
|
get: return velocity and input.is_running
|
||||||
|
@ -41,7 +42,7 @@ func _on_interact():
|
||||||
|
|
||||||
func _on_fire():
|
func _on_fire():
|
||||||
if is_weapon_ready:
|
if is_weapon_ready:
|
||||||
print('firing weapon')
|
equipment.use()
|
||||||
|
|
||||||
func on_save():
|
func on_save():
|
||||||
return {
|
return {
|
||||||
|
|
1
godot/src/raycast.gd.uid
Normal file
1
godot/src/raycast.gd.uid
Normal file
|
@ -0,0 +1 @@
|
||||||
|
uid://bgun1u5812uil
|
18
godot/src/usable.gd
Normal file
18
godot/src/usable.gd
Normal file
|
@ -0,0 +1,18 @@
|
||||||
|
class_name Usable extends Node
|
||||||
|
|
||||||
|
signal used
|
||||||
|
|
||||||
|
@export var enabled: bool = true
|
||||||
|
|
||||||
|
func enable() -> void:
|
||||||
|
enabled = true
|
||||||
|
|
||||||
|
func disable() -> void:
|
||||||
|
enabled = false
|
||||||
|
|
||||||
|
func set_enabled(is_enabled: bool) -> void:
|
||||||
|
self.enabled = is_enabled
|
||||||
|
|
||||||
|
func use():
|
||||||
|
if enabled:
|
||||||
|
used.emit()
|
1
godot/src/usable.gd.uid
Normal file
1
godot/src/usable.gd.uid
Normal file
|
@ -0,0 +1 @@
|
||||||
|
uid://bn7dr8s404qnf
|
Loading…
Add table
Reference in a new issue