Metabolism

B!0HAX

Member
Contributor
World
Edit: viewtopic.php?f=4&t=320


MetaboliteComponent has a list of possible types of metabolites (each metabolite has an effect in the players organism)
Metabolism is where those effects are defined in terms of the players organism's reaction.
An action (event handler) will be needed to connect the Metabolism effect to the Metabolite type.

Drink a Poison Potion Example:

greenpotion.prefab > will carry "Metabolite.type" : "poison" (for example) and the DrinkPotionAction (because its a potion).
DrinkPotionAction > is the event handler that knows what potion the user is drinking (in this case green : "poison")
MetabolismSystem > this receives that a poison metabolite has been consumed. returning the effects of the poison to the player and an empty vial where the green vial with the poison content was.
 

Attachments

Cervator

Org Co-Founder & Project Lead
Contributor
Design
Logistics
SpecOps
IRC discussion:

[14] <Cervator> one thing - and i may be wrong here (ironchefpython or immortius might be able to provide confirmation) - the use of prefab for individual potions (or books) might be too detailed
[14] <Cervator> they're more for the level of book.prefab, potion.prefab, chest.prefab, etc
[14] <Cervator> then some sort of item definition (like block definition files) would exist and be easily extensible via mods - and you'd put the details there (which effect, book content, etc)
[14] <Cervator> but then admittedly you could perhaps argue that you could have a container.prefab that could in turn provide the difference between chests and bookcases in data, hmm
[14] <Cervator> so i'm not totally certain on where the line is there
[14] <overdhose> currently looking at prefabs myself atm
[14] <Cervator> as for MetabolismSystem - great, would be awesome to have potions and that system would definitely be needed for stuff :)
[14] <overdhose> ingenious lil system
[14] <ironchefpython_> Assuming books all have similar behavior, there should be a single prefab for them
[14] <Cervator> yeah, although as visible here we're getting a little fuzzy on the edges between the different concepts, especially if you drag in the mod system :)
[14] <Cervator> prefab, definition file, component, prototype, model....
[14] <overdhose> I managed to create a new gelcube with different AI in a short time
[14] <Cervator> cool
[14] <ironchefpython_> If books had different components (and thus different information and behavior associated with them) that would justify multiple prefabs.
[14] <overdhose> so from my pov, using that system for potions would make it easy for mods
[14] <Cervator> right, so i guess the issue is - for potions, is each effect its own component? just varying in strength? in that case you *might* well have one prefab for "health potion" and one for "speed potion"
[14] <Cervator> tho perhaps the health potion prefab could include everything that directly affects health at one point in time, like a harmful potion
[14] <Cervator> so i think there's room for interpretation here
[14] <overdhose> hmmmm
[14] <Cervator> you could also picture some reuseability if there's one component for a health change (we have something similar for that already, don't we, ironchefpython?) and it just gets attached together with a potioncomponent (pointing at function)
[14] <Cervator> then you could attach a speed component as well, for a mixed health/speed potion
[14] <bi0hax> currently
[14] <overdhose> shouldn't a potion just have like a "Drink" component ? And then assign the effect through the prefab ?
[14] <bi0hax> I made a health potion
[14] <Cervator> and possible switch potion to spell
[14] <bi0hax> and DrinkPotionAction (event hanlder)
[14] <ironchefpython_> It could be a single component for "status effects", or a component per status effect.
[14] <bi0hax> Its on my git commits
[14] <bi0hax> and DrinkPotionAction handles what potion.type the entity used is
[14] <ironchefpython_> Right now however, for players and creatures, there is just a "HealthComponent", and no place to store status effects that aren't health realated.
[14] <bi0hax> so if the prefab says it is a potion.type = Red it goes to the Red case of the switch
[14] <ironchefpython_> I could expand the HealthComponent system to include things like strength and speed.
[14] <ironchefpython_> Or we could add additional components.
[14] <bi0hax> I prefer additional components
[14] <bi0hax> I would like to see a stamina component
[14] <ironchefpython_> Will you ever have a player that has health, but does not have speed or stamina or strength?
[14] <overdhose> qustion : what's the diff between biohax/ immmortius... one fork is listed under the other.
[14] <bi0hax> or a hunger component, that way I could tinker a poison component
[14] <bi0hax> In my branch you have my shit
[14] <bi0hax> like books, bookcases that store books, redpotion
[14] <bi0hax> and a sickle
[14] <bi0hax> also it has the new item pack (icons)
[14] <bi0hax> and they are all defined in the model/icons.java
[14] <bi0hax> I thought in MetaboliteComponent & MetabolizeAction
[14] <bi0hax> because there other stuff that aint potions could be added
[14] <bi0hax> all Action that has to do with absorbing a metabolite (effect)
[14] <bi0hax> so there could be a redpotion and a goldencookie
[14] <bi0hax> that both recall the metabolite.type.Heal
[14] <Cervator> back, sorta, work still happening, boo
[14] <Cervator> oh, so current HealthComponent is for stuff that has health - which is currently always the player, but could it in theory also be the health content of a healing potion? or would they not overlap perfectly?
[14] <bi0hax> I got it to work
[14] <Cervator> bi0hax forked originally from immortius' repo, that's why it looks like that, most our repos were forked directly from MovingBlocks/Terasology, so github will say that
[14] <bi0hax> because you define what healthcomponent actually you are using
[14] <bi0hax> you update the users healthcomponent
[14] <overdhose> ach k thx trying to understand the whole Git setup :p
[14] <Cervator> i think something like metabolite.type.Heal and switches would be fragile and somewhat counter-ES, as well as trickier to extend via mods
[14] <Cervator> i figure all sorts of things could hold health, be they players, monsters, potions, food, or even spells
[14] <bi0hax> the switch idea was immortius
[14] <bi0hax> I asked if there was a nicer way
[14] <bi0hax> instead of IF, IF, IF
[14] <Cervator> that makes me think HealthComponent should be able to hold health in all those situations, and a FoodSystem, PotionSystem, etc, would be able to transfer points from a component attached to something relevant to the player or what not
[14] <Cervator> ahh
[14] <Cervator> yeah, switch > if
[14] <Cervator> but maybe components > switch
[14] <bi0hax> have a look at the code it looks quite nice for adding new feature
[14] <bi0hax> but I hope to implement the Metabolite & Metabolize
[14] <Cervator> i'd love to, i really need to do work tho, prep for a meeting in 30 mins :(
[14] <bi0hax> I think it will be better for recalling various effects
[14] <Cervator> i do think there's something there, yeah
[14] <Cervator> my thinking is encouraging reuse between systems, it would make sense for food and potions to metabolize effects similarly, but spells could also do a similar effect, yet unrelated to metabolism ?
[14] <ironchefpython_> Cervator: The current HealthComponent is for things that can be damaged and destroyed, by being attacked or by falling.
[14] <ironchefpython_> A healthcomponent on a potion would me that it could be broken, not that it would apply health to the user.
[14] <Cervator> yup, but would that be a valid re-use scenario? or is there specific stuff in the component for attacking/falling?
[14] <bi0hax> yeah, in my case I use it to call upon the users health
[14] <Cervator> and yeah, true
[14] <ironchefpython_> I would create a statuseffect component or something similar... for things that effect an entity's status
[14] <bi0hax> and fatigued status could be added there
[14] <ironchefpython_> and a potion component, that has an event listener for a "drink" event, that applies the effect of the statuseffect component.
[14] <ironchefpython_> yes, fatigued would be part of the statuseffect component
[14] <bi0hax> statuseffect could be even called when a prop is low, like stamina = low then statuseffect : fatigued is called
[14] <Cervator> statuseffect sounds to me more like an over-time thing, but i do see the trick about being able to break a potion if it has health itself
[14] <bi0hax> but the thing is
[14] <bi0hax> no collisions are yet determined
[14] <ironchefpython_> but keeping the status effect separate from the potion component, you can add the status effect component to rings, armor, wands, locations, etc.
[14] <bi0hax> thats why (I think) tools dont break even if you said they did
[14] <bi0hax> or you cant hit gelcubes even if you added a healthcomponent
[14] == RoyAwesome [~RoyAwesom@c-98-232-169-164.hsd1.or.comcast.net] has joined #terasology
[14] <Cervator> yeah okay, that sounds like what i was trying to think up, potion and status separate
[14] == vbgunz [~vbgunz@70-119-22-93.res.bhn.net] has joined #terasology
[14] <Cervator> so would a status component have multiple possible "contents" that would be acted on? or is that waste / poor encapsulation if you're leaving some variables unused?
[14] <ironchefpython_> But there should be a StatusEffect (or is that StatusAffect ?) :) ... as well as a StatusEffectableComponent. The StatusEffect component would be added to potions and rings and wands and stuff, and the StatusEffectableComponent would be added to players and npcs
[14] <Cervator> interesting angle, yeah
[14] <ironchefpython_> Cervator: in the current implementation you cannot have multiple instances of a component associated with a single entity, so either you group all that data (fatigued/slowed/sleepy/horny) into a single Component and have most statuses go unused most of the time, or you create a different component for each status effect.
[14] <Cervator_> yeah - and wouldn't different components make it more extensible?
[14] <Cervator_> i posted the initial irc log in the thread: viewtopic.php?f=4&t=314&p=2218#p2218
[14] <ironchefpython_> perhaps, but it might be more bloated.
[14] <glasz> hello
[14] <Cervator_> might have to force myself to not pay attention to this window for a while so i can work -_-
[14] <ironchefpython_> you can augment new status effects either by adding more components, or adding them to the status effect component
 

