Module:Inventory slot

local p = {}

-- List of special prefixes which should be handled by -- other modules (such as being moved outside links) p.prefixes = { 'Any', 'Matching', 'Damaged' }

function p.slot( f ) local args = f.args or f	if f == mw.getCurrentFrame and args[1] == nil then args = f:getParent.args end args[1] = mw.text.trim( args[1] or '' ) -- Comment this next line out if you're not using aliases local aliases = mw.loadData( 'Module:Inventory slot/Aliases' ) local modAliases = args.modaliases or '' if modAliases ~= '' then modAliases = mw.loadData( 'Module:' .. modAliases ) else modAliases = nil end local randomise if args.class == 'invslot-large' then randomise = false end if aliases or modAliases then local frames = {} for frame in mw.text.gsplit( args[1], '%s*;%s*' ) do			local frameParts = p.getParts( frame, args.mod ) local id = frameParts.name if frameParts.mod then id = frameParts.mod .. ':' .. id			end local alias if modAliases and modAliases[id] then alias = modAliases[id] elseif aliases and aliases[id] then alias = aliases[id] end if alias then table.insert( frames, p.expandAlias( frameParts, alias ) ) else table.insert( frames, frame ) end -- Randomise starting frame for "Any *" aliases, as long as the alias is the only frame -- and this isn't an output slot if randomise ~= false and frameParts.name:match( '^Any ' ) then randomise = true else randomise = false end end args[1] = table.concat( frames, ';' ) end local sprite local ids = mw.loadData( Module:InvSprite/IDs ).ids local modIds = {} local animated = args[1]:find( ';' ) local pageName = mw.title.getCurrentTitle.text local imgClass = args.imgclass local numStyle = args.numstyle local body = mw.html.create( 'span' ):addClass( 'invslot' ):css{ ['vertical-align'] = args.align } if animated then body:addClass( 'animated' ) end if args.class then body:addClass( args.class ) end if args.style then body:cssText( args.style ) end if ( args.default or  ) ~=  then body:css( 'background-image', '' ) end local frames = mw.text.split( args[1], '%s*;%s*' ) local activeFrame = randomise and math.random( #frames ) or 1 for i, frame in ipairs( frames ) do		local item if frame ~=  or frame ==  and animated then item = body:tag( 'span' ):addClass( 'invslot-item' ) if imgClass then item:addClass( imgClass ) end end if frame == '' then ( item or body ):tag( 'br' ) else local category local parts = p.getParts( frame, args.mod ) local title = parts.title or mw.text.trim( args.title or '' ) local mod = parts.mod local name = parts.name local num = parts.num local description = parts.text local img, idData if mod then local modData = modIds[mod] if not modData and mw.title.new( 'Module:InvSprite/Mods/' .. mod .. '/IDs' ).exists then modData = mw.loadData( 'Module:InvSprite/Mods/' .. mod .. '/IDs' ) modIds[mod] = modData end if modData and modData[name] then idData = modData[name] else img = 'Grid ' .. name .. ' (' .. mod .. ').png' end elseif ids[name] then idData = ids[name] elseif name:match( '\.gif$' ) or name:match( '\.png$' ) then img = 'Invicon ' .. name name = name:sub( 0, -5 ) else img = 'Grid ' .. name .. '.png' end local link = args.link or '' if link == '' then if mod then link = 'Mods/' .. mod .. '/' .. name else link = name:gsub( '^Damaged ', '' ) end elseif link:lower == 'none' then link = nil end if link == pageName then link = nil end local formattedTitle local plainTitle if title == '' then plainTitle = name elseif title:lower ~= 'none' then plainTitle = title:gsub( '\\\\', '&#92;' ):gsub( '\\&', '&#38;' ) local formatPattern = '&[0-9a-fk-or]' if plainTitle:match( formatPattern ) then formattedTitle = title plainTitle = plainTitle:gsub( formatPattern, '' ) end if plainTitle == '' then plainTitle = name else plainTitle = plainTitle:gsub( '&#92;', '\\' ):gsub( '&#38;', '&' ) end elseif link then if img then formattedTitle = '' else plainTitle = '' end end item:attr{ ['data-minetip-title'] = formattedTitle, ['data-minetip-text'] = description }			if img then -- & is re-escaped because mw.html treats attributes -- as plain text, but MediaWiki doesn't				local escapedTitle = ( plainTitle or '' ):gsub( '&', '&#38;' ) item:addClass( 'invslot-item-image' ) :wikitext( '' ) else if not sprite then sprite = require( Module:Sprite ).sprite end local image if mod then image = args.spritesheet or mod .. 'Sprite.png' end if link then item:wikitext(  )				end				local image, spriteCat = sprite{					iddata = idData, title = plainTitle,					image = image, settings = 'InvSprite'				}				item:node( image )				category = spriteCat			end			if num and num > 1 and num < 1000 then				if img and link then					item:wikitext( '[[', link, '|' )				end				local number = item					:tag( 'span' )						:addClass( 'invslot-stacksize' )						:attr{ title = plainTitle }						:wikitext( num )				if numStyle then					number:cssText( numStyle )				end				if img and link then					item:wikitext(  )				end			end			if idData and link then				item:wikitext( ']]' ) end item:wikitext( category ) end if i == activeFrame and animated and item then item:addClass( 'animated-active' ) end end return tostring( body ) end

function p.expandAlias( frameParts, alias ) -- If the frame has no parts, we can just return the alias as-is if not frameParts.title and not frameParts.mod and not frameParts.num and not frameParts.text then return alias end local expandedFrames = {} for aliasFrame in mw.text.gsplit( alias, '%s*;%s*' ) do		local aliasParts = p.getParts( aliasFrame ) aliasParts.title = frameParts.title or aliasParts.title or '' aliasParts.mod = frameParts.mod or aliasParts.mod or 'Minecraft' aliasParts.num = frameParts.num or aliasParts.num or '' aliasParts.text = frameParts.text or aliasParts.text or '' table.insert( expandedFrames, string.format( '[%s]%s:%s,%s[%s]', aliasParts.title, aliasParts.mod, aliasParts.name, aliasParts.num, aliasParts.text ) )	end return table.concat( expandedFrames, ';' ) end

function p.getParts( frame, mod ) local parts = {} parts.title = frame:match( '^%[%s*([^%]]+)%s*%]' ) parts.mod = mw.text.trim( frame:match( '([^:%]]+):' ) or mod or '' ) local vanilla = { v = 1, vanilla = 1, mc = 1, minecraft = 1 } if parts.mod == '' or vanilla[mw.ustring.lower( parts.mod )] then parts.mod = nil end local nameStart = ( frame:find( ':' ) or frame:find( '%]' ) or 0 ) + 1 if nameStart - 1 == #frame then nameStart = 1 end parts.name = mw.text.trim( frame:sub( nameStart, ( frame:find( '[,%[]', nameStart ) or 0 ) - 1 ) ) parts.num = math.floor( frame:match( ',%s*(%d+)' ) or 0 ) if parts.num == 0 then parts.num = nil end parts.text = frame:match( '%[%s*([^%]]+)%s*%]$' ) return parts end return p