-------------------------------------------------------------------------------
--  Common methods used in scripts
-------------------------------------------------------------------------------

-- returns current mouse position
function getCursorPos()
    local rootwnd = obj( "srv.wnd" )
    local x = tonumber( get( rootwnd, "mousex" ) )
    local y = tonumber( get( rootwnd, "mousey" ) )
    return x, y
end

--  shows/hides in-game cursor
function showCursor( bShow )
    if bShow == false then
        set( "GameCursor", "visible", "false" )
    else
        set( "GameCursor", "visible", "true" )
    end
end

function isCursorVisible()
    return (get("GameCursor", "visible") == "true")
end

function setCursorPos( x, y )
    local pos = x .. "," .. y
    set( "GameCursor", "position", pos )
end

function getCursor()
    return get( "GameCursor", "Active" )
end

function setCursor( cursor )
    set( "game", "cursor", cursor )
end

--  returns value clamped to given bounds
function clamp( x, minv, maxv )
    local res
    if x < minv then 
        res = minv
    elseif x > maxv then 
        res = maxv
    else
        res = x
    end
    return res
end

--  returns uniform random number in range
function rand( minv, maxv )
	local r = math.random()
	return minv + r*(maxv - minv)
end

--  returns random element from the array
function randEl( tArr )
    if tArr == nil or  #tArr == 0 then 
        do return nil end 
    end
	return tArr[math.random( #tArr )]
end

function randSeed()
    math.randomseed( os.time() )
    math.random() 
    math.random() 
    math.random()
end

--  shows (hides) array of object references
function showObjects( objArr, bShow )
    local sShow = "true"
    if bShow == false then 
        sShow = "false" 
    end
    for i = 1, #objArr do
		set( objArr[i], "visible", sShow )
	end
end

--  deletes all objects in the object array
function delObjects( objArr )
    if objArr ~= nil then 
        for i, f in ipairs( objArr ) do
            delete( f )
        end
    end
end

--  sets property value to all objects in the array
function setObjects( objArr, prop, val )
    if objArr ~= nil then 
        for i, f in ipairs( objArr ) do
            set( f, prop, val )
        end
    end
end

--  find object by name in objects array
function findObject( objArr, name )
    local res = nil
    for i = 1, #objArr do
		if get( objArr[i], "name" ) == name then
            res = objArr[i]
        end
	end
    return res
end
    
--  performs random permutation of the array (inplace Fisher-Yates shuffle)
function shuffle( arr )
    for i = #arr, 1, -1 do
        local j = math.random( 1, i )
        if i ~= j then 
            arr[i], arr[j] = arr[j], arr[i]
        end
	end
end

--  connects a slot from array of objects to processing function
function connectObjects( objArr, slot, processFn )
    if (objArr == nil) then return end
    for i, f in ipairs( objArr ) do
        connect( f, slot, processFn )
	end
end

function map(func, array)
    local new_array = {}
    for i,v in ipairs(array) do
        new_array[i] = func(v)
    end
    return new_array
end

function reduce(func, initVal, array)
    local val = initVal
    for i,v in ipairs(array) do
        val = func(val, v)
    end
    return val
end

function findpattern(text, pattern, start)
    return string.sub(text, string.find(text, pattern, start))
end

function parseVec2( str )
    if (str == nil) then
        return 0.0, 0.0
    end      
    local sx, sy = 0.0, 0.0
    local sbeg, send = string.find( str, "[%d-%.]+", 0 )
    if sbeg ~= nil then
        sx = tonumber( string.sub( str, sbeg, send ) )
    end
    sbeg, send = string.find( str, "[%d-%.]+", send + 1 )
    if sbeg ~= nil then
        sy = tonumber( string.sub( str, sbeg, send ) )
    end      
    return sx, sy
end

Object_Metatable = 
{
    __index = function ( t, k )
        return get( t.obj, k )
    end,
    
    __newindex = function ( t, k, v )
        set( t.obj, k, v )
    end
}

function objt( sName )
    local res = {}
    res.obj = obj( sName )
    setmetatable( res, Object_Metatable )
    return res
end

function getIndex( item, tItems )
	for i, v in ipairs(tItems) do
        if (v == item) then
			return i
		end
    end
	return 0
end

function lerp( a, b, t )
	return a*t + b*(1 - t)
end

function vec2dist( ax, ay, bx, by )
	local dx = ax - bx
	local dy = ay - by
	return math.sqrt( dx*dx + dy*dy )
end

function hasParent( object, parentName )
	local cParent = parent( object )
	while cParent ~= nil do
		if (get( cParent, "name" ) == parentName) then
			return true
		end
		cParent = parent( cParent )
	end
	return false
end

function bringToFront( object )
	set( object, "index", "1000000" )
end

function bringToBack( object )
	set( object, "index", "0" )
end
