c1_lua/lua/app/bf/common/functions.lua
2023-08-30 19:11:38 +08:00

619 lines
14 KiB
Lua
Raw Blame History

This file contains ambiguous Unicode characters

This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

--[[
Copyright (c) 2014-2017 Chukong Technologies Inc.
Permission is hereby granted, free of charge, to any person obtaining a copy
of this software and associated documentation files (the "Software"), to deal
in the Software without restriction, including without limitation the rights
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
copies of the Software, and to permit persons to whom the Software is
furnished to do so, subject to the following conditions:
The above copyright notice and this permission notice shall be included in
all copies or substantial portions of the Software.
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
THE SOFTWARE.
]]
function checknumber(value, base)
return tonumber(value, base) or 0
end
function checkint(value)
return math.round(checknumber(value))
end
function checkbool(value)
return (value ~= nil and value ~= false)
end
function checktable(value)
if type(value) ~= "table" then value = {} end
return value
end
function clone(object)
local lookup_table = {}
local function _copy(object)
if type(object) ~= "table" then
return object
elseif lookup_table[object] then
return lookup_table[object]
end
local newObject = {}
lookup_table[object] = newObject
for key, value in pairs(object) do
newObject[_copy(key)] = _copy(value)
end
return setmetatable(newObject, getmetatable(object))
end
return _copy(object)
end
local function emptyFunction()
end
function class(classname, super)
local cls = {__cname = classname}
if super then
local superType = type(super)
assert(superType == "table",
string.format("class() - create class \"%s\" with invalid super class type \"%s\"",
classname, superType))
cls.super = super
setmetatable(cls, {__index = super})
end
cls.ctor = emptyFunction
cls.new = function(_, ...)
local instance = {}
setmetatable(instance, {__index = cls})
instance.class = cls
if instance.super then
local _constructor
_constructor = function(c, ...)
if c.super then
_constructor(c.super, ...)
end
c.ctor(instance, ...)
end
_constructor(instance.super, ...)
end
instance:ctor(...)
return instance
end
cls.create = cls.new
return cls
end
function iskindof(obj, classname)
local t = type(obj)
if t ~= "table" then return false end
local mt = getmetatable(obj)
if mt then
local __index = rawget(mt, "__index")
if type(__index) == "table" and rawget(__index, "__cname") == classname then return true end
end
if rawget(obj, "__cname") == classname then return true end
local super = obj.super
while super do
if rawget(super, "__cname") == classname then return true end
super = super.super
end
return false
end
function handler(obj, method)
return function(...)
return method(obj, ...)
end
end
function math.newrandomseed()
local ok, socket = pcall(function()
return require("socket")
end)
if ok then
math.randomseed(socket.gettime() * 1000)
else
math.randomseed(os.time())
end
math.random()
math.random()
math.random()
math.random()
end
function math.round(value)
value = checknumber(value)
return math.floor(value + 0.5)
end
function math.clamp(value, min, max)
if value < min then
return min
end
if value > max then
return max
end
return value
end
local pi_div_180 = math.pi / 180
function math.angle2radian(angle)
return angle * pi_div_180
end
function math.radian2angle(radian)
return radian * 180 / math.pi
end
function io.exists(path)
local file = io.open(path, "r")
if file then
io.close(file)
return true
end
return false
end
function io.readfile(path)
local file = io.open(path, "r")
if file then
local content = file:read("*a")
io.close(file)
return content
end
return nil
end
function io.writefile(path, content, mode)
mode = mode or "w+b"
local file = io.open(path, mode)
if file then
if file:write(content) == nil then return false end
io.close(file)
return true
else
return false
end
end
function io.pathinfo(path)
local pos = string.len(path)
local extpos = pos + 1
while pos > 0 do
local b = string.byte(path, pos)
if b == 46 then -- 46 = char "."
extpos = pos
elseif b == 47 then -- 47 = char "/"
break
end
pos = pos - 1
end
local dirname = string.sub(path, 1, pos)
local filename = string.sub(path, pos + 1)
extpos = extpos - pos
local basename = string.sub(filename, 1, extpos - 1)
local extname = string.sub(filename, extpos)
return {
dirname = dirname,
filename = filename,
basename = basename,
extname = extname
}
end
function io.filesize(path)
local size = false
local file = io.open(path, "r")
if file then
local current = file:seek()
size = file:seek("end")
file:seek("set", current)
io.close(file)
end
return size
end
function table.nums(t)
local count = 0
for k, v in pairs(t) do
count = count + 1
end
return count
end
function table.keys(hashtable)
local keys = {}
for k, v in pairs(hashtable) do
keys[#keys + 1] = k
end
return keys
end
function table.values(hashtable)
local values = {}
for k, v in pairs(hashtable) do
values[#values + 1] = v
end
return values
end
function table.merge(dest, src)
for k, v in pairs(src) do
dest[k] = v
end
end
function table.insertto(dest, src, begin)
begin = checkint(begin)
if begin <= 0 then
begin = #dest + 1
end
local len = #src
for i = 0, len - 1 do
dest[i + begin] = src[i + 1]
end
end
function table.indexof(array, value, begin)
for i = begin or 1, #array do
if array[i] == value then return i end
end
return false
end
function table.keyof(hashtable, value)
for k, v in pairs(hashtable) do
if v == value then return k end
end
return nil
end
function table.removebyvalue(array, value, removeall)
local c, i, max = 0, 1, #array
while i <= max do
if array[i] == value then
table.remove(array, i)
c = c + 1
i = i - 1
max = max - 1
if not removeall then break end
end
i = i + 1
end
return c
end
function table.map(t, fn)
for k, v in pairs(t) do
t[k] = fn(v, k)
end
end
function table.walk(t, fn)
for k,v in pairs(t) do
fn(v, k)
end
end
function table.filter(t, fn)
for k, v in pairs(t) do
if not fn(v, k) then t[k] = nil end
end
end
function table.unique(t, bArray)
local check = {}
local n = {}
local idx = 1
for k, v in pairs(t) do
if not check[v] then
if bArray then
n[idx] = v
idx = idx + 1
else
n[k] = v
end
check[v] = true
end
end
return n
end
function table.containValue(t, value)
for k, v in pairs(t) do
if v == value then
return true
end
end
return false
end
function table.shuffle(t)
if type(t)~="table" then
return
end
local tab = {}
local index = 1
while #t ~= 0 do
local n = math.random(1, #t)
if t[n] ~= nil then
tab[index] = t[n]
table.remove(t,n)
index = index + 1
end
end
return tab
end
function table.shuffleBySeed(t, seed)
if type(t)~="table" then
return
end
local tab = {}
local index = 1
while #t ~= 0 do
local n = GFunc.getRandomIndexBySeed(seed, 1, #t)
if t[n] ~= nil then
tab[index] = t[n]
table.remove(t,n)
index = index + 1
end
end
return tab
end
function table.clear(t)
if not t then
return
end
if type(t) ~= "table" then
return
end
for key, v in pairs(t) do
t[key] = nil
end
end
function table.clearOrCreate(t)
if not t then
return {}
end
if type(t) ~= "table" then
return {}
end
table.clear(t)
return t
end
---查找一个满足条件的元素
function table.find(t, predict)
for k, v in pairs(t) do
if predict(v) then
return v, k
end
end
end
---浅拷贝
function table.refCopy(t)
if not t then return nil end
local copy = {}
for i,v in pairs(t) do
copy[i] = v
end
return copy
end
---将array'from' insert到to
function table.addArray(to, from)
if not to or not from then return end
for _, v in ipairs(from) do
table.insert(to, v)
end
return to
end
---将array'from' insert到to
function table.addDic(to, from)
if not to or not from then return end
for _, v in pairs(from) do
to[_] = v
end
return to
end
--tbl需要删除对象的表 func用于判断是否是需要删除的对象的函数
--func返回两个参数1、是否remove 2、是否继续
---该函数会copy一次table
function table.removeEx(tbl, func)
if tbl == nil or func == nil then
return tbl
end
local newTbl = {}
for k, v in pairs(tbl) do
local needRemove, continue = func(k, v)
if not needRemove and v then
newTbl[#newTbl + 1] = v
end
if not continue then
break
end
end
return newTbl
end
--- 反转阵列
function table.revert(tableArray)
local length = #tableArray
local half = length / 2
local temp
for i = 1, half do
temp = tableArray[i]
tableArray[i] = tableArray[length - i + 1]
tableArray[length - i + 1] = temp
end
return tableArray
end
---满足任意条件
function table.any(tbl, func)
for _, v in pairs(tbl) do
if func(v) then
return true
end
end
return false
end
--- 遍历
function table.foreach(tbl, func)
for k, v in pairs(tbl) do
func(k, v)
end
end
--- 计算每一个val的满足条件的count
function table.count(tbl, func)
local result = 0
for _, v in pairs(tbl) do
result = result + func(v)
end
return result
end
string._htmlspecialchars_set = {}
string._htmlspecialchars_set["&"] = "&amp;"
string._htmlspecialchars_set["\""] = "&quot;"
string._htmlspecialchars_set["'"] = "&#039;"
string._htmlspecialchars_set["<"] = "&lt;"
string._htmlspecialchars_set[">"] = "&gt;"
function string.htmlspecialchars(input)
for k, v in pairs(string._htmlspecialchars_set) do
input = string.gsub(input, k, v)
end
return input
end
function string.restorehtmlspecialchars(input)
for k, v in pairs(string._htmlspecialchars_set) do
input = string.gsub(input, v, k)
end
return input
end
function string.nl2br(input)
return string.gsub(input, "\n", "<br />")
end
function string.text2html(input)
input = string.gsub(input, "\t", " ")
input = string.htmlspecialchars(input)
input = string.gsub(input, " ", "&nbsp;")
input = string.nl2br(input)
return input
end
function string.split(input, delimiter)
input = tostring(input)
delimiter = tostring(delimiter)
if (delimiter=='') then return false end
local pos,arr = 0, {}
-- for each divider found
for st,sp in function() return string.find(input, delimiter, pos, true) end do
table.insert(arr, string.sub(input, pos, st - 1))
pos = sp + 1
end
table.insert(arr, string.sub(input, pos))
return arr
end
function string.ltrim(input)
return string.gsub(input, "^[ \t\n\r]+", "")
end
function string.rtrim(input)
return string.gsub(input, "[ \t\n\r]+$", "")
end
function string.trim(input)
input = string.gsub(input, "^[ \t\n\r]+", "")
return string.gsub(input, "[ \t\n\r]+$", "")
end
function string.ucfirst(input)
return string.upper(string.sub(input, 1, 1)) .. string.sub(input, 2)
end
local function urlencodechar(char)
return "%" .. string.format("%02X", string.byte(char))
end
function string.urlencode(input)
-- convert line endings
input = string.gsub(tostring(input), "\n", "\r\n")
-- escape all characters but alphanumeric, '.' and '-'
input = string.gsub(input, "([^%w%.%- ])", urlencodechar)
-- convert spaces to "+" symbols
return string.gsub(input, " ", "+")
end
function string.urldecode(input)
input = string.gsub (input, "+", " ")
input = string.gsub (input, "%%(%x%x)", function(h) return string.char(checknumber(h,16)) end)
input = string.gsub (input, "\r\n", "\n")
return input
end
function string.utf8len(input)
local len = string.len(input)
local left = len
local cnt = 0
local arr = {0, 0xc0, 0xe0, 0xf0, 0xf8, 0xfc}
while left ~= 0 do
local tmp = string.byte(input, -left)
local i = #arr
while arr[i] do
if tmp >= arr[i] then
left = left - i
break
end
i = i - 1
end
cnt = cnt + 1
end
return cnt
end
function string.formatnumberthousands(num)
local formatted = tostring(checknumber(num))
local k
while true do
formatted, k = string.gsub(formatted, "^(-?%d+)(%d%d%d)", '%1,%2')
if k == 0 then break end
end
return formatted
end
function string.isEmptyOrNil(str)
return not str or #str == 0
end