diff --git a/locals/Weapon.csv b/locals/Item.csv similarity index 56% rename from locals/Weapon.csv rename to locals/Item.csv index 7bfa22a..3741a2b 100644 --- a/locals/Weapon.csv +++ b/locals/Item.csv @@ -1,3 +1,5 @@ id,zh,en,ja staff_of_the_undead,死灵法杖,StaffOfTheUndead,ネクロポリスの杖です -staff_of_the_undead_desc,发射诅咒,可将敌人转化为邪恶的怪物。,Cast a curse that transforms enemies into evil monsters.,呪いを発射して、敵を邪悪な怪物に変えることができます。 \ No newline at end of file +staff_of_the_undead_desc,发射诅咒,可将敌人转化为邪恶的怪物。,Cast a curse that transforms enemies into evil monsters.,呪いを発射して、敵を邪悪な怪物に変えることができます。 +packsack,背包,Packsack,背嚢 +packsack_desc,可以装载更多物品的背包。,A backpack that can hold more items.,より多くのアイテムを保持できるバックパックです。 \ No newline at end of file diff --git a/locals/Item.csv.import b/locals/Item.csv.import new file mode 100644 index 0000000..8692290 --- /dev/null +++ b/locals/Item.csv.import @@ -0,0 +1,17 @@ +[remap] + +importer="csv_translation" +type="Translation" +uid="uid://dydilbm2stxr4" + +[deps] + +files=["res://locals/Item.zh.translation", "res://locals/Item.en.translation", "res://locals/Item.ja.translation"] + +source_file="res://locals/Item.csv" +dest_files=["res://locals/Item.zh.translation", "res://locals/Item.en.translation", "res://locals/Item.ja.translation"] + +[params] + +compress=true +delimiter=0 diff --git a/locals/Item.en.translation b/locals/Item.en.translation new file mode 100644 index 0000000..1c8ae52 Binary files /dev/null and b/locals/Item.en.translation differ diff --git a/locals/Item.ja.translation b/locals/Item.ja.translation new file mode 100644 index 0000000..27c8bbc Binary files /dev/null and b/locals/Item.ja.translation differ diff --git a/locals/Item.zh.translation b/locals/Item.zh.translation new file mode 100644 index 0000000..b775a9f Binary files /dev/null and b/locals/Item.zh.translation differ diff --git a/locals/Weapon.csv.import b/locals/Weapon.csv.import deleted file mode 100644 index 27a557f..0000000 --- a/locals/Weapon.csv.import +++ /dev/null @@ -1,17 +0,0 @@ -[remap] - -importer="csv_translation" -type="Translation" -uid="uid://ci3wou75hhj6e" - -[deps] - -files=["res://locals/Weapon.zh.translation", "res://locals/Weapon.en.translation", "res://locals/Weapon.ja.translation"] - -source_file="res://locals/Weapon.csv" -dest_files=["res://locals/Weapon.zh.translation", "res://locals/Weapon.en.translation", "res://locals/Weapon.ja.translation"] - -[params] - -compress=true -delimiter=0 diff --git a/locals/Weapon.en.translation b/locals/Weapon.en.translation deleted file mode 100644 index 46fb4a6..0000000 Binary files a/locals/Weapon.en.translation and /dev/null differ diff --git a/locals/Weapon.ja.translation b/locals/Weapon.ja.translation deleted file mode 100644 index 054a56e..0000000 Binary files a/locals/Weapon.ja.translation and /dev/null differ diff --git a/locals/Weapon.zh.translation b/locals/Weapon.zh.translation deleted file mode 100644 index cff4f66..0000000 Binary files a/locals/Weapon.zh.translation and /dev/null differ diff --git a/prefab/packsacks/packsack.tscn b/prefab/packsacks/packsack.tscn new file mode 100644 index 0000000..3599009 --- /dev/null +++ b/prefab/packsacks/packsack.tscn @@ -0,0 +1,24 @@ +[gd_scene load_steps=4 format=3 uid="uid://cn10fimoem04m"] + +[ext_resource type="Script" path="res://scripts/inventory/Packsack.cs" id="1_8ehup"] +[ext_resource type="Texture2D" uid="uid://b1twcink38sh0" path="res://sprites/Player.png" id="2_e1ale"] + +[sub_resource type="RectangleShape2D" id="RectangleShape2D_xqyue"] +size = Vector2(41, 57) + +[node name="RigidBody2D" type="RigidBody2D"] +collision_layer = 8 +collision_mask = 38 +script = ExtResource("1_8ehup") +metadata/Id = "Packsack" +metadata/MaxStackQuantity = 1 +metadata/Icon = ExtResource("2_e1ale") +metadata/Name = "packsack" +metadata/Description = "packsack_desc" + +[node name="Player" type="Sprite2D" parent="."] +texture = ExtResource("2_e1ale") + +[node name="CollisionShape2D" type="CollisionShape2D" parent="."] +position = Vector2(-0.5, 3.5) +shape = SubResource("RectangleShape2D_xqyue") diff --git a/project.godot b/project.godot index 74595e4..0fcb4f3 100644 --- a/project.godot +++ b/project.godot @@ -146,7 +146,7 @@ hotbar_previous={ [internationalization] -locale/translations=PackedStringArray("res://locals/DeathInfo.en.translation", "res://locals/DeathInfo.ja.translation", "res://locals/DeathInfo.zh.translation", "res://locals/InputMapping.en.translation", "res://locals/InputMapping.ja.translation", "res://locals/InputMapping.zh.translation", "res://locals/Log.en.translation", "res://locals/Log.ja.translation", "res://locals/Log.zh.translation", "res://locals/Slogan.en.translation", "res://locals/Slogan.ja.translation", "res://locals/Slogan.zh.translation", "res://locals/UI.en.translation", "res://locals/UI.ja.translation", "res://locals/UI.zh.translation", "res://locals/Weapon.en.translation", "res://locals/Weapon.ja.translation", "res://locals/Weapon.zh.translation") +locale/translations=PackedStringArray("res://locals/DeathInfo.en.translation", "res://locals/DeathInfo.ja.translation", "res://locals/DeathInfo.zh.translation", "res://locals/InputMapping.en.translation", "res://locals/InputMapping.ja.translation", "res://locals/InputMapping.zh.translation", "res://locals/Log.en.translation", "res://locals/Log.ja.translation", "res://locals/Log.zh.translation", "res://locals/Slogan.en.translation", "res://locals/Slogan.ja.translation", "res://locals/Slogan.zh.translation", "res://locals/UI.en.translation", "res://locals/UI.ja.translation", "res://locals/UI.zh.translation", "res://locals/Item.en.translation", "res://locals/Item.ja.translation", "res://locals/Item.zh.translation") [layer_names] diff --git a/scenes/game.tscn b/scenes/game.tscn index 36421ee..b07ed07 100644 --- a/scenes/game.tscn +++ b/scenes/game.tscn @@ -96,3 +96,5 @@ visible = false [node name="PlayerContainer" type="Node2D" parent="."] [node name="AICharacterContainer" type="Node2D" parent="."] + +[node name="PacksackContainer" type="Node2D" parent="."] diff --git a/scripts/EventManager.cs b/scripts/EventManager.cs index 6f68d25..ab2d847 100644 --- a/scripts/EventManager.cs +++ b/scripts/EventManager.cs @@ -38,4 +38,10 @@ public static class EventManager /// 地图生成完成事件 /// public static Action? MapGenerationCompleteEvent; + + /// + /// Player Instance Change Event + /// 玩家实例改变事件 + /// + public static Action? PlayerInstanceChangeEvent; } \ No newline at end of file diff --git a/scripts/GameSceneNodeHolder.cs b/scripts/GameSceneNodeHolder.cs index 762cf8a..30bf59b 100644 --- a/scripts/GameSceneNodeHolder.cs +++ b/scripts/GameSceneNodeHolder.cs @@ -1,5 +1,6 @@ using ColdMint.scripts.character; using ColdMint.scripts.inventory; +using ColdMint.scripts.map.events; using Godot; namespace ColdMint.scripts; @@ -10,30 +11,52 @@ namespace ColdMint.scripts; /// public static class GameSceneNodeHolder { + private static Player? _player; + /// /// Player instances within the game scene /// 游戏场景内的玩家实例 /// - public static Player? Player { get; set; } + public static Player? Player + { + get => _player; + set + { + _player = value; + //Broadcast the event to the outside when the player instance changes. + //当玩家实例改变时,向外广播事件。 + var playerInstanceChangeEvent = new PlayerInstanceChangeEvent + { + PlayerInstance = _player + }; + EventManager.PlayerInstanceChangeEvent?.Invoke(playerInstanceChangeEvent); + } + } /// /// WeaponContainer /// 武器容器 /// public static Node2D? WeaponContainer { get; set; } - + + /// + /// PacksackContainer + /// 背包容器 + /// + public static Node2D? PacksackContainer { get; set; } + /// /// PlayerContainer /// 玩家容器 /// public static Node2D? PlayerContainer { get; set; } - + /// /// AICharacterContainer /// AICharacter角色 /// public static Node2D? AiCharacterContainer { get; set; } - + /// /// HotBar /// 快捷栏 @@ -46,7 +69,7 @@ public static class GameSceneNodeHolder /// 健康条UI /// public static HealthBarUi? HealthBarUi { get; set; } - + /// /// operation tip /// 操作提示 diff --git a/scripts/character/CharacterTemplate.cs b/scripts/character/CharacterTemplate.cs index b1930d4..f8b6891 100644 --- a/scripts/character/CharacterTemplate.cs +++ b/scripts/character/CharacterTemplate.cs @@ -662,6 +662,7 @@ public partial class CharacterTemplate : CharacterBody2D return; } + CallDeferred("NodeReparent", node2D); switch (item) { case WeaponTemplate weaponTemplate: @@ -671,7 +672,6 @@ public partial class CharacterTemplate : CharacterBody2D } weaponTemplate.Picked = false; - CallDeferred("WeaponTemplateReparent", weaponTemplate); var timer = new Timer(); weaponTemplate.AddChild(timer); timer.WaitTime = _itemCollisionRecoveryTime; @@ -720,13 +720,13 @@ public partial class CharacterTemplate : CharacterBody2D } /// - /// Replace the parent node of the weapon - /// 替换武器的父节点 + /// Replace the parent node of a node + /// 替换节点的父节点 /// - /// - private void WeaponTemplateReparent(WeaponTemplate weaponTemplate) + /// + private void NodeReparent(Node node) { - weaponTemplate.Reparent(GameSceneNodeHolder.WeaponContainer); + node.Reparent(NodeUtils.FindContainerNode(node, GetNode("/root"))); } public sealed override void _PhysicsProcess(double delta) diff --git a/scripts/character/Player.cs b/scripts/character/Player.cs index d851733..ff084d4 100644 --- a/scripts/character/Player.cs +++ b/scripts/character/Player.cs @@ -3,6 +3,8 @@ using System.Text; using System.Threading.Tasks; using ColdMint.scripts.damage; using ColdMint.scripts.deathInfo; +using ColdMint.scripts.debug; +using ColdMint.scripts.inventory; using ColdMint.scripts.map.events; using ColdMint.scripts.utils; using ColdMint.scripts.weapon; @@ -130,10 +132,9 @@ public partial class Player : CharacterTemplate operationTipBuilder.Append(TranslationServerUtils.Translate(InputMap.ActionGetEvents("throw")[0].AsText())); operationTipBuilder.Append("[/color]"); operationTipBuilder.Append(TranslationServerUtils.Translate("throw")); - if (CurrentItem is WeaponTemplate weaponTemplate) + if (CurrentItem is IItem item) { - operationTipBuilder.Append(TranslationServerUtils.Translate(weaponTemplate.Name)); - //提示武器攻击 + operationTipBuilder.Append(TranslationServerUtils.Translate(item.Name)); operationTipBuilder.Append(' '); operationTipBuilder.Append("[color="); operationTipBuilder.Append(Config.OperationTipActionColor); @@ -142,7 +143,7 @@ public partial class Player : CharacterTemplate TranslationServerUtils.Translate(InputMap.ActionGetEvents("use_item")[0].AsText())); operationTipBuilder.Append("[/color]"); operationTipBuilder.Append(TranslationServerUtils.Translate("use_item")); - operationTipBuilder.Append(TranslationServerUtils.Translate(weaponTemplate.Name)); + operationTipBuilder.Append(TranslationServerUtils.Translate(item.Name)); } } diff --git a/scripts/inventory/HotBar.cs b/scripts/inventory/HotBar.cs index 08c4315..0cc99dd 100644 --- a/scripts/inventory/HotBar.cs +++ b/scripts/inventory/HotBar.cs @@ -1,4 +1,4 @@ -using ColdMint.scripts.character; +using ColdMint.scripts.map.events; using ColdMint.scripts.utils; using Godot; @@ -10,19 +10,31 @@ namespace ColdMint.scripts.inventory; /// public partial class HotBar : HBoxContainer { - private UniversalItemContainer? _universalItemContainer; + private IItemContainer? _itemContainer; public override void _Ready() { base._Ready(); - _universalItemContainer = new UniversalItemContainer - { - CharacterTemplate = new Player() - }; + _itemContainer = new UniversalItemContainer(); + EventManager.PlayerInstanceChangeEvent += PlayerInstanceChangeEvent; NodeUtils.DeleteAllChild(this); for (var i = 0; i < Config.HotBarSize; i++) { - _universalItemContainer.AddItemSlot(this, i); + _itemContainer.AddItemSlot(this, i); + } + } + + + /// + /// When the player instance changes, we update the binding of the item container + /// 当玩家实例改变时,我们更新物品容器的绑定 + /// + /// + private void PlayerInstanceChangeEvent(PlayerInstanceChangeEvent playerInstanceChangeEvent) + { + if (_itemContainer is UniversalItemContainer universalItemContainer) + { + universalItemContainer.CharacterTemplate = GameSceneNodeHolder.Player; } } @@ -33,14 +45,14 @@ public partial class HotBar : HBoxContainer { //Mouse wheel down //鼠标滚轮向下 - _universalItemContainer?.SelectTheNextItemSlot(); + _itemContainer?.SelectTheNextItemSlot(); } if (Input.IsActionJustPressed("hotbar_previous")) { //Mouse wheel up //鼠标滚轮向上 - _universalItemContainer?.SelectThePreviousItemSlot(); + _itemContainer?.SelectThePreviousItemSlot(); } if (Input.IsActionJustPressed("hotbar_1")) @@ -98,15 +110,22 @@ public partial class HotBar : HBoxContainer /// private void SelectItemSlotByHotBarShortcutKey(int shortcutKeyIndex) { - if (_universalItemContainer == null) + if (_itemContainer == null) { return; } - _universalItemContainer.SelectItemSlot(shortcutKeyIndex); + + _itemContainer.SelectItemSlot(shortcutKeyIndex); } public IItemContainer? GetItemContainer() { - return _universalItemContainer; + return _itemContainer; + } + + public override void _ExitTree() + { + base._ExitTree(); + EventManager.PlayerInstanceChangeEvent -= PlayerInstanceChangeEvent; } } \ No newline at end of file diff --git a/scripts/inventory/Packsack.cs b/scripts/inventory/Packsack.cs new file mode 100644 index 0000000..31dcbc8 --- /dev/null +++ b/scripts/inventory/Packsack.cs @@ -0,0 +1,40 @@ +using System; +using ColdMint.scripts.debug; +using Godot; + +namespace ColdMint.scripts.inventory; + +/// +/// packsack +/// 背包 +/// +public partial class Packsack : RigidBody2D, IItem +{ + public string? Id { get; set; } + public int Quantity { get; set; } + public int MaxStackQuantity { get; set; } + public Texture2D? Icon { get; set; } + public new string? Name { get; set; } + public string? Description { get; set; } + public Action? OnUse { get; set; } + public Func? OnInstantiation { get; set; } + + private IItemContainer? _itemContainer; + + public override void _Ready() + { + base._Ready(); + Id = GetMeta("ID", "1").AsString(); + Quantity = GetMeta("Quantity", "1").AsInt32(); + MaxStackQuantity = GetMeta("MaxStackQuantity", Config.MaxStackQuantity).AsInt32(); + Icon = GetMeta("Icon", "").As(); + Name = GetMeta("Name", "").AsString(); + Description = GetMeta("Description", "").AsString(); + _itemContainer = new UniversalItemContainer(); + } + + public IItemContainer? GetItemContainer() + { + return _itemContainer; + } +} \ No newline at end of file diff --git a/scripts/inventory/UniversalItemContainer.cs b/scripts/inventory/UniversalItemContainer.cs index 538b695..3fe6594 100644 --- a/scripts/inventory/UniversalItemContainer.cs +++ b/scripts/inventory/UniversalItemContainer.cs @@ -1,5 +1,6 @@ using System.Collections.Generic; using ColdMint.scripts.character; +using ColdMint.scripts.debug; using ColdMint.scripts.utils; using Godot; diff --git a/scripts/loader/sceneLoader/GameSceneLoader.cs b/scripts/loader/sceneLoader/GameSceneLoader.cs index eb550eb..dd290f2 100644 --- a/scripts/loader/sceneLoader/GameSceneLoader.cs +++ b/scripts/loader/sceneLoader/GameSceneLoader.cs @@ -35,6 +35,10 @@ public partial class GameSceneLoader : SceneLoaderTemplate //加载武器容器 var weaponContainer = GetNode("WeaponContainer"); GameSceneNodeHolder.WeaponContainer = weaponContainer; + //Load Packsack container + //加载背包容器 + var packsackContainer = GetNode("PacksackContainer"); + GameSceneNodeHolder.PacksackContainer = packsackContainer; //Load AICharacter container //加载AICharacter容器 var aiCharacterContainer = GetNode("AICharacterContainer"); diff --git a/scripts/loader/uiLoader/MainMenuLoader.cs b/scripts/loader/uiLoader/MainMenuLoader.cs index 9dd308d..50a245d 100644 --- a/scripts/loader/uiLoader/MainMenuLoader.cs +++ b/scripts/loader/uiLoader/MainMenuLoader.cs @@ -47,14 +47,22 @@ public partial class MainMenuLoader : UiLoaderTemplate { Id = Config.LootListId.Test }; - var lootEntry = new LootEntry + var staffOfTheUndead = new LootEntry { - Chance = 1f, + Chance = 0.05f, MaxQuantity = 5, MinQuantity = 1, ResPath = "res://prefab/weapons/staffOfTheUndead.tscn" }; - testLootList.AddLootEntry(lootEntry); + testLootList.AddLootEntry(staffOfTheUndead); + var packsack = new LootEntry + { + Chance = 1f, + MaxQuantity = 1, + MinQuantity = 1, + ResPath = "res://prefab/packsacks/packsack.tscn" + }; + testLootList.AddLootEntry(packsack); LootListManager.RegisterLootList(testLootList); } DeathInfoGenerator.RegisterDeathInfoHandler(new SelfDeathInfoHandler()); diff --git a/scripts/map/MapGenerator.cs b/scripts/map/MapGenerator.cs index ebf421a..f77c834 100644 --- a/scripts/map/MapGenerator.cs +++ b/scripts/map/MapGenerator.cs @@ -300,7 +300,6 @@ public static class MapGenerator { Tag = AiCharacterGenerateEvent.TagMapGenerationComplete }; - LogCat.Log("触发事件" + (EventManager.AiCharacterGenerateEvent == null)); EventManager.AiCharacterGenerateEvent?.Invoke(aiCharacterGenerateEvent); } diff --git a/scripts/map/events/PlayerInstanceChangeEvent.cs b/scripts/map/events/PlayerInstanceChangeEvent.cs new file mode 100644 index 0000000..63a77b8 --- /dev/null +++ b/scripts/map/events/PlayerInstanceChangeEvent.cs @@ -0,0 +1,12 @@ +using ColdMint.scripts.character; + +namespace ColdMint.scripts.map.events; + +/// +/// Player instance change event +/// 玩家实例改变事件 +/// +public class PlayerInstanceChangeEvent +{ + public Player? PlayerInstance { get; set; } +} \ No newline at end of file diff --git a/scripts/utils/NodeUtils.cs b/scripts/utils/NodeUtils.cs index 5714db6..3f21fc4 100644 --- a/scripts/utils/NodeUtils.cs +++ b/scripts/utils/NodeUtils.cs @@ -2,6 +2,7 @@ using System.Collections.Generic; using System.Threading.Tasks; using ColdMint.scripts.debug; +using ColdMint.scripts.inventory; using ColdMint.scripts.weapon; using Godot; @@ -122,6 +123,11 @@ public static class NodeUtils { return GameSceneNodeHolder.WeaponContainer; } + + if (GameSceneNodeHolder.PacksackContainer!= null && childNode is Packsack) + { + return GameSceneNodeHolder.PacksackContainer; + } return defaultParentNode; }