forked from Mirrorlandia_minetest/minetest
* possibly improved water flow, by flyx86
- When flowing liquid starts to flow down, it stops contributing to its neighboring nodes' liquid level (possibly transforming it back to air) - Flowing liquid turns into a source if there are at least 2 adjacent liquid source nodes - If a new liquid flow reaches existing flowing liquid, the existing liquid is now updated properly.
This commit is contained in:
parent
5383aa847f
commit
5146c826be
@ -276,6 +276,7 @@ void content_mapnode_init()
|
|||||||
f->buildable_to = true;
|
f->buildable_to = true;
|
||||||
f->liquid_type = LIQUID_FLOWING;
|
f->liquid_type = LIQUID_FLOWING;
|
||||||
f->liquid_alternative_flowing = CONTENT_WATER;
|
f->liquid_alternative_flowing = CONTENT_WATER;
|
||||||
|
f->liquid_alternative_source = CONTENT_WATERSOURCE;
|
||||||
|
|
||||||
i = CONTENT_WATERSOURCE;
|
i = CONTENT_WATERSOURCE;
|
||||||
f = &content_features(i);
|
f = &content_features(i);
|
||||||
@ -307,6 +308,7 @@ void content_mapnode_init()
|
|||||||
f->liquid_type = LIQUID_SOURCE;
|
f->liquid_type = LIQUID_SOURCE;
|
||||||
f->dug_item = std::string("MaterialItem ")+itos(i)+" 1";
|
f->dug_item = std::string("MaterialItem ")+itos(i)+" 1";
|
||||||
f->liquid_alternative_flowing = CONTENT_WATER;
|
f->liquid_alternative_flowing = CONTENT_WATER;
|
||||||
|
f->liquid_alternative_source = CONTENT_WATERSOURCE;
|
||||||
|
|
||||||
i = CONTENT_TORCH;
|
i = CONTENT_TORCH;
|
||||||
f = &content_features(i);
|
f = &content_features(i);
|
||||||
|
44
src/map.cpp
44
src/map.cpp
@ -1204,16 +1204,24 @@ void Map::removeNodeAndUpdate(v3s16 p,
|
|||||||
|
|
||||||
/*
|
/*
|
||||||
Add neighboring liquid nodes to transform queue.
|
Add neighboring liquid nodes to transform queue.
|
||||||
|
|
||||||
|
Also add horizontal neighbors of node on top of removed node
|
||||||
|
because they could be affected of the water on top flowing
|
||||||
|
down instead of into them.
|
||||||
*/
|
*/
|
||||||
v3s16 dirs[6] = {
|
v3s16 dirs[10] = {
|
||||||
v3s16(0,0,1), // back
|
v3s16(0,0,1), // back
|
||||||
v3s16(0,1,0), // top
|
v3s16(0,1,0), // top
|
||||||
|
v3s16(1,1,0), // topright
|
||||||
|
v3s16(-1,1,0), // topleft
|
||||||
|
v3s16(0,1,1), // topback
|
||||||
|
v3s16(0,1,-1), // topfront
|
||||||
v3s16(1,0,0), // right
|
v3s16(1,0,0), // right
|
||||||
v3s16(0,0,-1), // front
|
v3s16(0,0,-1), // front
|
||||||
v3s16(0,-1,0), // bottom
|
v3s16(0,-1,0), // bottom
|
||||||
v3s16(-1,0,0), // left
|
v3s16(-1,0,0), // left
|
||||||
};
|
};
|
||||||
for(u16 i=0; i<6; i++)
|
for(u16 i=0; i<10; i++)
|
||||||
{
|
{
|
||||||
try
|
try
|
||||||
{
|
{
|
||||||
@ -1510,6 +1518,9 @@ void Map::transformLiquids(core::map<v3s16, MapBlock*> & modified_blocks)
|
|||||||
// Turn possible source into non-source
|
// Turn possible source into non-source
|
||||||
u8 nonsource_c = make_liquid_flowing(n0.d);
|
u8 nonsource_c = make_liquid_flowing(n0.d);
|
||||||
|
|
||||||
|
// Counts surrounding liquid source blocks
|
||||||
|
u8 surrounding_sources = 0;
|
||||||
|
|
||||||
/*
|
/*
|
||||||
If not source, check that some node flows into this one
|
If not source, check that some node flows into this one
|
||||||
and what is the level of liquid in this one
|
and what is the level of liquid in this one
|
||||||
@ -1547,7 +1558,9 @@ void Map::transformLiquids(core::map<v3s16, MapBlock*> & modified_blocks)
|
|||||||
}
|
}
|
||||||
bool n2_is_source = !content_flowing_liquid(n2.d);
|
bool n2_is_source = !content_flowing_liquid(n2.d);
|
||||||
s8 n2_liquid_level = 8;
|
s8 n2_liquid_level = 8;
|
||||||
if(n2_is_source == false)
|
if(n2_is_source)
|
||||||
|
surrounding_sources++;
|
||||||
|
else
|
||||||
n2_liquid_level = n2.param2 & 0x07;
|
n2_liquid_level = n2.param2 & 0x07;
|
||||||
|
|
||||||
s8 new_liquid_level = -1;
|
s8 new_liquid_level = -1;
|
||||||
@ -1560,9 +1573,22 @@ void Map::transformLiquids(core::map<v3s16, MapBlock*> & modified_blocks)
|
|||||||
new_liquid_level = n2_liquid_level + WATER_DROP_BOOST;
|
new_liquid_level = n2_liquid_level + WATER_DROP_BOOST;
|
||||||
}
|
}
|
||||||
else if(n2_liquid_level > 0)
|
else if(n2_liquid_level > 0)
|
||||||
|
{
|
||||||
|
// If the neighbor node isn't a source and flows downwards,
|
||||||
|
// it doesn't flow into this node
|
||||||
|
if (n2_is_source)
|
||||||
{
|
{
|
||||||
new_liquid_level = n2_liquid_level - 1;
|
new_liquid_level = n2_liquid_level - 1;
|
||||||
}
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
// Node below n2
|
||||||
|
MapNode n3 = getNodeNoEx(p2 + v3s16(0,-1,0));
|
||||||
|
// NOTE: collision of different liquids not yet handled here.
|
||||||
|
if (content_features(n3.d).liquid_type != LIQUID_FLOWING)
|
||||||
|
new_liquid_level = n2_liquid_level - 1;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
if(new_liquid_level > new_liquid_level_max)
|
if(new_liquid_level > new_liquid_level_max)
|
||||||
new_liquid_level_max = new_liquid_level;
|
new_liquid_level_max = new_liquid_level;
|
||||||
@ -1577,9 +1603,14 @@ void Map::transformLiquids(core::map<v3s16, MapBlock*> & modified_blocks)
|
|||||||
If liquid level should be something else, update it and
|
If liquid level should be something else, update it and
|
||||||
add all the neighboring water nodes to the transform queue.
|
add all the neighboring water nodes to the transform queue.
|
||||||
*/
|
*/
|
||||||
if(new_liquid_level_max != liquid_level)
|
if(new_liquid_level_max != liquid_level || (!is_source && surrounding_sources >= 2))
|
||||||
{
|
{
|
||||||
if(new_liquid_level_max == -1)
|
if (surrounding_sources >= 2)
|
||||||
|
{
|
||||||
|
n0.d = content_features(n0.d).liquid_alternative_source;
|
||||||
|
setNode(p0,n0);
|
||||||
|
}
|
||||||
|
else if(new_liquid_level_max == -1)
|
||||||
{
|
{
|
||||||
// Remove water alltoghether
|
// Remove water alltoghether
|
||||||
n0.d = CONTENT_AIR;
|
n0.d = CONTENT_AIR;
|
||||||
@ -1589,6 +1620,7 @@ void Map::transformLiquids(core::map<v3s16, MapBlock*> & modified_blocks)
|
|||||||
else
|
else
|
||||||
{
|
{
|
||||||
n0.param2 = new_liquid_level_max;
|
n0.param2 = new_liquid_level_max;
|
||||||
|
liquid_level = new_liquid_level_max;
|
||||||
setNode(p0, n0);
|
setNode(p0, n0);
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -1706,7 +1738,7 @@ void Map::transformLiquids(core::map<v3s16, MapBlock*> & modified_blocks)
|
|||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
if(liquid_next_level > liquid_level)
|
if(liquid_next_level > n2_liquid_level)
|
||||||
{
|
{
|
||||||
n2.param2 = liquid_next_level;
|
n2.param2 = liquid_next_level;
|
||||||
setNode(p2, n2);
|
setNode(p2, n2);
|
||||||
|
@ -141,8 +141,10 @@ struct ContentFeatures
|
|||||||
NodeMetadata *initial_metadata;
|
NodeMetadata *initial_metadata;
|
||||||
|
|
||||||
// If the content is liquid, this is the flowing version of the liquid.
|
// If the content is liquid, this is the flowing version of the liquid.
|
||||||
// If content is liquid, this is the same content.
|
// If content is flowing liquid, this is the same content.
|
||||||
u8 liquid_alternative_flowing;
|
u8 liquid_alternative_flowing;
|
||||||
|
// If the content is liquid, this is the source version of the liquid.
|
||||||
|
u8 liquid_alternative_source;
|
||||||
|
|
||||||
// Amount of light the node emits
|
// Amount of light the node emits
|
||||||
u8 light_source;
|
u8 light_source;
|
||||||
|
Loading…
Reference in New Issue
Block a user