Jump to content
Sign in to follow this  
Schatten

Function to get empty position

Recommended Posts

Function to get empty position for object.

Parameters:

_this select 0 - object's max size, number;

_this select 1 - circle's center position in which search will occur, position3D;

_this select 2 - minimum distance between circle's center and object, number;

_this select 3 - maximum distance between circle's center and object, number;

_this select 4 - minimum distance between object and other objects, number;

_this select 5 - maximum terrain gradient under object, number;

_this select 6 - water mode, number:

0 - can not be in water;

1 - can be in water;

2 - must be in water;

_this select 7 - shore mode, boolean:

true - must be on shore;

false - must not be on shore;

Function returns array with coordinates of empty position in format Position3D where Z coordinate is zero or empty array if not found.

Example:

_position = [_vehicleMaxSize, _markerPosition, 0, _markerSize - _vehicleMaxSize, 1, 0.5, 0, false] call getEmptyPosition;

private ["_angle", "_angle0", "_angle1", "_array", "_canBeOnShore", "_centerPosition", "_distance", "_dx", "_dy", "_emptyPosition", "_index", "_maxDistFromCenter", "_maxGradient", "_minDistFromCenter", "_minDistToObjects", "_objectMaxSize", "_position", "_positionNumber", "_positionsNumber", "_positionsNumbers", "_subarray", "_waterMode"];

_array = [];
_emptyPosition = [];

_objectMaxSize = _this select 0;
_centerPosition = _this select 1;
_minDistFromCenter = _this select 2;
_maxDistFromCenter = _this select 3;
_minDistToObjects = _this select 4;
_maxGradient = _this select 5;
_waterMode = _this select 6;
_canBeOnShore = _this select 7;

if (_minDistToObjects < _objectMaxSize / 2) then {_minDistToObjects = _objectMaxSize / 2};

_distance = _minDistFromCenter + _objectMaxSize / 2;

while {_distance <= (_maxDistFromCenter + _objectMaxSize / 2)} do {
_positionsNumber = floor (180 / (asin (_objectMaxSize / (2 * _distance))));

if (_positionsNumber > 1) then {
	_angle0 = floor (random 360);

	_angle1 = 2 * (asin (_objectMaxSize / (2 * _distance)));

	_array set [count _array, [_distance, _angle0, _angle1, _positionsNumber, []]];
};

_distance = _distance + _objectMaxSize;
};

while {(count _array) > 0} do {
_positionNumber = -1;

_index = floor (random (count _array));

_subarray = _array select _index;

_distance = _subarray select 0;
_angle0 = _subarray select 1;
_angle1 = _subarray select 2;
_positionsNumber = _subarray select 3;
_positionsNumbers = _subarray select 4;

while {true} do {
	_positionNumber = floor (random _positionsNumber);

	if (!(_positionNumber in _positionsNumbers)) exitWith {};
};

_angle = _angle0 + _positionNumber * _angle1;

_dx = _distance * (sin _angle);
_dy = _distance * (cos _angle);

_position = [(_centerPosition select 0) + _dx, (_centerPosition select 1) + _dy, 0];

if (
	((count (_position isFlatEmpty [_minDistToObjects, 0, _maxGradient, _objectMaxSize, _waterMode, _canBeOnShore, objNull])) > 0)
and
	{(count (nearestObjects [_position, ["Air", "LandVehicle"], _minDistToObjects])) == 0}
)
exitWith {_emptyPosition = _position};

_positionsNumbers set [count _positionsNumbers, _positionNumber];

if ((count _positionsNumbers) < _positionsNumber) then {(_array select _index) set [4, _positionsNumbers]} else {_array = [_array, _index] call BIS_fnc_removeIndex};
};

_emptyPosition

Share this post


Link to post
Share on other sites

I am sure that in this function position chosen randomly. Because of this, within one call positions can be repeated.

In addition, this function is no check existing other vehicles nearby. Because of this, there may be times when vehicles are in one another.

My function does not have these disadvantages.

Share this post


Link to post
Share on other sites

Ok cool, I was just wondering if it may have been the basis of your function, as quite a few of the parameters are similar, but it looks like the alterations are for the better :D

Could I recommend to you to use BIS_fnc_param on your parameters coming in, it would just make it more "idiot" proof, as well as allow for default values to come in, so that way if an undefined value comes in you could exitWith and error, but just a recommendation :p.

i.e.

_objectMaxSize = [_this, 0, 30, [0]] call BIS_fnc_param;//same as (_this select 0) but with a default value of 30, and only allows numbers to come in
_centerPosition = [_this, 1, [], [[]]] call BIS_fnc_param;//same as (_this select 1) but with a default value of an empty array, and only allows arrays to come in

if (count _centerPosition < 3) exitWith {hint "No 3D position defined.";};//checks if there are 3 elements in the position array, if not, exit with an error.

Edited by JShock

Share this post


Link to post
Share on other sites

Thanks, but I'll leave it to the discretion of those who will use my function. )

Share this post


Link to post
Share on other sites

Please sign in to comment

You will be able to leave a comment after signing in



Sign In Now
Sign in to follow this  

×