Module:DinoIcon

From ARK Wiki
Jump to navigation Jump to search
Template-info.png Documentation

This module handles recognition of creatures in {{ItemLink}}s and similar templates, and allows for dynamic, browser-side colorization of creature icons.

Configuration (and explanations of its fields) are found under Module:DinoIcon/config.

Requirements

The Entities Cargo table is leveraged. Additionally, creature infobox invokes this module to determine dynamic icon parameters, with the result stored in the Cargo table as an optimization.

Translators: your table definition and creature infobox must be updated to contain changes up to October 15th, 2023 for this module to fully work. After the templates are updated, recreate the Cargo table (the process may take up to an hour based on server load). Additionally, ItemLink and possibly other templates may need to be updated to leverage dynamic icons.

Matchers

The module performs three attempts at assigning a category to a creature:

  • "Rigged" matcher checks if the configuration provides a hard-wired result for the creature's article name.
  • Afterwards, creature's article name is compared against name patterns, which follow Lua's pattern format. The checking order is not guaranteed.
  • If the above two methods do not yield any results, finally, the creature's taxonomic groups are checked. The checking order is guaranteed to match the order in configuration.

File choice

In the rigged matcher, configured icon file is used. In other matchers, the icon file used will always be either the parent creature's name (if checked creature is a variant) or the checked creature's article name.


local p = {}

local Utility = require( 'Module:Utility' )
local Config = require( 'Module:DinoIcon/config' )


local function determineIconClass( row )
	if Config.Rigged[row.Article] then
		return Config.Rigged[row.Article]
	end

	local rVariantOf = row.VariantOf ~= '' and row.VariantOf or nil
	local baseIconName = rVariantOf or row.Article

	if rVariantOf then
		if Config.AllowIconOverrides and Utility.doesFileExist( row.Article .. '.png' ) then
			return { '', row.Article }
		end
	end

	for pattern, class in pairs( Config.NamePatterns ) do
		if row.Article:find( pattern, nil, false ) then
			if class.IfInGroup then
				if row.Groups:find( class.IfInGroup, nil, true ) then
					return { class[1], baseIconName }
				end
			else
				return { class, baseIconName }
			end
		end
	end

	for index = 1, #Config.Groups do
		-- pair : { group, class }
		local pair = Config.Groups[index]
		if row.Groups:find( pair[1], nil, true ) then
			return { pair[2], baseIconName }
		end
	end

	return { '', row.Article }
end
	

local function tryResolveStatic( creature )
	local result = Config.LUT[creature]
	if result == true then
		result = { '', creature }
	end
	return result
end


local function _resolveDynamicInternal( creature )
	local data = Utility.runCachedCargoQuery( 'DinoIconMetadata:4', {
		expiryTime = 60 * 2,
		inProcess = true,
		tableName = 'Entities',
		fields = 'Article, VariantOf, Groups, DynamicIcon',
		key = 'Article',
		options = {
			limit = 9999
		}
	} )

	local row = data[creature]
	if row then
		if Config.AllowCargoDynIconSetups and row.DynamicIcon and row.DynamicIcon ~= '' then
			local cls, icon = row.DynamicIcon:match( '(.*);(.*)' )
			return { cls, icon }
		end
		
		return determineIconClass( row )
	end

	return false
end


local function tryResolveDynamic( creature )
	if Config.Rigged[creature] then
		return Config.Rigged[creature]
	end
	
	local cached = Utility.getCachedOrSet(
		'DinoIcon:6::' .. creature,
		{
			expiryTime = 60 * 5,
			setCallback = _resolveDynamicInternal,
			setCallbackArg = creature,
		}
	)
	return cached == false and nil or cached
end


return {
	tryResolveStatic = tryResolveStatic,
	tryResolveDynamic = tryResolveDynamic,
	resolve = function ( creature )
		if not Config.Enable then
			return nil
		end

		if Config.Aliases[creature] then
			creature = Config.Aliases[creature]
		end

		local result = -2
		if Config.LUT ~= nil then
			result = tryResolveStatic( creature ) or -2
		end

		if result == -2 and Config.UseCargo then
			result = tryResolveDynamic( creature )
		end

		if result == -2 then
			result = nil
		end

		return result and {
			result[1] == '' and 'dinolink' or ( 'dinolink dinolink--' .. result[1] ),
			result[2],
		} or nil
	end,
	determineIconClass = determineIconClass,
	determineIconClassW = function ( frame )
		local articleName = frame.args.article
		local result = determineIconClass( {
			Article = Config.Aliases[articleName] or articleName,
			VariantOf = frame.args.variantOf,
			Groups = frame.args.groups,
		} )
		if result then
			return string.format( '%s;%s', result[1], result[2] )
		end
		return ''
	end,
}