The first implementation was way too complicated and prone to bugs.
This is much more simple flexible; first off, std::function is now used
instead of a raw function pointer, so lambdas and binds are fair game
which is great for scripting. Second, callbacks for all stacks are
executed. It is up to the callback target to ensure correct behavior.
Get rid of `iConditionBitFlag` in favor of a system of individual buff
objects that get composited to a bitflag on-the-fly.
Buff objects can have callbacks for application, expiration, and tick,
making them pretty flexible. Scripting languages can eventually use
these for custom behavior, too.
TODO:
- Get rid of bitflag in BaseNPC
- Apply buffs from passive nano powers
- Apply buffs from active nano powers
- Move eggs to new system
- ???
Was getting frustrated by the inconsistency in our include statements,
which were causing me problems. As a result, I went through and manually
re-organized every include statement in non-core files.
I'm just gonna copy my rant from Discord:
FOR HEADER FILES (.hpp):
- everything you use IN THE HEADER must be EXPLICITLY INCLUDED with the exception of things that fall under Core.hpp
- you may NOT include ANYTHING ELSE
FOR SOURCE FILES (.cpp):
- you can #include whatever you want as long as the partner header is included first
- anything that gets included by another include is fair game
- redundant includes are ok because they'll be harmless AS LONG AS our header files stay lean.
the point of this is NOT to optimize the number of includes used all around or make things more efficient necessarily. it's to improve readability & coherence and make it easier to avoid cyclical issues
Group structures are used now. Adds more checks in some places but simplifies things overall.
We can expand this system to entities as well now pretty trivially.
Start by replacing `hitMob` with `takeDamage` interface function.
Simplify `pcAttackChars` a little by utilizing the new interface, then add more interface functions as needed.
A lot of the combat logic is tied to the `Mob` class. Need to start moving stuff over to CombatNPC.
Mobs and CombatNPCs still need theirs in order to properly set their
roaming and spawn coords. Assignment of the latter has been moved to the
CombatNPC constructor, where it should have already been.
Storing certain things in appearance data and others in their own fields
was gross. Now everything is stored on the same level and functions have
been added to generate appearance data when it's needed by the client.