Snippet Bounds

Sevion

The DIY Ninja
Reaction score
413
JASS:
/*Utility Information
//===================================================================
Name: Bounds
Version: 1.2
Author: Sevion

Settings:
*/ //===================================================================
//! textmacro BOUNDS_BUFFER
    private constant real BUFFER = 0.
//! endtextmacro
/* //===================================================================

Description: World bounds and buffer safety with inline friendly functions.

Requirements: None

Installation: (N/A)

Variables:
-BUFFER
    The buffer distance from the actual world bounds and safety.
    Set to 0. for no difference. Can be used Directly instead.

-World
    The rect containing the world. Can be used Directly instead.

-WorldReg
    The region containing the world. Can be used Directly instead.

-Max_X
    The real comtaining the maximum X. Can be used Direclty instead.

-Min_X
    The real comtaining the minimum X. Can be used Direclty instead.

-Max_Y
    The real comtaining the maximum Y. Can be used Direclty instead.

-Min_Y
    The real comtaining the minimum Y. Can be used Direclty instead.

Functions:
------------------------------------------------------------------
-Bs_IsPosSafe(x, y) returns boolean
    Evaluates if the given x and y coordinates are within safety
    range.
    if Bs_IsPosSafe(GetUnitX(u), GetUnitY(u) then

-Bs_IsLocSafe(location) returns boolean
    Evaluates if the given location is within safety range.
    if Bs_isLocSafe(GetUnitLoc(u)) then

-Bs_SetUnitPosSafe(unit, x, y) returns nothing
    Evaluates if the given x and y coordinates is within safety
    range then sets the unit's position to that or displays a
    debug error.
    call Bs_SetUnitPosSafe(u, 0., 0.)

-Bs_SetUnitLocSafe(unit, location) returns nothing
    Evaluates if the given location is within safety range
    then sets the unit's location to that or displays a debug error.
    call Bs_SetUnitLocSafe(u, Location(0, 0))
------------------------------------------------------------------*/
//===================================================================

library Bounds initializer Initialization
    globals
        public rect World
        public region WorldReg
        //! runtextmacro BOUNDS_BUFFER()
        public real Max_X
        public real Min_X
        public real Max_Y
        public real Min_Y
    endglobals

    public function IsPosSafe takes real x, real y returns boolean
        return IsPointInRegion(WorldReg, x ,y)
    endfunction

    public function IsLocSafe takes location loc returns boolean
        return IsLocationInRegion(WorldReg, loc)
    endfunction

    public function SetUnitPosSafe takes unit u, real x, real y returns nothing
        if IsPointInRegion(WorldReg, x, y) then
            call SetUnitPosition(u, x, y)
            return
        endif
        debug call DisplayTextToPlayer(GetLocalPlayer(), 0, 0, SCOPE_PREFIX + "ERROR - Unsafe Pos!")
    endfunction

    public function SetUnitLocSafe takes unit u, location loc returns nothing
        if IsLocationInRegion(WorldReg, loc) then
            call SetUnitPositionLoc(u, loc)
            return
        endif
        debug call DisplayTextToPlayer(GetLocalPlayer(), 0, 0, SCOPE_PREFIX + "ERROR - Unsafe Loc!")
    endfunction

    private function Initialization takes nothing returns nothing
        set World = GetWorldBounds()
        set Max_X = GetRectMaxX(World) - BUFFER
        set Min_X = GetRectMinX(World) + BUFFER
        set Max_Y = GetRectMaxY(World) - BUFFER
        set Min_Y = GetRectMinY(World) + BUFFER
        set WorldReg = CreateRegion()
        call RegionAddRect(WorldReg, World)
    endfunction
endlibrary
 

Sevion

The DIY Ninja
Reaction score
413
Hmm. Got a link? I can't find anything with Search. I've looked for "Borderizer" only. Though, that's the name of an icon tool, too. >_>
 

Hatebreeder

So many apples
Reaction score
381
Well, I found it under Boarder safety, though, there is no official thread about this sniplett.
I posted Cohadars Boarder system below, but i'm not sure if this is Ok with him.

