forked from public/foundryvtt-wh4-lang-fr-fr
		
	
		
			
				
	
	
		
			111 lines
		
	
	
		
			2.7 KiB
		
	
	
	
		
			Lua
		
	
	
	
	
	
			
		
		
	
	
			111 lines
		
	
	
		
			2.7 KiB
		
	
	
	
		
			Lua
		
	
	
	
	
	
| --[[
 | |
| 	Licensed according to the included 'LICENSE' document
 | |
| 	Author: Thomas Harning Jr <harningt@gmail.com>
 | |
| ]]
 | |
| local jsonutil = require("json.util")
 | |
| 
 | |
| local type = type
 | |
| local pairs = pairs
 | |
| local assert = assert
 | |
| 
 | |
| local table = require("table")
 | |
| local math = require("math")
 | |
| local table_concat = table.concat
 | |
| local math_floor, math_modf = math.floor, math.modf
 | |
| 
 | |
| local jsonutil = require("json.util")
 | |
| local util_IsArray = jsonutil.IsArray
 | |
| 
 | |
| local _ENV = nil
 | |
| 
 | |
| local defaultOptions = {
 | |
| 	isArray = util_IsArray
 | |
| }
 | |
| 
 | |
| local modeOptions = {}
 | |
| 
 | |
| local function mergeOptions(options, mode)
 | |
| 	jsonutil.doOptionMerge(options, false, 'array', defaultOptions, mode and modeOptions[mode])
 | |
| end
 | |
| 
 | |
| --[[
 | |
| 	Utility function to determine whether a table is an array or not.
 | |
| 	Criteria for it being an array:
 | |
| 		* ExternalIsArray returns true (or false directly reports not-array)
 | |
| 		* If the table has an 'n' value that is an integer >= 1 then it
 | |
| 		  is an array... may result in false positives (should check some values
 | |
| 		  before it)
 | |
| 		* It is a contiguous list of values with zero string-based keys
 | |
| ]]
 | |
| local function isArray(val, options)
 | |
| 	local externalIsArray = options and options.isArray
 | |
| 
 | |
| 	if externalIsArray then
 | |
| 		local ret = externalIsArray(val)
 | |
| 		if ret == true or ret == false then
 | |
| 			return ret
 | |
| 		end
 | |
| 	end
 | |
| 	-- Use the 'n' element if it's a number
 | |
| 	if type(val.n) == 'number' and math_floor(val.n) == val.n and val.n >= 1 then
 | |
| 		return true
 | |
| 	end
 | |
| 	local len = #val
 | |
| 	for k,v in pairs(val) do
 | |
| 		if type(k) ~= 'number' then
 | |
| 			return false
 | |
| 		end
 | |
| 		local _, decim = math_modf(k)
 | |
| 		if not (decim == 0 and 1<=k) then
 | |
| 			return false
 | |
| 		end
 | |
| 		if k > len then -- Use Lua's length as absolute determiner
 | |
| 			return false
 | |
| 		end
 | |
| 	end
 | |
| 
 | |
| 	return true
 | |
| end
 | |
| 
 | |
| --[[
 | |
| 	Cleanup function to unmark a value as in the encoding process and return
 | |
| 	trailing results
 | |
| ]]
 | |
| local function unmarkAfterEncode(tab, state, ...)
 | |
| 	state.already_encoded[tab] = nil
 | |
| 	return ...
 | |
| end
 | |
| local function getEncoder(options)
 | |
| 	options = options and jsonutil.merge({}, defaultOptions, options) or defaultOptions
 | |
| 	local function encodeArray(tab,  state)
 | |
| 		if not isArray(tab, options) then
 | |
| 			return false
 | |
| 		end
 | |
| 		-- Make sure this value hasn't been encoded yet
 | |
| 		state.check_unique(tab)
 | |
| 		local encode = state.encode
 | |
| 		local compositeEncoder = state.outputEncoder.composite
 | |
| 		local valueEncoder = [[
 | |
| 		for i = 1, (composite.n or #composite) do
 | |
| 			local val = composite[i]
 | |
| 			PUTINNER(i ~= 1)
 | |
| 			val = encode(val, state)
 | |
| 			val = val or ''
 | |
| 			if val then
 | |
| 				PUTVALUE(val)
 | |
| 			end
 | |
| 		end
 | |
| 		]]
 | |
| 		return unmarkAfterEncode(tab, state, compositeEncoder(valueEncoder, '[', ']', ',', tab, encode, state))
 | |
| 	end
 | |
| 	return { table = encodeArray }
 | |
| end
 | |
| 
 | |
| local array = {
 | |
| 	mergeOptions = mergeOptions,
 | |
| 	isArray = isArray,
 | |
| 	getEncoder = getEncoder
 | |
| }
 | |
| 
 | |
| return array
 |