0
\$\begingroup\$
High level

At a high level, I'm looking to create a galaxy exploration-style game.

A number of points of interest will be selectable on the map (I'd like to aim for several hundred, but flexible and needs testing).

A POI can be something story-related or a source of one of 4 resources.

Players start with a ship, head to a resource node, harvest resources and can move on.

So far so good, I've got a small number of resources, so can just group them together as a single ResourceStockpile component and hide empty resources in the UI.

The POI that produce resources will have a service that increments their stockpile over time, and ships will have a "cargo bay" of ResourceStockpile.

The player can use [some resources] to create factories at a POI.

Factories convert resources to goods (both finished products and components/parts).

Complexity

I want to be able to ship goods. Unlike resources, I'm expecting to have several dozen types of finished good (and many more intermediate parts and components), with an eye to expanding over time.

Storing a few zeroes for resources seemed like a small overhead to maintain a consistent ResourceStockpile I could reuse.

As the number of items/fields grows, the design feels less and less desirable.

To make things more interesting, I'd ideally like to be able to ship pretty much anything (including the factories, if the ship is large enough).

Do I switch to a HasX component for every possible resource/good? If so, it seems like I'm going to spend an awful lot of time swapping between archetypes.

It also seems like a lot of duplicated code, unless there's some way to treat it as a generic Has<X> instead, but I believe that's quite complex to implement, and may negate some of the memory management benefits of ECS (?)

Or do I create a ResourceStockpile with -say- 100 integers, one per possible resource/good and just swallow the overhead?

What's the right™ way to break this down?

\$\endgroup\$

1 Answer 1

1
\$\begingroup\$

What you might be looking for is a DynamicBufferComponent. It's the go-to solution when an entity doesn't have one value but n values with variable values of n depending on the entity.

I would create a component like this:

[InternalBufferCapacity(2)]
public struct ResourceStack : IBufferElementData
{
    public ResourceType type;
    public int amount;
}

The 2 in [InternalBufferCapacity(2)] here is just a guess of how many key-value pairs of resources the average resource-stockpiling entity will have in your game (one input resource and one output resource). If that's not the typical number of resources in your game, you should adjust it accordingly. It's not a hard limit on how many you can have; it's an optimization hint for the Entities framework regarding how much memory it should initially allocate per entity with this buffer component.

ResourceType would be an ID type, probably an enum.

\$\endgroup\$

You must log in to answer this question.

Not the answer you're looking for? Browse other questions tagged .