Compare commits
No commits in common. "0e68c6e6664bf5c050fc75baea9a7abd72b704b9" and "7d4dc68196457bb0a5c2572f4dd4ea5cca7060c4" have entirely different histories.
0e68c6e666
...
7d4dc68196
Binary file not shown.
|
Before Width: | Height: | Size: 85 KiB |
|
|
@ -1,40 +0,0 @@
|
|||
[remap]
|
||||
|
||||
importer="texture"
|
||||
type="CompressedTexture2D"
|
||||
uid="uid://cw1lcd672mq87"
|
||||
path="res://.godot/imported/未命名作品(3).png-5152e47ab8192492e0d911592bc8c8f5.ctex"
|
||||
metadata={
|
||||
"vram_texture": false
|
||||
}
|
||||
|
||||
[deps]
|
||||
|
||||
source_file="res://_asset/ksw/未命名作品(3).png"
|
||||
dest_files=["res://.godot/imported/未命名作品(3).png-5152e47ab8192492e0d911592bc8c8f5.ctex"]
|
||||
|
||||
[params]
|
||||
|
||||
compress/mode=0
|
||||
compress/high_quality=false
|
||||
compress/lossy_quality=0.7
|
||||
compress/uastc_level=0
|
||||
compress/rdo_quality_loss=0.0
|
||||
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/channel_remap/red=0
|
||||
process/channel_remap/green=1
|
||||
process/channel_remap/blue=2
|
||||
process/channel_remap/alpha=3
|
||||
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
|
||||
|
|
@ -1,4 +1,4 @@
|
|||
[gd_scene load_steps=15 format=3 uid="uid://3vc8ojbiyy5w"]
|
||||
[gd_scene load_steps=18 format=3 uid="uid://3vc8ojbiyy5w"]
|
||||
|
||||
[ext_resource type="Script" uid="uid://crgac4manhoud" path="res://_game/game.gd" id="1_yksyv"]
|
||||
[ext_resource type="PackedScene" uid="uid://cvqehvdjpoar4" path="res://_player/player_controller.tscn" id="2_x2i0j"]
|
||||
|
|
@ -14,6 +14,26 @@
|
|||
[ext_resource type="PackedScene" uid="uid://2d457ndb7toe" path="res://_scene/level1/l1_s8.tscn" id="11_ktxjv"]
|
||||
[ext_resource type="PackedScene" uid="uid://dcoq4q3brnkw6" path="res://_scene/level1/l1_s9.tscn" id="12_enubi"]
|
||||
[ext_resource type="PackedScene" uid="uid://dsw3o2bhc8bve" path="res://_scene/level1/l1_s10.tscn" id="13_53pmm"]
|
||||
[ext_resource type="Script" uid="uid://c5in610cunjn2" path="res://_game/water_warp_controller.gd" id="15_jibn5"]
|
||||
[ext_resource type="Shader" uid="uid://ccpo4346to8ka" path="res://_shader/ripple2.gdshader" id="16_ef7py"]
|
||||
|
||||
[sub_resource type="ShaderMaterial" id="ShaderMaterial_5vsgs"]
|
||||
shader = ExtResource("16_ef7py")
|
||||
shader_parameter/debug_show = false
|
||||
shader_parameter/obj_uv = Vector2(0.5, 0.5)
|
||||
shader_parameter/obj_dir = Vector2(1, 0)
|
||||
shader_parameter/obj_speed = 1.0
|
||||
shader_parameter/lane_half_width = 0.085
|
||||
shader_parameter/edge_width = 0.04
|
||||
shader_parameter/trail_length = 0.55
|
||||
shader_parameter/push_strength = 0.075
|
||||
shader_parameter/drag_strength = 0.045
|
||||
shader_parameter/suck_strength = 0.03
|
||||
shader_parameter/curl_strength = 0.07
|
||||
shader_parameter/foam_strength = 0.45
|
||||
shader_parameter/noise_scale = 3.5
|
||||
shader_parameter/noise_advect = 0.5
|
||||
shader_parameter/chroma_shift = 0.6
|
||||
|
||||
[node name="Game" type="Node2D" groups=["PLAYER_RESPAWN"]]
|
||||
script = ExtResource("1_yksyv")
|
||||
|
|
@ -43,3 +63,15 @@ script = ExtResource("1_yksyv")
|
|||
[node name="L1_S9" parent="." instance=ExtResource("12_enubi")]
|
||||
|
||||
[node name="L1_S10" parent="." instance=ExtResource("13_53pmm")]
|
||||
|
||||
[node name="WaterWarp" type="CanvasLayer" parent="." node_paths=PackedStringArray("target")]
|
||||
script = ExtResource("15_jibn5")
|
||||
target = NodePath("../PlayerController")
|
||||
|
||||
[node name="ColorRect" type="ColorRect" parent="WaterWarp"]
|
||||
material = SubResource("ShaderMaterial_5vsgs")
|
||||
anchors_preset = 15
|
||||
anchor_right = 1.0
|
||||
anchor_bottom = 1.0
|
||||
grow_horizontal = 2
|
||||
grow_vertical = 2
|
||||
|
|
|
|||
|
|
@ -57,12 +57,6 @@ func _physics_process(delta: float) -> void:
|
|||
velocity = direction * pull_speed
|
||||
move_and_slide()
|
||||
|
||||
func get_attraction_force(pos: Vector2) -> Vector2:
|
||||
# 返回 (direction, strength) 格式
|
||||
var dir := (global_position - pos).normalized()
|
||||
var strength := 1500 # 调整这个值控制吸引力转向速度
|
||||
return dir * strength
|
||||
|
||||
##如果玩家进入收集区域,则切换为已收集状态。
|
||||
func _on_player_collected(body:CharacterBody2D) -> void:
|
||||
if body is Player:
|
||||
|
|
|
|||
|
|
@ -17,7 +17,6 @@ radius = 34.0147
|
|||
collision_layer = 16
|
||||
collision_mask = 2
|
||||
script = ExtResource("1_8vsnl")
|
||||
pull_speed = null
|
||||
|
||||
[node name="Sprite2D" type="Sprite2D" parent="."]
|
||||
unique_name_in_owner = true
|
||||
|
|
@ -37,7 +36,7 @@ debug_color = Color(0.19215687, 0.6431373, 0, 0)
|
|||
|
||||
[node name="HookAttractVolumn" type="Area2D" parent="."]
|
||||
unique_name_in_owner = true
|
||||
collision_layer = 32
|
||||
collision_layer = 16
|
||||
collision_mask = 0
|
||||
|
||||
[node name="CollisionShape2D" type="CollisionShape2D" parent="HookAttractVolumn"]
|
||||
|
|
|
|||
|
|
@ -225,16 +225,12 @@ tile_set = ExtResource("24_uiy5k")
|
|||
|
||||
[node name="DarkMaterialBall" parent="." instance=ExtResource("30_mu7ca")]
|
||||
position = Vector2(-164, 1283)
|
||||
pull_speed = 800.0
|
||||
|
||||
[node name="DarkMaterialBall2" parent="." instance=ExtResource("30_mu7ca")]
|
||||
position = Vector2(116, 1076)
|
||||
pull_speed = 800.0
|
||||
|
||||
[node name="DarkMaterialBall3" parent="." instance=ExtResource("30_mu7ca")]
|
||||
position = Vector2(33, 1188)
|
||||
pull_speed = 800.0
|
||||
|
||||
[node name="DarkMaterialBall4" parent="." instance=ExtResource("30_mu7ca")]
|
||||
position = Vector2(-78, 1192)
|
||||
pull_speed = 800.0
|
||||
|
|
|
|||
File diff suppressed because one or more lines are too long
|
|
@ -1,78 +1,92 @@
|
|||
[gd_resource type="TileSet" load_steps=5 format=3 uid="uid://cup1q1upvp18h"]
|
||||
[gd_resource type="TileSet" load_steps=7 format=3 uid="uid://cup1q1upvp18h"]
|
||||
|
||||
[ext_resource type="Texture2D" uid="uid://7psxuet3jk1p" path="res://_asset/ksw/basicTile.png" id="1_ln1fl"]
|
||||
[ext_resource type="Texture2D" uid="uid://dd622t4mw5vva" path="res://_asset/ksw/basicTile01.png" id="2_mucy5"]
|
||||
[ext_resource type="Texture2D" uid="uid://cwet2kw1mngmf" path="res://_asset/ksw/basicTile02.png" id="3_u6jqb"]
|
||||
|
||||
[sub_resource type="TileSetAtlasSource" id="TileSetAtlasSource_ln1fl"]
|
||||
texture = ExtResource("1_ln1fl")
|
||||
texture_region_size = Vector2i(96, 96)
|
||||
1:1/0 = 0
|
||||
2:1/0 = 0
|
||||
2:2/0 = 0
|
||||
3:2/0 = 0
|
||||
3:3/0 = 0
|
||||
3:1/0 = 0
|
||||
1:2/0 = 0
|
||||
1:3/0 = 0
|
||||
2:3/0 = 0
|
||||
6:1/0 = 0
|
||||
7:1/0 = 0
|
||||
8:1/0 = 0
|
||||
8:2/0 = 0
|
||||
8:3/0 = 0
|
||||
7:3/0 = 0
|
||||
6:3/0 = 0
|
||||
6:2/0 = 0
|
||||
7:2/0 = 0
|
||||
10:1/0 = 0
|
||||
11:1/0 = 0
|
||||
12:1/0 = 0
|
||||
9:5/0 = 0
|
||||
10:6/0 = 0
|
||||
11:5/0 = 0
|
||||
10:5/0 = 0
|
||||
9:6/0 = 0
|
||||
11:6/0 = 0
|
||||
7:5/0 = 0
|
||||
7:6/0 = 0
|
||||
6:6/0 = 0
|
||||
6:5/0 = 0
|
||||
3:5/0 = 0
|
||||
3:6/0 = 0
|
||||
4:6/0 = 0
|
||||
4:5/0 = 0
|
||||
1:5/0 = 0
|
||||
1:6/0 = 0
|
||||
1:7/0 = 0
|
||||
1:9/0 = 0
|
||||
1:10/0 = 0
|
||||
2:10/0 = 0
|
||||
2:9/0 = 0
|
||||
1:8/0 = 0
|
||||
4:9/0 = 0
|
||||
4:10/0 = 0
|
||||
5:10/0 = 0
|
||||
5:9/0 = 0
|
||||
5:8/0 = 0
|
||||
7:8/0 = 0
|
||||
8:8/0 = 0
|
||||
8:9/0 = 0
|
||||
8:10/0 = 0
|
||||
7:9/0 = 0
|
||||
6:9/0 = 0
|
||||
10:9/0 = 0
|
||||
11:9/0 = 0
|
||||
11:10/0 = 0
|
||||
10:10/0 = 0
|
||||
9:9/0 = 0
|
||||
9:10/0 = 0
|
||||
10:8/0 = 0
|
||||
11:8/0 = 0
|
||||
8:5/0 = 0
|
||||
9:4/0 = 0
|
||||
11:4/0 = 0
|
||||
7:4/0 = 0
|
||||
3:4/0 = 0
|
||||
1:4/0 = 0
|
||||
|
||||
[sub_resource type="TileSetAtlasSource" id="TileSetAtlasSource_u6jqb"]
|
||||
texture = ExtResource("2_mucy5")
|
||||
texture_region_size = Vector2i(96, 96)
|
||||
3:1/0 = 0
|
||||
3:2/0 = 0
|
||||
2:2/0 = 0
|
||||
5:1/0 = 0
|
||||
5:2/0 = 0
|
||||
6:2/0 = 0
|
||||
8:1/0 = 0
|
||||
8:2/0 = 0
|
||||
9:1/0 = 0
|
||||
11:1/0 = 0
|
||||
12:1/0 = 0
|
||||
12:2/0 = 0
|
||||
12:4/0 = 0
|
||||
12:5/0 = 0
|
||||
12:6/0 = 0
|
||||
10:6/0 = 0
|
||||
10:5/0 = 0
|
||||
9:5/0 = 0
|
||||
9:6/0 = 0
|
||||
7:5/0 = 0
|
||||
6:5/0 = 0
|
||||
6:6/0 = 0
|
||||
7:6/0 = 0
|
||||
4:6/0 = 0
|
||||
4:5/0 = 0
|
||||
3:5/0 = 0
|
||||
2:5/0 = 0
|
||||
2:6/0 = 0
|
||||
3:6/0 = 0
|
||||
|
||||
[sub_resource type="TileSetAtlasSource" id="TileSetAtlasSource_wtljp"]
|
||||
texture = ExtResource("3_u6jqb")
|
||||
texture_region_size = Vector2i(96, 96)
|
||||
10:6/0 = 0
|
||||
6:1/0 = 0
|
||||
6:2/0 = 0
|
||||
6:3/0 = 0
|
||||
6:4/0 = 0
|
||||
7:2/0 = 0
|
||||
7:3/0 = 0
|
||||
11:1/0 = 0
|
||||
12:1/0 = 0
|
||||
12:2/0 = 0
|
||||
12:3/0 = 0
|
||||
12:4/0 = 0
|
||||
11:4/0 = 0
|
||||
9:6/0 = 0
|
||||
8:6/0 = 0
|
||||
5:8/0 = 0
|
||||
5:9/0 = 0
|
||||
5:10/0 = 0
|
||||
6:10/0 = 0
|
||||
7:10/0 = 0
|
||||
7:9/0 = 0
|
||||
7:8/0 = 0
|
||||
6:8/0 = 0
|
||||
10:8/0 = 0
|
||||
11:8/0 = 0
|
||||
12:8/0 = 0
|
||||
12:9/0 = 0
|
||||
12:10/0 = 0
|
||||
11:10/0 = 0
|
||||
10:10/0 = 0
|
||||
10:9/0 = 0
|
||||
11:9/0 = 0
|
||||
|
||||
[resource]
|
||||
tile_size = Vector2i(96, 96)
|
||||
sources/0 = SubResource("TileSetAtlasSource_ln1fl")
|
||||
sources/1 = SubResource("TileSetAtlasSource_u6jqb")
|
||||
sources/2 = SubResource("TileSetAtlasSource_wtljp")
|
||||
|
|
|
|||
|
|
@ -1,10 +1,7 @@
|
|||
[gd_scene load_steps=3 format=3 uid="uid://ddwoxlqluxiq5"]
|
||||
[gd_scene load_steps=2 format=3 uid="uid://ddwoxlqluxiq5"]
|
||||
|
||||
[ext_resource type="Script" uid="uid://bvxgviq7l64ck" path="res://addons/reedcomponent/grap_hook/garpping_hook_v_2.gd" id="1_jrg4x"]
|
||||
|
||||
[sub_resource type="CircleShape2D" id="CircleShape2D_jrg4x"]
|
||||
radius = 5.0990195
|
||||
|
||||
[node name="GarppingHookV2" type="Node2D"]
|
||||
script = ExtResource("1_jrg4x")
|
||||
|
||||
|
|
@ -18,12 +15,3 @@ unique_name_in_owner = true
|
|||
target_position = Vector2(80, 0)
|
||||
collision_mask = 20
|
||||
collide_with_areas = true
|
||||
|
||||
[node name="TipDetector" type="Area2D" parent="."]
|
||||
position = Vector2(80, 0)
|
||||
collision_layer = 0
|
||||
collision_mask = 32
|
||||
|
||||
[node name="CollisionShape2D" type="CollisionShape2D" parent="TipDetector"]
|
||||
shape = SubResource("CircleShape2D_jrg4x")
|
||||
debug_color = Color(0, 0.6, 0.69803923, 0)
|
||||
|
|
|
|||
|
|
@ -13,7 +13,6 @@ extends Node2D
|
|||
|
||||
@onready var line_2d: Line2D = %Line2D
|
||||
@onready var ray: RayCast2D = %RayCast2D
|
||||
@onready var tip_detector: Area2D = $TipDetector
|
||||
|
||||
var _tween: Tween
|
||||
|
||||
|
|
@ -58,7 +57,6 @@ func start_stretching(direction: Vector2) -> void:
|
|||
_cached_cancel = false
|
||||
_stretching_dir = direction.normalized()
|
||||
_current_length = 0.0
|
||||
_current_velocity = Vector2.ZERO # 重置速度
|
||||
|
||||
_dir_id = _get_direction_id(direction,8)
|
||||
|
||||
|
|
@ -70,7 +68,6 @@ func end_stretching(force_end: bool = false) -> bool:
|
|||
|
||||
_is_stretching = false
|
||||
_stretching_dir = Vector2.ZERO
|
||||
_current_velocity = Vector2.ZERO # 重置速度
|
||||
return true
|
||||
|
||||
func is_stretching() -> bool:
|
||||
|
|
@ -100,42 +97,16 @@ func _process(_delta: float) -> void:
|
|||
# Core Logic
|
||||
# =================
|
||||
|
||||
## 钩爪当前速度
|
||||
var _current_velocity: Vector2 = Vector2.ZERO
|
||||
## 最大速度上限
|
||||
@export var max_speed: float = 800.0
|
||||
|
||||
func _update_stretching(delta: float) -> void:
|
||||
# 检测前端点的吸引力 (direction, strength)
|
||||
var attract_config := _get_attraction_at(global_position + _current_velocity.normalized() * _current_length)
|
||||
|
||||
# 初始速度(沿当前方向持续向前)
|
||||
if _current_velocity == Vector2.ZERO:
|
||||
_current_velocity = get_stretching_dir() * stretching_speed
|
||||
|
||||
# 应用吸引力作为加速度
|
||||
if attract_config.strength > 0:
|
||||
var acceleration : Vector2 = attract_config.dir * attract_config.strength
|
||||
_current_velocity += acceleration * delta
|
||||
|
||||
# 限制最大速度
|
||||
if _current_velocity.length() > max_speed:
|
||||
_current_velocity = _current_velocity.normalized() * max_speed
|
||||
|
||||
# 基于更新后的速度预测“下一帧累计长度”
|
||||
var velocity_dir := _current_velocity.normalized()
|
||||
var velocity_mag := _current_velocity.length()
|
||||
|
||||
var next_length := _current_length + velocity_mag * delta
|
||||
# 先嘗試推進
|
||||
var next_length := _current_length + stretching_speed * delta
|
||||
next_length = min(next_length, max_length)
|
||||
|
||||
# 预测末端位置:起点 + 方向 * 累计长度
|
||||
var predicted_pos := global_position + velocity_dir * next_length
|
||||
# 使用 getter 获取当前方向(允许外部复写)
|
||||
var current_dir := get_stretching_dir()
|
||||
|
||||
tip_detector.global_position = predicted_pos
|
||||
|
||||
# RayCast 也应该射到“累计长度”
|
||||
ray.target_position = velocity_dir * next_length
|
||||
# 先用「下一幀長度」做 Ray
|
||||
ray.target_position = current_dir * next_length
|
||||
ray.force_raycast_update()
|
||||
|
||||
# ===== 命中檢測(最高優先)=====
|
||||
|
|
@ -143,12 +114,13 @@ func _update_stretching(delta: float) -> void:
|
|||
var collider := ray.get_collider()
|
||||
if collider is Node2D and collider.is_in_group(GRAPABLE_GROUP):
|
||||
var hit_pos := ray.get_collision_point()
|
||||
|
||||
_current_length = global_position.distance_to(hit_pos)
|
||||
ray.target_position = velocity_dir * _current_length
|
||||
ray.target_position = current_dir * _current_length
|
||||
_handle_hit(collider as Node2D, hit_pos)
|
||||
return
|
||||
|
||||
# ===== 没命中,才正式推進 =====
|
||||
# ===== 沒命中,才正式推進 =====
|
||||
_current_length = next_length
|
||||
|
||||
# 取消邏輯
|
||||
|
|
@ -162,33 +134,9 @@ func _update_stretching(delta: float) -> void:
|
|||
stretching_finished.emit(true, null)
|
||||
end_stretching(true)
|
||||
|
||||
## 在指定位置检测吸引力,返回 {"dir": Vector2, "strength": float}
|
||||
func _get_attraction_at(pos: Vector2) -> Dictionary:
|
||||
var total_force := Vector2.ZERO
|
||||
|
||||
# 检测 Areas
|
||||
for area in tip_detector.get_overlapping_areas():
|
||||
if area is Node2D and area.has_method("get_attraction_force"):
|
||||
total_force += area.get_attraction_force(pos)
|
||||
elif area.owner is Node2D and area.owner.has_method("get_attraction_force"):
|
||||
total_force += area.owner.get_attraction_force(pos)
|
||||
|
||||
# 检测 Bodies
|
||||
for body in tip_detector.get_overlapping_bodies():
|
||||
if body is Node2D and body.has_method("get_attraction_force"):
|
||||
total_force += body.get_attraction_force(pos)
|
||||
elif body.owner is Node2D and body.owner.has_method("get_attraction_force"):
|
||||
total_force += body.owner.get_attraction_force(pos)
|
||||
|
||||
# 返回 {"dir": direction, "strength": magnitude}
|
||||
if total_force != Vector2.ZERO:
|
||||
return {"dir": total_force.normalized(), "strength": total_force.length()}
|
||||
return {"dir": Vector2.ZERO, "strength": 0.0}
|
||||
|
||||
func _handle_hit(target: Node2D, hit_pos: Vector2) -> void:
|
||||
_is_stretching = false
|
||||
_stretching_dir = Vector2.ZERO
|
||||
_current_velocity = Vector2.ZERO # 重置速度
|
||||
|
||||
ray.target_position = to_local(hit_pos)
|
||||
|
||||
|
|
@ -207,7 +155,6 @@ func _release_hook() -> void:
|
|||
# 1. 停止拉伸(保險)
|
||||
_is_stretching = false
|
||||
_stretching_dir = Vector2.ZERO
|
||||
_current_velocity = Vector2.ZERO # 重置速度
|
||||
_cached_cancel = false
|
||||
_current_length = 0.0
|
||||
|
||||
|
|
|
|||
|
|
@ -97,4 +97,3 @@ grap_hook={
|
|||
2d_physics/layer_3="Environment"
|
||||
2d_physics/layer_4="Damage"
|
||||
2d_physics/layer_5="Collectable"
|
||||
2d_physics/layer_6="Hook_Attract"
|
||||
|
|
|
|||
Loading…
Reference in New Issue