JASS:
//==============================================================================
//  Border by Cohadar - v2.0
//==============================================================================
//
//  PURPOUSE:
//       * Automatically prevents crashes caused by units getting off map
//       * Also provides a set of functions for safe unit movement
//
//  FUNCTION LIST:
//         Border_GetSafeX(real) -> real
//         Border_GetSafeY(real) -> real
//
//         Border_SetUnitXSafe(unit, x)
//         Border_SetUnitYSafe(unit, x)
//         Border_SetUnitPositionSafe(unit, x, y)
//
//  PROS: 
//       * Safe Set functions preserve current orderId of unit
//         This means that units can attack while being moved with triggers.
//
//       * You will get a warning message if some unit tries to get off-map
//         It means that you were using unsafe functions somewhere.
//
//       * Units that try to leave map will be automatically returned on map border
//
//  CONS:
//       * none?
//
//  HOW TO IMPORT:
//       * Just create a trigger named Border
//       * convert it to text and replace the whole trigger text with this one
//
//==============================================================================

library Border initializer Init

globals
    real MapMaxX
    real MapMaxY
    real MapMinX
    real MapMinY
endglobals


//==============================================================================
public function GetSafeX takes real x returns real
    if x < MapMinX then
        return MapMinX
    endif
    if x > MapMaxX then
        return MapMaxX
    endif
    return x
endfunction

//==============================================================================
public function GetSafeY takes real y returns real
    if y < MapMinY then
        return MapMinY
    endif
    if y > MapMaxY then
        return MapMaxY
    endif
    return y
endfunction

//==============================================================================
public function SetUnitXSafe takes unit whichUnit, real x returns nothing
    if x < MapMinX then
        call SetUnitX(whichUnit, MapMinX)
    elseif x > MapMaxX then
        call SetUnitX(whichUnit, MapMaxX)
    else
        call SetUnitX(whichUnit, x)
    endif
endfunction

//==============================================================================
public function SetUnitYSafe takes unit whichUnit, real y returns nothing
    if y < MapMinY then
        call SetUnitY(whichUnit, MapMinY)
    elseif y > MapMaxY then
        call SetUnitY(whichUnit, MapMaxY)
    else
        call SetUnitY(whichUnit, y)
    endif
endfunction

//==============================================================================
public function SetUnitPositionSafe takes unit whichUnit, real x, real y returns nothing
    if x < MapMinX then
        call SetUnitX(whichUnit, MapMinX)
    elseif x > MapMaxX then
        call SetUnitX(whichUnit, MapMaxX)
    else
        call SetUnitX(whichUnit, x)
    endif
    
    if y < MapMinY then
        call SetUnitY(whichUnit, MapMinY)
    elseif y > MapMaxY then
        call SetUnitY(whichUnit, MapMaxY)
    else
        call SetUnitY(whichUnit, y)
    endif
endfunction


//===========================================================================
private function Init takes nothing returns nothing
    local trigger trig = CreateTrigger()
    set MapMaxX = GetRectMaxX(bj_mapInitialPlayableArea)
    set MapMaxY = GetRectMaxY(bj_mapInitialPlayableArea)
    set MapMinX = GetRectMinX(bj_mapInitialPlayableArea)
    set MapMinY = GetRectMinY(bj_mapInitialPlayableArea)    
endfunction    

endlibrary
 

Sevion

The DIY Ninja
Reaction score
413
Hmm. Mine has more features :p

Plus, it is inline friendly.

And mine is faster all around ;)
 

Azlier

Old World Ghost
Reaction score
461
JASS:
public constant function isPosSafe takes real x, real y returns boolean
    return (x>=min_X and x<=max_X) and (y>=min_Y and y<=max_Y)
endfunction

FYI, this is not inline friendly.
 

Azlier

Old World Ghost
Reaction score
461
JASS:
public constant function isXSafe takes real x returns boolean
    return (x>=min_X and x<=max_X)
endfunction

public constant function isYSafe takes real y returns boolean
    return (y>=min_Y and y<=max_Y)
endfunction

Not these. So, the most used functions are not inline friendly. Loveleh.

JASS:
debug call DisplayTextToPlayer(GetLocalPlayer(), 0, 0, SCOPE_PREFIX + "ERROR - Unsafe X!")

If debug mode is on, these are displayed with every single call, whether it's safe or not.

...Why does that debug message even exist?

JASS:
public constant rect WORLD  = GetWorldBounds()
//! runtextmacro BOUNDS_BUFFER()
public constant real MAX_X  = GetRectMaxX(WORLD) - BUFFER
public constant real MIN_X  = GetRectMinX(WORLD) + BUFFER
public constant real MAX_Y  = GetRectMaxY(WORLD) - BUFFER
public constant real MIN_Y  = GetRectMinY(WORLD) + BUFFER