B!0HAX

Member
Contributor
World
Stat Effects

StatusEffectsComponent: Enum of different StatEffectType:
-HealthBoost
-Poison
-Cure
-Food
-Refresh
-InFlames
-Fatigued
-etc...

StatAffectableComponent : For Player & NPCs, like the current Health Component.

StatAffector : Event Handler for when items with StatusEffectComponent are used.

or is there a better way?
 

Cervator

Org Co-Founder & Project Lead
Contributor
Design
Logistics
SpecOps
I'm still torn between the easy extensibility (and encapsulation) with a component per effect, but that's fairly bloated, vs. a bigger monster component like that. I suppose we could have a big "core" set of effects and still let modders add new components for their stuff?

One thing I would suggest: Differentiate between instantly consumed effects vs over-time effects (being on fire). Does that make sense?
 

Immortius

Lead Software Architect
Contributor
Architecture
GUI
Cervator said:
IRC discussion:

[14] <Cervator> one thing - and i may be wrong here (ironchefpython or immortius might be able to provide confirmation) - the use of prefab for individual potions (or books) might be too detailed
[14] <Cervator> they're more for the level of book.prefab, potion.prefab, chest.prefab, etc
[14] <Cervator> then some sort of item definition (like block definition files) would exist and be easily extensible via mods - and you'd put the details there (which effect, book content, etc)
[14] <Cervator> but then admittedly you could perhaps argue that you could have a container.prefab that could in turn provide the difference between chests and bookcases in data, hmm
[14] <Cervator> so i'm not totally certain on where the line is there
[14] <overdhose> currently looking at prefabs myself atm
[14] <Cervator> as for MetabolismSystem - great, would be awesome to have potions and that system would definitely be needed for stuff :)
[14] <overdhose> ingenious lil system
[14] <ironchefpython_> Assuming books all have similar behavior, there should be a single prefab for them
...
[14] <ironchefpython_> If books had different components (and thus different information and behavior associated with them) that would justify multiple prefabs.
On the use of prefabs, my feeling is they they should be used more rather than less. Having a RedBook and BlueBook prefab, which differ only by icon, is fine because they do differ, and presumably they'ld be crafted differently or otherwise be produced from different sources which would want to refer to the individual variations. However for ease of maintainability you would likely want a Book prefab which both RedBook and BlueBook prefabs "inherit". Prefab inheritance is a little iffy at the moment (needs to be moved from using cloning to the ComponentLibrary system, serialization/deserialization needs some work), but when working correctly it would mean you could change the parent (Book) and the changes will flow on to the child prefabs (RedBook and BlueBook), and then onto existing instances. Or you can just create a Book prefab and change the icon in code, if that is sensible.

