Thursday, April 28, 2016

Hammer devlog 17

I did an event flag system this morning. No gif because it's an event flag system: just take my word for it, if you open the chest in the starting room and reload the scene it stays open. Excitement!

Anyway, I had one of those moments while I was doing it: I was lamenting how I couldn't very easily fit all my event flags into one enum, and I was thinking of a way to handle that! I had halfway designed this completely ludicrous solution which would require a custom inspector, and included both an int to cast to the necessary enum and a separate index value that we'd use to look up the enum type to cast to and the parameter in GameStateManager we needed to compare that to.

Basically, it would've been a giant clusterfuck that'd break horribly if you looked at it wrong.

But then I realized that, no, wait, why was I trying to do this?

So I just defined a generic FlagManager type and decided that things would take a reference to that, and I could then extend FlagManager to implement the abstract methods that'd actually do the heavy lifting. You don't need to do some overcomplicated quasi-dynamic type system to figure out which enum this flag should be cast to and what to compare it to - just stick the appropriate FlagManager on the thing, pick the flag from the dropdown, point the thing that needs to look at the flag to the FlagManager.

I spent more time designing and scrapping the ludicrously overcomplicated, look-how-clever-I-am solution to the problem of "event flags" than I did actually implementing the thing that's in place and works. And it's not even ugly or anything? There's a little bit of code repetition that's completely fucking worth it because it lets me Just Say No to dynamic typing, but it's eminently readable in the way that the "smarter" solution I came up with in the first place definitely would not have been.

I do hope the compiler basically inlines the FlagManager object out of existence, though, lol. Since an enum isn't a "real" type - it's just a friendly face for the integral type behind it - it'd be really embarrassing if the result of this design was that I wound up repeating the same tiny section of machine code 20 times and having different things using different repetitions of that code to do their checks for no apparent reason.

[​IMG]

Event flags being a thing means keys can be a thing, so keys are now a thing.

Also: man, I really need to build a fight that's not complete shit sometime soon. Well past the point where that room with the ghosts is useful. 

[​IMG]

WIP minimap and a subregion name popup thing. Subregions are different "areas" within the same scene, so of course the minimap doesn't try to fill cells that exist but aren't part of the current subregion.

Minimap only tracks rooms right now; it doesn't include any support for identifying which rooms you've visited, and it doesn't display connections between map cells. But it does populate automatically based entirely on the layout of rooms in the level and behave nicely with big rooms, so that's cool. Tracking visited rooms is easy enough and I just haven't bothered to implement it yet, but I'm not entirely sure how I want to handle connections. I definitely want this to display that information - but the problem is that (as you can see here!) internally, there's no such thing as a room-to-room connection. Every room is connected to its adjacent rooms; some of them just have collision in the way. I don't want anything as clumsy as a separate array stored with the RoomController that just tracks where to draw connections and whether they're room-to-room or represent fused big room cells, but I might have to do that, really. I could generate connections at runtime from big room cells, but there's nothing reasonably performant I can think of to go over the entire level and immediately check which cells are accessible from which which doesn't leave room for error. And I want to be able to do this within the space of one frame, so - probably am gonna have to suck it up and have rooms specify their connections manually?

Obviously: I really need to optimize the code that handles player world coords updating on big maps. That framerate is pretty gross considering there's nothing else on the map.