Alright, thought I'd expand on the concept a bit more and include some related topics
Say we introduce river entities to a redesigned liquid flow system. Not quite sure that's entirely the right way to do it, but easier to think about. We have a RiverComponent that stores a given name for a river as well as the strength and exact location of its source (might need more details later if we get fancy with the hydrological cycle). We also give it a list of chunks it exists in (using a LinkedList seems like it would have potential?)
The related chunk summary data concept as discussed in the
height limit thread might come in handy here, as you could note there how many/which rivers exist per chunk. As the river is born it creates a source tile and starts simulating outflow from that source using its strength. If the water crosses a chunk barrier that chunk is added to the river's list of chunks, and the chunk's river counter is incremented by one. As long as there's only
one body of water in that chunk we can assume all the water there belongs to the river. If a second body of water is added we do some magic.
If a player simple drops a bucket of water on the ground and the engine detects there are now two separate bodies of water it could generate an entity for the chunk with a simple list of what block position belong to what source of water (what entity). That way we prevent acting on "flow" in disconnected pools and such. Or maybe one entity per body of water (with a WaterComponent?) that is linked to the river entity if appropriate.
If the player (or terrain) instead causes the river to fork, we detect that and generate a new River entity with its source being its branching point from the parent river, which inherits the appropriate amount of flow from the parent and in return adds a sink to drain the parent's flow accordingly.
On the other hand if a river enters a chunk that holds an
existing river and then joins it we end whichever River entity has the weaker flow (sink its entire flow into the more powerful river, or maybe the older river if it happens post-world gen) then re-simulate the added flow on the remaining river segment going wherever. Maps with accurate river names that can change over time, gasp! On the technical side of things you'd probably use ES events here to communicate between the entities to find out how a river splits or is merged, or how a new body of water inserted into the world reacts.
Similar flow mechanics could probably be used to simulate aquifers, just held under pressure until released somehow. Not totally sure how my crazy block dynamics and per-block pressure counters would factor into that
Chunks holding what we define as ocean (at world gen time) consider its ocean body of water (you could still have disconnected bodies of water in the same chunk) as having infinite sink ability so any inflow terminates there. However, if due to player intervention something causes an ocean body to outflow (don't mine through the ceiling under an ocean!) then we create a river object with outflow set to the size of the breach. In some cases we might want a new body of water that gets large enough (think a whole valley below sea level but a fair distance from the ocean) connected with a narrow enough river to the higher ocean like that to start simulating outflow that goes nowhere (evaporation and sinking into soil) so you end up with a balance where the inflow equals outflow without the two bodies of water necessarily being at the same level. Heck, you could end up with a subterranean cave ocean that itself could be a near infinite sink for underground rivers.
Simulating rivers into areas where chunks aren't loaded could use the height map of the world (a naive approach, more detail later) to figure out which chunks it should hit without having to load the chunks at all, just adding to their summary data / water body counter. If the chunks haven't previously generated then
on generation the presence of water could be considered (avoid putting a walled goblin compound in the way if you've decided there's a river going through it - or place it
next to the river, goofy!). There might be a bit of a disconnect here between since-dawn-of-time major rivers (that should probably belong to
world gen phase) vs local rivers and player-caused events (that are based on more accurate
simulations).
A big problem with using a height map is that you only have one surface - that also came up in the height limit thread (or a world gen thread?). Rather than working with a magic surface (or two, like a separate but equal skyworld) we probably should look into intelligently working out what
is a surface local to a large amount of chunks (a mini height map specific to a layer of chunks that may go up or down? Chunk metadata?). That could then also be used for displaying a minimap, assigning region names, doing lighting calculations, running growth simulation, and calculating pre-emptive water generation. Although for water that's easier to imagine if you already generated the caves, not sure exactly when we'd do that in a world with stacked chunks.
Okay, I'm done for now. Back to work!
Edit: Come to think of it, you could probably use the pressure system in parallel to the liquid simulation. Pressure in blocks (think aquifer) or special bodies of liquid (think magma chamber) could be the sources for starting flow for a river simulation. Mmm, lava rivers.