I would emphasize that two entities do not have to have different components to warrant different prefabs - it is entirely possible for two entities to behave quite differently based purely on the settings of their prefabs. For instance you might have a bunch of Monsters with the same components (Location, Mesh, Collision, CharacterController, SimpleAI, Health), but have different meshes, materials, health, damage, size, and AI configuration.

Will you ever have a player that has health, but does not have speed or stamina or strength?
I would ask "Will you ever have something that has health, but does not have speed or stamina or strength?". Blocks have a Health Component for instance. The idea of having a numeric value that can be damaged and doing something when it hits zero is not unique to players, thus having a component that handles that aspect and can be given to any entity is nice.

That said something There is a balance to be sought around how much goes into each component, and what gets split out - as with any programming exercise.
...
[14] <Cervator> yeah okay, that sounds like what i was trying to think up, potion and status separate
[14] == vbgunz [~vbgunz@70-119-22-93.res.bhn.net] has joined #terasology
[14] <Cervator> so would a status component have multiple possible "contents" that would be acted on? or is that waste / poor encapsulation if you're leaving some variables unused?
[14] <ironchefpython_> But there should be a StatusEffect (or is that StatusAffect ?) :) ... as well as a StatusEffectableComponent. The StatusEffect component would be added to potions and rings and wands and stuff, and the StatusEffectableComponent would be added to players and npcs
[14] <Cervator> interesting angle, yeah
[14] <ironchefpython_> Cervator: in the current implementation you cannot have multiple instances of a component associated with a single entity, so either you group all that data (fatigued/slowed/sleepy/horny) into a single Component and have most statuses go unused most of the time, or you create a different component for each status effect.
[14] <Cervator_> yeah - and wouldn't different components make it more extensible?
[14] <Cervator_> i posted the initial irc log in the thread: viewtopic.php?f=4&t=314&p=2218#p2218
[14] <ironchefpython_> perhaps, but it might be more bloated.
[14] <glasz> hello
[14] <Cervator_> might have to force myself to not pay attention to this window for a while so i can work -_-
[14] <ironchefpython_> you can augment new status effects either by adding more components, or adding them to the status effect component
I've been reflecting on the current setup with how items work and how it could be refined (it is quite rough and suboptimal), as well as how item usage, actions, status and events could work together nicely, based on this discussion and the one I had with ironchefpython last weekend.

