lua-users home
lua-l archive

[Date Prev][Date Next][Thread Prev][Thread Next] [Date Index] [Thread Index]




On Fri, Aug 2, 2019 at 12:47 AM Egor Skriptunoff <egor.skriptunoff@gmail.com> wrote:
On Fri, Aug 2, 2019 at 12:14 AM Soni "They/Them" L. wrote:
On 2019-08-01 6:05 p.m., Egor Skriptunoff wrote:
> Could you provide an example to show benefits of traits?
> What kinds of tasks traits solve better than conventional
> 'objects-and-methods' approach?
>

Inventory may not be self-contained. Inventory could reference another
trait.

I recommend reading https://en.wikipedia.org/wiki/Entity_component_system


I'm aware of entity-component-system approach.
And this is my understanding of how it should be implemented in Lua:
And I don't see how traits could help implementing it.
The best way to implement ECS is "don't use OOP at all".

I'm not quite sure how you come to that conclusion. ECS is an inherently object-oriented technique, and the ID-based technique exists specifically to enable an object-oriented technique to be implemented in languages that don't make it easy to write object-oriented code. In your SO post, you've basically reinvented pointers, and you've scattered the contents of things around instead of keeping related information together.

Traits are a perfect fit for ECS. Each entity is an object that has traits. Each component type is a trait, which carries with it the definition of what the trait is, what data it contains, and how to interface with it. An object can possess multiple traits, and their encapsulation means that they don't interfere with each other (which is an improvement over interfaces or multiple inheritance). Any object possessing a trait can be used interchangeably any context that expects that trait (that is, traits enable polymorphism).

Traits also make it easier to define prefabs, that is, an entity with preselected traits and properties that can be created on demand. Creating a new monster using the syntax in your post means picking out a new, unused ID, finding out what traits exist on the monster being created, and making new copies of those traits. With traits, you can just say "monster = Monster.new()" and be done with it.

As a Unity3D user, I have thousands of lines of real-world code demonstrating how to use object-oriented ECS. I won't necessarily say that my particular way of doing things is optimal, because I have a strong C++ background and I'm mixing components, interfaces, and normal OO inheritance all in one codebase, and Unity3D is C# so it doesn't have a native trait syntax so it's not as elegant as it COULD be, but it's a pretty clear illustration that it's valuable.

/s/ Adam