Ticket #4152: heightmapFix2016-12-3.patch

File heightmapFix2016-12-3.patch, 3.4 KB (added by FeXoR, 7 years ago)

Fixes as suggersted by elexis but the loop

  • binaries/data/mods/public/maps/random/heightmap/heightmap.js

     
    107107 * @param {array} [entityList=[g_Gaia.stoneLarge, g_Gaia.metalLarge]] - Entity/actor strings to be placed with placeObject()
    108108 * @param {integer} [maxTries=1000] - How often random player distributions are rolled to be compared
    109109 * @param {boolean} [isCircular=g_MapSettings.CircularMap] - If the map is circular or rectangular
     110 * @return {array} [placements] Array of points where entities were placed
    110111 */
    111112function distributeEntitiesByHeight(heightRange, avoidPoints, minDistance = 30, entityList = [g_Gaia.stoneLarge, g_Gaia.metalLarge], maxTries = 1000, heightmap = g_Map.height, isCircular = g_MapSettings.CircularMap)
    112113{
    113     let placements = deepcopy(avoidPoints);
    114     let validTiles = [];
     114    let validPoints = [];
    115115    let r = 0.5 * (heightmap.length - 1); // Map center x/y as well as radius
    116116    for (let x = minDistance; x < heightmap.length - minDistance; ++x)
     117    {
    117118        for (let y = minDistance; y < heightmap[0].length - minDistance; ++y)
    118             if (heightmap[x][y] > heightRange.min && heightmap[x][y] < heightRange.max) // Has the right height
    119                 if (!isCircular || r - getDistance(x, y, r, r) >= minDistance) // Is far enough away from map border
    120                     validTiles.push({ "x": x, "y": y });
     119        {
     120            // Has the right height
     121            if (heightmap[x][y] >= heightRange.min && heightmap[x][y] <= heightRange.max)
     122            {
     123                // Center of tile is far enough away from map border
     124                if (!isCircular || r - getDistance(x + 0.5, y + 0.5, r, r) >= minDistance)
     125                {
     126                    // Avoid avoidPoints by minDistance
     127                    let isValid = true;
     128                    for (let i = 0; i < avoidPoints.length; ++i)
     129                    {
     130                        if (getDistance(x + 0.5, y + 0.5, avoidPoints[i].x, avoidPoints[i].y) < minDistance)
     131                        {
     132                            isValid = false;
     133                            break;
     134                        }
     135                    }
     136                    if (isValid)
     137                        validPoints.push({ "x": x + 0.5, "y": y + 0.5 });
     138                }
     139            }
     140        }
     141    }
    121142
     143    let placements = [];
     144    if (!validPoints.length) // Early return if no valid poins found
     145    {
     146        log("No placement points found for the given arguments: " +  new Error().stack);
     147        return placements;
     148    }
     149
    122150    for (let tries = 0; tries < maxTries; ++tries)
    123151    {
    124         let tile = validTiles[randInt(validTiles.length)];
     152       
     153        let checkPointIndex = randInt(validPoints.length);
     154        let checkPoint = validPoints[checkPointIndex];
    125155        let isValid = true;
    126156        for (let p = 0; p < placements.length; ++p)
    127157        {
    128             if (getDistance(placements[p].x, placements[p].y, tile.x, tile.y) < minDistance)
     158            if (getDistance(placements[p].x, placements[p].y, checkPoint.x, checkPoint.y) < minDistance)
    129159            {
    130160                isValid = false;
    131161                break;
     
    133163        }
    134164        if (isValid)
    135165        {
    136             placeObject(tile.x, tile.y, entityList[randInt(entityList.length)], 0, randFloat(0, 2*PI));
    137             placements.push(tile);
     166            placeObject(checkPoint.x, checkPoint.y, entityList[randInt(entityList.length)], 0, randFloat(0, 2*PI));
     167            placements.push(checkPoint);
    138168        }
     169
     170        validPoints.splice(checkPointIndex);
     171        if (!validPoints.length) // No more valid points left
     172            break;
    139173    }
     174
     175    if (!placements.length)
     176        log("Nothing was placed: " +  new Error().stack);
     177
     178    return placements;
    140179}
    141180
    142181/**