Merge pull request 'multiplayer_and_some_card_art' (#2) from multiplayer-and-card-art into main
Reviewed-on: https://forge.darkwagonstudio.com/dark-wagon-studio/tcg/pulls/2
This commit is contained in:
commit
172ce12e79
42 changed files with 1476 additions and 121 deletions
BIN
assets/Bohemian Soul.otf
(Stored with Git LFS)
Normal file
BIN
assets/Bohemian Soul.otf
(Stored with Git LFS)
Normal file
Binary file not shown.
34
assets/Bohemian Soul.otf.import
Normal file
34
assets/Bohemian Soul.otf.import
Normal file
|
|
@ -0,0 +1,34 @@
|
||||||
|
[remap]
|
||||||
|
|
||||||
|
importer="font_data_dynamic"
|
||||||
|
type="FontFile"
|
||||||
|
uid="uid://ncoq4i61plvt"
|
||||||
|
path="res://.godot/imported/Bohemian Soul.otf-321180efeec0e46d48937761716dc66f.fontdata"
|
||||||
|
|
||||||
|
[deps]
|
||||||
|
|
||||||
|
source_file="res://assets/Bohemian Soul.otf"
|
||||||
|
dest_files=["res://.godot/imported/Bohemian Soul.otf-321180efeec0e46d48937761716dc66f.fontdata"]
|
||||||
|
|
||||||
|
[params]
|
||||||
|
|
||||||
|
Rendering=null
|
||||||
|
antialiasing=1
|
||||||
|
generate_mipmaps=false
|
||||||
|
disable_embedded_bitmaps=true
|
||||||
|
multichannel_signed_distance_field=false
|
||||||
|
msdf_pixel_range=8
|
||||||
|
msdf_size=48
|
||||||
|
allow_system_fallback=true
|
||||||
|
force_autohinter=false
|
||||||
|
hinting=1
|
||||||
|
subpixel_positioning=1
|
||||||
|
oversampling=0.0
|
||||||
|
Fallbacks=null
|
||||||
|
fallbacks=[]
|
||||||
|
Compress=null
|
||||||
|
compress=true
|
||||||
|
preload=[]
|
||||||
|
language_support={}
|
||||||
|
script_support={}
|
||||||
|
opentype_features={}
|
||||||
BIN
assets/Inter-Regular.otf
(Stored with Git LFS)
Normal file
BIN
assets/Inter-Regular.otf
(Stored with Git LFS)
Normal file
Binary file not shown.
34
assets/Inter-Regular.otf.import
Normal file
34
assets/Inter-Regular.otf.import
Normal file
|
|
@ -0,0 +1,34 @@
|
||||||
|
[remap]
|
||||||
|
|
||||||
|
importer="font_data_dynamic"
|
||||||
|
type="FontFile"
|
||||||
|
uid="uid://08q3kkwmd4u6"
|
||||||
|
path="res://.godot/imported/Inter-Regular.otf-e79282422267193643bc1266eabc7aef.fontdata"
|
||||||
|
|
||||||
|
[deps]
|
||||||
|
|
||||||
|
source_file="res://assets/Inter-Regular.otf"
|
||||||
|
dest_files=["res://.godot/imported/Inter-Regular.otf-e79282422267193643bc1266eabc7aef.fontdata"]
|
||||||
|
|
||||||
|
[params]
|
||||||
|
|
||||||
|
Rendering=null
|
||||||
|
antialiasing=1
|
||||||
|
generate_mipmaps=false
|
||||||
|
disable_embedded_bitmaps=true
|
||||||
|
multichannel_signed_distance_field=false
|
||||||
|
msdf_pixel_range=8
|
||||||
|
msdf_size=48
|
||||||
|
allow_system_fallback=true
|
||||||
|
force_autohinter=false
|
||||||
|
hinting=1
|
||||||
|
subpixel_positioning=1
|
||||||
|
oversampling=0.0
|
||||||
|
Fallbacks=null
|
||||||
|
fallbacks=[]
|
||||||
|
Compress=null
|
||||||
|
compress=true
|
||||||
|
preload=[]
|
||||||
|
language_support={}
|
||||||
|
script_support={}
|
||||||
|
opentype_features={}
|
||||||
BIN
assets/card_base/Frame.png
(Stored with Git LFS)
Normal file
BIN
assets/card_base/Frame.png
(Stored with Git LFS)
Normal file
Binary file not shown.
34
assets/card_base/Frame.png.import
Normal file
34
assets/card_base/Frame.png.import
Normal file
|
|
@ -0,0 +1,34 @@
|
||||||
|
[remap]
|
||||||
|
|
||||||
|
importer="texture"
|
||||||
|
type="CompressedTexture2D"
|
||||||
|
uid="uid://l2nxxhh0pvh8"
|
||||||
|
path="res://.godot/imported/Frame.png-2cc9ebde58565bbc3036395eb0041ae9.ctex"
|
||||||
|
metadata={
|
||||||
|
"vram_texture": false
|
||||||
|
}
|
||||||
|
|
||||||
|
[deps]
|
||||||
|
|
||||||
|
source_file="res://assets/card_base/Frame.png"
|
||||||
|
dest_files=["res://.godot/imported/Frame.png-2cc9ebde58565bbc3036395eb0041ae9.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
|
||||||
BIN
assets/card_base/G-OuterFill.png
(Stored with Git LFS)
Normal file
BIN
assets/card_base/G-OuterFill.png
(Stored with Git LFS)
Normal file
Binary file not shown.
34
assets/card_base/G-OuterFill.png.import
Normal file
34
assets/card_base/G-OuterFill.png.import
Normal file
|
|
@ -0,0 +1,34 @@
|
||||||
|
[remap]
|
||||||
|
|
||||||
|
importer="texture"
|
||||||
|
type="CompressedTexture2D"
|
||||||
|
uid="uid://liitr32ap646"
|
||||||
|
path="res://.godot/imported/G-OuterFill.png-08376930c432a32d81cb0c7a55fb089e.ctex"
|
||||||
|
metadata={
|
||||||
|
"vram_texture": false
|
||||||
|
}
|
||||||
|
|
||||||
|
[deps]
|
||||||
|
|
||||||
|
source_file="res://assets/card_base/G-OuterFill.png"
|
||||||
|
dest_files=["res://.godot/imported/G-OuterFill.png-08376930c432a32d81cb0c7a55fb089e.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
|
||||||
BIN
assets/card_base/InnerFill.png
(Stored with Git LFS)
Normal file
BIN
assets/card_base/InnerFill.png
(Stored with Git LFS)
Normal file
Binary file not shown.
34
assets/card_base/InnerFill.png.import
Normal file
34
assets/card_base/InnerFill.png.import
Normal file
|
|
@ -0,0 +1,34 @@
|
||||||
|
[remap]
|
||||||
|
|
||||||
|
importer="texture"
|
||||||
|
type="CompressedTexture2D"
|
||||||
|
uid="uid://blejyda8mendg"
|
||||||
|
path="res://.godot/imported/InnerFill.png-75781e681a40959b716289bec2b32336.ctex"
|
||||||
|
metadata={
|
||||||
|
"vram_texture": false
|
||||||
|
}
|
||||||
|
|
||||||
|
[deps]
|
||||||
|
|
||||||
|
source_file="res://assets/card_base/InnerFill.png"
|
||||||
|
dest_files=["res://.godot/imported/InnerFill.png-75781e681a40959b716289bec2b32336.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
|
||||||
BIN
assets/card_base/Pill.png
(Stored with Git LFS)
Normal file
BIN
assets/card_base/Pill.png
(Stored with Git LFS)
Normal file
Binary file not shown.
34
assets/card_base/Pill.png.import
Normal file
34
assets/card_base/Pill.png.import
Normal file
|
|
@ -0,0 +1,34 @@
|
||||||
|
[remap]
|
||||||
|
|
||||||
|
importer="texture"
|
||||||
|
type="CompressedTexture2D"
|
||||||
|
uid="uid://0gxplli5krq2"
|
||||||
|
path="res://.godot/imported/Pill.png-f7a0d13f20f1ea9ba344cea7c095427a.ctex"
|
||||||
|
metadata={
|
||||||
|
"vram_texture": false
|
||||||
|
}
|
||||||
|
|
||||||
|
[deps]
|
||||||
|
|
||||||
|
source_file="res://assets/card_base/Pill.png"
|
||||||
|
dest_files=["res://.godot/imported/Pill.png-f7a0d13f20f1ea9ba344cea7c095427a.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
|
||||||
BIN
assets/card_base/R-OuterFill.png
(Stored with Git LFS)
Normal file
BIN
assets/card_base/R-OuterFill.png
(Stored with Git LFS)
Normal file
Binary file not shown.
34
assets/card_base/R-OuterFill.png.import
Normal file
34
assets/card_base/R-OuterFill.png.import
Normal file
|
|
@ -0,0 +1,34 @@
|
||||||
|
[remap]
|
||||||
|
|
||||||
|
importer="texture"
|
||||||
|
type="CompressedTexture2D"
|
||||||
|
uid="uid://ip7xjs20pd3d"
|
||||||
|
path="res://.godot/imported/R-OuterFill.png-f999c1a1aec742072b5689d6ee4573cf.ctex"
|
||||||
|
metadata={
|
||||||
|
"vram_texture": false
|
||||||
|
}
|
||||||
|
|
||||||
|
[deps]
|
||||||
|
|
||||||
|
source_file="res://assets/card_base/R-OuterFill.png"
|
||||||
|
dest_files=["res://.godot/imported/R-OuterFill.png-f999c1a1aec742072b5689d6ee4573cf.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
|
||||||
BIN
assets/card_base/Separator.png
(Stored with Git LFS)
Normal file
BIN
assets/card_base/Separator.png
(Stored with Git LFS)
Normal file
Binary file not shown.
34
assets/card_base/Separator.png.import
Normal file
34
assets/card_base/Separator.png.import
Normal file
|
|
@ -0,0 +1,34 @@
|
||||||
|
[remap]
|
||||||
|
|
||||||
|
importer="texture"
|
||||||
|
type="CompressedTexture2D"
|
||||||
|
uid="uid://by7ws88pn4tvb"
|
||||||
|
path="res://.godot/imported/Separator.png-3ef36f6d9a7c45cb144c99255cbf2668.ctex"
|
||||||
|
metadata={
|
||||||
|
"vram_texture": false
|
||||||
|
}
|
||||||
|
|
||||||
|
[deps]
|
||||||
|
|
||||||
|
source_file="res://assets/card_base/Separator.png"
|
||||||
|
dest_files=["res://.godot/imported/Separator.png-3ef36f6d9a7c45cb144c99255cbf2668.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
|
||||||
BIN
assets/card_base/Stroke.png
(Stored with Git LFS)
Normal file
BIN
assets/card_base/Stroke.png
(Stored with Git LFS)
Normal file
Binary file not shown.
34
assets/card_base/Stroke.png.import
Normal file
34
assets/card_base/Stroke.png.import
Normal file
|
|
@ -0,0 +1,34 @@
|
||||||
|
[remap]
|
||||||
|
|
||||||
|
importer="texture"
|
||||||
|
type="CompressedTexture2D"
|
||||||
|
uid="uid://crgrple0uik7x"
|
||||||
|
path="res://.godot/imported/Stroke.png-9acc55e7647197941083043ac51c45a4.ctex"
|
||||||
|
metadata={
|
||||||
|
"vram_texture": false
|
||||||
|
}
|
||||||
|
|
||||||
|
[deps]
|
||||||
|
|
||||||
|
source_file="res://assets/card_base/Stroke.png"
|
||||||
|
dest_files=["res://.godot/imported/Stroke.png-9acc55e7647197941083043ac51c45a4.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
|
||||||
BIN
assets/energy.png
(Stored with Git LFS)
Normal file
BIN
assets/energy.png
(Stored with Git LFS)
Normal file
Binary file not shown.
34
assets/energy.png.import
Normal file
34
assets/energy.png.import
Normal file
|
|
@ -0,0 +1,34 @@
|
||||||
|
[remap]
|
||||||
|
|
||||||
|
importer="texture"
|
||||||
|
type="CompressedTexture2D"
|
||||||
|
uid="uid://rh3aswb0p7ri"
|
||||||
|
path="res://.godot/imported/energy.png-d31ae10deb2f267a25814b3eac80d643.ctex"
|
||||||
|
metadata={
|
||||||
|
"vram_texture": false
|
||||||
|
}
|
||||||
|
|
||||||
|
[deps]
|
||||||
|
|
||||||
|
source_file="res://assets/energy.png"
|
||||||
|
dest_files=["res://.godot/imported/energy.png-d31ae10deb2f267a25814b3eac80d643.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
|
||||||
8
cards.tres
Normal file
8
cards.tres
Normal file
|
|
@ -0,0 +1,8 @@
|
||||||
|
[gd_resource type="Theme" load_steps=2 format=3 uid="uid://cj3vs5hq2mcbp"]
|
||||||
|
|
||||||
|
[ext_resource type="FontFile" uid="uid://ncoq4i61plvt" path="res://assets/Bohemian Soul.otf" id="1_yowck"]
|
||||||
|
|
||||||
|
[resource]
|
||||||
|
default_font = ExtResource("1_yowck")
|
||||||
|
Label/font_sizes/font_size = 12
|
||||||
|
Label/fonts/font = ExtResource("1_yowck")
|
||||||
|
|
@ -1,16 +0,0 @@
|
||||||
[gd_resource type="Resource" script_class="SupportCard" load_steps=5 format=3 uid="uid://4eod3m0vc5a8"]
|
|
||||||
|
|
||||||
[ext_resource type="Script" path="res://tcg/card/support_card_effect_instance.gd" id="1_alamh"]
|
|
||||||
[ext_resource type="Resource" uid="uid://cvu0rtt5nggf" path="res://data/support_effects/heal.tres" id="2_3x5mu"]
|
|
||||||
[ext_resource type="Script" path="res://tcg/card/support_card.gd" id="2_72hmi"]
|
|
||||||
|
|
||||||
[sub_resource type="Resource" id="Resource_88lmk"]
|
|
||||||
script = ExtResource("1_alamh")
|
|
||||||
magnitude = 5
|
|
||||||
effect = ExtResource("2_3x5mu")
|
|
||||||
|
|
||||||
[resource]
|
|
||||||
script = ExtResource("2_72hmi")
|
|
||||||
type = "green"
|
|
||||||
priority = 0
|
|
||||||
effects = Array[ExtResource("1_alamh")]([SubResource("Resource_88lmk")])
|
|
||||||
20
data/cards/support/potion.tres
Normal file
20
data/cards/support/potion.tres
Normal file
|
|
@ -0,0 +1,20 @@
|
||||||
|
[gd_resource type="Resource" script_class="SupportCard" load_steps=6 format=3 uid="uid://4eod3m0vc5a8"]
|
||||||
|
|
||||||
|
[ext_resource type="Script" path="res://tcg/card/support_card_effect_instance.gd" id="1_ujm0o"]
|
||||||
|
[ext_resource type="Resource" uid="uid://cvu0rtt5nggf" path="res://data/support_effects/heal.tres" id="2_k1cnl"]
|
||||||
|
[ext_resource type="Script" path="res://tcg/card/support_card.gd" id="3_6r4k4"]
|
||||||
|
[ext_resource type="Texture2D" uid="uid://rh3aswb0p7ri" path="res://assets/energy.png" id="3_kyx3v"]
|
||||||
|
|
||||||
|
[sub_resource type="Resource" id="Resource_88lmk"]
|
||||||
|
script = ExtResource("1_ujm0o")
|
||||||
|
magnitude = 30
|
||||||
|
effect = ExtResource("2_k1cnl")
|
||||||
|
|
||||||
|
[resource]
|
||||||
|
script = ExtResource("3_6r4k4")
|
||||||
|
type = "green"
|
||||||
|
priority = 0
|
||||||
|
effects = Array[ExtResource("1_ujm0o")]([SubResource("Resource_88lmk")])
|
||||||
|
name = "Potion"
|
||||||
|
description = "Heal 30 HP"
|
||||||
|
icon = ExtResource("3_kyx3v")
|
||||||
112
demo_game.gd
112
demo_game.gd
|
|
@ -1,4 +1,10 @@
|
||||||
extends Control
|
extends Control
|
||||||
|
class_name DemoGame
|
||||||
|
|
||||||
|
signal own_played_card(card: Card)
|
||||||
|
signal opponent_played_card(card: Card)
|
||||||
|
signal own_played_rts(move: String)
|
||||||
|
signal opponent_played_rts(move: String)
|
||||||
|
|
||||||
@export var player_1_deck: Array[Card]
|
@export var player_1_deck: Array[Card]
|
||||||
@export var player_2_deck: Array[Card]
|
@export var player_2_deck: Array[Card]
|
||||||
|
|
@ -7,6 +13,8 @@ extends Control
|
||||||
@onready var opponent_side = $Opponent
|
@onready var opponent_side = $Opponent
|
||||||
@onready var start_game_btn = $StartGameButton
|
@onready var start_game_btn = $StartGameButton
|
||||||
|
|
||||||
|
var id_to_card: Dictionary = {}
|
||||||
|
|
||||||
var player_action_queue: Dictionary
|
var player_action_queue: Dictionary
|
||||||
var player_1_action: Action:
|
var player_1_action: Action:
|
||||||
get:
|
get:
|
||||||
|
|
@ -19,14 +27,30 @@ var player_2_action: Action:
|
||||||
set(value):
|
set(value):
|
||||||
player_action_queue[MatchManager.PLAYER_2_ID] = value
|
player_action_queue[MatchManager.PLAYER_2_ID] = value
|
||||||
|
|
||||||
func _ready() -> void:
|
var id
|
||||||
|
var signal_connected := false
|
||||||
|
|
||||||
|
func init(player_id: int) -> void:
|
||||||
|
id = player_id
|
||||||
|
|
||||||
|
id_to_card.clear()
|
||||||
|
|
||||||
|
var cards = player_1_deck.duplicate()
|
||||||
|
cards.append_array(player_2_deck)
|
||||||
|
for card in cards:
|
||||||
|
if card.id not in id_to_card:
|
||||||
|
id_to_card[card.id] = card
|
||||||
|
|
||||||
match_manager.init({
|
match_manager.init({
|
||||||
MatchManager.PLAYER_1_ID: player_1_deck,
|
MatchManager.PLAYER_1_ID: player_1_deck,
|
||||||
MatchManager.PLAYER_2_ID: player_2_deck
|
MatchManager.PLAYER_2_ID: player_2_deck
|
||||||
})
|
})
|
||||||
own_side.attach(match_manager)
|
own_side.attach(match_manager, player_id == MatchManager.PLAYER_1_ID)
|
||||||
opponent_side.attach(match_manager)
|
opponent_side.attach(match_manager, player_id == MatchManager.PLAYER_2_ID)
|
||||||
match_manager.state_transitioned.connect(_on_match_manager_state_transitioned)
|
|
||||||
|
if !signal_connected:
|
||||||
|
match_manager.state_transitioned.connect(_on_match_manager_state_transitioned)
|
||||||
|
signal_connected = true
|
||||||
|
|
||||||
var transition_history: Array[PhaseTransition] = []
|
var transition_history: Array[PhaseTransition] = []
|
||||||
func _on_match_manager_state_transitioned(transition: PhaseTransition):
|
func _on_match_manager_state_transitioned(transition: PhaseTransition):
|
||||||
|
|
@ -35,28 +59,100 @@ func _on_match_manager_state_transitioned(transition: PhaseTransition):
|
||||||
print("Phase: ", Match.phase_to_str(transition.from), " -> ", Match.phase_to_str(transition.to))
|
print("Phase: ", Match.phase_to_str(transition.from), " -> ", Match.phase_to_str(transition.to))
|
||||||
|
|
||||||
func _on_start_game_button_button_up() -> void:
|
func _on_start_game_button_button_up() -> void:
|
||||||
|
#match_manager.resolve({})
|
||||||
|
pass
|
||||||
|
|
||||||
|
func rpc_start_game() -> void:
|
||||||
match_manager.resolve({})
|
match_manager.resolve({})
|
||||||
|
|
||||||
func _on_own_play_card(card: Card) -> void:
|
func rpc_own_play_card(id: String) -> void:
|
||||||
player_1_action = ActionPlayCard.new(card)
|
if !id.is_empty():
|
||||||
|
var card = id_to_card[id]
|
||||||
|
player_1_action = ActionPlayCard.new(card)
|
||||||
|
else:
|
||||||
|
player_1_action = ActionSkipCard.new()
|
||||||
|
|
||||||
|
print(self.id, " rpc_own_play_card", player_1_action, player_2_action)
|
||||||
|
|
||||||
if player_2_action:
|
if player_2_action:
|
||||||
match_manager.resolve(player_action_queue)
|
match_manager.resolve(player_action_queue)
|
||||||
player_action_queue.clear()
|
player_action_queue.clear()
|
||||||
|
|
||||||
func _on_opponent_play_card(card: Card) -> void:
|
func _on_own_play_card(card: Card) -> void:
|
||||||
player_2_action = ActionPlayCard.new(card)
|
if card:
|
||||||
|
player_1_action = ActionPlayCard.new(card)
|
||||||
|
own_played_card.emit(card)
|
||||||
|
else:
|
||||||
|
player_1_action = ActionSkipCard.new()
|
||||||
|
own_played_card.emit(null)
|
||||||
|
|
||||||
|
print(id, " _on_own_play_card", player_1_action, player_2_action)
|
||||||
|
|
||||||
|
if player_2_action:
|
||||||
|
match_manager.resolve(player_action_queue)
|
||||||
|
player_action_queue.clear()
|
||||||
|
|
||||||
|
func rpc_opponent_play_card(id: String) -> void:
|
||||||
|
if !id.is_empty():
|
||||||
|
var card = id_to_card[id]
|
||||||
|
player_2_action = ActionPlayCard.new(card)
|
||||||
|
else:
|
||||||
|
player_2_action = ActionSkipCard.new()
|
||||||
|
|
||||||
|
print(self.id , " rpc_opponent_play_card", player_1_action, player_2_action)
|
||||||
|
|
||||||
if player_1_action:
|
if player_1_action:
|
||||||
match_manager.resolve(player_action_queue)
|
match_manager.resolve(player_action_queue)
|
||||||
player_action_queue.clear()
|
player_action_queue.clear()
|
||||||
|
|
||||||
|
func _on_opponent_play_card(card: Card) -> void:
|
||||||
|
if card:
|
||||||
|
player_2_action = ActionPlayCard.new(card)
|
||||||
|
opponent_played_card.emit(card)
|
||||||
|
else:
|
||||||
|
player_2_action = ActionSkipCard.new()
|
||||||
|
opponent_played_card.emit(null)
|
||||||
|
|
||||||
|
print(id, " _on_opponent_play_card", player_1_action, player_2_action)
|
||||||
|
|
||||||
|
if player_1_action:
|
||||||
|
match_manager.resolve(player_action_queue)
|
||||||
|
player_action_queue.clear()
|
||||||
|
|
||||||
|
func rpc_own_rps_move(move: String) -> void:
|
||||||
|
player_1_action = ActionRPSMove.new(move)
|
||||||
|
|
||||||
|
print(id, " rpc_own_rps_move", player_1_action, player_2_action, move)
|
||||||
|
|
||||||
|
if player_2_action:
|
||||||
|
match_manager.resolve(player_action_queue)
|
||||||
|
player_action_queue.clear()
|
||||||
|
|
||||||
func _on_own_rps_move(move: String) -> void:
|
func _on_own_rps_move(move: String) -> void:
|
||||||
player_1_action = ActionRPSMove.new(move)
|
player_1_action = ActionRPSMove.new(move)
|
||||||
|
own_played_rts.emit(move)
|
||||||
|
|
||||||
|
print(id, " _on_own_rps_move", player_1_action, player_2_action, move)
|
||||||
|
|
||||||
if player_2_action:
|
if player_2_action:
|
||||||
match_manager.resolve(player_action_queue)
|
match_manager.resolve(player_action_queue)
|
||||||
player_action_queue.clear()
|
player_action_queue.clear()
|
||||||
|
|
||||||
|
func rpc_opponent_rps_move(move: String) -> void:
|
||||||
|
player_2_action = ActionRPSMove.new(move)
|
||||||
|
|
||||||
|
print(id, " rpc_opponent_rps_move", player_1_action, player_2_action, move)
|
||||||
|
|
||||||
|
if player_1_action:
|
||||||
|
match_manager.resolve(player_action_queue)
|
||||||
|
player_action_queue.clear()
|
||||||
|
|
||||||
func _on_opponent_rps_move(move: String) -> void:
|
func _on_opponent_rps_move(move: String) -> void:
|
||||||
player_2_action = ActionRPSMove.new(move)
|
player_2_action = ActionRPSMove.new(move)
|
||||||
|
opponent_played_rts.emit(move)
|
||||||
|
|
||||||
|
print(id, " rpc_opponent_rps_move", player_1_action, player_2_action, move)
|
||||||
|
|
||||||
if player_1_action:
|
if player_1_action:
|
||||||
match_manager.resolve(player_action_queue)
|
match_manager.resolve(player_action_queue)
|
||||||
player_action_queue.clear()
|
player_action_queue.clear()
|
||||||
|
|
|
||||||
|
|
@ -1,12 +1,12 @@
|
||||||
[gd_scene load_steps=8 format=3 uid="uid://bgc0u117jqyr1"]
|
[gd_scene load_steps=8 format=3 uid="uid://l2ehohbd1xhk"]
|
||||||
|
|
||||||
[ext_resource type="Script" path="res://demo_game.gd" id="1_jn16u"]
|
[ext_resource type="Script" path="res://demo_game.gd" id="1_jn16u"]
|
||||||
[ext_resource type="Script" path="res://player_side.gd" id="2_w4tnt"]
|
[ext_resource type="Script" path="res://player_side.gd" id="2_w4tnt"]
|
||||||
[ext_resource type="Script" path="res://tcg/card/card.gd" id="2_xuft0"]
|
[ext_resource type="Script" path="res://tcg/card/card.gd" id="2_xuft0"]
|
||||||
[ext_resource type="PackedScene" uid="uid://cikstg43mudkn" path="res://tcg/match/match_manager.tscn" id="3_3yhrl"]
|
[ext_resource type="PackedScene" uid="uid://cikstg43mudkn" path="res://tcg/match/match_manager.tscn" id="3_3yhrl"]
|
||||||
[ext_resource type="Resource" uid="uid://cs7q8i7bvohmj" path="res://data/cards/baraga.tres" id="3_we1tk"]
|
[ext_resource type="Resource" uid="uid://cs7q8i7bvohmj" path="res://data/cards/monster/baraga.tres" id="3_we1tk"]
|
||||||
[ext_resource type="Resource" uid="uid://4eod3m0vc5a8" path="res://data/cards/potion.tres" id="4_kkhfk"]
|
[ext_resource type="Resource" uid="uid://4eod3m0vc5a8" path="res://data/cards/support/potion.tres" id="4_kkhfk"]
|
||||||
[ext_resource type="Resource" uid="uid://di76avwc0gn8e" path="res://data/cards/taiman.tres" id="5_3cm5x"]
|
[ext_resource type="Resource" uid="uid://di76avwc0gn8e" path="res://data/cards/monster/taiman.tres" id="5_3cm5x"]
|
||||||
|
|
||||||
[node name="DemoGame" type="Control"]
|
[node name="DemoGame" type="Control"]
|
||||||
layout_mode = 3
|
layout_mode = 3
|
||||||
|
|
@ -16,8 +16,8 @@ anchor_bottom = 1.0
|
||||||
grow_horizontal = 2
|
grow_horizontal = 2
|
||||||
grow_vertical = 2
|
grow_vertical = 2
|
||||||
script = ExtResource("1_jn16u")
|
script = ExtResource("1_jn16u")
|
||||||
player_1_deck = Array[ExtResource("2_xuft0")]([ExtResource("3_we1tk"), ExtResource("4_kkhfk"), ExtResource("4_kkhfk")])
|
player_1_deck = Array[ExtResource("2_xuft0")]([ExtResource("3_we1tk"), ExtResource("4_kkhfk"), ExtResource("4_kkhfk"), ExtResource("4_kkhfk"), ExtResource("5_3cm5x")])
|
||||||
player_2_deck = Array[ExtResource("2_xuft0")]([ExtResource("5_3cm5x"), ExtResource("4_kkhfk"), ExtResource("4_kkhfk")])
|
player_2_deck = Array[ExtResource("2_xuft0")]([ExtResource("5_3cm5x"), ExtResource("4_kkhfk"), ExtResource("4_kkhfk"), ExtResource("4_kkhfk"), ExtResource("3_we1tk")])
|
||||||
|
|
||||||
[node name="Own" type="VBoxContainer" parent="." node_paths=PackedStringArray("deck", "monster_name_label", "monster_health_label", "incoming_damage_label", "energy_label")]
|
[node name="Own" type="VBoxContainer" parent="." node_paths=PackedStringArray("deck", "monster_name_label", "monster_health_label", "incoming_damage_label", "energy_label")]
|
||||||
layout_mode = 1
|
layout_mode = 1
|
||||||
|
|
|
||||||
|
|
@ -130,3 +130,211 @@ Unregister-ScheduledTask -TaskName godot_remote_debug -Confirm:$false -ErrorActi
|
||||||
ssh_remote_deploy/cleanup_script="Stop-ScheduledTask -TaskName godot_remote_debug -ErrorAction:SilentlyContinue
|
ssh_remote_deploy/cleanup_script="Stop-ScheduledTask -TaskName godot_remote_debug -ErrorAction:SilentlyContinue
|
||||||
Unregister-ScheduledTask -TaskName godot_remote_debug -Confirm:$false -ErrorAction:SilentlyContinue
|
Unregister-ScheduledTask -TaskName godot_remote_debug -Confirm:$false -ErrorAction:SilentlyContinue
|
||||||
Remove-Item -Recurse -Force '{temp_dir}'"
|
Remove-Item -Recurse -Force '{temp_dir}'"
|
||||||
|
|
||||||
|
[preset.2]
|
||||||
|
|
||||||
|
name="Android"
|
||||||
|
platform="Android"
|
||||||
|
runnable=true
|
||||||
|
advanced_options=false
|
||||||
|
dedicated_server=false
|
||||||
|
custom_features=""
|
||||||
|
export_filter="all_resources"
|
||||||
|
include_filter=""
|
||||||
|
exclude_filter=""
|
||||||
|
export_path=""
|
||||||
|
encryption_include_filters=""
|
||||||
|
encryption_exclude_filters=""
|
||||||
|
encrypt_pck=false
|
||||||
|
encrypt_directory=false
|
||||||
|
script_export_mode=2
|
||||||
|
|
||||||
|
[preset.2.options]
|
||||||
|
|
||||||
|
custom_template/debug=""
|
||||||
|
custom_template/release=""
|
||||||
|
gradle_build/use_gradle_build=false
|
||||||
|
gradle_build/gradle_build_directory=""
|
||||||
|
gradle_build/android_source_template=""
|
||||||
|
gradle_build/compress_native_libraries=false
|
||||||
|
gradle_build/export_format=0
|
||||||
|
gradle_build/min_sdk=""
|
||||||
|
gradle_build/target_sdk=""
|
||||||
|
architectures/armeabi-v7a=false
|
||||||
|
architectures/arm64-v8a=true
|
||||||
|
architectures/x86=false
|
||||||
|
architectures/x86_64=false
|
||||||
|
version/code=1
|
||||||
|
version/name=""
|
||||||
|
package/unique_name="com.example.$genname"
|
||||||
|
package/name=""
|
||||||
|
package/signed=true
|
||||||
|
package/app_category=2
|
||||||
|
package/retain_data_on_uninstall=false
|
||||||
|
package/exclude_from_recents=false
|
||||||
|
package/show_in_android_tv=false
|
||||||
|
package/show_in_app_library=true
|
||||||
|
package/show_as_launcher_app=false
|
||||||
|
launcher_icons/main_192x192=""
|
||||||
|
launcher_icons/adaptive_foreground_432x432=""
|
||||||
|
launcher_icons/adaptive_background_432x432=""
|
||||||
|
graphics/opengl_debug=false
|
||||||
|
xr_features/xr_mode=0
|
||||||
|
screen/immersive_mode=true
|
||||||
|
screen/support_small=true
|
||||||
|
screen/support_normal=true
|
||||||
|
screen/support_large=true
|
||||||
|
screen/support_xlarge=true
|
||||||
|
user_data_backup/allow=false
|
||||||
|
command_line/extra_args=""
|
||||||
|
apk_expansion/enable=false
|
||||||
|
apk_expansion/SALT=""
|
||||||
|
apk_expansion/public_key=""
|
||||||
|
permissions/custom_permissions=PackedStringArray()
|
||||||
|
permissions/access_checkin_properties=false
|
||||||
|
permissions/access_coarse_location=false
|
||||||
|
permissions/access_fine_location=false
|
||||||
|
permissions/access_location_extra_commands=false
|
||||||
|
permissions/access_mock_location=false
|
||||||
|
permissions/access_network_state=false
|
||||||
|
permissions/access_surface_flinger=false
|
||||||
|
permissions/access_wifi_state=false
|
||||||
|
permissions/account_manager=false
|
||||||
|
permissions/add_voicemail=false
|
||||||
|
permissions/authenticate_accounts=false
|
||||||
|
permissions/battery_stats=false
|
||||||
|
permissions/bind_accessibility_service=false
|
||||||
|
permissions/bind_appwidget=false
|
||||||
|
permissions/bind_device_admin=false
|
||||||
|
permissions/bind_input_method=false
|
||||||
|
permissions/bind_nfc_service=false
|
||||||
|
permissions/bind_notification_listener_service=false
|
||||||
|
permissions/bind_print_service=false
|
||||||
|
permissions/bind_remoteviews=false
|
||||||
|
permissions/bind_text_service=false
|
||||||
|
permissions/bind_vpn_service=false
|
||||||
|
permissions/bind_wallpaper=false
|
||||||
|
permissions/bluetooth=false
|
||||||
|
permissions/bluetooth_admin=false
|
||||||
|
permissions/bluetooth_privileged=false
|
||||||
|
permissions/brick=false
|
||||||
|
permissions/broadcast_package_removed=false
|
||||||
|
permissions/broadcast_sms=false
|
||||||
|
permissions/broadcast_sticky=false
|
||||||
|
permissions/broadcast_wap_push=false
|
||||||
|
permissions/call_phone=false
|
||||||
|
permissions/call_privileged=false
|
||||||
|
permissions/camera=false
|
||||||
|
permissions/capture_audio_output=false
|
||||||
|
permissions/capture_secure_video_output=false
|
||||||
|
permissions/capture_video_output=false
|
||||||
|
permissions/change_component_enabled_state=false
|
||||||
|
permissions/change_configuration=false
|
||||||
|
permissions/change_network_state=false
|
||||||
|
permissions/change_wifi_multicast_state=false
|
||||||
|
permissions/change_wifi_state=false
|
||||||
|
permissions/clear_app_cache=false
|
||||||
|
permissions/clear_app_user_data=false
|
||||||
|
permissions/control_location_updates=false
|
||||||
|
permissions/delete_cache_files=false
|
||||||
|
permissions/delete_packages=false
|
||||||
|
permissions/device_power=false
|
||||||
|
permissions/diagnostic=false
|
||||||
|
permissions/disable_keyguard=false
|
||||||
|
permissions/dump=false
|
||||||
|
permissions/expand_status_bar=false
|
||||||
|
permissions/factory_test=false
|
||||||
|
permissions/flashlight=false
|
||||||
|
permissions/force_back=false
|
||||||
|
permissions/get_accounts=false
|
||||||
|
permissions/get_package_size=false
|
||||||
|
permissions/get_tasks=false
|
||||||
|
permissions/get_top_activity_info=false
|
||||||
|
permissions/global_search=false
|
||||||
|
permissions/hardware_test=false
|
||||||
|
permissions/inject_events=false
|
||||||
|
permissions/install_location_provider=false
|
||||||
|
permissions/install_packages=false
|
||||||
|
permissions/install_shortcut=false
|
||||||
|
permissions/internal_system_window=false
|
||||||
|
permissions/internet=false
|
||||||
|
permissions/kill_background_processes=false
|
||||||
|
permissions/location_hardware=false
|
||||||
|
permissions/manage_accounts=false
|
||||||
|
permissions/manage_app_tokens=false
|
||||||
|
permissions/manage_documents=false
|
||||||
|
permissions/manage_external_storage=false
|
||||||
|
permissions/master_clear=false
|
||||||
|
permissions/media_content_control=false
|
||||||
|
permissions/modify_audio_settings=false
|
||||||
|
permissions/modify_phone_state=false
|
||||||
|
permissions/mount_format_filesystems=false
|
||||||
|
permissions/mount_unmount_filesystems=false
|
||||||
|
permissions/nfc=false
|
||||||
|
permissions/persistent_activity=false
|
||||||
|
permissions/post_notifications=false
|
||||||
|
permissions/process_outgoing_calls=false
|
||||||
|
permissions/read_calendar=false
|
||||||
|
permissions/read_call_log=false
|
||||||
|
permissions/read_contacts=false
|
||||||
|
permissions/read_external_storage=false
|
||||||
|
permissions/read_frame_buffer=false
|
||||||
|
permissions/read_history_bookmarks=false
|
||||||
|
permissions/read_input_state=false
|
||||||
|
permissions/read_logs=false
|
||||||
|
permissions/read_phone_state=false
|
||||||
|
permissions/read_profile=false
|
||||||
|
permissions/read_sms=false
|
||||||
|
permissions/read_social_stream=false
|
||||||
|
permissions/read_sync_settings=false
|
||||||
|
permissions/read_sync_stats=false
|
||||||
|
permissions/read_user_dictionary=false
|
||||||
|
permissions/reboot=false
|
||||||
|
permissions/receive_boot_completed=false
|
||||||
|
permissions/receive_mms=false
|
||||||
|
permissions/receive_sms=false
|
||||||
|
permissions/receive_wap_push=false
|
||||||
|
permissions/record_audio=false
|
||||||
|
permissions/reorder_tasks=false
|
||||||
|
permissions/restart_packages=false
|
||||||
|
permissions/send_respond_via_message=false
|
||||||
|
permissions/send_sms=false
|
||||||
|
permissions/set_activity_watcher=false
|
||||||
|
permissions/set_alarm=false
|
||||||
|
permissions/set_always_finish=false
|
||||||
|
permissions/set_animation_scale=false
|
||||||
|
permissions/set_debug_app=false
|
||||||
|
permissions/set_orientation=false
|
||||||
|
permissions/set_pointer_speed=false
|
||||||
|
permissions/set_preferred_applications=false
|
||||||
|
permissions/set_process_limit=false
|
||||||
|
permissions/set_time=false
|
||||||
|
permissions/set_time_zone=false
|
||||||
|
permissions/set_wallpaper=false
|
||||||
|
permissions/set_wallpaper_hints=false
|
||||||
|
permissions/signal_persistent_processes=false
|
||||||
|
permissions/status_bar=false
|
||||||
|
permissions/subscribed_feeds_read=false
|
||||||
|
permissions/subscribed_feeds_write=false
|
||||||
|
permissions/system_alert_window=false
|
||||||
|
permissions/transmit_ir=false
|
||||||
|
permissions/uninstall_shortcut=false
|
||||||
|
permissions/update_device_stats=false
|
||||||
|
permissions/use_credentials=false
|
||||||
|
permissions/use_sip=false
|
||||||
|
permissions/vibrate=false
|
||||||
|
permissions/wake_lock=false
|
||||||
|
permissions/write_apn_settings=false
|
||||||
|
permissions/write_calendar=false
|
||||||
|
permissions/write_call_log=false
|
||||||
|
permissions/write_contacts=false
|
||||||
|
permissions/write_external_storage=false
|
||||||
|
permissions/write_gservices=false
|
||||||
|
permissions/write_history_bookmarks=false
|
||||||
|
permissions/write_profile=false
|
||||||
|
permissions/write_secure_settings=false
|
||||||
|
permissions/write_settings=false
|
||||||
|
permissions/write_sms=false
|
||||||
|
permissions/write_social_stream=false
|
||||||
|
permissions/write_sync_settings=false
|
||||||
|
permissions/write_user_dictionary=false
|
||||||
|
|
|
||||||
235
main.gd
235
main.gd
|
|
@ -1,76 +1,213 @@
|
||||||
extends Node
|
extends Node
|
||||||
|
class_name MainNode
|
||||||
|
|
||||||
const PORT = 25565
|
const PORT = 25565
|
||||||
|
const PORT_RANGE := 10
|
||||||
const MAX_CONNECTIONS = 20
|
const MAX_CONNECTIONS = 20
|
||||||
|
|
||||||
var counter = 0
|
|
||||||
|
|
||||||
@onready var before_connect_container = get_node("BeforeConnect") as Container
|
@onready var before_connect_container = get_node("BeforeConnect") as Container
|
||||||
@onready var host_text_edit = get_node("%HostTextEdit") as TextEdit
|
|
||||||
@onready var connect_button = get_node("%ConnectButton") as Button
|
@onready var connect_button = get_node("%ConnectButton") as Button
|
||||||
|
@onready var host_button = get_node("%HostButton") as Button
|
||||||
|
@onready var server_discovery = get_node("%ServerDiscovery") as ServerDiscovery
|
||||||
|
|
||||||
@onready var after_connect_container = get_node("%AfterConnect") as Container
|
@onready var after_connect_container = get_node("%AfterConnect") as Node
|
||||||
@onready var counter_label = get_node("%CounterLabel") as Label
|
@onready var disconnect_button = get_node("%DisconnectButton") as Button
|
||||||
@onready var decrement_button = get_node("%DecrementButton") as Button
|
|
||||||
@onready var increment_button = get_node("%IncrementButton") as Button
|
@onready var demo_game = get_node("AfterConnect/DemoGame") as DemoGame
|
||||||
|
@onready var start_game_button = (get_node("AfterConnect/DemoGame") as DemoGame).start_game_btn
|
||||||
|
|
||||||
|
|
||||||
|
var active_port: int
|
||||||
|
var server_buttons: Dictionary = Dictionary()
|
||||||
|
var base_seed: int
|
||||||
|
|
||||||
|
func _clean_room():
|
||||||
|
# this is if someone left the room and we will just clean the game room again
|
||||||
|
# should only called on host
|
||||||
|
# need to clean for server
|
||||||
|
pass
|
||||||
|
|
||||||
|
func _on_start_game_clicked():
|
||||||
|
if !multiplayer.multiplayer_peer:
|
||||||
|
return
|
||||||
|
if !multiplayer.is_server():
|
||||||
|
return
|
||||||
|
if (multiplayer.get_peers().size() == 0):
|
||||||
|
return
|
||||||
|
# do start game here, should only run on host
|
||||||
|
_start_game.rpc()
|
||||||
|
pass
|
||||||
|
|
||||||
func _ready() -> void:
|
func _ready() -> void:
|
||||||
if OS.has_feature("dedicated_server"):
|
host_button.button_up.connect(_on_host_pressed)
|
||||||
print("Starting dedicated server")
|
host_button.text = "Host (%s)" % server_discovery.id
|
||||||
var peer = ENetMultiplayerPeer.new()
|
|
||||||
var err = peer.create_server(PORT, MAX_CONNECTIONS)
|
start_game_button.button_up.connect(_on_start_game_clicked)
|
||||||
|
|
||||||
|
print("Attach client")
|
||||||
|
multiplayer.peer_connected.connect(_on_player_connected)
|
||||||
|
multiplayer.peer_disconnected.connect(_on_player_disconnected)
|
||||||
|
multiplayer.connected_to_server.connect(_on_connected_ok)
|
||||||
|
#multiplayer.connection_failed.connect(_on_connected_fail)
|
||||||
|
multiplayer.server_disconnected.connect(_on_server_disconnected)
|
||||||
|
|
||||||
|
disconnect_button.button_up.connect(_on_disconnect_clicked)
|
||||||
|
connect_button.get_parent().remove_child(connect_button)
|
||||||
|
|
||||||
|
server_discovery.server_added.connect(_on_server_added)
|
||||||
|
server_discovery.server_removed.connect(_on_server_removed)
|
||||||
|
|
||||||
|
demo_game.own_played_card.connect(func (card): _on_own_played_card.rpc(card.id if card else ""))
|
||||||
|
demo_game.opponent_played_card.connect(func (card): _on_opponent_played_card.rpc(card.id if card else ""))
|
||||||
|
demo_game.own_played_rts.connect(func (move): _on_own_played_rts.rpc(move))
|
||||||
|
demo_game.opponent_played_rts.connect(func (move): _on_opponent_played_rts.rpc(move))
|
||||||
|
|
||||||
|
@rpc("any_peer", "call_remote", "reliable")
|
||||||
|
func _on_own_played_card(card_id: String):
|
||||||
|
demo_game.rpc_own_play_card(card_id)
|
||||||
|
|
||||||
|
@rpc("any_peer", "call_remote", "reliable")
|
||||||
|
func _on_opponent_played_card(card_id: String):
|
||||||
|
demo_game.rpc_opponent_play_card(card_id)
|
||||||
|
|
||||||
|
@rpc("any_peer", "call_remote", "reliable")
|
||||||
|
func _on_own_played_rts(move: String):
|
||||||
|
demo_game.rpc_own_rps_move(move)
|
||||||
|
|
||||||
|
@rpc("any_peer", "call_remote", "reliable")
|
||||||
|
func _on_opponent_played_rts(move: String):
|
||||||
|
demo_game.rpc_opponent_rps_move(move)
|
||||||
|
|
||||||
|
@rpc("authority", "call_local", "reliable")
|
||||||
|
func _sync_seed(seed: int):
|
||||||
|
seed(seed)
|
||||||
|
|
||||||
|
@rpc("authority", "call_local", "reliable")
|
||||||
|
func _start_game():
|
||||||
|
if multiplayer.is_server():
|
||||||
|
demo_game.init(MatchManager.PLAYER_1_ID)
|
||||||
|
else:
|
||||||
|
demo_game.init(MatchManager.PLAYER_2_ID)
|
||||||
|
|
||||||
|
demo_game.rpc_start_game()
|
||||||
|
|
||||||
|
func _on_disconnect_clicked():
|
||||||
|
if (multiplayer.is_server()):
|
||||||
|
server_discovery.disable_server()
|
||||||
|
for peer_id in multiplayer.get_peers():
|
||||||
|
multiplayer.disconnect_peer(peer_id)
|
||||||
|
|
||||||
|
multiplayer.multiplayer_peer = null
|
||||||
|
|
||||||
|
$BeforeConnect.visible = true
|
||||||
|
$AfterConnect.visible = false
|
||||||
|
|
||||||
|
func _on_server_added(id, ip, port):
|
||||||
|
print("%s | Server added %s %s" % [server_discovery.id, id, ip])
|
||||||
|
|
||||||
|
var button = connect_button.duplicate()
|
||||||
|
before_connect_container.add_child(button)
|
||||||
|
|
||||||
|
var key = "%s|%s" % [id,ip]
|
||||||
|
server_buttons[key] = button
|
||||||
|
|
||||||
|
button.text = "%s\nConnect\n%s:%d" % [id, ip, port]
|
||||||
|
for conn in button.button_down.get_connections():
|
||||||
|
button.button_down.disconnect(conn)
|
||||||
|
|
||||||
|
var _on_button_downed = func():
|
||||||
|
_do_connect(ip, port)
|
||||||
|
button.button_down.connect(_on_button_downed)
|
||||||
|
|
||||||
|
func _on_server_removed(id, ip):
|
||||||
|
print("%s | Server removed %s %s" % [server_discovery.id, id, ip])
|
||||||
|
|
||||||
|
var key = "%s|%s" % [id,ip]
|
||||||
|
var button = server_buttons[key]
|
||||||
|
button.queue_free()
|
||||||
|
server_buttons.erase(key)
|
||||||
|
|
||||||
|
func _do_connect(ip: String, port: int):
|
||||||
|
var peer = ENetMultiplayerPeer.new()
|
||||||
|
print("%s Connecting to %s:%d" % [server_discovery.id, ip, port])
|
||||||
|
peer.create_client(ip, port)
|
||||||
|
multiplayer.multiplayer_peer = peer
|
||||||
|
|
||||||
|
func _on_host_pressed():
|
||||||
|
print("%s | Starting dedicated server" % server_discovery.id)
|
||||||
|
var peer = ENetMultiplayerPeer.new()
|
||||||
|
for offset in range(PORT_RANGE):
|
||||||
|
if not is_port_available(PORT + offset):
|
||||||
|
continue
|
||||||
|
|
||||||
|
active_port = PORT + offset
|
||||||
|
var err = peer.create_server(active_port, MAX_CONNECTIONS)
|
||||||
if err:
|
if err:
|
||||||
print(err)
|
print(err)
|
||||||
multiplayer.multiplayer_peer = peer
|
break
|
||||||
multiplayer.peer_connected.connect(_on_player_connected)
|
|
||||||
else:
|
|
||||||
print("Game starting")
|
|
||||||
#multiplayer.peer_disconnected.connect(_on_player_disconnected)
|
|
||||||
multiplayer.connected_to_server.connect(_on_connected_ok)
|
|
||||||
#multiplayer.connection_failed.connect(_on_connected_fail)
|
|
||||||
#multiplayer.server_disconnected.connect(_on_server_disconnected)
|
|
||||||
|
|
||||||
increment_button.button_up.connect(func(): _increment.rpc())
|
|
||||||
decrement_button.button_up.connect(func(): _decrement.rpc())
|
|
||||||
connect_button.button_up.connect(_on_connect_pressed)
|
|
||||||
|
|
||||||
@rpc("any_peer", "call_local")
|
|
||||||
func _increment():
|
|
||||||
counter += 1
|
|
||||||
counter_label.text = str(counter)
|
|
||||||
|
|
||||||
@rpc("any_peer", "call_local")
|
|
||||||
func _decrement():
|
|
||||||
counter -= 1
|
|
||||||
counter_label.text = str(counter)
|
|
||||||
|
|
||||||
@rpc("authority", "call_remote")
|
|
||||||
func _set_counter(value: int):
|
|
||||||
counter = value
|
|
||||||
counter_label.text = str(counter)
|
|
||||||
|
|
||||||
func _on_connect_pressed():
|
|
||||||
var peer = ENetMultiplayerPeer.new()
|
|
||||||
var parsed: PackedStringArray = host_text_edit.text.split(":")
|
|
||||||
print("Connecting to ", parsed[0])
|
|
||||||
peer.create_client(parsed[0] if not parsed[0].is_empty() else "localhost", int(parsed[1]) if parsed.size() > 1 else PORT)
|
|
||||||
multiplayer.multiplayer_peer = peer
|
multiplayer.multiplayer_peer = peer
|
||||||
|
|
||||||
|
_on_connected_ok()
|
||||||
|
|
||||||
|
start_game_button.disabled = true
|
||||||
|
start_game_button.text = "Start Game (Not enough player)"
|
||||||
|
|
||||||
|
base_seed = randi()
|
||||||
|
_sync_seed.rpc(base_seed)
|
||||||
|
|
||||||
|
server_discovery.enable_server(active_port)
|
||||||
|
|
||||||
|
func is_port_available(port: int) -> bool:
|
||||||
|
var udp_peer = PacketPeerUDP.new()
|
||||||
|
|
||||||
|
var error = udp_peer.bind(port)
|
||||||
|
|
||||||
|
if error == OK:
|
||||||
|
udp_peer.close()
|
||||||
|
return true
|
||||||
|
else:
|
||||||
|
return false
|
||||||
|
|
||||||
func _on_player_connected(id: int):
|
func _on_player_connected(id: int):
|
||||||
if multiplayer.get_unique_id() == 1:
|
if multiplayer.get_unique_id() == 1:
|
||||||
_set_counter.rpc_id(id, counter)
|
|
||||||
|
_sync_seed.rpc(base_seed)
|
||||||
|
|
||||||
|
if (multiplayer.get_peers().size() > 0):
|
||||||
|
start_game_button.disabled = false
|
||||||
|
start_game_button.text = "Start Game"
|
||||||
|
server_discovery.disable_server()
|
||||||
|
|
||||||
func _on_player_disconnected():
|
func _on_player_disconnected(id):
|
||||||
pass
|
print("%s | _on_player_disconnected %s" % [server_discovery.id, id])
|
||||||
|
|
||||||
|
if multiplayer.get_unique_id() == id:
|
||||||
|
$BeforeConnect.visible = true
|
||||||
|
$AfterConnect.visible = false
|
||||||
|
|
||||||
|
if (id != 1 and multiplayer.get_unique_id() == 1):
|
||||||
|
_clean_room()
|
||||||
|
start_game_button.disabled = true
|
||||||
|
start_game_button.text = "Start Game (Not enough player)"
|
||||||
|
server_discovery.enable_server(active_port)
|
||||||
|
|
||||||
func _on_connected_ok():
|
func _on_connected_ok():
|
||||||
$AfterConnect.visible = true
|
$AfterConnect.visible = true
|
||||||
$BeforeConnect.visible = false
|
$BeforeConnect.visible = false
|
||||||
counter_label.text = str(counter)
|
|
||||||
|
if (multiplayer.is_server()):
|
||||||
|
disconnect_button.text = "Disconnect (Host)"
|
||||||
|
start_game_button.visible = true
|
||||||
|
else:
|
||||||
|
disconnect_button.text = "Disconnect"
|
||||||
|
start_game_button.visible = false
|
||||||
|
|
||||||
func _on_connected_fail():
|
func _on_connected_fail():
|
||||||
pass
|
pass
|
||||||
|
|
||||||
func _on_server_disconnected():
|
func _on_server_disconnected():
|
||||||
pass
|
print("%s | _on_server_disconnected" % [server_discovery.id])
|
||||||
|
$AfterConnect.visible = false
|
||||||
|
$BeforeConnect.visible = true
|
||||||
|
|
||||||
|
|
|
||||||
61
main.tscn
61
main.tscn
|
|
@ -1,6 +1,8 @@
|
||||||
[gd_scene load_steps=2 format=3 uid="uid://c7gn46af6whf8"]
|
[gd_scene load_steps=4 format=3 uid="uid://c7gn46af6whf8"]
|
||||||
|
|
||||||
[ext_resource type="Script" path="res://main.gd" id="1_e0ud3"]
|
[ext_resource type="Script" path="res://main.gd" id="1_e0ud3"]
|
||||||
|
[ext_resource type="Script" path="res://server_discovery.gd" id="2_hed18"]
|
||||||
|
[ext_resource type="PackedScene" uid="uid://l2ehohbd1xhk" path="res://demo_game.tscn" id="3_2ln6b"]
|
||||||
|
|
||||||
[node name="Main" type="Control"]
|
[node name="Main" type="Control"]
|
||||||
layout_mode = 3
|
layout_mode = 3
|
||||||
|
|
@ -27,11 +29,11 @@ grow_horizontal = 2
|
||||||
grow_vertical = 2
|
grow_vertical = 2
|
||||||
alignment = 1
|
alignment = 1
|
||||||
|
|
||||||
[node name="HostTextEdit" type="TextEdit" parent="BeforeConnect"]
|
[node name="HostButton" type="Button" parent="BeforeConnect"]
|
||||||
unique_name_in_owner = true
|
unique_name_in_owner = true
|
||||||
|
custom_minimum_size = Vector2(0, 64)
|
||||||
layout_mode = 2
|
layout_mode = 2
|
||||||
size_flags_vertical = 3
|
text = "Host"
|
||||||
placeholder_text = "192.168.*.*"
|
|
||||||
|
|
||||||
[node name="ConnectButton" type="Button" parent="BeforeConnect"]
|
[node name="ConnectButton" type="Button" parent="BeforeConnect"]
|
||||||
unique_name_in_owner = true
|
unique_name_in_owner = true
|
||||||
|
|
@ -39,42 +41,31 @@ custom_minimum_size = Vector2(0, 64)
|
||||||
layout_mode = 2
|
layout_mode = 2
|
||||||
text = "Connect"
|
text = "Connect"
|
||||||
|
|
||||||
[node name="AfterConnect" type="VBoxContainer" parent="."]
|
[node name="DiscoveryTimer" type="Timer" parent="BeforeConnect"]
|
||||||
|
unique_name_in_owner = true
|
||||||
|
|
||||||
|
[node name="ServerDiscovery" type="Node" parent="BeforeConnect"]
|
||||||
|
unique_name_in_owner = true
|
||||||
|
script = ExtResource("2_hed18")
|
||||||
|
|
||||||
|
[node name="AfterConnect" type="Control" parent="."]
|
||||||
unique_name_in_owner = true
|
unique_name_in_owner = true
|
||||||
visible = false
|
visible = false
|
||||||
layout_mode = 1
|
layout_mode = 1
|
||||||
anchors_preset = 8
|
anchors_preset = 15
|
||||||
anchor_left = 0.5
|
anchor_right = 1.0
|
||||||
anchor_top = 0.5
|
anchor_bottom = 1.0
|
||||||
anchor_right = 0.5
|
|
||||||
anchor_bottom = 0.5
|
|
||||||
offset_left = -187.5
|
|
||||||
offset_top = -88.5
|
|
||||||
offset_right = 187.5
|
|
||||||
offset_bottom = 88.5
|
|
||||||
grow_horizontal = 2
|
grow_horizontal = 2
|
||||||
grow_vertical = 2
|
grow_vertical = 2
|
||||||
|
|
||||||
[node name="CounterLabel" type="Label" parent="AfterConnect"]
|
[node name="DemoGame" parent="AfterConnect" instance=ExtResource("3_2ln6b")]
|
||||||
|
layout_mode = 1
|
||||||
|
|
||||||
|
[node name="DisconnectButton" type="Button" parent="AfterConnect"]
|
||||||
unique_name_in_owner = true
|
unique_name_in_owner = true
|
||||||
layout_mode = 2
|
layout_mode = 2
|
||||||
size_flags_vertical = 3
|
offset_left = 966.0
|
||||||
theme_override_font_sizes/font_size = 64
|
offset_right = 1152.0
|
||||||
text = "1"
|
offset_bottom = 31.0
|
||||||
horizontal_alignment = 1
|
size_flags_horizontal = 8
|
||||||
vertical_alignment = 1
|
text = "Disconnect"
|
||||||
|
|
||||||
[node name="Actions" type="HBoxContainer" parent="AfterConnect"]
|
|
||||||
layout_mode = 2
|
|
||||||
|
|
||||||
[node name="DecrementButton" type="Button" parent="AfterConnect/Actions"]
|
|
||||||
unique_name_in_owner = true
|
|
||||||
layout_mode = 2
|
|
||||||
size_flags_horizontal = 3
|
|
||||||
text = "-"
|
|
||||||
|
|
||||||
[node name="IncrementButton" type="Button" parent="AfterConnect/Actions"]
|
|
||||||
unique_name_in_owner = true
|
|
||||||
layout_mode = 2
|
|
||||||
size_flags_horizontal = 3
|
|
||||||
text = "+"
|
|
||||||
|
|
|
||||||
|
|
@ -10,10 +10,15 @@ signal rps_move(move: String)
|
||||||
@export var energy_label: Label
|
@export var energy_label: Label
|
||||||
|
|
||||||
var match_manager: MatchManager
|
var match_manager: MatchManager
|
||||||
|
var show_buttons: bool
|
||||||
|
var signal_connected: bool
|
||||||
|
|
||||||
func attach(match_manager: MatchManager):
|
func attach(match_manager: MatchManager, show_buttons: bool = true):
|
||||||
|
self.show_buttons = show_buttons
|
||||||
self.match_manager = match_manager
|
self.match_manager = match_manager
|
||||||
match_manager.state_transitioned.connect(_on_update)
|
if !signal_connected:
|
||||||
|
match_manager.state_transitioned.connect(_on_update)
|
||||||
|
signal_connected = true
|
||||||
|
|
||||||
func _on_update(transition):
|
func _on_update(transition):
|
||||||
for child in deck.get_children():
|
for child in deck.get_children():
|
||||||
|
|
@ -28,13 +33,28 @@ func _on_update(transition):
|
||||||
monster_health_label.text = "Health: " + str(monster.health)
|
monster_health_label.text = "Health: " + str(monster.health)
|
||||||
incoming_damage_label.text = "Incoming Damage: " + str(monster.health_delta)
|
incoming_damage_label.text = "Incoming Damage: " + str(monster.health_delta)
|
||||||
if match_manager.phase in [Match.Phase.SUMMON, Match.Phase.SUPPORT_1, Match.Phase.SUPPORT_2]:
|
if match_manager.phase in [Match.Phase.SUMMON, Match.Phase.SUPPORT_1, Match.Phase.SUPPORT_2]:
|
||||||
|
|
||||||
|
if (
|
||||||
|
match_manager.phase != Match.Phase.SUMMON && show_buttons
|
||||||
|
) or (
|
||||||
|
match_manager.phase == Match.Phase.SUMMON and player.monster and player.monster.health > 0 && show_buttons
|
||||||
|
):
|
||||||
|
var skip_btn = Button.new()
|
||||||
|
skip_btn.text = "Skip"
|
||||||
|
skip_btn.button_up.connect(func (): play_card.emit(null))
|
||||||
|
deck.add_child(skip_btn)
|
||||||
|
|
||||||
for card: Card in player.hand:
|
for card: Card in player.hand:
|
||||||
if match_manager.phase == Match.Phase.SUMMON and card is not MonsterCard:
|
#if match_manager.phase == Match.Phase.SUMMON and card is not MonsterCard:
|
||||||
continue
|
#continue
|
||||||
if (match_manager.phase == Match.Phase.SUPPORT_1 or match_manager.phase == Match.Phase.SUPPORT_2) and card is not SupportCard:
|
#if (match_manager.phase == Match.Phase.SUPPORT_1 or match_manager.phase == Match.Phase.SUPPORT_2) and card is not SupportCard:
|
||||||
continue
|
#continue
|
||||||
if match_manager.phase == Match.Phase.SUPPORT_1 and card.type == "red":
|
#if match_manager.phase == Match.Phase.SUPPORT_1 and card.type == "red":
|
||||||
|
#continue
|
||||||
|
|
||||||
|
if !show_buttons :
|
||||||
continue
|
continue
|
||||||
|
|
||||||
var btn = Button.new()
|
var btn = Button.new()
|
||||||
btn.text = card.id
|
btn.text = card.id
|
||||||
btn.button_up.connect(func (): play_card.emit(card))
|
btn.button_up.connect(func (): play_card.emit(card))
|
||||||
|
|
@ -44,10 +64,16 @@ func _on_update(transition):
|
||||||
card is SupportCard and match_manager.phase != Match.Phase.SUPPORT_1 and match_manager.phase != Match.Phase.SUPPORT_2
|
card is SupportCard and match_manager.phase != Match.Phase.SUPPORT_1 and match_manager.phase != Match.Phase.SUPPORT_2
|
||||||
) or (
|
) or (
|
||||||
card is SupportCard and card.type == "red" and match_manager.phase != Match.Phase.SUPPORT_2
|
card is SupportCard and card.type == "red" and match_manager.phase != Match.Phase.SUPPORT_2
|
||||||
|
) or (
|
||||||
|
card is MonsterCard and match_manager.phase == Match.Phase.SUMMON and player.monster and player.monster.health > 0
|
||||||
)
|
)
|
||||||
deck.add_child(btn)
|
deck.add_child(btn)
|
||||||
if match_manager.phase == Match.Phase.RPS:
|
if match_manager.phase == Match.Phase.RPS:
|
||||||
for move in ["rock", "paper", "scissors"]:
|
for move in ["rock", "paper", "scissors"]:
|
||||||
|
|
||||||
|
if !show_buttons:
|
||||||
|
continue
|
||||||
|
|
||||||
var btn = Button.new()
|
var btn = Button.new()
|
||||||
btn.text = move
|
btn.text = move
|
||||||
btn.button_up.connect(func (): rps_move.emit(move))
|
btn.button_up.connect(func (): rps_move.emit(move))
|
||||||
|
|
|
||||||
|
|
@ -22,3 +22,4 @@ Match="*res://tcg/match/match.gd"
|
||||||
[rendering]
|
[rendering]
|
||||||
|
|
||||||
renderer/rendering_method="mobile"
|
renderer/rendering_method="mobile"
|
||||||
|
textures/vram_compression/import_etc2_astc=true
|
||||||
|
|
|
||||||
100
server_discovery.gd
Normal file
100
server_discovery.gd
Normal file
|
|
@ -0,0 +1,100 @@
|
||||||
|
extends Node
|
||||||
|
class_name ServerDiscovery
|
||||||
|
|
||||||
|
const PORT := 26566
|
||||||
|
const PORT_RANGE := 10 # cannot listen to the same port on one device
|
||||||
|
|
||||||
|
signal server_added(id: String, ip: String, port: int)
|
||||||
|
signal server_removed(id: String, ip: String)
|
||||||
|
|
||||||
|
var server: UDPServer = null
|
||||||
|
var client: PacketPeerUDP = null
|
||||||
|
var port_offset: int
|
||||||
|
var id: String
|
||||||
|
var servers: Array[String] = []
|
||||||
|
var enabled := false
|
||||||
|
|
||||||
|
func enable_server(server_port: int):
|
||||||
|
enabled = true
|
||||||
|
var data = "%s|AVAILABLE|%d" %[id,server_port]
|
||||||
|
_broadcast_packet(data.to_utf8_buffer())
|
||||||
|
|
||||||
|
func disable_server():
|
||||||
|
enabled = false
|
||||||
|
var data = "%s|NOT_AVAILABLE" %id
|
||||||
|
_broadcast_packet(data.to_utf8_buffer())
|
||||||
|
|
||||||
|
func _ready():
|
||||||
|
id = _generate_id()
|
||||||
|
_init_server()
|
||||||
|
_init_client()
|
||||||
|
|
||||||
|
func _process(_delta):
|
||||||
|
server.poll()
|
||||||
|
while(server.is_connection_available()):
|
||||||
|
var peer = server.take_connection()
|
||||||
|
while(peer.get_available_packet_count() > 0):
|
||||||
|
var packet = peer.get_packet()
|
||||||
|
var packet_str = packet.get_string_from_utf8()
|
||||||
|
if (packet_str.begins_with(id)):
|
||||||
|
continue
|
||||||
|
|
||||||
|
var ip = peer.get_packet_ip()
|
||||||
|
var port = peer.get_packet_port()
|
||||||
|
print(id, " | Received data from ", ip, ":", port, " => ", packet_str)
|
||||||
|
|
||||||
|
var data = packet_str.split("|")
|
||||||
|
var conn_id = data[0]
|
||||||
|
var conn_detail = data[1]
|
||||||
|
var key = "%s:%s" %[ip, port]
|
||||||
|
|
||||||
|
if (conn_detail == "AVAILABLE" and key not in servers):
|
||||||
|
var conn_actual_server_port = int(data[2])
|
||||||
|
servers.append(key)
|
||||||
|
server_added.emit(conn_id, ip, conn_actual_server_port)
|
||||||
|
elif (conn_detail == "NOT_AVAILABLE" and key in servers):
|
||||||
|
servers.erase(key)
|
||||||
|
server_removed.emit(conn_id, ip)
|
||||||
|
elif (conn_detail == "DISCOVERY" and enabled):
|
||||||
|
var available_data = "%s|AVAILABLE" %id
|
||||||
|
_broadcast_packet(available_data.to_utf8_buffer())
|
||||||
|
|
||||||
|
func _exit_tree():
|
||||||
|
var data = "%s|NOT_AVAILABLE" %id
|
||||||
|
_broadcast_packet(data.to_utf8_buffer())
|
||||||
|
|
||||||
|
func _init_server():
|
||||||
|
server = UDPServer.new()
|
||||||
|
|
||||||
|
for offset in range(PORT_RANGE):
|
||||||
|
var err = server.listen(PORT + offset)
|
||||||
|
if !err:
|
||||||
|
port_offset = offset
|
||||||
|
break
|
||||||
|
|
||||||
|
print("Server ", id, " initialized on port ", PORT + port_offset)
|
||||||
|
|
||||||
|
func _init_client():
|
||||||
|
client = PacketPeerUDP.new()
|
||||||
|
client.set_broadcast_enabled(true)
|
||||||
|
|
||||||
|
var data = "%s|DISCOVERY" %id
|
||||||
|
_broadcast_packet(data.to_utf8_buffer())
|
||||||
|
|
||||||
|
func _broadcast_packet(buffer: PackedByteArray):
|
||||||
|
for offset in range(PORT_RANGE):
|
||||||
|
client.connect_to_host("255.255.255.255", PORT + offset)
|
||||||
|
client.put_packet(buffer)
|
||||||
|
|
||||||
|
func _generate_id() -> String:
|
||||||
|
var id_len = 5
|
||||||
|
var from = 'A'.unicode_at(0)
|
||||||
|
var to = 'Z'.unicode_at(0)
|
||||||
|
|
||||||
|
var result:= ""
|
||||||
|
|
||||||
|
for i in range(id_len):
|
||||||
|
var rand_char = char(randi_range(from, to))
|
||||||
|
result += rand_char
|
||||||
|
|
||||||
|
return result
|
||||||
|
|
@ -1,6 +1,10 @@
|
||||||
extends Resource
|
extends Resource
|
||||||
class_name Card
|
class_name Card
|
||||||
|
|
||||||
|
@export var name: String
|
||||||
|
@export var description: String
|
||||||
|
@export var icon: Texture2D
|
||||||
|
|
||||||
var id: String:
|
var id: String:
|
||||||
get:
|
get:
|
||||||
return resource_path.rsplit(".", true, 1)[0].rsplit("/", true, 1)[1]
|
return resource_path.rsplit(".", true, 1)[0].rsplit("/", true, 1)[1]
|
||||||
|
|
|
||||||
2
tcg/match/action/action_skip_card.gd
Normal file
2
tcg/match/action/action_skip_card.gd
Normal file
|
|
@ -0,0 +1,2 @@
|
||||||
|
extends Action
|
||||||
|
class_name ActionSkipCard
|
||||||
|
|
@ -29,6 +29,14 @@ func init(decks: Dictionary):
|
||||||
cleanup()
|
cleanup()
|
||||||
for player_id in [PLAYER_1_ID, PLAYER_2_ID]:
|
for player_id in [PLAYER_1_ID, PLAYER_2_ID]:
|
||||||
var deck_shuffled = decks[player_id].duplicate() as Array[Card]
|
var deck_shuffled = decks[player_id].duplicate() as Array[Card]
|
||||||
|
|
||||||
|
var first_monster = deck_shuffled.filter(func (card): return card is MonsterCard)[0]
|
||||||
|
var first_monster_idx = deck_shuffled.find(first_monster)
|
||||||
|
deck_shuffled.pop_at(first_monster_idx)
|
||||||
|
var zero_idx_card = deck_shuffled.pop_at(0)
|
||||||
|
deck_shuffled.insert(0, first_monster)
|
||||||
|
deck_shuffled.insert(first_monster_idx, zero_idx_card)
|
||||||
|
|
||||||
deck_shuffled.shuffle()
|
deck_shuffled.shuffle()
|
||||||
players[player_id] = MatchPlayer.new(player_id, deck_shuffled)
|
players[player_id] = MatchPlayer.new(player_id, deck_shuffled)
|
||||||
|
|
||||||
|
|
@ -75,11 +83,13 @@ func resolve(action_by_player_id: Dictionary) -> PhaseTransition:
|
||||||
"player": player_1,
|
"player": player_1,
|
||||||
"card": player_1_action.card
|
"card": player_1_action.card
|
||||||
})
|
})
|
||||||
|
player_1.hand.erase(player_1_action.card)
|
||||||
if player_2_action is ActionPlayCard:
|
if player_2_action is ActionPlayCard:
|
||||||
support_cards.append({
|
support_cards.append({
|
||||||
"player": player_2,
|
"player": player_2,
|
||||||
"card": player_2_action.card
|
"card": player_2_action.card
|
||||||
})
|
})
|
||||||
|
player_2.hand.erase(player_2_action.card)
|
||||||
support_cards.sort_custom(func(a, b): return a.card.priority < b.card.priority)
|
support_cards.sort_custom(func(a, b): return a.card.priority < b.card.priority)
|
||||||
for played_card in support_cards:
|
for played_card in support_cards:
|
||||||
var player: MatchPlayer = played_card.player
|
var player: MatchPlayer = played_card.player
|
||||||
|
|
@ -102,11 +112,13 @@ func resolve(action_by_player_id: Dictionary) -> PhaseTransition:
|
||||||
"player": player_1,
|
"player": player_1,
|
||||||
"card": player_1_action.card
|
"card": player_1_action.card
|
||||||
})
|
})
|
||||||
|
player_1.hand.erase(player_1_action.card)
|
||||||
if player_2_action is ActionPlayCard:
|
if player_2_action is ActionPlayCard:
|
||||||
support_cards.append({
|
support_cards.append({
|
||||||
"player": player_2,
|
"player": player_2,
|
||||||
"card": player_2_action.card
|
"card": player_2_action.card
|
||||||
})
|
})
|
||||||
|
player_2.hand.erase(player_2_action.card)
|
||||||
support_cards.sort_custom(func(a, b): return a.card.priority < b.card.priority)
|
support_cards.sort_custom(func(a, b): return a.card.priority < b.card.priority)
|
||||||
for played_card in support_cards:
|
for played_card in support_cards:
|
||||||
var player: MatchPlayer = played_card.player
|
var player: MatchPlayer = played_card.player
|
||||||
|
|
|
||||||
7
test_card.gd
Normal file
7
test_card.gd
Normal file
|
|
@ -0,0 +1,7 @@
|
||||||
|
extends Control
|
||||||
|
|
||||||
|
@export var card: SupportCard
|
||||||
|
|
||||||
|
func _ready() -> void:
|
||||||
|
$Green.card = card
|
||||||
|
$Red.card = card
|
||||||
28
test_card.tscn
Normal file
28
test_card.tscn
Normal file
|
|
@ -0,0 +1,28 @@
|
||||||
|
[gd_scene load_steps=5 format=3 uid="uid://dhm4v4r7he0op"]
|
||||||
|
|
||||||
|
[ext_resource type="Script" path="res://test_card.gd" id="1_tqmas"]
|
||||||
|
[ext_resource type="PackedScene" uid="uid://dg5amjm1gqi06" path="res://ui/card_template/support_card_green.tscn" id="2_22pto"]
|
||||||
|
[ext_resource type="Resource" uid="uid://4eod3m0vc5a8" path="res://data/cards/support/potion.tres" id="2_tbbjy"]
|
||||||
|
[ext_resource type="PackedScene" uid="uid://cds50kwwhlgam" path="res://ui/card_template/support_card_red.tscn" id="3_7wd2e"]
|
||||||
|
|
||||||
|
[node name="TestCard" type="Control"]
|
||||||
|
layout_mode = 3
|
||||||
|
anchors_preset = 15
|
||||||
|
anchor_right = 1.0
|
||||||
|
anchor_bottom = 1.0
|
||||||
|
grow_horizontal = 2
|
||||||
|
grow_vertical = 2
|
||||||
|
script = ExtResource("1_tqmas")
|
||||||
|
card = ExtResource("2_tbbjy")
|
||||||
|
|
||||||
|
[node name="Green" parent="." instance=ExtResource("2_22pto")]
|
||||||
|
offset_left = 225.0
|
||||||
|
offset_top = 165.0
|
||||||
|
offset_right = 445.0
|
||||||
|
offset_bottom = 485.0
|
||||||
|
|
||||||
|
[node name="Red" parent="." instance=ExtResource("3_7wd2e")]
|
||||||
|
offset_left = 699.0
|
||||||
|
offset_top = 168.0
|
||||||
|
offset_right = 919.0
|
||||||
|
offset_bottom = 488.0
|
||||||
20
ui/card_template/card_base.gd
Normal file
20
ui/card_template/card_base.gd
Normal file
|
|
@ -0,0 +1,20 @@
|
||||||
|
extends Control
|
||||||
|
|
||||||
|
@export var card_name_label: Label
|
||||||
|
@export var card_desc_label: Label
|
||||||
|
@export var icon_rect: TextureRect
|
||||||
|
|
||||||
|
var _card: SupportCard
|
||||||
|
var card: SupportCard:
|
||||||
|
get:
|
||||||
|
return _card
|
||||||
|
set(value):
|
||||||
|
_update(value)
|
||||||
|
_card = value
|
||||||
|
|
||||||
|
func _update(card: SupportCard):
|
||||||
|
card_name_label.text = card.name
|
||||||
|
card_desc_label.text = card.description
|
||||||
|
icon_rect.texture = card.icon
|
||||||
|
|
||||||
|
|
||||||
9
ui/card_template/monster_card.tscn
Normal file
9
ui/card_template/monster_card.tscn
Normal file
|
|
@ -0,0 +1,9 @@
|
||||||
|
[gd_scene format=3 uid="uid://bhrelvt51cbp2"]
|
||||||
|
|
||||||
|
[node name="MonsterCard" type="Control"]
|
||||||
|
layout_mode = 3
|
||||||
|
anchors_preset = 15
|
||||||
|
anchor_right = 1.0
|
||||||
|
anchor_bottom = 1.0
|
||||||
|
grow_horizontal = 2
|
||||||
|
grow_vertical = 2
|
||||||
165
ui/card_template/support_card_green.tscn
Normal file
165
ui/card_template/support_card_green.tscn
Normal file
|
|
@ -0,0 +1,165 @@
|
||||||
|
[gd_scene load_steps=11 format=3 uid="uid://dg5amjm1gqi06"]
|
||||||
|
|
||||||
|
[ext_resource type="Texture2D" uid="uid://l2nxxhh0pvh8" path="res://assets/card_base/Frame.png" id="1_4ivbl"]
|
||||||
|
[ext_resource type="Script" path="res://ui/card_template/card_base.gd" id="1_rpopv"]
|
||||||
|
[ext_resource type="Texture2D" uid="uid://liitr32ap646" path="res://assets/card_base/G-OuterFill.png" id="2_c6lcl"]
|
||||||
|
[ext_resource type="Texture2D" uid="uid://crgrple0uik7x" path="res://assets/card_base/Stroke.png" id="3_qajq3"]
|
||||||
|
[ext_resource type="Texture2D" uid="uid://blejyda8mendg" path="res://assets/card_base/InnerFill.png" id="4_pgomu"]
|
||||||
|
[ext_resource type="Texture2D" uid="uid://by7ws88pn4tvb" path="res://assets/card_base/Separator.png" id="5_501uu"]
|
||||||
|
[ext_resource type="Texture2D" uid="uid://0gxplli5krq2" path="res://assets/card_base/Pill.png" id="6_ce7hm"]
|
||||||
|
[ext_resource type="Theme" uid="uid://cj3vs5hq2mcbp" path="res://cards.tres" id="7_va1d7"]
|
||||||
|
[ext_resource type="Texture2D" uid="uid://rh3aswb0p7ri" path="res://assets/energy.png" id="8_4yq42"]
|
||||||
|
[ext_resource type="FontFile" uid="uid://08q3kkwmd4u6" path="res://assets/Inter-Regular.otf" id="10_c2ugn"]
|
||||||
|
|
||||||
|
[node name="CardBase" type="Control" node_paths=PackedStringArray("card_name_label", "card_desc_label", "icon_rect")]
|
||||||
|
layout_mode = 3
|
||||||
|
anchors_preset = 0
|
||||||
|
offset_right = 220.0
|
||||||
|
offset_bottom = 320.0
|
||||||
|
script = ExtResource("1_rpopv")
|
||||||
|
card_name_label = NodePath("MarginContainer/Label")
|
||||||
|
card_desc_label = NodePath("MarginContainer/DescriptionLabel")
|
||||||
|
icon_rect = NodePath("MarginContainer/Icon")
|
||||||
|
|
||||||
|
[node name="Frame" type="TextureRect" parent="."]
|
||||||
|
layout_mode = 1
|
||||||
|
anchors_preset = 15
|
||||||
|
anchor_right = 1.0
|
||||||
|
anchor_bottom = 1.0
|
||||||
|
grow_horizontal = 2
|
||||||
|
grow_vertical = 2
|
||||||
|
texture = ExtResource("1_4ivbl")
|
||||||
|
expand_mode = 1
|
||||||
|
|
||||||
|
[node name="MarginContainer" type="Control" parent="."]
|
||||||
|
layout_mode = 1
|
||||||
|
anchors_preset = 15
|
||||||
|
anchor_right = 1.0
|
||||||
|
anchor_bottom = 1.0
|
||||||
|
offset_left = 4.0
|
||||||
|
offset_top = 3.0
|
||||||
|
offset_right = -5.0
|
||||||
|
offset_bottom = -4.0
|
||||||
|
grow_horizontal = 2
|
||||||
|
grow_vertical = 2
|
||||||
|
|
||||||
|
[node name="TextureRect" type="TextureRect" parent="MarginContainer"]
|
||||||
|
layout_mode = 1
|
||||||
|
anchors_preset = 15
|
||||||
|
anchor_right = 1.0
|
||||||
|
anchor_bottom = 1.0
|
||||||
|
grow_horizontal = 2
|
||||||
|
grow_vertical = 2
|
||||||
|
texture = ExtResource("2_c6lcl")
|
||||||
|
expand_mode = 1
|
||||||
|
|
||||||
|
[node name="OuterStroke" type="NinePatchRect" parent="MarginContainer"]
|
||||||
|
layout_mode = 1
|
||||||
|
anchors_preset = 15
|
||||||
|
anchor_right = 1.0
|
||||||
|
anchor_bottom = 1.0
|
||||||
|
grow_horizontal = 2
|
||||||
|
grow_vertical = 2
|
||||||
|
texture = ExtResource("3_qajq3")
|
||||||
|
|
||||||
|
[node name="TextureRect2" type="TextureRect" parent="MarginContainer"]
|
||||||
|
layout_mode = 1
|
||||||
|
anchors_preset = 15
|
||||||
|
anchor_right = 1.0
|
||||||
|
anchor_bottom = 1.0
|
||||||
|
offset_top = 62.0
|
||||||
|
grow_horizontal = 2
|
||||||
|
grow_vertical = 2
|
||||||
|
texture = ExtResource("4_pgomu")
|
||||||
|
expand_mode = 1
|
||||||
|
|
||||||
|
[node name="InnerStroke" type="NinePatchRect" parent="MarginContainer"]
|
||||||
|
layout_mode = 1
|
||||||
|
anchors_preset = 15
|
||||||
|
anchor_right = 1.0
|
||||||
|
anchor_bottom = 1.0
|
||||||
|
offset_top = 62.0
|
||||||
|
grow_horizontal = 2
|
||||||
|
grow_vertical = 2
|
||||||
|
texture = ExtResource("3_qajq3")
|
||||||
|
|
||||||
|
[node name="TextureRect3" type="TextureRect" parent="MarginContainer"]
|
||||||
|
layout_mode = 1
|
||||||
|
anchors_preset = -1
|
||||||
|
anchor_left = 0.01
|
||||||
|
anchor_top = 1.0
|
||||||
|
anchor_right = 1.0
|
||||||
|
anchor_bottom = 1.0
|
||||||
|
offset_left = -0.0100002
|
||||||
|
offset_top = -112.0
|
||||||
|
offset_right = -1.0
|
||||||
|
offset_bottom = -110.0
|
||||||
|
grow_horizontal = 2
|
||||||
|
grow_vertical = 2
|
||||||
|
texture = ExtResource("5_501uu")
|
||||||
|
expand_mode = 1
|
||||||
|
metadata/_edit_use_anchors_ = true
|
||||||
|
|
||||||
|
[node name="TextureRect4" type="NinePatchRect" parent="MarginContainer"]
|
||||||
|
modulate = Color(0.356863, 0.54902, 0.243137, 1)
|
||||||
|
layout_mode = 1
|
||||||
|
anchors_preset = 8
|
||||||
|
anchor_left = 0.5
|
||||||
|
anchor_top = 0.5
|
||||||
|
anchor_right = 0.5
|
||||||
|
anchor_bottom = 0.5
|
||||||
|
offset_left = 4.5
|
||||||
|
offset_top = 30.5
|
||||||
|
offset_right = 90.5
|
||||||
|
offset_bottom = 60.5
|
||||||
|
grow_horizontal = 2
|
||||||
|
grow_vertical = 2
|
||||||
|
texture = ExtResource("6_ce7hm")
|
||||||
|
|
||||||
|
[node name="Label" type="Label" parent="MarginContainer"]
|
||||||
|
layout_mode = 1
|
||||||
|
anchors_preset = 10
|
||||||
|
anchor_right = 1.0
|
||||||
|
offset_left = 2.0
|
||||||
|
offset_top = 16.0
|
||||||
|
offset_right = -3.0
|
||||||
|
offset_bottom = 50.0
|
||||||
|
grow_horizontal = 2
|
||||||
|
theme = ExtResource("7_va1d7")
|
||||||
|
theme_override_colors/font_color = Color(0.576471, 0.788235, 0.819608, 1)
|
||||||
|
theme_override_font_sizes/font_size = 24
|
||||||
|
text = "green card"
|
||||||
|
horizontal_alignment = 1
|
||||||
|
vertical_alignment = 1
|
||||||
|
|
||||||
|
[node name="Label2" type="Label" parent="MarginContainer"]
|
||||||
|
layout_mode = 0
|
||||||
|
offset_left = 118.0
|
||||||
|
offset_top = 190.0
|
||||||
|
offset_right = 188.0
|
||||||
|
offset_bottom = 213.0
|
||||||
|
theme = ExtResource("7_va1d7")
|
||||||
|
text = "Green card"
|
||||||
|
horizontal_alignment = 1
|
||||||
|
vertical_alignment = 1
|
||||||
|
|
||||||
|
[node name="Icon" type="TextureRect" parent="MarginContainer"]
|
||||||
|
offset_left = 26.0
|
||||||
|
offset_top = 74.0
|
||||||
|
offset_right = 169.0
|
||||||
|
offset_bottom = 179.0
|
||||||
|
texture = ExtResource("8_4yq42")
|
||||||
|
expand_mode = 1
|
||||||
|
stretch_mode = 6
|
||||||
|
|
||||||
|
[node name="DescriptionLabel" type="Label" parent="MarginContainer"]
|
||||||
|
offset_left = 11.0
|
||||||
|
offset_top = 224.0
|
||||||
|
offset_right = 200.0
|
||||||
|
offset_bottom = 302.0
|
||||||
|
theme = ExtResource("7_va1d7")
|
||||||
|
theme_override_fonts/font = ExtResource("10_c2ugn")
|
||||||
|
theme_override_font_sizes/font_size = 12
|
||||||
|
text = "If your monster is supposed to be dead, keep it alive at 10 HP"
|
||||||
|
horizontal_alignment = 1
|
||||||
|
autowrap_mode = 3
|
||||||
167
ui/card_template/support_card_red.tscn
Normal file
167
ui/card_template/support_card_red.tscn
Normal file
|
|
@ -0,0 +1,167 @@
|
||||||
|
[gd_scene load_steps=11 format=3 uid="uid://cds50kwwhlgam"]
|
||||||
|
|
||||||
|
[ext_resource type="Script" path="res://ui/card_template/card_base.gd" id="1_d22a5"]
|
||||||
|
[ext_resource type="Texture2D" uid="uid://l2nxxhh0pvh8" path="res://assets/card_base/Frame.png" id="1_x5ex0"]
|
||||||
|
[ext_resource type="Texture2D" uid="uid://ip7xjs20pd3d" path="res://assets/card_base/R-OuterFill.png" id="2_xjg8y"]
|
||||||
|
[ext_resource type="Texture2D" uid="uid://crgrple0uik7x" path="res://assets/card_base/Stroke.png" id="3_q71h0"]
|
||||||
|
[ext_resource type="Texture2D" uid="uid://blejyda8mendg" path="res://assets/card_base/InnerFill.png" id="4_2fw8n"]
|
||||||
|
[ext_resource type="Texture2D" uid="uid://by7ws88pn4tvb" path="res://assets/card_base/Separator.png" id="5_n3v14"]
|
||||||
|
[ext_resource type="Texture2D" uid="uid://0gxplli5krq2" path="res://assets/card_base/Pill.png" id="6_wrd2a"]
|
||||||
|
[ext_resource type="Theme" uid="uid://cj3vs5hq2mcbp" path="res://cards.tres" id="7_fp6ys"]
|
||||||
|
[ext_resource type="FontFile" uid="uid://08q3kkwmd4u6" path="res://assets/Inter-Regular.otf" id="9_vilw6"]
|
||||||
|
[ext_resource type="Texture2D" uid="uid://rh3aswb0p7ri" path="res://assets/energy.png" id="10_2t0ey"]
|
||||||
|
|
||||||
|
[node name="CardBase" type="Control" node_paths=PackedStringArray("card_name_label", "card_desc_label", "icon_rect")]
|
||||||
|
layout_mode = 3
|
||||||
|
anchors_preset = 0
|
||||||
|
offset_right = 220.0
|
||||||
|
offset_bottom = 320.0
|
||||||
|
script = ExtResource("1_d22a5")
|
||||||
|
card_name_label = NodePath("MarginContainer/Title")
|
||||||
|
card_desc_label = NodePath("MarginContainer/DescriptionLabel")
|
||||||
|
icon_rect = NodePath("MarginContainer/Icon")
|
||||||
|
|
||||||
|
[node name="Frame" type="TextureRect" parent="."]
|
||||||
|
layout_mode = 1
|
||||||
|
anchors_preset = 15
|
||||||
|
anchor_right = 1.0
|
||||||
|
anchor_bottom = 1.0
|
||||||
|
grow_horizontal = 2
|
||||||
|
grow_vertical = 2
|
||||||
|
texture = ExtResource("1_x5ex0")
|
||||||
|
expand_mode = 1
|
||||||
|
|
||||||
|
[node name="MarginContainer" type="Control" parent="."]
|
||||||
|
layout_mode = 1
|
||||||
|
anchors_preset = 15
|
||||||
|
anchor_right = 1.0
|
||||||
|
anchor_bottom = 1.0
|
||||||
|
offset_left = 4.0
|
||||||
|
offset_top = 3.0
|
||||||
|
offset_right = -5.0
|
||||||
|
offset_bottom = -4.0
|
||||||
|
grow_horizontal = 2
|
||||||
|
grow_vertical = 2
|
||||||
|
|
||||||
|
[node name="TextureRect" type="TextureRect" parent="MarginContainer"]
|
||||||
|
layout_mode = 1
|
||||||
|
anchors_preset = 15
|
||||||
|
anchor_right = 1.0
|
||||||
|
anchor_bottom = 1.0
|
||||||
|
grow_horizontal = 2
|
||||||
|
grow_vertical = 2
|
||||||
|
texture = ExtResource("2_xjg8y")
|
||||||
|
expand_mode = 1
|
||||||
|
|
||||||
|
[node name="OuterStroke" type="NinePatchRect" parent="MarginContainer"]
|
||||||
|
layout_mode = 1
|
||||||
|
anchors_preset = 15
|
||||||
|
anchor_right = 1.0
|
||||||
|
anchor_bottom = 1.0
|
||||||
|
grow_horizontal = 2
|
||||||
|
grow_vertical = 2
|
||||||
|
texture = ExtResource("3_q71h0")
|
||||||
|
|
||||||
|
[node name="TextureRect2" type="TextureRect" parent="MarginContainer"]
|
||||||
|
layout_mode = 1
|
||||||
|
anchors_preset = 15
|
||||||
|
anchor_right = 1.0
|
||||||
|
anchor_bottom = 1.0
|
||||||
|
offset_top = 62.0
|
||||||
|
grow_horizontal = 2
|
||||||
|
grow_vertical = 2
|
||||||
|
texture = ExtResource("4_2fw8n")
|
||||||
|
expand_mode = 1
|
||||||
|
|
||||||
|
[node name="InnerStroke" type="NinePatchRect" parent="MarginContainer"]
|
||||||
|
layout_mode = 1
|
||||||
|
anchors_preset = 15
|
||||||
|
anchor_right = 1.0
|
||||||
|
anchor_bottom = 1.0
|
||||||
|
offset_top = 62.0
|
||||||
|
grow_horizontal = 2
|
||||||
|
grow_vertical = 2
|
||||||
|
texture = ExtResource("3_q71h0")
|
||||||
|
|
||||||
|
[node name="TextureRect3" type="TextureRect" parent="MarginContainer"]
|
||||||
|
layout_mode = 1
|
||||||
|
anchors_preset = -1
|
||||||
|
anchor_left = 0.01
|
||||||
|
anchor_top = 1.0
|
||||||
|
anchor_right = 1.0
|
||||||
|
anchor_bottom = 1.0
|
||||||
|
offset_left = -0.0100002
|
||||||
|
offset_top = -112.0
|
||||||
|
offset_right = -1.0
|
||||||
|
offset_bottom = -110.0
|
||||||
|
grow_horizontal = 2
|
||||||
|
grow_vertical = 2
|
||||||
|
texture = ExtResource("5_n3v14")
|
||||||
|
expand_mode = 1
|
||||||
|
metadata/_edit_use_anchors_ = true
|
||||||
|
|
||||||
|
[node name="TextureRect4" type="NinePatchRect" parent="MarginContainer"]
|
||||||
|
modulate = Color(0.54902, 0.243137, 0.243137, 1)
|
||||||
|
layout_mode = 1
|
||||||
|
anchors_preset = 8
|
||||||
|
anchor_left = 0.5
|
||||||
|
anchor_top = 0.5
|
||||||
|
anchor_right = 0.5
|
||||||
|
anchor_bottom = 0.5
|
||||||
|
offset_left = 4.5
|
||||||
|
offset_top = 30.5
|
||||||
|
offset_right = 90.5
|
||||||
|
offset_bottom = 60.5
|
||||||
|
grow_horizontal = 2
|
||||||
|
grow_vertical = 2
|
||||||
|
texture = ExtResource("6_wrd2a")
|
||||||
|
|
||||||
|
[node name="Title" type="Label" parent="MarginContainer"]
|
||||||
|
layout_mode = 1
|
||||||
|
anchors_preset = 10
|
||||||
|
anchor_right = 1.0
|
||||||
|
offset_left = 2.0
|
||||||
|
offset_top = 16.0
|
||||||
|
offset_right = -3.0
|
||||||
|
offset_bottom = 50.0
|
||||||
|
grow_horizontal = 2
|
||||||
|
theme = ExtResource("7_fp6ys")
|
||||||
|
theme_override_colors/font_color = Color(0.819608, 0.576471, 0.576471, 1)
|
||||||
|
theme_override_font_sizes/font_size = 24
|
||||||
|
text = "red card"
|
||||||
|
horizontal_alignment = 1
|
||||||
|
vertical_alignment = 1
|
||||||
|
|
||||||
|
[node name="PillLabel" type="Label" parent="MarginContainer"]
|
||||||
|
layout_mode = 0
|
||||||
|
offset_left = 118.0
|
||||||
|
offset_top = 190.0
|
||||||
|
offset_right = 188.0
|
||||||
|
offset_bottom = 213.0
|
||||||
|
theme = ExtResource("7_fp6ys")
|
||||||
|
text = "Red card"
|
||||||
|
horizontal_alignment = 1
|
||||||
|
vertical_alignment = 1
|
||||||
|
|
||||||
|
[node name="DescriptionLabel" type="Label" parent="MarginContainer"]
|
||||||
|
layout_mode = 0
|
||||||
|
offset_left = 11.0
|
||||||
|
offset_top = 224.0
|
||||||
|
offset_right = 200.0
|
||||||
|
offset_bottom = 302.0
|
||||||
|
theme = ExtResource("7_fp6ys")
|
||||||
|
theme_override_fonts/font = ExtResource("9_vilw6")
|
||||||
|
theme_override_font_sizes/font_size = 12
|
||||||
|
text = "If your monster is supposed to be dead, keep it alive at 10 HP"
|
||||||
|
horizontal_alignment = 1
|
||||||
|
autowrap_mode = 3
|
||||||
|
|
||||||
|
[node name="Icon" type="TextureRect" parent="MarginContainer"]
|
||||||
|
layout_mode = 0
|
||||||
|
offset_left = 30.0
|
||||||
|
offset_top = 77.0
|
||||||
|
offset_right = 173.0
|
||||||
|
offset_bottom = 182.0
|
||||||
|
texture = ExtResource("10_2t0ey")
|
||||||
|
expand_mode = 1
|
||||||
|
stretch_mode = 6
|
||||||
Loading…
Add table
Add a link
Reference in a new issue