Fix Loc_Space and allow direction parameter instead of just horizontal/vertical.

The old implementation was buggy as it would disallow the location if it had too much space (and PathFree2 returns nil). It also doesn't make sense to ask for a location that has space in either direction of a dimension because the location is not automatically adjusted to lie at the center of that space. For example, it would effectively cause fish to spawn directly at walls sometimes.
Controls
Sven Eberhardt 2015-07-31 00:33:57 -04:00
parent 0d48105b46
commit ed2e56c3fa
6 changed files with 20 additions and 21 deletions

View File

@ -25,7 +25,7 @@ func Place(int amount, proplist rectangle, proplist settings)
while ((amount > 0) && (--max_tries > 0))
{
var spot = FindLocation(Loc_Material("Water"), Loc_Space(50, false), loc_area);
var spot = FindLocation(Loc_Material("Water"), Loc_Space(20), loc_area);
if (!spot) continue;
f = CreateObjectAbove(this, spot.x, spot.y, NO_OWNER);

View File

@ -19,7 +19,7 @@ public func Place(int amount, proplist area, proplist settings)
// look for free underground spot to place groups of three or so..
while ((amount > 0) && (--max_tries > 0))
{
var spot = FindLocation(Loc_Tunnel(), Loc_Wall(CNAT_Bottom), Loc_Space(20, true), Loc_Func(LargeCaveMushroom.GoodSpot), loc_area);
var spot = FindLocation(Loc_Tunnel(), Loc_Wall(CNAT_Bottom), Loc_Space(20, CNAT_Top), Loc_Func(LargeCaveMushroom.GoodSpot), loc_area);
// can't place more
if (!spot && !terraform) return plants;

View File

@ -21,7 +21,7 @@ protected func Initialize()
for (var i=0; i<10; ++i)
{
// Find a good cave
cave_loc = FindLocation(Loc_InRect(50,LandscapeHeight()/6,LandscapeWidth()-100,LandscapeHeight()*17/25), Loc_Material("Tunnel"), Loc_Space(20), Loc_Space(20,true));
cave_loc = FindLocation(Loc_InRect(50,LandscapeHeight()/6,LandscapeWidth()-100,LandscapeHeight()*17/25), Loc_Material("Tunnel"), Loc_Space(10));
if (cave_loc)
{
// No other check point nearby?

View File

@ -132,11 +132,11 @@ global func Loc_Wall(int direction)
/*
returns a spot with enough space either vertically or horizontally.
For example Loc_Space(20, true) would only return points where a Clonk could stand.
For example Loc_Space(20, CNAT_Top) would only return points where a Clonk could stand.
*/
global func Loc_Space(int space, bool vertical)
global func Loc_Space(int space, int direction)
{
return [LOC_SPACE, space, vertical];
return [LOC_SPACE, space, direction ?? 0x0f];
}
global func FindLocation(condition1, ...)
@ -277,17 +277,16 @@ global func FindLocationConditionCheckIsValid(flag, x, y)
// has some space?
if (flag[0] == LOC_SPACE)
{
var xd = 0, yd = 0;
if (flag[2]) yd = flag[1];
else xd = flag[1];
var d1 = PathFree2(x, y, x + xd, y + yd);
var d2 = PathFree2(x, y, x - xd, y - yd);
var d = 0;
if (d1) d += Distance(x, y, d1[0], d1[1]);
if (d2) d += Distance(x, y, d2[0], d2[1]);
if (d >= flag[1]) return true;
return false;
var dist = flag[1], dirs = flag[2];
// if only one direction is given in one dimension, the other dimension is tested from a center point halfway off in that dimension
var cy = y + dist * ((dirs&CNAT_Bottom)/CNAT_Bottom - (dirs&CNAT_Top)/CNAT_Top) / 2;
var cx = x + dist * ((dirs&CNAT_Right)/CNAT_Right - (dirs&CNAT_Left)/CNAT_Left) / 2;
// check all desired directions
if (dirs & CNAT_Top) if (!PathFree(cx,y,cx,y-dist)) return false;
if (dirs & CNAT_Bottom) if (!PathFree(cx,y,cx,y+dist)) return false;
if (dirs & CNAT_Left) if (!PathFree(x,cy,x-dist,cy)) return false;
if (dirs & CNAT_Right) if (!PathFree(x,cy,x+dist,cy)) return false;
return true;
}
// invalid flag? always fulfilled

View File

@ -118,7 +118,7 @@ protected func InitializePlayer(int plr)
private func FindTopSpot()
{
return FindLocation(Loc_InRect(LandscapeWidth()/4,0,LandscapeWidth()/2,LandscapeHeight()/9), Loc_Wall(CNAT_Bottom), Loc_Space(10)) ?? {x=LandscapeWidth()/3+Random(30), y=LandscapeHeight()/12 };
return FindLocation(Loc_InRect(LandscapeWidth()/4,0,LandscapeWidth()/2,LandscapeHeight()/9), Loc_Wall(CNAT_Bottom), Loc_Space(10, CNAT_Top)) ?? {x=LandscapeWidth()/3+Random(30), y=LandscapeHeight()/12 };
}

View File

@ -188,7 +188,7 @@ global func FxGrowGemStalactitesTimer(object target, proplist effect, int time)
{
good_pos = false;
var dist = 64; // distance from border
pos = FindLocation(Loc_Sky(), Loc_Wall(CNAT_Top), Loc_Space(8), Loc_InRect(dist, dist, LandscapeWidth() - 2 * dist, LandscapeHeight() - 2 * dist));
pos = FindLocation(Loc_Sky(), Loc_Wall(CNAT_Top), Loc_Space(8, CNAT_Bottom | CNAT_Left | CNAT_Right), Loc_InRect(dist, dist, LandscapeWidth() - 2 * dist, LandscapeHeight() - 2 * dist));
if (!pos)
continue;
@ -411,7 +411,7 @@ private func ProvideIsland(array island, int number, int amount)
// All of the islands have a few in-earth loam pieces.
PlaceObjects(Loam, amount + RandomX(1, 3), "Earth", island[0], island[1], island[2], island[3]);
var spot = FindLocation(Loc_InRect(island[0], island[1], island[2], island[3] / 2), Loc_Wall(CNAT_Bottom), Loc_Space(20), Loc_Sky());
var spot = FindLocation(Loc_InRect(island[0], island[1], island[2], island[3] / 2), Loc_Wall(CNAT_Bottom), Loc_Space(20, CNAT_Left | CNAT_Right | CNAT_Top), Loc_Sky());
if (!spot)
return 0;
@ -471,7 +471,7 @@ private func ProvideIsland(array island, int number, int amount)
// For all the islands some decoration.
if (!Random(3))
{
var spot = FindLocation(Loc_InRect(island[0], island[1], island[2], island[3] / 2), Loc_Wall(CNAT_Bottom), Loc_Space(20), Loc_Sky());
var spot = FindLocation(Loc_InRect(island[0], island[1], island[2], island[3] / 2), Loc_Wall(CNAT_Bottom), Loc_Space(20, CNAT_Top | CNAT_Left | CNAT_Right), Loc_Sky());
if (spot)
CreateObjectAbove(Column, spot.x, spot.y);
}