Firstly there are a few types of status' which we are talking about. There are the big primary things which characters need to have all the time for them to work - Health, Stamina/Fatigue, Hunger, Strength and other stats. Some of these are gametype specific - a "genesis" gametype (starting with nothing and inventing fire/hunting/etc) would certainly want Fatigue and Hunger. A sandbox gametype would not. If introduced in a mod may need to override certain systems or introduce intercepting event handlers - for instance if strength limits inventory size, intercepting the ReceiveItem event for entities with both a... CharacterStats and Inventory component. This suggests mods need a way to specify exactly what prefab is used for players in it, or to modify the players on creation (which is currently doable). I see no issue with chucking all the RPG stats onto a single component, might want fatigue and hunger on separate components, basically that is a decision based around what may be used together and what might be used independently.

The second type of status is an extra effect that sits on the player and changes those core statistics or adds something additional - often temporarily. Poison, Regen, Burning, Speed Increase, Poison Immunity, Invunerability. Some of these might stack, some of these might overlap, some of these cancel or protect against others.

Certainly these could be done by settings on the primary stat components. Some of these may be components that get slapped on the player, which make it eligible for certain systems to process the entity or intercept events against it - Invunerability as a component could allow an event handler to stop all Damage events. Similar a Poisoned component could send a Damage event against the player every X seconds, and removed itself after X damage/seconds. The interesting thing there is that the poison component would not even need to be on the player - it could be placed on a separate entity and just direct the damage events to the player. This would allow moving the common behavior of timing out after some time to another component - a Lifespan component that destroys its own entity after some time - which could be reused for other effects. Although with this sort of set up it you'ld need to set some link up between the character and its effect entities so they can be tracked and manipulated by other systems. But if gives a lot more flexibility in defining effects, especially because they can be mixed in that entity and live and die together. Could chuck in a StatusEffect component that identifies it for determining stacking/overlap behavior.

