Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Significant re-write, changing the algorithm and lake shape. #14

Merged
merged 5 commits into from Nov 14, 2020

Conversation

4Denthusiast
Copy link
Contributor

@4Denthusiast 4Denthusiast commented Nov 14, 2020

I started updating for MovingBlocks/Terasology#4237, then ended up re-writing pretty much the whole module instead. Now lakes are more rounded in shape, with the floor smoothly curving up to the shore, rather than there being a sudden cliff at the shore. Also, it's better at detecting when an area is too sloped for a lake, and the shape of the lakes' surfaces is somewhat different too, because now it's based on distorting a circle with brownian noise, rather than making polygons, as before.

The polygon based algorithm did give reasonable shapes for the lake surfaces, but it didn't integrate well into calculating the depth of the lakes, so I made it essentially calculate the depths first, then the lake is all those locations where the depth is greater than 0.

Resolves #11, #10, #9 (although that's only still current because I recently re-introduced in in a CoreWorlds PR), #1, and probably #7 and #12 too (basically it's a complete re-write, so all the old bugs are replaced with exciting new bugs).

Copy link
Collaborator

@skaldarnar skaldarnar left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The code changes look good to me, I haven't tested the PR in-game, though.

"author": "The Terasology Foundation",
"displayName": "Lakes",
"description": "Plugin for Worldgenerator, which creates lakes based on random polygons",
"description": "Plugin for world generation, which creates small lakes",
"dependencies": [
{ "id": "CoreAssets", "minVersion": "2.0.1" },
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

(just me thinking out loud)
Hm, I somehow expected some dependency update because of the new facets that are now required... 🤔 now I'm wondering whether we should move those to the CoreWorlds repo instead 🤔 (related engine commit MovingBlocks/Terasology@5d5c7a6)

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

That's a good point. I probably should have updated the version number of CoreWorlds.

public static final int MAX_DEPTH = 12;
public static final int MIN_VERTICES = 10;
public static final int MAX_VERTICES = 30;
public class Lake implements Iterable<Vector3i> {
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Hm, I'm not sure I like that Lake is an Iterable<Vector3i> ... this way we can write something like the following to iterate over all block positions in the lake, right?

for (Vector3i position: lake) {
 ...
}

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I wrote it this way so as to not give write access to the set of points. If there were an explicit function returning an Iterator, that wouldn't work with the for syntax. I guess I could just make the Set public instead. There isn't really any harm in it (and if other facet providers need to modify lakes, they might have a legitimate reason to access it anyway).

-Missing biome modification to prevent grass and trees to spawn on lakes
~~-surface lakes have difficulties appearing in perlin and other non flat world gens (unknown reason)~~
-the "tubs" of surface lakes are sometimes incomplete
- Occasionally, lakes have uneven surfaces
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Do they still have that? Does that happen if two lakes intersect with each other? Or is this fixed by the lake having a single surface height value? (https://github.com/Terasology/Lakes/pull/14/files#diff-f18b6a2bae9571d62ca21dbb5303170d4c694f954c0f5842b879bb6ef8c4fb96R33)

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I assume it's something to do with lakes intersecting, although I don't know how that would be possible. It is at least very rare, and if you have FlowingLiquids enabled, it would quickly stabilise to a lower flat surface anyway, so I just decided to not worry about it.

Comment on lines +42 to +46
for (Lake lake : lakeFacet.getLakes()) {
for (Vector3i pos : lake) {
if (chunkRegion.getRegion().encompasses(pos)) {
Block block = pos.y > lake.surfaceHeight ? air : lake.liquid;
chunk.setBlock(ChunkMath.calcRelativeBlockPos(pos), block);
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This is neat! 🤓

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

It allows somewhat less explicit control over how intersecting lakes are dealt with than the previous approach, but it should also be much more efficient.

@RegisterPlugin
@Produces(LakeFacet.class)
@Updates({
@Facet(value = SurfacesFacet.class, border = @FacetBorder(sides = Lake.MAX_RADIUS * 3, bottom = Lake.MAX_DEPTH + 3, top = Lake.MAX_DEPTH + 3)),
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

A facet that is being updated is automatically also part of @Requires(...)?

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Yes, it's a bit like a combination of @Requires and @Produces, although I think there's a slight problem with borders and @Updates.

Comment on lines +98 to +101
SurfacesFacet surfacesFacet = region.getRegionFacet(SurfacesFacet.class);
DensityFacet densityFacet = region.getRegionFacet(DensityFacet.class);
ElevationFacet elevationFacet = region.getRegionFacet(ElevationFacet.class);
SeaLevelFacet seaLevelFacet = region.getRegionFacet(SeaLevelFacet.class);
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I like how you retrieved all the facets right in the beginning.

(just thinking out loud again)
This looks quite similar to the way we @ReceiveEvent and that it would be nice to write

@ProcessRegion
public void process(GeneratingRegion region, SurfacesFacet surfacesFacet, DensityFacet densityFacet, ...) {
	...
}

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I guess that would be possible. This pattern is very common in facet providers and rasterizers. The @Requires and @Updates annotations could even be moved here too, to reduce duplication a bit (e.g. something like replacing a SurfaceHeightFacet with an ElevationFacet would just require one change, rather than three).

Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

(dreamland mode off)

@4Denthusiast
Copy link
Contributor Author

I increased the minimum radius from 3 to 5, and increased the minimum depth a bit too so that one-block deep lakes are rarer. Lakes smaller than 10 blocks across are still quite common, due to the noise that's added, and technically even lakes of only 1 block are possible, but that would be extremely rare.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

Do not spawn lakes on steep slopes
2 participants