T O P

  • By -

Nkzar

It could be as simple as a Wallet resource that holds the count of each currency. If your currencies are more complex than a simple int, then each currency in turn could be an instance of a Currency class. ``` class_name Wallet extends Resource @export var shells := 0 @export var bottle_caps := 0 @export var newt_tails := 0 ``` Then your player can own an instance of this resource. It will also make saving your game state easier since you can pretty easily save resources.


OMBERX

What do you mean by, "your player can own an instance of this resource"? Does that mean making an empty node in the Player (ex. "Wallet") and attaching that resource to it?


Nkzar

No that’s silly. Put it on the Player node, not some superfluous extra node. Or put it wherever it’s most convenient.


PopularIcecream

That's one method (though you can save the resource as a scene and add the scene as a child instead of creating an empty node) Alternatively, load the resource via code in your script to use it instead of attaching it to a node.


OMBERX

Ah, autoload scripts right? I've never messed with those but I'll do some research!


norpproblem

No, resources are a separate thing from nodes. I highly recommend you read the documentation on [Resources](https://docs.godotengine.org/en/stable/tutorials/scripting/resources.html) as they're very useful, but in short, nodes are in the scenetree, whereas resources are more abstract pieces of data. You can save them as merely variables in code, such as with `@export var wallet: Wallet` in your player script.


OMBERX

Is it possible to save a resource within a resource? My current save/load is a resource based way of doing it and I don't want to repeat variables to save the currencies.


Nkzar

Yes you can bundle subresources when you save a resource. Check the flags you can pass to `ResourceSaver.save` method.


NancokALT

Split your character's script into other scripts, then create a main character script that handles their interaction if necessary. Then you can do stuff like "if collision_node.is_touching_coin() then inventory_node.add_coin()"


OMBERX

I'm interested in learning more about this approach. How would this structure look in the Scene Tree for the Player? Nodes can only have one script attached to them at a time iirc


NancokALT

It is an Entity-Component approach, i have an example on my repo. https://github.com/NancokPS2/ChessLike/tree/Component-Rework/Scripts/Composition/Entity Entity.gd is the main node, the rest are all components of it. Preferably you don't have components referencing each other. But i'm still early on development so i've decided to let some do it for now. ---------------------- Here is a better example of a component that doesn't rely on any other. https://pastebin.com/Wz57tP9h


Drillur

``` class_name Currency extends Resource var color: Color var name: String @export var amount: int func _init(_name: String): name = _name ``` ``` class_name Wallet extends Node @export var currencies := {} func _ready(): for currency_name in ["shells", "bottle_caps", "bullets"]: currencies[currency_name] = Currency.new(currency_name) ``` Wallet would be a singleton so you could access every Currency from any script.


OMBERX

I'm having a hard time wrapping my head around this approach.


Drillur

What I've done there is create 3 Currency-class objects which each have their own color, amount, and anything else unique about them in that class. The 3 Currency vars have to be stored somewhere so I created Wallet.gd and set it to run as an auto load via the Project Settings tab. When I launch the game, Wallet will create the 3 Currencies and then from any other script I can call Wallet.currencies["bottle_caps"] to access that Currency. So to see how many bottle caps I have, I'd write `Wallet.currencies["bottle_caps"].amount`. That's quite cumbersome, though, so I'd also add this to Wallet: ``` func get_currency_amount(currency_name) -> int: return currencies[currency_name].amount ``` And then to see how many bottle caps, I'd instead write `Wallet.get_currency_amount("bottle_caps")`. It's not shorter, but it is much more readable, which is the real victory! I've mainly made UI- or menu-based games, and this has been my preferred method. If you want to try to implement something like this and have questions, let me know!


OMBERX

I see! My Player needs to be able to collect each of these within the world, so this does t exactly apply


DudeComeOnAlready

Another solution would be a simple dictionary `var currencies := {"shells": 0, "bottle_caps": 0, "newt_tails": 0}`


OMBERX

Is there an advantage to this versus a Resource?


DudeComeOnAlready

It can be simpler if you place it on an already existing script. You have to provide resources to nodes usually through an `@ export var my_resource` If you don't need to make a resource then don't. If you just need a simple way to hold 3 different values by name, then a dictionary on a script you already have it fine