How can I find the height of the ground in Lua?

Kodiologist
Member
 
Posts: 13
Joined: Fri Dec 27, 2013 18:06

How can I find the height of the ground in Lua?

by Kodiologist » Fri Jan 03, 2014 02:20

The application here is that I'm writing a game that randomly chooses node positions the player is supposed to visit. The x- and z-coordinates are chosen without regard for terrain, but I'd like to choose the y-coordinate to be 1 unit above ground level at that point. So if the mapgen happens to make a mountain there, you'd have to climb it, or if the mapgen makes a lake there, you'd have to swim to the lakebed.

The Mapgen class seems to have a getGroundLevelAtPoint method at the C++ level, but it seems inaccessible to mods.

minetest.register_on_generated seems difficult to use for this purpose because the first generated slice of map including the (x, z) coordinates in question may not include the ground-level y-coordinate.
 

Nore
Member
 
Posts: 468
Joined: Wed Nov 28, 2012 11:35
GitHub: Ekdohibs

by Nore » Fri Jan 03, 2014 09:00

There was a pull request about that, but it was not merged: https://github.com/minetest/minetest/pull/640
The other possibility is to start somewhere in the ground (like y = -100), and while the light is less than 15 (sunlight), increase y. You then have ground level... (however, you need to wait that the area is generated before doing that...)
 

User avatar
aldobr
Member
 
Posts: 316
Joined: Sun Nov 25, 2012 05:46

by aldobr » Fri Jan 03, 2014 09:32

start at 0 heigth.

if node is air, walk node by node, decreasing heigth by one until node no longer is air.
z positon is current position + 1
if node is not air, walk node by node, increasng heigth by one until node is air.
z position is current position
 

Kodiologist
Member
 
Posts: 13
Joined: Fri Dec 27, 2013 18:06

by Kodiologist » Fri Jan 03, 2014 13:22

Nore wrote:There was a pull request about that, but it was not merged


Rats.

Lazy map generation seems to be the chief obstacle here. (x, -100, z) may well never be generated if the player doesn't dig down there. Similar concerns apply to your solution, aldobr. Is there any way to force generation of a map chunk containing a given node position?
 

Nore
Member
 
Posts: 468
Joined: Wed Nov 28, 2012 11:35
GitHub: Ekdohibs

by Nore » Fri Jan 03, 2014 13:41

You can always know if the player is above or below the level of ground (except lakebeds) by looking at the sunlight. So: if the player is somewhere where there is no sunlight, you know he is below ground level, etc.
 

paramat
Member
 
Posts: 2662
Joined: Sun Oct 28, 2012 00:05
GitHub: paramat

by paramat » Fri Jan 03, 2014 17:18

Until the terrain generates at a particular distant x z location, the y value of ground level is undefined, the only way to know that in advance is to rewrite mapgen v6 in lua and do the perlin noise calculations to see where ground level will be, this is possible (i could do it but not interested) but not easy.
I rely on donations to help provide an income https://forum.minetest.net/viewtopic.php?f=3&t=14935
 

Sokomine
Member
 
Posts: 2980
Joined: Sun Sep 09, 2012 17:31

by Sokomine » Fri Jan 03, 2014 19:29

Hybrid Dog wrote:It wouldn't work if you redefine water to let sunlight through it.

In such a case, checking one node above might be enough. Perhaps the original poster doesn't care about positions on water anyway.
A list of my mods can be found here.
 

Kodiologist
Member
 
Posts: 13
Joined: Fri Dec 27, 2013 18:06

by Kodiologist » Sat Jan 04, 2014 01:53

Great, I seem to have been able to get this to work by checking the light level (as you suggested, Nore) along with a manual check for water. Here's my implementation in MoonScript:

Your phone or window isn't wide enough to display the code box. If it's a phone, try rotating it to landscape mode.
Code: Select all
MAX_LIGHT = 15
NOON = .5

waypoints = for _ = 1, 1
   {created: false,
    ymin: -1/0,  -- negative infinity
    ymax: 1/0,   -- positive infinity
    pos: {x: 5, z: 5}}
--waypoints = for _ = 1, 2
--   {created: false,
--    ymin: -1/0,    -- negative infinity
--    ymax: 1/0,   -- positive infinity
--    pos: {
--        x: (if coinflip! then 1 else -1) * math.random(100, 200),
--        z: (if coinflip! then 1 else -1) * math.random(100, 200)}}

minetest.register_on_generated (minp, maxp, blockseed) ->
    for wp in *waypoints
        if not wp.created and do
                wp.pos.x >= minp.x and wp.pos.x <= maxp.x and do
                wp.pos.z >= minp.z and wp.pos.z <= maxp.z
            for y = minp.y, maxp.y
                here = {x: wp.pos.x, y: y, z: wp.pos.z}
                if minetest.get_node_light(here, NOON) == MAX_LIGHT or do
                        minetest.get_node(here).name == 'default:water_source'
                    wp.ymax = math.min wp.ymax, y
                else
                    wp.ymin = math.max wp.ymin, y + 1
            if wp.ymin == wp.ymax
                wp.pos.y = wp.ymin
                wp.created = true
Last edited by Kodiologist on Sat Jan 04, 2014 02:13, edited 1 time in total.
 


Return to WIP Mods

Who is online

Users browsing this forum: No registered users and 8 guests

cron