WRONG. Unconstantize those, or the optimizer will inline them and you get mass leaks and lose efficiency.
 

Sevion

The DIY Ninja
Reaction score
413
Updated to fix some of the function and variable names.

Updated to not display the errors if it's safe. I forgot to add "return" :eek:

Updated so the optimizer doesn't inline the globals.

Edit:

I hate it when you edit like that.

Cuz then I don't know when you've posted something new :( So I have to keep refreshing until I find something new >_<
 

Viikuna

No Marlo no game.
Reaction score
265
Id rather use some general system for moving stuff, and have some UnitLeaveRegion event for calling correct methods for each object or unit, but I guess something like this is usefull if you dont have systems like that, and you trigger movement for each spell or script separately.
 

Sevion

The DIY Ninja
Reaction score
413
That's really what this is for. Checking safety for triggered movement :p

If you want something for non-triggered movement, just use something like Bound Sentinel by Vexorian. It triggers on rect leave and moves the unit back in.
 

Romek

Super Moderator
Reaction score
963
Why have you suddenly adopted Nestharus-coding-style?

Note that you can declare a globals block more than once.
Naming constant functions which you expect users to use in all-caps looks horrible. There's no need whatsoever for that constant keyword as a matter of fact.
camelCase shouldn't be used for function names, at all.

Frankly, I don't care how you name your stuff if it's all private, but when the methods are public and you expect people to use them, it really helps if you stick to the standard vJASS naming conventions. It makes it easier to use.

You even copied Nestharus' headers and stuff. What's wrong with you? o_O

> library Bs
Other than a pretty rude word/phrase, I can't figure out what this stands for.
Oh, wait. Nestharus does that.
 

Sevion

The DIY Ninja
Reaction score
413
o_o'

I don't see what's wrong about using camelCase for function names. I don't see why you disapprove of this coding style. It's neat and contained. Constants should be capitalized. It's a pretty generalized convention.

The library name is:

B-Bounds
s-Sevion

Just because I know nothing ever gets approved when the mod doesn't like how the function is named, I'll change them...
 

Romek

Super Moderator
Reaction score
963
> I don't see why you disapprove of this coding style. It's neat and contained.
A coding style which everyone else uses would be preferred, especially when other people are the ones who will be using the system.

> Constants should be capitalized.
When 50% of the functions are constants, and the other 50% aren't, it's silly.
It's also difficult to even tell which of your functions are/aren't constant from just the names, as you put 'constant' in whenever it doesn't syntax.
ALL_CAPS constants are good and all in configurables and such, but not when used like this.

On a somewhat related note, what's the point in those GETSOMETHING functions if the values they return are public anyway?
 

quraji

zap
Reaction score
144
On a somewhat related note, what's the point in those GETSOMETHING functions if the values they return are public anyway?

Just so they look like constants I guess..I would understand that but having a constant-like name (all caps) then having to use function syntax is lame.
call whatever(CONSTANT) > call whatever(CONSTANT())

Maybe you can use a struct for it's syntax.
 

Sevion

The DIY Ninja
Reaction score
413
Updated to conform with "the norm".

Removed Get functions because no one liked them.
 

Renendaru

(Evol)ution is nothing without love.
Reaction score
309
Is it just me or is IsXSafe non-existent in that code?
 

Jesus4Lyf

Good Idea™
Reaction score
397
I'm currently intending to graveyard this soon.
Description: World bounds and buffer safety with inline friendly functions.
That's an awfully strange thing to say for a snippet that has no inlining functions (none).

The right way to do this is put BoundSentinel into your map. Should rip it off and make it use world bounds or something instead. :)

Checking the safety before moving the unit is just the wrong way to do it. Especially when it calls something like 5 functions to check.
 

Azlier

Old World Ghost
Reaction score
461
BoundSentinel COULD be improved, but this is not the way to do it.
 
General chit-chat
Help Users
  • No one is chatting at the moment.

      The Helper Discord

      Members online

      Affiliates

      Hive Workshop NUON Dome World Editor Tutorials

      Network Sponsors

      Apex Steel Pipe - Buys and sells Steel Pipe.
      Top