For stat boosts, it might even make sense to put a CharacterStats component on, say, item entities and effect entities, and have systems know that to calculate a player's effective stats they need to sum the player's stats with the item stats and effect stats (and then to apply the sum of multipliers) - possibly though some shared system or helper method.

So basically there are a number of ways to formulate this, and to a certain extent which one to use depends on the gameplay desired. I envision most components being introduced outside of the engine eventually, except for a few very core components and engine driven things (like rendering components, attached sounds, camera, physics related components...), and health would probably fall in the engine due to use by block so I would be inclined to keep the more gametype specific effects separate from it.

On the item system in general, what I'm thinking of at the moment is:

* An InputSystem that translates key and mouse inputs into bounds "buttons" and/or "axis". Button interactions will cause events to be sent against the LocalPlayerEntity, which they both can be polled as well (my experience is both have their uses, and most engine I've used support both).
* When the LocalPlayer receives an event for the UseItem button, it will create an activate event with the details of what the player is targetting and send it against the item (that is, remove all the existing rubbish that checks the item's usage type and sends one of four events).
* The Item system will receive the event first, and abort it if the target doesn't match the item's usage type
* All the other event handlers relevant will receive the Activate event and act. These are based on component(s), so common usage would be to have components for the sort of actions the item should do, like DealDamage, Heal, InflictPoison. Something like BlockComponent would be linked to placing the block.
* Finally the Item system will receive the event again, and decrement the stack size or destroy the item if it is consumable.

For these sorts of "Action" components, they should have a setting determining what they should affect (the instigating player, the target, or the item itself) - this would allow items that, say, damage a target and heal the user at the same time. Then there should be an event handler that receives the Activate Event and sends an appropriate event to the target - PoisonEvent, DamageEvent, HealEvent, etc. Then other event handlers can pick these up and act appropriately.

Sorry that came out as more a less a stream of thought, but hopefully gives you all some ideas. :)
 

Cervator

Org Co-Founder & Project Lead
Contributor
Design
Logistics
SpecOps
Yay for walls of constructive text :D

I'll just comment on prefabs for now - it makes more sense to me now then to do more of them for subtly different objects of the same type (colored books) if they indeed do differ in some way. IIRC the red book / blue book etc also were trying to differ in starting book text content, which struck me as more of a data difference than a prefab difference (correct me if I'm wrong here, bi0hax - that may just have been something incomplete waiting for something else to happen).

Admittedly at the same time the alternative was loading text from some arbitrary sample text file at creation time, which might not be too graceful either. That made me think we'd need book definition files (just like block definition files) if there were to be actual titled books known to the game (for examples if nothing else). Book definition files would be nothing more than a data object listing the title, the body, and the prefab=bluebook or what not.

If books just started with a random color I could see just doing "book.prefab" - if there indeed is an actual physical difference (to create a book with a blue cover you need a certain dye) then yeah, "bluebook.prefab" makes sense, probably with some sort of prefab inheritance from "book.prefab"
 
Top