diff --git a/assets/textures/portal/portal.png b/assets/textures/portal/portal.png index db2cc58..a7b11af 100644 Binary files a/assets/textures/portal/portal.png and b/assets/textures/portal/portal.png differ diff --git a/assets/textures/portal/portal_light.png b/assets/textures/portal/portal_light.png new file mode 100644 index 0000000..2480336 Binary files /dev/null and b/assets/textures/portal/portal_light.png differ diff --git a/assets/textures/portal/portal_light.png.import b/assets/textures/portal/portal_light.png.import new file mode 100644 index 0000000..4299299 --- /dev/null +++ b/assets/textures/portal/portal_light.png.import @@ -0,0 +1,34 @@ +[remap] + +importer="texture" +type="CompressedTexture2D" +uid="uid://h45qkvmrh0ey" +path="res://.godot/imported/portal_light.png-d532b82e892c0e52c813f6e6c6a7a723.ctex" +metadata={ +"vram_texture": false +} + +[deps] + +source_file="res://assets/textures/portal/portal_light.png" +dest_files=["res://.godot/imported/portal_light.png-d532b82e892c0e52c813f6e6c6a7a723.ctex"] + +[params] + +compress/mode=0 +compress/high_quality=false +compress/lossy_quality=0.7 +compress/hdr_compression=1 +compress/normal_map=0 +compress/channel_pack=0 +mipmaps/generate=false +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=1 diff --git a/assets/textures/portal/portal_normal.png b/assets/textures/portal/portal_normal.png new file mode 100644 index 0000000..66dd095 Binary files /dev/null and b/assets/textures/portal/portal_normal.png differ diff --git a/assets/textures/portal/portal_normal.png.import b/assets/textures/portal/portal_normal.png.import new file mode 100644 index 0000000..b08963f --- /dev/null +++ b/assets/textures/portal/portal_normal.png.import @@ -0,0 +1,34 @@ +[remap] + +importer="texture" +type="CompressedTexture2D" +uid="uid://cv7rv8wlhpbg1" +path="res://.godot/imported/portal_normal.png-451e042ab64ba3e4f59ef197b788c326.ctex" +metadata={ +"vram_texture": false +} + +[deps] + +source_file="res://assets/textures/portal/portal_normal.png" +dest_files=["res://.godot/imported/portal_normal.png-451e042ab64ba3e4f59ef197b788c326.ctex"] + +[params] + +compress/mode=0 +compress/high_quality=false +compress/lossy_quality=0.7 +compress/hdr_compression=1 +compress/normal_map=0 +compress/channel_pack=0 +mipmaps/generate=false +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=1 diff --git a/maps/purple_portals.tscn b/maps/purple_portals.tscn index cf5e6f1..364728e 100644 --- a/maps/purple_portals.tscn +++ b/maps/purple_portals.tscn @@ -46,21 +46,21 @@ tile_set = ExtResource("5_hgo3q") format = 2 layer_0/tile_data = PackedInt32Array(720896, 0, 0, 720897, 0, 0, 720898, 0, 0, 720899, 0, 0, 720900, 0, 0, 720901, 0, 0, 720902, 0, 0, 720903, 0, 0, 720904, 0, 0, 720905, 0, 0, 720906, 0, 0, 720907, 0, 0, 720908, 0, 0, 720909, 0, 0, 720910, 0, 0, 720911, 0, 0, 720912, 0, 0, 720913, 0, 0, 15, 0, 0, 65551, 0, 0, 131087, 0, 0, 196623, 0, 0, 262159, 0, 0, 327695, 0, 0, 393231, 0, 0, 458767, 0, 0, 524303, 0, 0, 589839, 0, 0, 655375, 0, 0, 0, 0, 0, 65536, 0, 0, 131072, 0, 0, 196608, 0, 0, 6, 0, 0, 65542, 0, 0, 131078, 0, 0, 196614, 0, 0, 262150, 0, 0, 327686, 0, 0, 393222, 0, 0, 393216, 0, 0, 262144, 0, 0, 327680, 0, 0, 458758, 0, 0, 524294, 0, 0, 589830, 0, 0, 655366, 0, 0, 393227, 0, 0, 393228, 0, 0, 393229, 0, 0, 393230, 0, 0, 458757, 0, 0, 458756, 0, 0, 458755, 0, 0, 458754, 0, 0, 458753, 0, 0, 458752, 0, 0) -[node name="Portal" parent="." instance=ExtResource("6_hgo3q")] +[node name="Portal" parent="." node_paths=PackedStringArray("linked_portal") instance=ExtResource("6_hgo3q")] position = Vector2(73, 144) -connected_portal = NodePath("../Portal2") +linked_portal = NodePath("../Portal2") -[node name="Portal2" parent="." instance=ExtResource("6_hgo3q")] +[node name="Portal2" parent="." node_paths=PackedStringArray("linked_portal") instance=ExtResource("6_hgo3q")] position = Vector2(152, 120) -connected_portal = NodePath("../Portal") +linked_portal = NodePath("../Portal") -[node name="Portal3" parent="." instance=ExtResource("6_hgo3q")] +[node name="Portal3" parent="." node_paths=PackedStringArray("linked_portal") instance=ExtResource("6_hgo3q")] position = Vector2(233, 144) -connected_portal = NodePath("../Portal4") +linked_portal = NodePath("../Portal4") -[node name="Portal4" parent="." instance=ExtResource("6_hgo3q")] +[node name="Portal4" parent="." node_paths=PackedStringArray("linked_portal") instance=ExtResource("6_hgo3q")] position = Vector2(40, 56) -connected_portal = NodePath("../Portal3") +linked_portal = NodePath("../Portal3") [node name="EndDoor" parent="." instance=ExtResource("7_ti0gq")] position = Vector2(24, 88) diff --git a/objects/player/player.tscn b/objects/player/player.tscn index a61f72a..7e60ec2 100644 --- a/objects/player/player.tscn +++ b/objects/player/player.tscn @@ -387,8 +387,8 @@ delay_in_seconds = ".25" [connection signal="state_physics_processing" from="StateChart/Root/Grounded/Standing/Stopping" to="." method="_slow_to_stop"] [connection signal="state_physics_processing" from="StateChart/Root/Grounded/Standing/Stopping" to="." method="_scale_run_animation"] [connection signal="state_entered" from="StateChart/Root/Grounded/Running" to="Graphics/Sprite/Run" method="play"] -[connection signal="state_physics_processing" from="StateChart/Root/Grounded/Running" to="." method="_scale_run_animation"] [connection signal="state_physics_processing" from="StateChart/Root/Grounded/Running" to="." method="_apply_run_acceleration"] +[connection signal="state_physics_processing" from="StateChart/Root/Grounded/Running" to="." method="_scale_run_animation"] [connection signal="state_entered" from="StateChart/Root/Grounded/Turning" to="Graphics/Sprite/Skid" method="play"] [connection signal="state_physics_processing" from="StateChart/Root/Grounded/Turning" to="." method="_apply_turn_acceleration"] [connection signal="state_physics_processing" from="StateChart/Root/Airborne" to="." method="_apply_gravity"] diff --git a/objects/portal/portal.gd b/objects/portal/portal.gd index eb5f359..22a46e8 100644 --- a/objects/portal/portal.gd +++ b/objects/portal/portal.gd @@ -1,16 +1,71 @@ +@tool +class_name Portal extends Node2D -@export var connected_portal: NodePath -@onready var portal = get_node(connected_portal) -var check_for_bodies = true -func _on_area_2d_body_entered(body: Node2D) -> void: - if body is Player && check_for_bodies: - body.global_position = portal.global_position - body.launch(body.velocity * 1.25) - portal.check_for_bodies = false - +## color the portal is tinted as +@export_color_no_alpha var color: Color = Color.PURPLE: + set(value): + color = value + sprite.modulate = color + if linked_portal and linked_portal.color != color: + linked_portal.color = color + queue_redraw() -func _on_area_2d_body_exited(body: Node2D) -> void: - await get_tree().create_timer(0.1).timeout - check_for_bodies = true +## Other connected portal. The linked +@export var linked_portal: Portal: + set(new_portal): + if new_portal == self: + return + if new_portal == null: + linked_portal = null + return + if linked_portal: + linked_portal.linked_portal = null + linked_portal = new_portal + if linked_portal: + if linked_portal.linked_portal != self: + linked_portal.linked_portal = self + linked_portal.color = color + queue_redraw() + +## Multiplier to the player's velocity when they travel through the portal. +@export var speed_multiplier: float = 1.25 +## Delay in seconds until an exited portal can be re-entered. +@export var teleport_cooldown: float = 0.1 + +@export_group("Internal References") +@export var sprite: Sprite2D + + +var check_for_player: bool = true + + +func _init() -> void: + set_notify_transform(true) + +func _notification(what: int) -> void: + if what == NOTIFICATION_TRANSFORM_CHANGED: + queue_redraw() + if linked_portal: + linked_portal.queue_redraw() + +func _draw() -> void: + if Engine.is_editor_hint(): + if linked_portal: + draw_line(Vector2.ZERO, to_local(linked_portal.global_position), color, 1.5) + + +func _on_player_detector_body_entered(body: Node2D) -> void: + if check_for_player and body is Player and linked_portal: + body.global_position = linked_portal.global_position + body.launch(body.velocity * speed_multiplier) + linked_portal.check_for_player = false + create_tween().tween_property( + linked_portal, ^"check_for_player", true, 0.0 + ).set_delay(teleport_cooldown) + + +func _on_player_detector_body_exited(body: Node2D) -> void: + var tween = create_tween().set_process_mode(Tween.TWEEN_PROCESS_PHYSICS) + tween.tween_property(self, ^"check_for_player", true, 0.0).set_delay(teleport_cooldown) diff --git a/objects/portal/portal.tscn b/objects/portal/portal.tscn index a03aeba..233fe53 100644 --- a/objects/portal/portal.tscn +++ b/objects/portal/portal.tscn @@ -1,25 +1,12 @@ -[gd_scene load_steps=7 format=3 uid="uid://cypj35yv5auuc"] +[gd_scene load_steps=10 format=3 uid="uid://cypj35yv5auuc"] [ext_resource type="Script" uid="uid://dbrblyk7xttpj" path="res://objects/portal/portal.gd" id="1_v7atq"] [ext_resource type="Texture2D" uid="uid://dtwp3ohanw2sn" path="res://assets/textures/portal/portal.png" id="2_ah4id"] +[ext_resource type="Texture2D" uid="uid://cv7rv8wlhpbg1" path="res://assets/textures/portal/portal_normal.png" id="3_ah4id"] +[ext_resource type="Texture2D" uid="uid://h45qkvmrh0ey" path="res://assets/textures/portal/portal_light.png" id="4_xxtm7"] -[sub_resource type="Animation" id="Animation_xxtm7"] -resource_name = "spin" -length = 0.5 -loop_mode = 1 -step = 0.25 -tracks/0/type = "value" -tracks/0/imported = false -tracks/0/enabled = true -tracks/0/path = NodePath("Sprite2D:rotation") -tracks/0/interp = 1 -tracks/0/loop_wrap = true -tracks/0/keys = { -"times": PackedFloat32Array(0, 0.5), -"transitions": PackedFloat32Array(1, 1), -"update": 0, -"values": [0.0, 6.28319] -} +[sub_resource type="RectangleShape2D" id="RectangleShape2D_v7atq"] +size = Vector2(16, 16) [sub_resource type="Animation" id="Animation_0po8f"] length = 0.001 @@ -35,6 +22,47 @@ tracks/0/keys = { "update": 0, "values": [0.0] } +tracks/1/type = "value" +tracks/1/imported = false +tracks/1/enabled = true +tracks/1/path = NodePath("LightPivot:rotation") +tracks/1/interp = 1 +tracks/1/loop_wrap = true +tracks/1/keys = { +"times": PackedFloat32Array(0), +"transitions": PackedFloat32Array(1), +"update": 0, +"values": [0.0] +} + +[sub_resource type="Animation" id="Animation_xxtm7"] +resource_name = "spin" +loop_mode = 1 +step = 0.25 +tracks/0/type = "value" +tracks/0/imported = false +tracks/0/enabled = true +tracks/0/path = NodePath("Sprite2D:rotation") +tracks/0/interp = 1 +tracks/0/loop_wrap = true +tracks/0/keys = { +"times": PackedFloat32Array(0, 1), +"transitions": PackedFloat32Array(1, 1), +"update": 0, +"values": [0.0, 12.5664] +} +tracks/1/type = "value" +tracks/1/imported = false +tracks/1/enabled = true +tracks/1/path = NodePath("LightPivot:rotation") +tracks/1/interp = 1 +tracks/1/loop_wrap = true +tracks/1/keys = { +"times": PackedFloat32Array(0, 1), +"transitions": PackedFloat32Array(1, 1), +"update": 0, +"values": [0.0, -6.28319] +} [sub_resource type="AnimationLibrary" id="AnimationLibrary_6y8yo"] _data = { @@ -42,14 +70,21 @@ _data = { &"spin": SubResource("Animation_xxtm7") } -[sub_resource type="RectangleShape2D" id="RectangleShape2D_v7atq"] -size = Vector2(16, 16) +[sub_resource type="CanvasTexture" id="CanvasTexture_xxtm7"] +diffuse_texture = ExtResource("2_ah4id") +normal_texture = ExtResource("3_ah4id") -[node name="Portal" type="Node2D"] +[node name="Portal" type="Node2D" node_paths=PackedStringArray("sprite")] script = ExtResource("1_v7atq") +sprite = NodePath("Sprite2D") -[node name="Sprite2D" type="Sprite2D" parent="."] -texture = ExtResource("2_ah4id") +[node name="PlayerDetector" type="Area2D" parent="."] +collision_layer = 0 +collision_mask = 16 +monitorable = false + +[node name="CollisionShape2D" type="CollisionShape2D" parent="PlayerDetector"] +shape = SubResource("RectangleShape2D_v7atq") [node name="AnimationPlayer" type="AnimationPlayer" parent="."] libraries = { @@ -57,11 +92,21 @@ libraries = { } autoplay = "spin" -[node name="Area2D" type="Area2D" parent="."] -collision_mask = 16 +[node name="Sprite2D" type="Sprite2D" parent="."] +modulate = Color(0.627451, 0.12549, 0.941176, 1) +self_modulate = Color(1, 1, 1, 0.75) +light_mask = 32 +texture = SubResource("CanvasTexture_xxtm7") -[node name="CollisionShape2D" type="CollisionShape2D" parent="Area2D"] -shape = SubResource("RectangleShape2D_v7atq") +[node name="LightPivot" type="Node2D" parent="."] +position = Vector2(-4, 4) -[connection signal="body_entered" from="Area2D" to="." method="_on_area_2d_body_entered"] -[connection signal="body_exited" from="Area2D" to="." method="_on_area_2d_body_exited"] +[node name="PointLight2D" type="PointLight2D" parent="LightPivot"] +position = Vector2(4, 0) +range_item_cull_mask = 32 +texture = ExtResource("4_xxtm7") +texture_scale = 2.0 +height = 4.0 + +[connection signal="body_entered" from="PlayerDetector" to="." method="_on_player_detector_body_entered"] +[connection signal="body_exited" from="PlayerDetector" to="." method="_on_player_detector_body_exited"]