sokoban
Diffstat (limited to 'Level.gd')
-rw-r--r--Level.gd304
1 files changed, 0 insertions, 304 deletions
diff --git a/Level.gd b/Level.gd
deleted file mode 100644
index df597f8..0000000
--- a/Level.gd
+++ /dev/null
@@ -1,304 +0,0 @@
-extends Node2D
-
-const GRID_SIZE = 16
-const grassDecorationIds = [0, 1, 2, 3, 4, 5, 6, 7]
-const treeDecorationIds = [8, 9, 10, 11]
-const stoneDecorationIds = [12, 13, 14, 15, 16]
-const mushroomDecorationIds = [17, 18, 19, 20, 21, 22, 23, 24]
-var explosionEffect = preload("res://ExplosionEffect.tscn")
-
-var thread: Thread
-var wall_positions: PoolVector2Array = []
-var crate_prefab = preload("res://Crate.tscn")
-var target_prefab = preload("res://Target.tscn")
-
-var game_over := false
-
-onready var crates = $LevelContainer/Crates
-onready var player = $LevelContainer/Player
-onready var targets = $LevelContainer/Targets
-onready var walls = $LevelContainer/Walls
-onready var floors = $LevelContainer/Floors
-onready var timer = $Timer
-onready var others = $LevelContainer/Others
-onready var cam = $LevelContainer/Player/Camera2D
-var consol
-
-var current_level := ""
-onready var tilemaps = [walls, others, floors]
-var just_started = true
-
-var level_size = Vector2(0, 0)
-
-signal game_over
-signal level_completed(completed)
-signal level_reset
-signal level_made
-
-
-func _ready():
- player.connect("level_reset_requested", self, "_on_Player_level_reset_requested")
- thread = Thread.new()
- reset_time()
-
-
-func reset_time():
- MainInstances.stopwatch.reset()
- player.started = false
-
-
-func start_stopwatch():
- MainInstances.stopwatch.start()
-
-
-func load_level(level: String, decorate = true):
- $LevelContainer/Walls.modulate = Color.white
- $LevelContainer/Player/RayCast2D.set_collision_mask_bit(0, true)
- if thread.is_alive():
- return
- if thread.is_active():
- thread.wait_to_finish()
- reset_time()
- consol = MainInstances.console
- if decorate:
- consol.Log("Generating level " + level, .5, .5)
- SaveLoad.files.level.data.current_level = level
- SaveLoad.save("level")
- thread.start(self, "level_load", [level, decorate])
-
-
-func level_load(level: Array):
- just_started = true
- player.set_moves(0)
- current_level = level[0]
- call_deferred("_reset_level", level[1])
-
-
-func _exit_tree():
- if thread.is_active():
- thread.wait_to_finish()
-
-
-func _reset_level(decorate):
- game_over = false
- player.initialize()
- delete_children(crates)
- if decorate:
- walls.clear()
- others.clear()
- delete_children(floors)
- delete_children(targets)
-
- if current_level == "":
- return
-
- var file = File.new()
- file.open("res://Levels/%s.sokolvl" % current_level, File.READ)
-
- var version = 0
- var row = 0
- var player_pos
- level_size = Vector2(0, 0)
-
- while !file.eof_reached():
- var line = file.get_line()
- if line.begins_with(";"):
- var meta = line.split(": ", false, 1)
- if meta[0] == ";version":
- version = int(meta[1])
- elif line != "":
- if version != 1:
- push_error("Not supported .sokolvl version: " + str(version))
- return
- var col = 0
-
- for x in line:
- var tile_pos = Vector2(col, row) * GRID_SIZE
-
- if x == "#":
- if decorate:
- add_wall(tile_pos)
- if x in [".", "X", "O", "@", "%", "A"]:
- if decorate:
- add_floor(tile_pos)
- if x in ["@", "A"]:
- player_pos = tile_pos
- if x in ["X", "%"]:
- add_crate(tile_pos)
- if x in ["O", "%", "A"]:
- if decorate:
- add_target(tile_pos)
-
- col += 1
- row += 1
- level_size.y += 1
- level_size.x = max(level_size.x, col)
-
- file.close()
-
- $CanvasLayer/HUD/LevelLabel.text = "Level = %s" % current_level
-
- var new_zoom = .5
- new_zoom = clamp(new_zoom, get_parent().min_zoom, get_parent().max_zoom)
- new_zoom = Vector2(new_zoom, new_zoom)
- var level_int
- if level_size.x > level_size.y:
- level_int = level_size.x
- else:
- level_int = level_size.y
-
- new_zoom += Vector2(level_int / 45, level_int / 45)
- $Tween.interpolate_property(
- cam, "zoom", cam.zoom, new_zoom, 2, Tween.TRANS_LINEAR, Tween.EASE_IN_OUT
- )
- $Tween.start()
- timer.start(2)
- if decorate:
- decorate(-50, 50)
- initialize_player(player_pos)
- Utils.unload_loading_screen()
- yield(timer, "timeout")
- just_started = false
- emit_signal("level_made")
- return
-
-
-static func delete_children(node):
- for n in node.get_children():
- node.remove_child(n)
- n.queue_free()
-
-
-func decorate(x, y):
- for tile in check_for_empty_tile(Vector2(x, y)):
- match randi() % 101:
- 1:
- add_mushroom(tile)
- 2:
- add_rock(tile)
- 3:
- add_tree(tile)
-
-
-func _on_Crate_target_updated():
- var crates_in_place = 0
-
- for crate in crates.get_children():
- if crate.target_count > 0:
- crates_in_place += 1
-
- if crates_in_place == crates.get_child_count():
- emit_signal("level_completed")
-
-
-func _on_Player_level_reset_requested():
- if player.tween.is_active():
- yield(player.tween, "tween_all_completed")
- load_level(current_level, false)
- emit_signal("level_reset")
-
-
-func _on_Crate_game_over():
- if not game_over:
- game_over = true
- emit_signal("game_over")
-
-
-func add_target(tile_pos):
- var target = target_prefab.instance()
- target.main = self
- target.position = tile_pos
- targets.add_child(target)
-
-
-func add_crate(tile_pos):
- var crate = crate_prefab.instance()
- crate.position = tile_pos
- crate.main = get_parent()
- crate.connect("target_updated", self, "_on_Crate_target_updated")
- crate.connect("game_over_detected", self, "_on_Crate_game_over")
- crates.add_child(crate)
-
-
-func initialize_player(tile_pos):
- player.position = tile_pos
- player.world = get_parent()
-
-
-func add_floor(tile_pos):
- floors.set_cellv(tile_pos / 16, 0)
- randomize()
- if randi() % 5 == 2:
- others.set_cellv(tile_pos / 16, grassDecorationIds[randi() % grassDecorationIds.size()])
-
-
-func add_wall(tile_pos):
- wall_positions.append(tile_pos)
- walls.set_cellv(tile_pos / 16, 1)
- walls.update_bitmask_area(tile_pos / 16)
-
-
-func check_for_empty_tile(size: Vector2 = Vector2(-75, 75)):
- var empty_tiles: PoolVector2Array = []
- for x in range(size.x, size.y):
- for y in range(size.x, size.y):
- var tile_pos = Vector2(x, y)
- var lower_tile_pos = tile_pos
- var left_tile_pos = tile_pos
- var right_tile_pos = tile_pos
- var up_tile_pos = tile_pos
- var down_right_tile_pos = tile_pos
- var down_left_tile_pos = tile_pos
- down_right_tile_pos += Vector2.DOWN + Vector2.RIGHT
- down_left_tile_pos += Vector2.DOWN + Vector2.LEFT
- lower_tile_pos += Vector2.DOWN
- left_tile_pos += Vector2.LEFT
- right_tile_pos += Vector2.RIGHT
- up_tile_pos += Vector2.UP
- var tile_positions = [
- down_left_tile_pos,
- down_right_tile_pos,
- lower_tile_pos,
- left_tile_pos,
- right_tile_pos,
- up_tile_pos,
- tile_pos
- ]
- var count2 := 0
- for tile in tile_positions:
- var count := 0
- for tilemap in tilemaps:
- if empty(tilemap, tile):
- count += 1
- if count == tilemaps.size():
- count2 += 1
- if count2 == tile_positions.size():
- empty_tiles.append(tile_pos)
- return empty_tiles
-
-
-func empty(tilemap, tile) -> bool:
- if tilemap.get_cellv(tile) != -1:
- return false
- return true
-
-
-func add_tree(tile):
- others.set_cellv(tile, treeDecorationIds[randi() % treeDecorationIds.size()])
-
-
-func add_rock(tile):
- others.set_cellv(tile, stoneDecorationIds[randi() % stoneDecorationIds.size()])
-
-
-func add_mushroom(tile):
- others.set_cellv(tile, mushroomDecorationIds[randi() % mushroomDecorationIds.size()])
-
-
-func explode_walls():
- for positions in wall_positions:
- Utils.instance_scene_on_main(positions, explosionEffect)
-
-
-func _on_Player_won():
- emit_signal("level_completed", true)