Refactor RPG Demo

closes #263 

- Rename dialog to dialogue
- Give meaningful name to generic actors
- Move combat screen content to turn_combat folder
- Add new icon.png and .svg
- Change combat UI to not emit a signal from its parent, instead pass parameters to a function and let the combat work on them there
- Remove UI accessing deep layers on the hierarchy (get_parent().get_node("../etc/etc../etc...")
- Fix defend() stacking, making the player invulnerable, now evey turn the Health.armor resets to a base_armor value
- Remove useless Inventory button (maybe added again in the future when an inventory is added to the demo)
This commit is contained in:
Henrique Campos
2018-09-22 23:07:46 -03:00
committed by Nathan Lovato
parent 5b01dccc82
commit 2c260e0103
47 changed files with 1240 additions and 361 deletions

View File

@@ -0,0 +1,52 @@
extends Node
export (NodePath) var combat_screen
export (NodePath) var exploration_screen
const PLAYER_WIN = "res://dialogue/dialogue_data/player_won.json"
const PLAYER_LOSE = "res://dialogue/dialogue_data/player_lose.json"
func _ready():
exploration_screen = get_node(exploration_screen)
combat_screen = get_node(combat_screen)
combat_screen.connect("combat_finished", self, "_on_combat_finished")
for n in $Exploration/Grid.get_children():
if not n.type == n.ACTOR:
continue
if not n.has_node("DialoguePlayer"):
continue
n.get_node("DialoguePlayer").connect("dialogue_finished", self,
"_on_opponent_dialogue_finished", [n])
remove_child(combat_screen)
func _on_opponent_dialogue_finished(opponent):
if opponent.lost:
return
var player = $Exploration/Grid/Player
var combatents = [player.combat_actor, opponent.combat_actor]
start_combat(combatents)
func start_combat(combat_actors):
remove_child($Exploration)
$AnimationPlayer.play("fade")
yield($AnimationPlayer, "animation_finished")
add_child(combat_screen)
combat_screen.show()
combat_screen.initialize(combat_actors)
$AnimationPlayer.play_backwards("fade")
func _on_combat_finished(winner, loser):
remove_child(combat_screen)
$AnimationPlayer.play_backwards("fade")
add_child(exploration_screen)
var dialogue = load("res://dialogue/dialogue_player/DialoguePlayer.tscn").instance()
if winner.name == "Player":
dialogue.dialogue_file = PLAYER_WIN
else:
dialogue.dialogue_file = PLAYER_LOSE
yield($AnimationPlayer, "animation_finished")
var player = $Exploration/Grid/Player
exploration_screen.get_node("DialogueUI").show_dialogue(player, dialogue)
combat_screen.clear_combat()
yield(dialogue, "dialogue_finished")
dialogue.queue_free()

View File

@@ -1,65 +1,10 @@
[gd_scene load_steps=5 format=2]
[ext_resource path="res://screens/combat/Combat.tscn" type="PackedScene" id=1]
[ext_resource path="res://screens/exploration/Exploration.tscn" type="PackedScene" id=2]
[ext_resource path="res://Game.gd" type="Script" id=1]
[ext_resource path="res://screens/combat/Combat.tscn" type="PackedScene" id=2]
[ext_resource path="res://screens/exploration/Exploration.tscn" type="PackedScene" id=3]
[sub_resource type="GDScript" id=1]
script/source = "extends Node
export (NodePath) var combat_screen
export (NodePath) var exploration_screen
const PLAYER_WIN = \"res://dialog_system/dialogs/player_won.json\"
const PLAYER_LOSE = \"res://dialog_system/dialogs/player_lose.json\"
func _ready():
exploration_screen = get_node(exploration_screen)
combat_screen = get_node(combat_screen)
combat_screen.connect(\"combat_finished\", self, \"_on_combat_finished\")
for n in $Exploration/Grid.get_children():
if not n.type == n.ACTOR:
continue
if not n.has_node(\"DialogPlayer\"):
continue
n.get_node(\"DialogPlayer\").connect(\"dialog_finished\", self,
\"_on_opponent_dialog_finished\", [n])
remove_child(combat_screen)
func _on_opponent_dialog_finished(opponent):
if opponent.lost:
return
var player = $Exploration/Grid/Player
var combatents = [player.combat_actor, opponent.combat_actor]
start_combat(combatents)
func start_combat(combat_actors):
remove_child($Exploration)
$AnimationPlayer.play(\"fade\")
yield($AnimationPlayer, \"animation_finished\")
add_child(combat_screen)
combat_screen.show()
combat_screen.initialize(combat_actors)
$AnimationPlayer.play_backwards(\"fade\")
func _on_combat_finished(winner, loser):
remove_child(combat_screen)
$AnimationPlayer.play_backwards(\"fade\")
add_child(exploration_screen)
var dialog = load(\"res://dialog_system/dialog_player/DialogPlayer.tscn\").instance()
if winner.name == \"Player\":
dialog.dialog_file = PLAYER_WIN
else:
dialog.dialog_file = PLAYER_LOSE
yield($AnimationPlayer, \"animation_finished\")
var player = $Exploration/Grid/Player
exploration_screen.get_node(\"DialogUI\").show_dialog(player, dialog)
combat_screen.clear_combat()
yield(dialog, \"dialog_finished\")
dialog.queue_free()
"
[sub_resource type="Animation" id=2]
[sub_resource type="Animation" id=1]
length = 0.5
loop = false
@@ -77,9 +22,10 @@ tracks/0/keys = {
"values": [ Color( 0.0703125, 0.0703125, 0.0703125, 0 ), Color( 0.0703125, 0.0703125, 0.0703125, 1 ) ]
}
[node name="Game" type="Node"]
[node name="Game" type="Node" index="0"]
script = SubResource( 1 )
script = ExtResource( 1 )
_sections_unfolded = [ "Pause" ]
combat_screen = NodePath("Combat")
exploration_screen = NodePath("Exploration")
@@ -90,7 +36,7 @@ autoplay = ""
playback_process_mode = 1
playback_default_blend_time = 0.0
playback_speed = 1.0
anims/fade = SubResource( 2 )
anims/fade = SubResource( 1 )
blend_times = [ ]
[node name="Transition" type="CanvasLayer" parent="." index="1"]
@@ -118,10 +64,10 @@ size_flags_vertical = 1
color = Color( 0.0703125, 0.0703125, 0.0703125, 0 )
_sections_unfolded = [ "Focus", "Mouse", "Visibility" ]
[node name="Combat" parent="." index="2" instance=ExtResource( 1 )]
[node name="Combat" parent="." index="2" instance=ExtResource( 2 )]
visible = false
[node name="Exploration" parent="." index="3" instance=ExtResource( 2 )]
[node name="Exploration" parent="." index="3" instance=ExtResource( 3 )]

View File

@@ -1,38 +0,0 @@
extends Node
export (String, FILE, "*.json") var dialog_file
var dialog_keys = []
var dialog_name = ""
var current = 0
var dialog_text = ""
signal dialog_started
signal dialog_finished
func start_dialog():
emit_signal("dialog_started")
current = 0
index_dialog()
dialog_text = dialog_keys[current].text
dialog_name = dialog_keys[current].name
func next_dialog():
current += 1
if current == dialog_keys.size():
emit_signal("dialog_finished")
return
dialog_text = dialog_keys[current].text
dialog_name = dialog_keys[current].name
func index_dialog():
var dialog = load_dialogue(dialog_file)
dialog_keys.clear()
for key in dialog:
dialog_keys.append(dialog[key])
func load_dialogue(file_path):
var file = File.new()
if file.file_exists(file_path):
file.open(file_path, file.READ)
var dialog = parse_json(file.get_as_text())
return dialog

View File

@@ -1,12 +0,0 @@
[gd_scene load_steps=2 format=2]
[ext_resource path="res://dialog_system/dialog_player/DialogPlayer.gd" type="Script" id=1]
[node name="DialogPlayer" type="Node"]
script = ExtResource( 1 )
dialog_file = null

View File

@@ -1,3 +1,3 @@
{
"dialog_1" : {"name": "Opponent", "text": "Aha! I won, maybe you can try again next time"},
"dialog_1" : {"name": "Opponent", "text": "Aha! I won, maybe you can try again next time"}
}

View File

@@ -1,3 +1,3 @@
{
"dialog_1" : {"name": "Opponent", "text": "Congratulations, you won!"},
"dialog_1" : {"name": "Opponent", "text": "Congratulations, you won!"}
}

View File

@@ -0,0 +1,38 @@
extends Node
export (String, FILE, "*.json") var dialogue_file
var dialogue_keys = []
var dialogue_name = ""
var current = 0
var dialogue_text = ""
signal dialogue_started
signal dialogue_finished
func start_dialogue():
emit_signal("dialogue_started")
current = 0
index_dialogue()
dialogue_text = dialogue_keys[current].text
dialogue_name = dialogue_keys[current].name
func next_dialogue():
current += 1
if current == dialogue_keys.size():
emit_signal("dialogue_finished")
return
dialogue_text = dialogue_keys[current].text
dialogue_name = dialogue_keys[current].name
func index_dialogue():
var dialogue = load_dialogue(dialogue_file)
dialogue_keys.clear()
for key in dialogue:
dialogue_keys.append(dialogue[key])
func load_dialogue(file_path):
var file = File.new()
if file.file_exists(file_path):
file.open(file_path, file.READ)
var dialogue = parse_json(file.get_as_text())
return dialogue

View File

@@ -0,0 +1,10 @@
[gd_scene load_steps=2 format=2]
[ext_resource path="res://dialogue/dialogue_player/DialoguePlayer.gd" type="Script" id=1]
[node name="DialoguePlayer" type="Node"]
script = ExtResource( 1 )
dialogue_file = null

View File

@@ -0,0 +1,34 @@
extends Control
var dialogue_node = null
func _ready():
hide()
func show_dialogue(player, dialogue):
show()
$Button.grab_focus()
dialogue_node = dialogue
for c in dialogue.get_signal_connection_list("dialogue_finished"):
if self == c.target:
dialogue_node.start_dialogue()
break
return
dialogue_node.connect("dialogue_started", player, "set_active", [false])
dialogue_node.connect("dialogue_finished", player, "set_active", [true])
dialogue_node.connect("dialogue_finished", self, "hide")
dialogue_node.connect("dialogue_finished", self, "_on_dialogue_finished", [player])
dialogue_node.start_dialogue()
$Name.text = dialogue_node.dialogue_name
$Text.text = dialogue_node.dialogue_text
func _on_Button_button_up():
dialogue_node.next_dialogue()
$Name.text = dialogue_node.dialogue_name
$Text.text = dialogue_node.dialogue_text
func _on_dialogue_finished(player):
dialogue_node.disconnect("dialogue_started", player, "set_active")
dialogue_node.disconnect("dialogue_finished", player, "set_active")
dialogue_node.disconnect("dialogue_finished", self, "hide")
dialogue_node.disconnect("dialogue_finished", self, "_on_dialogue_finished")

View File

@@ -1,46 +1,10 @@
[gd_scene load_steps=3 format=2]
[ext_resource path="res://theme/theme.tres" type="Theme" id=1]
[ext_resource path="res://dialogue/interface/Interface.gd" type="Script" id=2]
[sub_resource type="GDScript" id=1]
script/source = "extends Control
var dialog_node = null
func _ready():
hide()
func show_dialog(player, dialog):
show()
$Button.grab_focus()
dialog_node = dialog
for c in dialog.get_signal_connection_list(\"dialog_finished\"):
if self == c.target:
dialog_node.start_dialog()
break
return
dialog_node.connect(\"dialog_started\", player, \"set_active\", [false])
dialog_node.connect(\"dialog_finished\", player, \"set_active\", [true])
dialog_node.connect(\"dialog_finished\", self, \"hide\")
dialog_node.connect(\"dialog_finished\", self, \"_on_dialog_finished\", [player])
dialog_node.start_dialog()
$Name.text = dialog_node.dialog_name
$Text.text = dialog_node.dialog_text
func _on_Button_button_up():
dialog_node.next_dialog()
$Name.text = dialog_node.dialog_name
$Text.text = dialog_node.dialog_text
func _on_dialog_finished(player):
dialog_node.disconnect(\"dialog_started\", player, \"set_active\")
dialog_node.disconnect(\"dialog_finished\", player, \"set_active\")
dialog_node.disconnect(\"dialog_finished\", self, \"hide\")
dialog_node.disconnect(\"dialog_finished\", self, \"_on_dialog_finished\")
"
[node name="DialogUI" type="Panel" index="0"]
[node name="Dialogue" type="Panel"]
anchor_left = 0.0
anchor_top = 0.0
@@ -56,7 +20,7 @@ mouse_default_cursor_shape = 0
size_flags_horizontal = 1
size_flags_vertical = 1
theme = ExtResource( 1 )
script = SubResource( 1 )
script = ExtResource( 2 )
[node name="Name" type="RichTextLabel" parent="." index="0"]
@@ -108,7 +72,7 @@ visible_characters = -1
percent_visible = 1.0
meta_underlined = true
tab_size = 4
text = "Dialog Text"
text = "Dialogue Text"
scroll_active = true
scroll_following = false
selection_enabled = false

View File

@@ -0,0 +1,36 @@
extends TileMap
enum CELL_TYPES { ACTOR, OBSTACLE, OBJECT }
export(NodePath) var dialogue_ui
func _ready():
for child in get_children():
set_cellv(world_to_map(child.position), child.type)
func get_cell_pawn(cell, type = ACTOR):
for node in get_children():
if node.type != type:
continue
if world_to_map(node.position) == cell:
return(node)
func request_move(pawn, direction):
var cell_start = world_to_map(pawn.position)
var cell_target = cell_start + direction
var cell_tile_id = get_cellv(cell_target)
match cell_tile_id:
-1:
set_cellv(cell_target, ACTOR)
set_cellv(cell_start, -1)
return map_to_world(cell_target) + cell_size / 2
OBJECT, ACTOR:
var target_pawn = get_cell_pawn(cell_target, cell_tile_id)
print("Cell %s contains %s" % [cell_target, target_pawn.name])
if not target_pawn.has_node("DialoguePlayer"):
return
get_node(dialogue_ui).show_dialogue(pawn, target_pawn.get_node("DialoguePlayer"))

View File

@@ -0,0 +1,7 @@
extends 'Pawn.gd'
export (PackedScene) var combat_actor
var lost = false
func _ready():
set_process(false)

View File

@@ -0,0 +1,114 @@
[gd_scene load_steps=5 format=2]
[ext_resource path="res://grid_movement/pawns/Walker.gd" type="Script" id=1]
[ext_resource path="res://grid_movement/pawns/sprite.png" type="Texture" id=2]
[sub_resource type="Animation" id=1]
resource_name = "bump"
length = 0.1
loop = false
step = 0.01
tracks/0/type = "value"
tracks/0/path = NodePath("Pivot/Sprite:position")
tracks/0/interp = 1
tracks/0/loop_wrap = true
tracks/0/imported = false
tracks/0/enabled = true
tracks/0/keys = {
"times": PoolRealArray( 0, 0.02, 0.04, 0.06, 0.08, 0.1 ),
"transitions": PoolRealArray( 1, 1, 1, 1, 1, 1 ),
"update": 0,
"values": [ Vector2( 0, 0 ), Vector2( -1.5, -9 ), Vector2( 6.5, 2.5 ), Vector2( -11.5, 8.5 ), Vector2( 4, -5 ), Vector2( 0, 0 ) ]
}
[sub_resource type="Animation" id=2]
resource_name = "walk"
length = 0.25
loop = false
step = 0.05
tracks/0/type = "value"
tracks/0/path = NodePath("Pivot/Sprite:self_modulate")
tracks/0/interp = 1
tracks/0/loop_wrap = true
tracks/0/imported = false
tracks/0/enabled = false
tracks/0/keys = {
"times": PoolRealArray( 0, 0.1, 0.25 ),
"transitions": PoolRealArray( 1, 1, 1 ),
"update": 0,
"values": [ Color( 1, 1, 1, 1 ), Color( 1, 0.9375, 0, 1 ), Color( 1, 1, 1, 1 ) ]
}
tracks/1/type = "value"
tracks/1/path = NodePath("Pivot/Sprite:position")
tracks/1/interp = 1
tracks/1/loop_wrap = true
tracks/1/imported = false
tracks/1/enabled = true
tracks/1/keys = {
"times": PoolRealArray( 0, 0.1, 0.15, 0.25 ),
"transitions": PoolRealArray( 1, 0.303143, 2.61003, 1 ),
"update": 0,
"values": [ Vector2( 1.43051e-06, -1.90735e-06 ), Vector2( 1.43051e-06, -1.90735e-06 ), Vector2( 0, -20 ), Vector2( 1.43051e-06, -1.90735e-06 ) ]
}
tracks/2/type = "value"
tracks/2/path = NodePath("Pivot/Sprite:scale")
tracks/2/interp = 1
tracks/2/loop_wrap = true
tracks/2/imported = false
tracks/2/enabled = true
tracks/2/keys = {
"times": PoolRealArray( 0, 0.05, 0.15, 0.25 ),
"transitions": PoolRealArray( 1, 0.354553, 1, 1 ),
"update": 0,
"values": [ Vector2( 1, 1 ), Vector2( 1.20007, 0.917384 ), Vector2( 0.916712, 1.13495 ), Vector2( 1, 1 ) ]
}
[node name="Actor" type="Node2D"]
position = Vector2( 32, 32 )
z_index = 1
script = ExtResource( 1 )
_sections_unfolded = [ "Offset", "Transform", "Z Index" ]
__meta__ = {
"_edit_group_": true
}
type = 0
combat_actor = null
[node name="AnimationPlayer" type="AnimationPlayer" parent="." index="0"]
root_node = NodePath("..")
autoplay = ""
playback_process_mode = 1
playback_default_blend_time = 0.0
playback_speed = 1.0
anims/bump = SubResource( 1 )
anims/walk = SubResource( 2 )
blend_times = [ ]
[node name="Tween" type="Tween" parent="." index="1"]
repeat = false
playback_process_mode = 1
playback_speed = 1.0
playback/active = false
playback/repeat = false
playback/speed = 1.0
[node name="Pivot" type="Position2D" parent="." index="2"]
_sections_unfolded = [ "Transform" ]
[node name="Sprite" type="Sprite" parent="Pivot" index="0"]
texture = ExtResource( 2 )
centered = false
offset = Vector2( -32, -32 )
_sections_unfolded = [ "Transform", "Visibility" ]

View File

@@ -0,0 +1,11 @@
extends Node2D
enum CELL_TYPES { ACTOR, OBSTACLE, OBJECT }
export(CELL_TYPES) var type = ACTOR
var active = true setget set_active
func set_active(value):
active = value
set_process(value)
set_process_input(value)

View File

@@ -0,0 +1,45 @@
extends 'Pawn.gd'
onready var Grid = get_parent()
export (PackedScene) var combat_actor
var lost = false
func _ready():
update_look_direction(Vector2(1, 0))
func _process(delta):
var input_direction = get_input_direction()
if not input_direction:
return
update_look_direction(input_direction)
var target_position = Grid.request_move(self, input_direction)
if target_position:
move_to(target_position)
$Tween.start()
else:
bump()
func get_input_direction():
return Vector2(
int(Input.is_action_pressed("ui_right")) - int(Input.is_action_pressed("ui_left")),
int(Input.is_action_pressed("ui_down")) - int(Input.is_action_pressed("ui_up"))
)
func update_look_direction(direction):
$Pivot/Sprite.rotation = direction.angle()
func move_to(target_position):
set_process(false)
$AnimationPlayer.play("walk")
var move_direction = (position - target_position).normalized()
$Tween.interpolate_property($Pivot, "position", move_direction * 32, Vector2(), $AnimationPlayer.current_animation_length, Tween.TRANS_LINEAR, Tween.EASE_IN)
$Pivot/Sprite.position = position - target_position
position = target_position
yield($AnimationPlayer, "animation_finished")
set_process(true)
func bump():
$AnimationPlayer.play("bump")

Binary file not shown.

After

Width:  |  Height:  |  Size: 1.2 KiB

View File

@@ -0,0 +1,29 @@
[remap]
importer="texture"
type="StreamTexture"
path="res://.import/sprite.png-e28cedc69371816a3468e6325b327ece.stex"
[deps]
source_file="res://grid_movement/pawns/sprite.png"
dest_files=[ "res://.import/sprite.png-e28cedc69371816a3468e6325b327ece.stex" ]
[params]
compress/mode=0
compress/lossy_quality=0.7
compress/hdr_mode=0
compress/normal_map=0
flags/repeat=0
flags/filter=true
flags/mipmaps=false
flags/anisotropic=false
flags/srgb=2
process/fix_alpha_border=true
process/premult_alpha=false
process/HDR_as_SRGB=false
stream=false
size_limit=0
detect_3d=true
svg/scale=1.0

Binary file not shown.

Before

Width:  |  Height:  |  Size: 3.4 KiB

After

Width:  |  Height:  |  Size: 3.3 KiB

0
2d/role_playing_game/icon.png.import Executable file → Normal file
View File

View File

@@ -0,0 +1,341 @@
<?xml version="1.0" encoding="UTF-8" standalone="no"?>
<!-- Created with Inkscape (http://www.inkscape.org/) -->
<svg
xmlns:dc="http://purl.org/dc/elements/1.1/"
xmlns:cc="http://creativecommons.org/ns#"
xmlns:rdf="http://www.w3.org/1999/02/22-rdf-syntax-ns#"
xmlns:svg="http://www.w3.org/2000/svg"
xmlns="http://www.w3.org/2000/svg"
xmlns:xlink="http://www.w3.org/1999/xlink"
xmlns:sodipodi="http://sodipodi.sourceforge.net/DTD/sodipodi-0.dtd"
xmlns:inkscape="http://www.inkscape.org/namespaces/inkscape"
width="64"
height="64"
viewBox="0 0 16.933333 16.933334"
version="1.1"
id="svg839"
inkscape:version="0.92.2 2405546, 2018-03-11"
sodipodi:docname="icon.svg"
inkscape:export-filename="/home/henrique/Documents/GitHub/godot-demo-projects/2d/role_playing_game/icon.png"
inkscape:export-xdpi="96"
inkscape:export-ydpi="96">
<defs
id="defs833">
<linearGradient
inkscape:collect="always"
id="linearGradient1525">
<stop
style="stop-color:#5f5fd3;stop-opacity:1"
offset="0"
id="stop1521" />
<stop
style="stop-color:#8d5fd3;stop-opacity:1"
offset="1"
id="stop1523" />
</linearGradient>
<clipPath
id="_clip1">
<path
inkscape:connector-curvature="0"
d="M 782,389.065 C 782,379.095 772.59,371 761,371 h -42 c -11.59,0 -21,8.095 -21,18.065 v 144.523 c 0,9.971 9.41,18.065 21,18.065 h 42 c 11.59,0 21,-8.094 21,-18.065 z"
id="path4" />
</clipPath>
<clipPath
id="clipPath1397">
<path
id="path1395"
d="M 782,389.065 C 782,379.095 772.59,371 761,371 h -42 c -11.59,0 -21,8.095 -21,18.065 v 144.523 c 0,9.971 9.41,18.065 21,18.065 h 42 c 11.59,0 21,-8.094 21,-18.065 z"
inkscape:connector-curvature="0" />
</clipPath>
<linearGradient
inkscape:collect="always"
xlink:href="#linearGradient1525"
id="linearGradient1527"
x1="6.1421132"
y1="296.99997"
x2="10.21282"
y2="288.28638"
gradientUnits="userSpaceOnUse" />
</defs>
<sodipodi:namedview
id="base"
pagecolor="#ffffff"
bordercolor="#666666"
borderopacity="1.0"
inkscape:pageopacity="0.0"
inkscape:pageshadow="2"
inkscape:zoom="3.959798"
inkscape:cx="24.889913"
inkscape:cy="29.585249"
inkscape:document-units="mm"
inkscape:current-layer="layer1"
showgrid="false"
units="px"
inkscape:snap-page="true"
inkscape:window-width="1920"
inkscape:window-height="1026"
inkscape:window-x="0"
inkscape:window-y="26"
inkscape:window-maximized="1" />
<metadata
id="metadata836">
<rdf:RDF>
<cc:Work
rdf:about="">
<dc:format>image/svg+xml</dc:format>
<dc:type
rdf:resource="http://purl.org/dc/dcmitype/StillImage" />
<dc:title></dc:title>
</cc:Work>
</rdf:RDF>
</metadata>
<g
inkscape:label="Layer 1"
inkscape:groupmode="layer"
id="layer1"
transform="translate(0,-280.06665)">
<rect
style="opacity:1;fill:url(#linearGradient1527);fill-opacity:1;stroke:none;stroke-width:0.25955623;stroke-linecap:round;stroke-linejoin:round;stroke-miterlimit:4;stroke-dasharray:none;stroke-opacity:1"
id="rect1519"
width="16.933332"
height="16.933332"
x="0"
y="280.06665"
ry="0.16704336" />
<path
style="opacity:0.22000002;fill:#ffffff;fill-opacity:1;stroke:none;stroke-width:0.25955623;stroke-linecap:round;stroke-linejoin:round;stroke-miterlimit:4;stroke-dasharray:none;stroke-opacity:1"
d="m 9.905854,280.06665 -9.68467855,16.77469 c 0.004508,0.0885 0.0762661,0.15864 0.16588052,0.15864 H 1.9528522 L 11.729,280.06665 Z m 3.160014,0 -9.7766636,16.93333 h 1.0945071 l 9.7761475,-16.93333 z m 3.038575,0 -9.7761472,16.93333 h 0.6071976 l 9.7766636,-16.93333 z"
id="rect1542"
inkscape:connector-curvature="0" />
<g
id="g1497"
transform="matrix(1.0119908,0,0,1.0119908,3.2611903,-0.01978024)"
style="stroke-width:1.04486346">
<g
transform="translate(-0.48442605)"
id="g1483"
style="stroke-width:1.04486346">
<path
style="opacity:1;fill:#b7bec8;fill-opacity:1;stroke:#939dac;stroke-width:0.24960057;stroke-miterlimit:4;stroke-dasharray:none;stroke-opacity:1"
d="m 7.1441754,286.28934 c -0.8987875,0 -1.7760709,1.08611 -1.975802,1.43205 -0.3994608,0.69189 1.1986223,3.45955 1.997544,3.45955 0.7989226,0 2.3965286,-2.76766 1.9970676,-3.45955 -0.19973,-0.34594 -1.120022,-1.43205 -2.0188096,-1.43205 z"
id="path1434"
inkscape:connector-curvature="0"
sodipodi:nodetypes="scscs" />
<rect
style="opacity:1;fill:#ac9d93;fill-opacity:1;stroke:#917c6f;stroke-width:0.27120084;stroke-linecap:round;stroke-linejoin:round;stroke-miterlimit:4;stroke-dasharray:none;stroke-opacity:1"
id="rect1479"
width="2.5891733"
height="0.70158249"
x="5.8710999"
y="288.28033"
ry="0.20079997" />
</g>
<path
inkscape:connector-curvature="0"
d="m 6.6335794,284.84194 c 0,-0.50467 -0.4097646,-0.91444 -0.9144587,-0.91444 H 3.8902034 c -0.504694,0 -0.9144586,0.40977 -0.9144586,0.91444 v 7.31568 c 0,0.50472 0.4097646,0.91444 0.9144586,0.91444 h 1.8289173 c 0.5046941,0 0.9144587,-0.40972 0.9144587,-0.91444 z"
style="clip-rule:evenodd;fill:#5dc4f8;fill-rule:evenodd;stroke-width:0.04905583;stroke-linecap:round;stroke-linejoin:bevel;stroke-miterlimit:1.5"
id="path2" />
<g
transform="matrix(0.04354565,0,0,0.05061944,-27.419119,265.14769)"
clip-path="url(#_clip1)"
id="g11"
style="clip-rule:evenodd;fill-rule:evenodd;stroke-width:1.04486346;stroke-linecap:round;stroke-linejoin:bevel;stroke-miterlimit:1.5">
<g
transform="translate(0,42.5826)"
id="g9"
style="stroke-width:1.04486346">
<path
inkscape:connector-curvature="0"
d="M 782,389.065 C 782,379.095 772.59,371 761,371 h -42 c -11.59,0 -21,8.095 -21,18.065 v 144.523 c 0,9.971 9.41,18.065 21,18.065 h 42 c 11.59,0 21,-8.094 21,-18.065 z"
style="fill:#2c9de6;stroke-width:1.04486346"
id="path7" />
</g>
</g>
<path
inkscape:connector-curvature="0"
d="m 6.6335794,284.84194 c 0,-0.50467 -0.4097646,-0.91444 -0.9144587,-0.91444 H 3.8902034 c -0.504694,0 -0.9144586,0.40977 -0.9144586,0.91444 v 7.31568 c 0,0.50472 0.4097646,0.91444 0.9144586,0.91444 h 1.8289173 c 0.5046941,0 0.9144587,-0.40972 0.9144587,-0.91444 z"
style="clip-rule:evenodd;fill:none;fill-rule:evenodd;stroke:#2267c2;stroke-width:0.27120087;stroke-linecap:round;stroke-linejoin:bevel;stroke-miterlimit:1.5;stroke-dasharray:none"
id="path13" />
<g
transform="rotate(-15,7.362507,255.90714)"
id="g1475"
style="stroke-width:1.04486346">
<rect
style="opacity:1;fill:#ac9d93;fill-opacity:1;stroke:#917c6f;stroke-width:0.27120084;stroke-linecap:round;stroke-linejoin:round;stroke-miterlimit:4;stroke-dasharray:none;stroke-opacity:1"
id="rect1470"
width="0.67327011"
height="1.5709635"
x="-6.0889969"
y="286.16861"
ry="0.20079997" />
<path
style="opacity:1;fill:#b7bec8;fill-opacity:1;stroke:#939dac;stroke-width:1.02501094;stroke-linecap:round;stroke-linejoin:round;stroke-miterlimit:4;stroke-dasharray:none;stroke-opacity:1"
d="M -23.125,8.0744882 V 22.169922 c 0,0.420661 0.339319,0.757812 0.759766,0.757812 h 1.25 c 0.420446,0 0.757812,-0.33734 0.757812,-0.757812 V 8.0744882 l -1.382812,-4.8669085 z"
id="rect1464"
inkscape:connector-curvature="0"
sodipodi:nodetypes="cssssccc"
transform="matrix(0.26458333,0,0,0.26458333,0,280.06665)" />
<rect
style="opacity:1;fill:#b7bec8;fill-opacity:1;stroke:#939dac;stroke-width:0.27120084;stroke-linecap:round;stroke-linejoin:round;stroke-miterlimit:4;stroke-dasharray:none;stroke-opacity:1"
id="rect1468"
width="1.8190104"
height="0.69689357"
x="-6.6618671"
y="285.73157"
ry="0.20079997" />
</g>
</g>
<path
inkscape:connector-curvature="0"
style="opacity:1;fill:#f9f9f9;fill-opacity:1;stroke:#b7bec8;stroke-width:0.25955626;stroke-linecap:round;stroke-linejoin:round;stroke-miterlimit:4;stroke-dasharray:none;stroke-opacity:1"
d="m 3.5834747,281.49299 c -0.3924424,0 -0.7085566,0.31542 -0.7085566,0.70699 v 2.48726 c 0,0.39157 0.3161142,0.70651 0.7085566,0.70651 H 7.936716 v 1.33509 l 1.1309286,-1.33509 h 5.6903564 c 0.392442,0 0.70808,-0.31494 0.70808,-0.70651 v -2.48726 c 0,-0.39157 -0.315638,-0.70699 -0.70808,-0.70699 z"
id="rect1499" />
<rect
style="opacity:1;fill:#939dac;fill-opacity:1;stroke:none;stroke-width:0.25955623;stroke-linecap:round;stroke-linejoin:round;stroke-miterlimit:4;stroke-dasharray:none;stroke-opacity:1"
id="rect1507"
width="4.9563775"
height="0.30716547"
x="3.552417"
y="282.24554"
ry="0.15358274" />
<rect
ry="0.1535777"
y="283.02881"
x="3.552417"
height="0.3071554"
width="10.959443"
id="rect1509"
style="opacity:1;fill:#939dac;fill-opacity:1;stroke:none;stroke-width:0.25955623;stroke-linecap:round;stroke-linejoin:round;stroke-miterlimit:4;stroke-dasharray:none;stroke-opacity:1" />
<rect
ry="0.13071308"
y="282.24554"
x="8.9089985"
height="0.3071554"
width="2.7552533"
id="rect1511"
style="opacity:1;fill:#939dac;fill-opacity:1;stroke:none;stroke-width:0.25955623;stroke-linecap:round;stroke-linejoin:round;stroke-miterlimit:4;stroke-dasharray:none;stroke-opacity:1" />
<rect
style="opacity:1;fill:#939dac;fill-opacity:1;stroke:none;stroke-width:0.25955623;stroke-linecap:round;stroke-linejoin:round;stroke-miterlimit:4;stroke-dasharray:none;stroke-opacity:1"
id="rect1513"
width="2.7552533"
height="0.3071554"
x="8.9089985"
y="282.24554"
ry="0.13071308" />
<rect
ry="0.13071308"
y="283.76599"
x="3.552417"
height="0.3071554"
width="2.7552533"
id="rect1515"
style="opacity:1;fill:#939dac;fill-opacity:1;stroke:none;stroke-width:0.25955623;stroke-linecap:round;stroke-linejoin:round;stroke-miterlimit:4;stroke-dasharray:none;stroke-opacity:1" />
<rect
ry="0.15358274"
y="283.76599"
x="7.0465093"
height="0.30716547"
width="4.9563775"
id="rect1517"
style="opacity:1;fill:#939dac;fill-opacity:1;stroke:none;stroke-width:0.25955623;stroke-linecap:round;stroke-linejoin:round;stroke-miterlimit:4;stroke-dasharray:none;stroke-opacity:1" />
<path
sodipodi:type="star"
style="opacity:0.22000002;fill:#ffffff;fill-opacity:1;stroke:none;stroke-width:0.25955623;stroke-linecap:round;stroke-linejoin:round;stroke-miterlimit:4;stroke-dasharray:none;stroke-opacity:1"
id="path1550"
sodipodi:sides="5"
sodipodi:cx="14.032366"
sodipodi:cy="292.36978"
sodipodi:r1="0.73499119"
sodipodi:r2="0.40645012"
sodipodi:arg1="0.78539816"
sodipodi:arg2="1.4137167"
inkscape:flatsided="false"
inkscape:rounded="0.12"
inkscape:randomized="0"
d="m 14.552083,292.8895 c -0.03998,0.04 -0.400284,-0.12712 -0.456134,-0.11827 -0.05585,0.009 -0.346879,0.2791 -0.397262,0.25343 -0.05038,-0.0257 -0.0028,-0.41997 -0.02847,-0.47035 -0.02567,-0.0504 -0.372638,-0.24366 -0.363792,-0.29951 0.0088,-0.0558 0.398554,-0.13244 0.438538,-0.17242 0.03998,-0.04 0.116576,-0.42969 0.172426,-0.43854 0.05585,-0.009 0.249119,0.33812 0.299502,0.36379 0.05038,0.0257 0.444686,-0.0219 0.470358,0.0285 0.02567,0.0504 -0.24459,0.34141 -0.253436,0.39726 -0.0088,0.0559 0.158255,0.41615 0.118271,0.45614 z"
inkscape:transform-center-x="-1.426933e-06"
inkscape:transform-center-y="0.067388288"
transform="rotate(45,14.033142,292.37056)" />
<path
transform="matrix(0.50454017,0.50454017,-0.50454017,0.50454017,142.3716,132.29856)"
inkscape:transform-center-y="0.048086405"
inkscape:transform-center-x="1.1465329e-06"
d="m 14.552083,292.8895 c -0.03998,0.04 -0.400284,-0.12712 -0.456134,-0.11827 -0.05585,0.009 -0.346879,0.2791 -0.397262,0.25343 -0.05038,-0.0257 -0.0028,-0.41997 -0.02847,-0.47035 -0.02567,-0.0504 -0.372638,-0.24366 -0.363792,-0.29951 0.0088,-0.0558 0.398554,-0.13244 0.438538,-0.17242 0.03998,-0.04 0.116576,-0.42969 0.172426,-0.43854 0.05585,-0.009 0.249119,0.33812 0.299502,0.36379 0.05038,0.0257 0.444686,-0.0219 0.470358,0.0285 0.02567,0.0504 -0.24459,0.34141 -0.253436,0.39726 -0.0088,0.0559 0.158255,0.41615 0.118271,0.45614 z"
inkscape:randomized="0"
inkscape:rounded="0.12"
inkscape:flatsided="false"
sodipodi:arg2="1.4137167"
sodipodi:arg1="0.78539816"
sodipodi:r2="0.40645012"
sodipodi:r1="0.73499119"
sodipodi:cy="292.36978"
sodipodi:cx="14.032366"
sodipodi:sides="5"
id="path1552"
style="opacity:0.22000002;fill:#ffffff;fill-opacity:1;stroke:none;stroke-width:0.36376485;stroke-linecap:round;stroke-linejoin:round;stroke-miterlimit:4;stroke-dasharray:none;stroke-opacity:1"
sodipodi:type="star" />
<path
sodipodi:type="star"
style="opacity:0.22000002;fill:#ffffff;fill-opacity:1;stroke:none;stroke-width:0.36376485;stroke-linecap:round;stroke-linejoin:round;stroke-miterlimit:4;stroke-dasharray:none;stroke-opacity:1"
id="path1554"
sodipodi:sides="5"
sodipodi:cx="14.032366"
sodipodi:cy="292.36978"
sodipodi:r1="0.73499119"
sodipodi:r2="0.40645012"
sodipodi:arg1="0.78539816"
sodipodi:arg2="1.4137167"
inkscape:flatsided="false"
inkscape:rounded="0.12"
inkscape:randomized="0"
d="m 14.552083,292.8895 c -0.03998,0.04 -0.400284,-0.12712 -0.456134,-0.11827 -0.05585,0.009 -0.346879,0.2791 -0.397262,0.25343 -0.05038,-0.0257 -0.0028,-0.41997 -0.02847,-0.47035 -0.02567,-0.0504 -0.372638,-0.24366 -0.363792,-0.29951 0.0088,-0.0558 0.398554,-0.13244 0.438538,-0.17242 0.03998,-0.04 0.116576,-0.42969 0.172426,-0.43854 0.05585,-0.009 0.249119,0.33812 0.299502,0.36379 0.05038,0.0257 0.444686,-0.0219 0.470358,0.0285 0.02567,0.0504 -0.24459,0.34141 -0.253436,0.39726 -0.0088,0.0559 0.158255,0.41615 0.118271,0.45614 z"
inkscape:transform-center-x="1.1465329e-06"
inkscape:transform-center-y="0.048086405"
transform="matrix(0.50454017,0.50454017,-0.50454017,0.50454017,142.98966,133.81866)" />
<path
transform="matrix(0.21352693,0.36983949,-0.36983949,0.21352693,117.84722,226.88973)"
inkscape:transform-center-y="0.0045220952"
inkscape:transform-center-x="0.024398526"
d="m 14.552083,292.8895 c -0.03998,0.04 -0.400284,-0.12712 -0.456134,-0.11827 -0.05585,0.009 -0.346879,0.2791 -0.397262,0.25343 -0.05038,-0.0257 -0.0028,-0.41997 -0.02847,-0.47035 -0.02567,-0.0504 -0.372638,-0.24366 -0.363792,-0.29951 0.0088,-0.0558 0.398554,-0.13244 0.438538,-0.17242 0.03998,-0.04 0.116576,-0.42969 0.172426,-0.43854 0.05585,-0.009 0.249119,0.33812 0.299502,0.36379 0.05038,0.0257 0.444686,-0.0219 0.470358,0.0285 0.02567,0.0504 -0.24459,0.34141 -0.253436,0.39726 -0.0088,0.0559 0.158255,0.41615 0.118271,0.45614 z"
inkscape:randomized="0"
inkscape:rounded="0.12"
inkscape:flatsided="false"
sodipodi:arg2="1.4137167"
sodipodi:arg1="0.78539816"
sodipodi:r2="0.40645012"
sodipodi:r1="0.73499119"
sodipodi:cy="292.36978"
sodipodi:cx="14.032366"
sodipodi:sides="5"
id="path1556"
style="opacity:0.22000002;fill:#ffffff;fill-opacity:1;stroke:none;stroke-width:0.60778338;stroke-linecap:round;stroke-linejoin:round;stroke-miterlimit:4;stroke-dasharray:none;stroke-opacity:1"
sodipodi:type="star" />
<path
sodipodi:type="star"
style="opacity:0.22000002;fill:#ffffff;fill-opacity:1;stroke:none;stroke-width:0.60778338;stroke-linecap:round;stroke-linejoin:round;stroke-miterlimit:4;stroke-dasharray:none;stroke-opacity:1"
id="path1558"
sodipodi:sides="5"
sodipodi:cx="14.032366"
sodipodi:cy="292.36978"
sodipodi:r1="0.73499119"
sodipodi:r2="0.40645012"
sodipodi:arg1="0.78539816"
sodipodi:arg2="1.4137167"
inkscape:flatsided="false"
inkscape:rounded="0.12"
inkscape:randomized="0"
d="m 14.552083,292.8895 c -0.03998,0.04 -0.400284,-0.12712 -0.456134,-0.11827 -0.05585,0.009 -0.346879,0.2791 -0.397262,0.25343 -0.05038,-0.0257 -0.0028,-0.41997 -0.02847,-0.47035 -0.02567,-0.0504 -0.372638,-0.24366 -0.363792,-0.29951 0.0088,-0.0558 0.398554,-0.13244 0.438538,-0.17242 0.03998,-0.04 0.116576,-0.42969 0.172426,-0.43854 0.05585,-0.009 0.249119,0.33812 0.299502,0.36379 0.05038,0.0257 0.444686,-0.0219 0.470358,0.0285 0.02567,0.0504 -0.24459,0.34141 -0.253436,0.39726 -0.0088,0.0559 0.158255,0.41615 0.118271,0.45614 z"
inkscape:transform-center-x="0.024398526"
inkscape:transform-center-y="0.0045220952"
transform="matrix(0.21352693,0.36983949,-0.36983949,0.21352693,108.32694,219.47195)" />
<rect
ry="0.16704336"
y="280.06665"
x="0"
height="16.933332"
width="16.933332"
id="rect1567"
style="opacity:1;fill:none;fill-opacity:1;stroke:#8787de;stroke-width:0.52916667;stroke-linecap:round;stroke-linejoin:round;stroke-miterlimit:4;stroke-dasharray:none;stroke-opacity:1;paint-order:normal" />
</g>
</svg>

After

Width:  |  Height:  |  Size: 18 KiB

View File

@@ -0,0 +1,29 @@
[remap]
importer="texture"
type="StreamTexture"
path="res://.import/icon.svg-218a8f2b3041327d8a5756f3a245f83b.stex"
[deps]
source_file="res://icon.svg"
dest_files=[ "res://.import/icon.svg-218a8f2b3041327d8a5756f3a245f83b.stex" ]
[params]
compress/mode=0
compress/lossy_quality=0.7
compress/hdr_mode=0
compress/normal_map=0
flags/repeat=0
flags/filter=true
flags/mipmaps=false
flags/anisotropic=false
flags/srgb=2
process/fix_alpha_border=true
process/premult_alpha=false
process/HDR_as_SRGB=false
stream=false
size_limit=0
detect_3d=true
svg/scale=1.0

View File

@@ -0,0 +1,36 @@
extends Node
signal combat_finished(winner, loser)
const Combatant = preload("res://turn_combat/combatants/Combatant.gd")
func initialize(combat_combatants):
for combatant in combat_combatants:
combatant = combatant.instance()
if combatant is Combatant:
$Combatants.add_combatant(combatant)
combatant.get_node("Health").connect("dead", self, "_on_combatant_death", [combatant])
else:
combatant.queue_free()
$UI.initialize()
$TurnQueue.initialize()
func _on_combatant_death(combatant):
var winner
if not combatant.name == "Player":
winner = $Combatants/Player
else:
for n in $Combatants.get_children():
if not n.name == "Player":
winner = n
break
finish_combat(winner, combatant)
func clear_combat():
for n in $Combatants.get_children():
n.queue_free()
for n in $UI/Combatants.get_children():
n.queue_free()
func finish_combat(winner, loser):
emit_signal("combat_finished", winner, loser)

View File

@@ -1,69 +1,34 @@
[gd_scene load_steps=7 format=2]
[ext_resource path="res://turn_combat_system/turn_queue/TurnQueue.tscn" type="PackedScene" id=1]
[ext_resource path="res://theme/theme.tres" type="Theme" id=2]
[ext_resource path="res://screens/combat/interface/UI.gd" type="Script" id=3]
[ext_resource path="res://screens/combat/interface/ActorInfo.tscn" type="PackedScene" id=4]
[ext_resource path="res://screens/combat/Combat.gd" type="Script" id=1]
[ext_resource path="res://turn_combat/turn_queue/TurnQueue.tscn" type="PackedScene" id=2]
[ext_resource path="res://theme/theme.tres" type="Theme" id=3]
[ext_resource path="res://screens/combat/interface/UI.gd" type="Script" id=4]
[ext_resource path="res://screens/combat/interface/Info.tscn" type="PackedScene" id=5]
[sub_resource type="GDScript" id=1]
script/source = "extends Node
signal combat_finished(winner, loser)
func initialize(combat_actors):
for actor in combat_actors:
actor = actor.instance()
if actor is load(\"res://turn_combat_system/actors/Actor.gd\"):
$Actors.add_actor(actor)
actor.get_node(\"Health\").connect(\"dead\", self, \"_on_actor_death\", [actor])
else:
actor.queue_free()
$UI.initialize()
$TurnQueue.initialize()
$TurnQueue.play_turn()
$UI/Buttons/GridContainer/Attack.grab_focus()
func _on_actor_death(actor):
var winner
if not actor.name == \"Player\":
winner = $Actors/Player
else:
for n in $Actors.get_children():
if not n.name == \"Player\":
winner = n
break
emit_signal(\"combat_finished\", winner, actor)
func clear_combat():
for n in $Actors.get_children():
n.queue_free()
for n in $UI/Actors.get_children():
n.queue_free()
"
[sub_resource type="GDScript" id=2]
script/source = "extends Node2D
func add_actor(actor):
actor.position.x += 200 * get_child_count()
add_child(actor)"
func add_combatant(new_combatant):
new_combatant.position.x += 200 * get_child_count()
add_child(new_combatant)
"
[node name="Combat" type="Node2D" index="0"]
[node name="Combat" type="Node2D"]
script = SubResource( 1 )
script = ExtResource( 1 )
[node name="TurnQueue" parent="." index="0" instance=ExtResource( 1 )]
actors_node = NodePath("../Actors")
[node name="Actors" type="Node2D" parent="." index="1"]
[node name="Combatants" type="Node2D" parent="." index="0"]
position = Vector2( 539, 275 )
script = SubResource( 2 )
script = SubResource( 1 )
_sections_unfolded = [ "Transform" ]
[node name="TurnQueue" parent="." index="1" instance=ExtResource( 2 )]
combatants_list = NodePath("../Combatants")
[node name="UI" type="Control" parent="." index="2"]
anchor_left = 0.0
@@ -78,13 +43,13 @@ mouse_filter = 0
mouse_default_cursor_shape = 0
size_flags_horizontal = 1
size_flags_vertical = 1
theme = ExtResource( 2 )
script = ExtResource( 3 )
theme = ExtResource( 3 )
script = ExtResource( 4 )
_sections_unfolded = [ "Theme" ]
actors_node = NodePath("../Actors")
actor_info = ExtResource( 4 )
combatants_node = NodePath("../Combatants")
info_scene = ExtResource( 5 )
[node name="Actors" type="HBoxContainer" parent="UI" index="0"]
[node name="Combatants" type="HBoxContainer" parent="UI" index="0"]
anchor_left = 0.0
anchor_top = 0.0
@@ -147,7 +112,7 @@ anchor_top = 0.0
anchor_right = 0.0
anchor_bottom = 0.0
margin_right = 468.0
margin_bottom = 119.0
margin_bottom = 121.0
rect_pivot_offset = Vector2( 0, 0 )
rect_clip_content = false
focus_mode = 2
@@ -171,7 +136,7 @@ anchor_right = 0.0
anchor_bottom = 0.0
margin_left = 472.0
margin_right = 940.0
margin_bottom = 119.0
margin_bottom = 121.0
rect_pivot_offset = Vector2( 0, 0 )
rect_clip_content = false
focus_mode = 2
@@ -187,40 +152,15 @@ text = "Defend"
flat = false
align = 1
[node name="Inventory" type="Button" parent="UI/Buttons/GridContainer" index="2"]
[node name="Flee" type="Button" parent="UI/Buttons/GridContainer" index="2"]
anchor_left = 0.0
anchor_top = 0.0
anchor_right = 0.0
anchor_bottom = 0.0
margin_top = 123.0
margin_top = 125.0
margin_right = 468.0
margin_bottom = 242.0
rect_pivot_offset = Vector2( 0, 0 )
rect_clip_content = false
focus_mode = 2
mouse_filter = 0
mouse_default_cursor_shape = 0
size_flags_horizontal = 3
size_flags_vertical = 3
toggle_mode = false
enabled_focus_mode = 2
shortcut = null
group = null
text = "Inventory"
flat = false
align = 1
[node name="Flee" type="Button" parent="UI/Buttons/GridContainer" index="3"]
anchor_left = 0.0
anchor_top = 0.0
anchor_right = 0.0
anchor_bottom = 0.0
margin_left = 472.0
margin_top = 123.0
margin_right = 940.0
margin_bottom = 242.0
margin_bottom = 246.0
rect_pivot_offset = Vector2( 0, 0 )
rect_clip_content = false
focus_mode = 2

View File

@@ -0,0 +1,72 @@
[gd_scene load_steps=2 format=2]
[ext_resource path="res://theme/labels/Title.tscn" type="PackedScene" id=1]
[node name="Info" type="PanelContainer"]
anchor_left = 0.0
anchor_top = 0.0
anchor_right = 0.0
anchor_bottom = 0.0
margin_right = 409.0
margin_bottom = 239.0
rect_pivot_offset = Vector2( 0, 0 )
rect_clip_content = false
mouse_filter = 0
mouse_default_cursor_shape = 0
size_flags_horizontal = 3
size_flags_vertical = 3
[node name="VBoxContainer" type="VBoxContainer" parent="." index="0"]
anchor_left = 0.0
anchor_top = 0.0
anchor_right = 0.0
anchor_bottom = 0.0
margin_left = 7.0
margin_top = 7.0
margin_right = 402.0
margin_bottom = 232.0
rect_pivot_offset = Vector2( 0, 0 )
rect_clip_content = false
mouse_filter = 1
mouse_default_cursor_shape = 0
size_flags_horizontal = 1
size_flags_vertical = 1
alignment = 0
[node name="Name" parent="VBoxContainer" index="0" instance=ExtResource( 1 )]
margin_right = 395.0
margin_bottom = 110.0
size_flags_horizontal = 3
size_flags_vertical = 7
text = "{name}"
_sections_unfolded = [ "Rect", "Size Flags", "custom_colors", "custom_constants", "custom_fonts" ]
[node name="Health" type="ProgressBar" parent="VBoxContainer" index="1"]
anchor_left = 0.0
anchor_top = 0.0
anchor_right = 0.0
anchor_bottom = 0.0
margin_top = 161.0
margin_right = 395.0
margin_bottom = 177.0
rect_pivot_offset = Vector2( 0, 0 )
rect_clip_content = false
mouse_filter = 0
mouse_default_cursor_shape = 0
size_flags_horizontal = 1
size_flags_vertical = 6
min_value = 0.0
max_value = 10.0
step = 1.0
page = 0.0
value = 5.0
exp_edit = false
rounded = true
percent_visible = false
_sections_unfolded = [ "Percent", "Size Flags" ]

View File

@@ -1,34 +1,37 @@
extends Control
export (NodePath) var actors_node
export (PackedScene) var actor_info
export (NodePath) var combatants_node
export (PackedScene) var info_scene
func _ready():
actors_node = get_node(actors_node)
combatants_node = get_node(combatants_node)
func initialize():
for actor in actors_node.get_children():
var health = actor.get_node("Health")
var info = actor_info.instance()
for combatant in combatants_node.get_children():
var health = combatant.get_node("Health")
var info = info_scene.instance()
var health_info = info.get_node("VBoxContainer/Health")
health_info.value = health.life
health_info.max_value = health.max_life
info.get_node("VBoxContainer/Name").text = actor.name
info.get_node("VBoxContainer/Name").text = combatant.name
health.connect("health_changed", health_info, "set_value")
$Actors.add_child(info)
$Combatants.add_child(info)
$Buttons/GridContainer/Attack.grab_focus()
func _on_Attack_button_up():
if not actors_node.get_node("Player").active:
if not combatants_node.get_node("Player").active:
return
actors_node.get_node("Player").attack(actors_node.get_node("Opponent"))
combatants_node.get_node("Player").attack(combatants_node.get_node("Opponent"))
func _on_Defend_button_up():
if not actors_node.get_node("Player").active:
if not combatants_node.get_node("Player").active:
return
actors_node.get_node("Player").defend()
combatants_node.get_node("Player").defend()
func _on_Flee_button_up():
if not actors_node.get_node("Player").active:
if not combatants_node.get_node("Player").active:
return
actors_node.get_node("Player").flee()
get_parent().emit_signal("combat_finished", $"../Actors/Opponent", $"../Actors/Player")
combatants_node.get_node("Player").flee()
var loser = combatants_node.get_node("Player")
var winner = combatants_node.get_node("Opponent")
get_parent().finish_combat(winner, loser)

View File

@@ -3,15 +3,13 @@
[ext_resource path="res://grid_movement/tilesets/grid_lines/grid_lines_tileset.tres" type="TileSet" id=1]
[ext_resource path="res://grid_movement/tilesets/grid/grid_tileset.tres" type="TileSet" id=2]
[ext_resource path="res://grid_movement/grid/Grid.gd" type="Script" id=3]
[ext_resource path="res://grid_movement/pawns/Actor.tscn" type="PackedScene" id=4]
[ext_resource path="res://screens/combat/actors/Player.tscn" type="PackedScene" id=5]
[ext_resource path="res://grid_movement/pawns/IdleActor.gd" type="Script" id=6]
[ext_resource path="res://screens/combat/actors/Opponent.tscn" type="PackedScene" id=7]
[ext_resource path="res://dialog_system/dialog_player/DialogPlayer.tscn" type="PackedScene" id=8]
[ext_resource path="res://grid_movement/pawns/pawn.gd" type="Script" id=9]
[ext_resource path="res://dialog_system/interface/DialogUI.tscn" type="PackedScene" id=10]
[ext_resource path="res://grid_movement/pawns/Character.tscn" type="PackedScene" id=4]
[ext_resource path="res://turn_combat/combatants/Player.tscn" type="PackedScene" id=5]
[ext_resource path="res://grid_movement/pawns/Character.gd" type="Script" id=6]
[ext_resource path="res://turn_combat/combatants/Opponent.tscn" type="PackedScene" id=7]
[ext_resource path="res://dialogue/dialogue_player/DialoguePlayer.tscn" type="PackedScene" id=8]
[ext_resource path="res://grid_movement/pawns/Pawn.gd" type="Script" id=9]
[ext_resource path="res://dialogue/interface/Interface.tscn" type="PackedScene" id=10]
[node name="Exploration" type="Node2D"]
@@ -66,7 +64,7 @@ _sections_unfolded = [ "Visibility" ]
__meta__ = {
"_edit_lock_": true
}
dialog_ui = NodePath("../DialogUI")
dialogue_ui = NodePath("../DialogueUI")
[node name="Player" parent="Grid" index="0" instance=ExtResource( 4 )]
@@ -81,9 +79,9 @@ rotation = -1.5708
script = ExtResource( 6 )
combat_actor = ExtResource( 7 )
[node name="DialogPlayer" parent="Grid/Opponent" index="3" instance=ExtResource( 8 )]
[node name="DialoguePlayer" parent="Grid/Opponent" index="3" instance=ExtResource( 8 )]
dialog_file = "res://dialog_system/dialogs/npc_01.json"
dialogue_file = "res://dialogue/dialogue_data/npc.json"
[node name="Timer" type="Timer" parent="Grid/Opponent" index="4"]
@@ -94,20 +92,16 @@ autostart = true
[node name="Object" type="Node2D" parent="Grid" index="2"]
editor/display_folded = true
position = Vector2( 544, 288 )
script = ExtResource( 9 )
type = 2
combat_actor = null
[node name="DialogPlayer" parent="Grid/Object" index="0" instance=ExtResource( 8 )]
[node name="DialoguePlayer" parent="Grid/Object" index="0" instance=ExtResource( 8 )]
dialog_file = "res://dialog_system/dialogs/object.json"
dialogue_file = "res://dialogue/dialogue_data/object.json"
[node name="DialogUI" parent="." index="2" instance=ExtResource( 10 )]
[node name="DialogueUI" parent="." index="2" instance=ExtResource( 10 )]
[connection signal="dialog_finished" from="Grid/Opponent/DialogPlayer" to="Grid/Opponent" method="set_active" binds= [ true ]]
[connection signal="dialog_started" from="Grid/Opponent/DialogPlayer" to="Grid/Opponent" method="set_active" binds= [ false ]]
visible = false

View File

@@ -11,6 +11,11 @@ func set_active(value):
set_process(value)
set_process_input(value)
if not active:
return
if $Health.armor >= $Health.base_armor + defense:
$Health.armor = $Health.base_armor
func attack(target):
target.take_damage(damage)
emit_signal("turn_finished")

View File

@@ -0,0 +1,21 @@
[gd_scene load_steps=4 format=2]
[ext_resource path="res://turn_combat/combatants/Combatant.gd" type="Script" id=1]
[ext_resource path="res://turn_combat/combatants/health/Health.tscn" type="PackedScene" id=2]
[ext_resource path="res://turn_combat/combatants/sprites/Sprite.tscn" type="PackedScene" id=3]
[node name="Combatant" type="Node2D"]
script = ExtResource( 1 )
damage = 2
defense = 1
[node name="Health" parent="." index="0" instance=ExtResource( 2 )]
life = 10
base_armor = 0
[node name="Sprite" parent="." index="1" instance=ExtResource( 3 )]

View File

@@ -0,0 +1,15 @@
extends "Combatant.gd"
func set_active(value):
.set_active(value)
if not active:
return
$Timer.start()
yield($Timer, "timeout")
var target
for actor in get_parent().get_children():
if not actor == self:
target = actor
break
attack(target)

View File

@@ -0,0 +1,30 @@
[gd_scene load_steps=4 format=2]
[ext_resource path="res://turn_combat/combatants/Combatant.tscn" type="PackedScene" id=1]
[ext_resource path="res://turn_combat/combatants/Opponent.gd" type="Script" id=2]
[ext_resource path="res://turn_combat/combatants/sprites/green.png" type="Texture" id=3]
[node name="Opponent" instance=ExtResource( 1 )]
script = ExtResource( 2 )
_sections_unfolded = [ "Transform" ]
damage = 3
[node name="Health" parent="." index="0"]
life = 7
max_life = 7
[node name="Body" parent="Sprite/Pivot" index="1"]
texture = ExtResource( 3 )
[node name="Timer" type="Timer" parent="." index="2"]
process_mode = 1
wait_time = 0.25
one_shot = true
autostart = false
[editable path="Sprite"]

View File

@@ -0,0 +1,13 @@
[gd_scene load_steps=2 format=2]
[ext_resource path="res://turn_combat/combatants/Combatant.tscn" type="PackedScene" id=1]
[node name="Player" instance=ExtResource( 1 )]
_sections_unfolded = [ "Transform" ]
[node name="Health" parent="." index="0"]
base_armor = 1

View File

@@ -5,13 +5,16 @@ signal health_changed(life)
export var life = 0
export var max_life = 10
export var armor = 0
export var base_armor = 0
var armor = 0
func _ready():
armor = base_armor
func take_damage(damage):
var applied_damage = max(damage - armor, 0)
life = max(life - applied_damage, 0)
if life == 0:
emit_signal('dead')
life = life - damage + armor
if life <= 0:
emit_signal("dead")
else:
emit_signal("health_changed", life)

View File

@@ -1,6 +1,11 @@
[gd_scene load_steps=2 format=2]
[ext_resource path="res://turn_combat_system/actors/health/Health.gd" type="Script" id=1]
[ext_resource path="res://turn_combat/combatants/health/Health.gd" type="Script" id=1]
[node name="Health" type="Node"]

View File

@@ -0,0 +1,63 @@
[gd_scene load_steps=4 format=2]
[ext_resource path="res://turn_combat/combatants/sprites/shadow.png" type="Texture" id=1]
[ext_resource path="res://turn_combat/combatants/sprites/blue.png" type="Texture" id=2]
[sub_resource type="Animation" id=1]
resource_name = "take_damage"
length = 0.2
loop = false
step = 0.05
tracks/0/type = "value"
tracks/0/path = NodePath("Pivot/Body:modulate")
tracks/0/interp = 1
tracks/0/loop_wrap = true
tracks/0/imported = false
tracks/0/enabled = true
tracks/0/keys = {
"times": PoolRealArray( 0, 0.05, 0.1, 0.15, 0.2 ),
"transitions": PoolRealArray( 1, 1, 1, 1, 1 ),
"update": 0,
"values": [ Color( 1, 1, 1, 1 ), Color( 3, 0.253906, 0.253906, 1 ), Color( 1, 1, 1, 1 ), Color( 3, 0.253906, 0.253906, 1 ), Color( 1, 1, 1, 1 ) ]
}
[node name="Sprite" type="Node2D"]
[node name="AnimationPlayer" type="AnimationPlayer" parent="." index="0"]
root_node = NodePath("..")
autoplay = ""
playback_process_mode = 1
playback_default_blend_time = 0.0
playback_speed = 1.0
anims/take_damage = SubResource( 1 )
blend_times = [ ]
[node name="Tween" type="Tween" parent="." index="1"]
repeat = false
playback_process_mode = 1
playback_speed = 1.0
playback/active = false
playback/repeat = false
playback/speed = 1.0
[node name="Pivot" type="Position2D" parent="." index="2"]
[node name="Shadow" type="Sprite" parent="Pivot" index="0"]
position = Vector2( 0, -15 )
texture = ExtResource( 1 )
_sections_unfolded = [ "Transform" ]
[node name="Body" type="Sprite" parent="Pivot" index="1"]
position = Vector2( 0, -76 )
texture = ExtResource( 2 )
_sections_unfolded = [ "Visibility" ]

Binary file not shown.

After

Width:  |  Height:  |  Size: 1.9 KiB

View File

@@ -0,0 +1,29 @@
[remap]
importer="texture"
type="StreamTexture"
path="res://.import/blue.png-1646430371c0817627bfbad8bb1bf0ab.stex"
[deps]
source_file="res://turn_combat/combatants/sprites/blue.png"
dest_files=[ "res://.import/blue.png-1646430371c0817627bfbad8bb1bf0ab.stex" ]
[params]
compress/mode=0
compress/lossy_quality=0.7
compress/hdr_mode=0
compress/normal_map=0
flags/repeat=0
flags/filter=true
flags/mipmaps=false
flags/anisotropic=false
flags/srgb=2
process/fix_alpha_border=true
process/premult_alpha=false
process/HDR_as_SRGB=false
stream=false
size_limit=0
detect_3d=true
svg/scale=1.0

Binary file not shown.

After

Width:  |  Height:  |  Size: 1.9 KiB

View File

@@ -0,0 +1,29 @@
[remap]
importer="texture"
type="StreamTexture"
path="res://.import/green.png-0c539b10234a7340c6135a5edb21b0e1.stex"
[deps]
source_file="res://turn_combat/combatants/sprites/green.png"
dest_files=[ "res://.import/green.png-0c539b10234a7340c6135a5edb21b0e1.stex" ]
[params]
compress/mode=0
compress/lossy_quality=0.7
compress/hdr_mode=0
compress/normal_map=0
flags/repeat=0
flags/filter=true
flags/mipmaps=false
flags/anisotropic=false
flags/srgb=2
process/fix_alpha_border=true
process/premult_alpha=false
process/HDR_as_SRGB=false
stream=false
size_limit=0
detect_3d=true
svg/scale=1.0

Binary file not shown.

After

Width:  |  Height:  |  Size: 1.1 KiB

View File

@@ -0,0 +1,29 @@
[remap]
importer="texture"
type="StreamTexture"
path="res://.import/shadow.png-0d089e013d2449a666ec492b25e627fe.stex"
[deps]
source_file="res://turn_combat/combatants/sprites/shadow.png"
dest_files=[ "res://.import/shadow.png-0d089e013d2449a666ec492b25e627fe.stex" ]
[params]
compress/mode=0
compress/lossy_quality=0.7
compress/hdr_mode=0
compress/normal_map=0
flags/repeat=0
flags/filter=true
flags/mipmaps=false
flags/anisotropic=false
flags/srgb=2
process/fix_alpha_border=true
process/premult_alpha=false
process/HDR_as_SRGB=false
stream=false
size_limit=0
detect_3d=true
svg/scale=1.0

View File

@@ -0,0 +1,52 @@
extends Node
const combatant = preload("../combatants/Combatant.gd")
export (NodePath) var combatants_list
var queue = [] setget set_queue
var active_combatant = null setget _set_active_combatant
signal active_combatant_changed(active_combatant)
func _ready():
combatants_list = get_node(combatants_list)
func initialize():
set_queue(combatants_list.get_children())
play_turn()
func play_turn():
yield(active_combatant, "turn_finished")
get_next_in_queue()
play_turn()
func get_next_in_queue():
var current_combatant = queue.pop_front()
current_combatant.active = false
queue.append(current_combatant)
self.active_combatant = queue[0]
return active_combatant
func remove(combatant):
var new_queue = []
for n in queue:
new_queue.append(n)
new_queue.remove(new_queue.find(combatant))
combatant.queue_free()
self.queue = new_queue
func set_queue(new_queue):
queue.clear()
var names = []
for node in new_queue:
if not node is combatant:
continue
queue.append(node)
node.active = false
if queue.size() > 0:
self.active_combatant = queue[0]
func _set_active_combatant(new_combatant):
active_combatant = new_combatant
active_combatant.active = true
emit_signal("active_combatant_changed", active_combatant)

View File

@@ -0,0 +1,11 @@
[gd_scene load_steps=2 format=2]
[ext_resource path="res://turn_combat/turn_queue/TurnQueue.gd" type="Script" id=1]
[node name="TurnQueue" type="Node"]
script = ExtResource( 1 )
combatants_list = null

View File

@@ -1,14 +0,0 @@
[gd_scene load_steps=3 format=2]
[ext_resource path="res://turn_combat_system/actors/Actor.gd" type="Script" id=1]
[ext_resource path="res://turn_combat_system/actors/health/Health.tscn" type="PackedScene" id=2]
[node name="Actor" type="Node"]
script = ExtResource( 1 )
damage = 1
defense = 1
[node name="Health" parent="." index="0" instance=ExtResource( 2 )]

View File

@@ -1,52 +0,0 @@
extends Node
const Actor = preload("../actors/Actor.gd")
export (NodePath) var actors_node
var queue = [] setget set_queue
var active_actor = null setget _set_active_actor
signal active_actor_changed(active_actor)
func _ready():
actors_node = get_node(actors_node)
initialize()
func initialize():
set_queue(actors_node.get_children())
func play_turn():
yield(active_actor, "turn_finished")
get_next_in_queue()
play_turn()
func get_next_in_queue():
var current_actor = queue.pop_front()
current_actor.active = false
queue.append(current_actor)
self.active_actor = queue[0]
return active_actor
func remove(actor):
var new_queue = []
for n in queue:
new_queue.append(n)
new_queue.remove(new_queue.find(actor))
actor.queue_free()
self.queue = new_queue
func set_queue(new_queue):
queue.clear()
var names = []
for node in new_queue:
if not node is Actor:
continue
queue.append(node)
node.active = false
if queue.size() > 0:
self.active_actor = queue[0]
func _set_active_actor(new_actor):
active_actor = new_actor
active_actor.active = true
emit_signal("active_actor_changed", active_actor)

View File

@@ -1,11 +0,0 @@
[gd_scene load_steps=2 format=2]
[ext_resource path="res://turn_combat_system/turn_queue/TurnQueue.gd" type="Script" id=1]
[node name="TurnQueue" type="Node"]
script = ExtResource( 1 )
actors_node = null