From ee2b9d4dac47a106140396333dd4b8c0571f7f19 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Micha=C3=ABl=20Lemaire?= Date: Mon, 10 Feb 2020 00:28:05 +0100 Subject: [PATCH] Added basic unit combat --- arenas/anchor.gd | 14 +++++++-- helpers/battle.gd | 17 +++++++++++ project.godot | 14 ++++++++- screens/battle/battle.gd | 2 ++ tests/unit_combat.tscn | 37 +++++++++++++++++++++++ units/base_unit.gd | 63 +++++++++++++++++++++++++++++++++++++++- units/points.gd | 2 ++ 7 files changed, 144 insertions(+), 5 deletions(-) create mode 100644 tests/unit_combat.tscn diff --git a/arenas/anchor.gd b/arenas/anchor.gd index 0f63147..3e71c82 100644 --- a/arenas/anchor.gd +++ b/arenas/anchor.gd @@ -5,7 +5,7 @@ class_name Anchor export var selectable = false export var selected = false export(String, "normal", "attack_start", "defend_start") var anchor_type = "normal" -var content +export(NodePath) var content func _process(delta): if selected: @@ -32,7 +32,15 @@ func set_content(val): old_parent.set_content(null) old_parent.remove_child(val) self.add_child(val) - content = val + content = val.get_path() + else: + content = null + +func get_content(): + if content: + return get_node_or_null(content) + else: + return null func is_empty() -> bool: - return not content + return not get_content() diff --git a/helpers/battle.gd b/helpers/battle.gd index 1b9d132..ad2592d 100644 --- a/helpers/battle.gd +++ b/helpers/battle.gd @@ -26,3 +26,20 @@ static func spawn_unit(name: String, anchor: Anchor) -> Node: var node = scene.instance() anchor.set_content(node) return node + +static func get_state(tree: SceneTree): + """ Build the simple state associated with current battle scene + """ + var nodes = [] + var routes = [] + + for anchor in tree.get_nodes_in_group("anchors"): + pass + + for route in tree.get_nodes_in_group("routes"): + pass + + return { + "nodes": nodes, + "routes": routes + } diff --git a/project.godot b/project.godot index 46b69aa..9c35dc9 100644 --- a/project.godot +++ b/project.godot @@ -14,14 +14,26 @@ _global_script_classes=[ { "language": "GDScript", "path": "res://arenas/anchor.gd" }, { +"base": "Panel", +"class": "BaseUnit", +"language": "GDScript", +"path": "res://units/base_unit.gd" +}, { "base": "Line2D", "class": "Route", "language": "GDScript", "path": "res://arenas/route.gd" +}, { +"base": "Control", +"class": "UnitPoints", +"language": "GDScript", +"path": "res://units/points.gd" } ] _global_script_class_icons={ "Anchor": "", -"Route": "" +"BaseUnit": "", +"Route": "", +"UnitPoints": "" } [application] diff --git a/screens/battle/battle.gd b/screens/battle/battle.gd index 862148b..3ac6c5e 100644 --- a/screens/battle/battle.gd +++ b/screens/battle/battle.gd @@ -17,6 +17,8 @@ func _ready(): fill_hand($hand_attack, deck_attack_cards, hero_attack) fill_hand($hand_defend, deck_defend_cards, hero_defend) + print(BattleHelper.get_state(get_tree())) + func find_free_anchor(anchor_type: String): for anchor in get_tree().get_nodes_in_group("anchors"): if anchor.anchor_type == anchor_type and anchor.is_empty(): diff --git a/tests/unit_combat.tscn b/tests/unit_combat.tscn new file mode 100644 index 0000000..a92f202 --- /dev/null +++ b/tests/unit_combat.tscn @@ -0,0 +1,37 @@ +[gd_scene load_steps=6 format=2] + +[ext_resource path="res://arenas/route.tscn" type="PackedScene" id=1] +[ext_resource path="res://arenas/anchor.tscn" type="PackedScene" id=2] +[ext_resource path="res://units/trapper.tscn" type="PackedScene" id=3] +[ext_resource path="res://units/flea.tscn" type="PackedScene" id=4] +[ext_resource path="res://units/avenger.tscn" type="PackedScene" id=5] + +[node name="Node2D" type="Node2D"] + +[node name="route" parent="." instance=ExtResource( 1 )] +points = PoolVector2Array( 400, 800, 700, 800 ) +start = NodePath("../anchor") +end = NodePath("../anchor2") + +[node name="route2" parent="." instance=ExtResource( 1 )] +points = PoolVector2Array( 400, 800, 550, 1100 ) +start = NodePath("../anchor") +end = NodePath("../anchor3") + +[node name="anchor" parent="." instance=ExtResource( 2 )] +position = Vector2( 400, 800 ) +content = NodePath("flea") + +[node name="flea" parent="anchor" instance=ExtResource( 4 )] + +[node name="anchor2" parent="." instance=ExtResource( 2 )] +position = Vector2( 700, 800 ) +content = NodePath("trapper") + +[node name="trapper" parent="anchor2" instance=ExtResource( 3 )] + +[node name="anchor3" parent="." instance=ExtResource( 2 )] +position = Vector2( 550, 1100 ) +content = NodePath("avenger") + +[node name="avenger" parent="anchor3" instance=ExtResource( 5 )] diff --git a/units/base_unit.gd b/units/base_unit.gd index 4f59a8a..e8fc9ff 100644 --- a/units/base_unit.gd +++ b/units/base_unit.gd @@ -1,6 +1,8 @@ tool extends Panel +class_name BaseUnit + const AnimHelper = preload("res://helpers/anims.gd") const BattleHelper = preload("res://helpers/battle.gd") @@ -23,6 +25,12 @@ func _ready(): set_base_hull_points(base_hull_points) set_base_shield_points(base_shield_points) +func destroy(): + if get_parent() is Anchor: + (get_parent() as Anchor).set_content(null) + + queue_free() + func set_sprite(val): sprite = val if has_node("sprite"): @@ -47,17 +55,70 @@ func set_base_damage_points(val): base_damage_points = val if has_node("points"): $points.damage = val + +func can_target(other): + if other == self: + return false + else: + return true func can_be_used_on_anchor(anchor): - return anchor is Anchor and anchor.is_empty() and anchor.is_connected_to(get_parent()) + return anchor is Anchor and anchor.is_connected_to(get_parent()) and (anchor.is_empty() or can_target(anchor.get_content())) func update_anchors(): var position = rect_global_position + rect_size / 2 if dragged else null selected_anchor = BattleHelper.update_anchors(get_tree(), position, funcref(self, "can_be_used_on_anchor")) func play(anchor): + if anchor.is_empty(): + move_to(anchor) + else: + var other = anchor.get_content() + if other.has_method("get_points"): + var won = attack(other) + if won: + move_to(anchor) + else: + return_to_base() + else: + return_to_base() + +func move_to(anchor): anchor.set_content(self) rect_position = base_position + +func get_points() -> UnitPoints: + if $points is UnitPoints: + return $points as UnitPoints + else: + return null + +func attack(other) -> bool: + var selfpoints = get_points() + var otherpoints = other.get_points() + + while selfpoints.damage: + selfpoints.damage -= 1 + + if otherpoints.shield: + otherpoints.shield -= 1 + elif otherpoints.hull: + otherpoints.hull -= 1 + + while otherpoints.damage: + otherpoints.damage -= 1 + + if selfpoints.shield: + selfpoints.shield -= 1 + elif selfpoints.hull: + selfpoints.hull -= 1 + + if selfpoints.hull <= 0: + destroy() + if otherpoints.hull <= 0: + other.destroy() + + return selfpoints.hull > 0 && otherpoints.hull == 0 func return_to_base(): AnimHelper.linear_goto(self, base_position, 0.3) diff --git a/units/points.gd b/units/points.gd index 902c44b..ca6d3bf 100644 --- a/units/points.gd +++ b/units/points.gd @@ -1,6 +1,8 @@ tool extends Control +class_name UnitPoints + export var move = 0 setget set_move export var hull = 0 setget set_hull export var shield = 0 setget set_shield