Модуль:HeroData

Данная группа модулей хранит информацию обо всех героях из Крушителей подземелий. Перечень модулей:

Информация из Модуль:HeroData/doc


local p = {}

local lib       = require('Module:Feature')
local libItem   = require('Module:ItemData')
local userError = require('Module:User error')

function p.get(frame)
	local args; if frame.args == nil then args = lib.arguments(frame) else args = lib.arguments(frame.args) end
	
	local get      = require ('Module:HeroData/getter')
    local hero     = args['hero'] or args[1]
    local datatype = args['datatype'] or args[2]
    local output   = args['output'] or args[3] or nil
    
    local result = get[datatype](hero)
    
    if output ~= nil and type(result) == "table" then
        if output == "csv" then
            return lib.tbl_concat{result}
        elseif output == "custom" then 
            return frame:preprocess(lib.tbl_concat({result, prepend = args['prepend'], append = args['append'], separator = args['separator'], index = args["index"]}))
        elseif output == "template" then 
            return frame:preprocess(lib.tbl_concat{result, prepend = "{{" .. args['t_name'] .. "|", append = "}}", separator = args['separator']})
        end
    elseif result == nil then
        return ""
    else
        return result
    end
end

function p.heroIcon(frame)
	local args; if frame.args == nil then args = lib.arguments(frame) else args = lib.arguments(frame.args) end
	
	hero = args["hero"] or args[1]
	if(not(p.get{args["hero"], "exists"})) then
		return userError("Указанный герой не найден в [[Модуль:HeroData/data]] (message from [[Модуль:HeroData]])", "LuaError")
	end
	
	local IL = require("Модуль:ImageLink")
	
	return IL.hero(args)
end

function p.getRoster()
	local heroes  = mw.loadData('Module:HeroData/data')
	local heroesTable = {}
	local s = ""
	
	for k, v in pairs(heroes) do
        table.insert(heroesTable, k)
    end
    table.sort(heroesTable)
    
    for i, hero in ipairs(heroesTable) do
    	local icon = p.get{hero, "icon", "csv"}
        local race = p.get{hero, "race", "csv"}
        local class = p.get{hero, "class", "csv"}
        local alliance = p.get{hero, "alliance", "csv"}
        
        if (hero) == "ХТ-02/6" then
        	icon = "hero_xt.png"
        end
        
        local listNode = mw.html.create('li')
        listNode
            :tag('span')
            	:addClass('hero_roster')
                :attr('data-hero', hero)
                :attr('data-search', search)
                :attr('data-race', race)
                :attr('data-class', class)
                :attr('data-alliance', alliance)
                :wikitext(
                    mw.ustring.format("[[File:%s|48px|alt=%s|link=%s]]",
                    icon,
                    hero,
                    hero)
                )
                :done()
            :done()
        listNode:newline()
        
        s = s .. tostring(listNode)
    end
	
	return s
end

function p.getHeroSkill(frame)
	local args; if frame.args == nil then args = lib.arguments(frame) else args = lib.arguments(frame.args) end
		
	local get     = require ('Module:HeroData/getter')
	local hero    = args['hero'] or args[1]
	local skill   = "skills"
	local str     = ""
	
    local result = get[skill](hero)
    
    for k, v in ipairs(result) do
    	if tonumber(args['index']) == k then
	    	str = mw.ustring.format('{{hsk|%s|%s|%s|%s|%s|%s|link=%s}}', v[1], v[2], v[3], v[4], v[5], v[6], lib.ternary(string.gsub(v[1], " %W+", "") == "Подарок", v[1], ""))
	    end
    end
    return frame:preprocess(tostring(str))
end

function p.getHeroAbility(frame)
	local args; if frame.args == nil then args = lib.arguments(frame) else args = lib.arguments(frame.args) end
		
	local get     = require ('Module:HeroData/getter')
	local hero    = args['hero'] or args[1]
	local ability = "abilities"
	local str     = ""
	
	local result = get[ability](hero)
	
	for k, v in ipairs(result) do
    	if tonumber(args['index']) == k then
    		str = mw.ustring.format('%s/%s/%s/%s', v[1], v[2], v[3], v[4])
    	end
    end
    
    return str
end

function p.getHeroTableItems(frame)
	local args; if frame.args == nil then args = lib.arguments(frame) else args = lib.arguments(frame.args) end
		
	local get          = require ('Module:HeroData/getter')
	local hero         = args['hero'] or args[1]
	local equip        = "equip"
	local tableNode    = mw.html.create('table')
	local type
	local divNode      = mw.html.create('div')
	
	local result = get[equip](hero)
	
	if hero == "Тотем душ" or hero == "Теолдуин" or hero == "Герой игрока" or hero == "Гримбольц" then
		divNode
			:cssText('background: #042539; color: #91c5ca; padding: 10px; border: 1px solid #6b879f; border-radius: 10px; width: fit-content; margin: 0 auto;')
			:wikitext('Данный герой не наносит никакого урона, поэтому у него нет комплектов экипировки для улучшения.')
		return frame:preprocess(tostring(divNode))
	end
	
	tableNode
        :addClass('custom-table active-hover')
        :cssText('width: fit-content; display: table; overflow-x: auto; margin: 0 auto;')
        :newline()
        
    tableNode
		:tag('tr')
            :tag('th')
            	:css('width', '16%')
                :done()
            :tag('th')
            	:css('width', '14%')
            	:wikitext('Шлем')
        		:done()
            :tag('th')
            	:css('width', '14%')
            	:tag('div')
            		:addClass('hidden pc-block')	
            		:wikitext('Доспехи')
            		:done()
            	:tag('div')
            		:addClass('mobile-block')	
            		:wikitext('Досп')
            		:done()
                :done()
            :tag('th')
            	:css('width', '14%')
            	:tag('div')
            		:addClass('hidden pc-block')	
            		:wikitext('Оружие')
            		:done()
            	:tag('div')
            		:addClass('mobile-block')	
            		:wikitext('Оруж')
            		:done()
                :done()
            :tag('th')
            	:css('width', '14%')
            	:tag('div')
            		:addClass('hidden pc-block')	
            		:wikitext('Ботинки')
            		:done()
            	:tag('div')
            		:addClass('mobile-block')	
            		:wikitext('Боты')
            		:done()
                :done()
            :tag('th')
            	:css('width', '14%')
            	:tag('div')
            		:addClass('hidden pc-block')	
            		:wikitext('Кольцо')
            		:done()
            	:tag('div')
            		:addClass('mobile-block')	
            		:wikitext('Колц')
            		:done()
                :done()
            :tag('th')
            	:css('width', '14%')
            	:tag('div')
            		:addClass('hidden pc-block')	
            		:wikitext('Ожерелье')
            		:done()
            	:tag('div')
            		:addClass('mobile-block')	
            		:wikitext('Ожер')
            		:done()
                :done()
            :done()
            
    	for k, v in lib.pairsByAlphabeticalKeys(result) do
    		if k > 0 and k < 5 then
    			type = 0
    		elseif k > 4 and k < 9 then
    			type = 1
    		elseif k > 8 then
    			type = 2
    		end
    		
    		
    		local rowNode = mw.html.create('tr')
	    	rowNode
	    		:tag('td')
		    		:tag('div')
	            		:addClass('hidden pc-block')	
	            		:wikitext(setStarMultiple(k, type))
	            		:done()
	            	:tag('div')
	            		:addClass('mobile-block')	
	            		:wikitext(setStarMultipleMobile(k, type))
	            		:done()
					:done()
				:tag('td')
					:css('text-align', 'center')
					:wikitext(mw.ustring.format('%s', libItem.getItemIcon(v[1], "40px")))
					:done()
				:tag('td')
					:css('text-align', 'center')
					:wikitext(mw.ustring.format('%s', libItem.getItemIcon(v[2], "40px")))
					:done()
				:tag('td')
					:css('text-align', 'center')
					:wikitext(mw.ustring.format('%s', libItem.getItemIcon(v[3], "40px")))
					:done()
				:tag('td')
					:css('text-align', 'center')
					:wikitext(mw.ustring.format('%s', libItem.getItemIcon(v[4], "40px")))
					:done()
				:tag('td')
					:css('text-align', 'center')
					:wikitext(mw.ustring.format('%s', libItem.getItemIcon(v[5], "40px")))
					:done()
				:tag('td')
					:css('text-align', 'center')
					:wikitext(mw.ustring.format('%s', libItem.getItemIcon(v[6], "40px")))
					:done()
	    		:done()
	    	tableNode:node(rowNode):newline()
	    end
	    
    return frame:preprocess(tostring(tableNode))
end

function p.getHeroTableInfo(frame)
	local args; if frame.args == nil then args = lib.arguments(frame) else args = lib.arguments(frame.args) end
	local get       = require ('Module:HeroData/getter')
	local hero      = args['hero'] or args[1]
	
	local params    = {"base_cost", "base_dps", "icon_shard", "shard_count", "info"}
	local tableNode = mw.html.create('table')
	
	local cost        = get[params[1]](hero)
	local dps         = get[params[2]](hero)
	local shard_count = get[params[4]](hero)
	local info        = get[params[5]](hero)
	
	if get[params[3]](hero) ~= nil then
		local shard = get[params[3]](hero)
	else
		local shard = ""
	end
	
	tableNode
        :addClass('custom-table')
        :cssText('display: table; width: fit-content; world-wrap: break-word;')
        :newline()
    
    tableNode
        :tag('tr')
            :tag('th')
            	:css('width', '15%')
                :wikitext('Базовая стоимость')
                :done()
            :tag('th')
            	:css('width', '15%')
                :wikitext('Базовый ДПС')
                :done()
            :tag('th')
            	:css('width', '15%')
                :wikitext('Осколки героя')
                :done()
            :tag('th')
                :wikitext('Способ получения')
                :done()
            :done()
        :tag('tr')
            :tag('td')
            	:css('text-align', 'center')
                :wikitext(mw.ustring.format('%s{{%s}}', cost, "золото"))
                :done()
            :tag('td')
            	:css('text-align', 'center')
                :wikitext(mw.ustring.format('%s', dps))
                :done()
            :tag('td')
	            :css('text-align', 'center')
		        :wikitext(string.format('%s', lib.ternary(shard ~= "", getHeroShard(hero, shard, shard_count), "-")))
		        :done()
            :tag('td')
            	:cssText('text-align:center; white-space: pre-wrap;')
                :wikitext(mw.ustring.format('%s', info))
                :done()
        :done()
	
	return frame:preprocess(tostring(tableNode))
end

function p.getHeroesTable(frame)
    local tableNode = mw.html.create('table')
    tableNode
        :addClass('custom-table active-hover sortable')
        :cssText('width: 80%; text-align: center; display: table;')
        :newline()
    
    tableNode
        :tag('tr')
            :css('white-space', 'nowrap')
            :tag('th')
                :wikitext('Имя')
                :done()
            :tag('th')
                :attr('class', 'unsortable')
                :css('width', '60px')
                :wikitext('Иконка')
                :done()
            :tag('th')
                :css('width', '80px')
                :wikitext('Раса')
                :done()
            :tag('th')
                :css('width', '80px')
                :wikitext('Класс')
                :done()
            :tag('th')
                :attr('class', 'unsortable')
                :css('width', '60px')
                :wikitext('Альянс')
                :done()
            :tag('th')
                :css('width', '60px')
                :wikitext('HP')
                :done()
            :tag('th')
                :css('width', '60px')
                :wikitext('DEF')
                :done()
            :tag('th')
                :css('width', '60px')
                :wikitext('ATK')
                :done()
            :tag('th')
                :css('width', '60px')
                :wikitext('WIS')
                :done()
            :tag('th')
                :css('width', '60px')
                :wikitext('AGI')
                :done()
            :done()
    
	    local heroes    = mw.loadData('Module:HeroData/data')
	    local races     = mw.loadData('Module:HeroData/races')
	    local classes   = mw.loadData('Module:HeroData/classes')
	    local alliances = mw.loadData('Module:HeroData/alliances')
		local race      = ""
		local class     = ""
		local alliance  = ""
    	
	    for k, v in lib.pairsByAlphabeticalKeys(heroes) do
	    	if v['race'] ~= nil then
	    		race = races[v['race']]
	    	else
	    		race = "-"
	    	end
	    	
	    	if v['class'] ~= nil then
	    		class = classes[v['class']]
	    	else
	    		class = "-"
	    	end
	    	
	    	if v['alliance'] ~= nil then
	    		alliance = alliances[v['alliance']]
	    	else
	    		alliance = "-"
	    	end
    	
	        local rowNode = mw.html.create('tr')
	        rowNode
	            :tag('td')
	                :attr('data-sort-value', k)
	                :wikitext(mw.ustring.format('[[%s]]', v['name']))
	                :done()
	            :tag('td')
	                :wikitext(mw.ustring.format('%s', p.getHeroIcon(k, "35px")))
	                :done()
	            :tag('td')
	                :attr('data-sort-value', race)
	                :wikitext(mw.ustring.format('%s', lib.ternary(type(v['race']) ~= "nil", 
                	mw.ustring.format('[[:Категория:%s (раса)|%s]]', race, race), 
                	"-")))
	                :done()
	            :tag('td')
	                :attr('data-sort-value', class)
	                :wikitext(mw.ustring.format('%s', lib.ternary(type(v['class']) ~= "nil", 
                	mw.ustring.format('[[:Категория:%s (класс)|%s]]', class, class), 
                	"-")))
                :tag('td')
	                :attr('data-sort-value', alliance)
	                :wikitext(mw.ustring.format('%s',  lib.ternary(v['alliance'] ~= nil, AllianceIcon(alliance, "45px"), "-")))
	                :done()
	            :tag('td')
	                 :wikitext(mw.ustring.format('%s', lib.ternary(v['stats']['hp_base'] == nil, "N/A", v['stats']['hp_base'])))
	                 :done()
	            :tag('td')
	                 :wikitext(mw.ustring.format('%s', lib.ternary(v['stats']['def_base'] == nil, "N/A", v['stats']['def_base'])))
	                 :done()
	            :tag('td')
	                 :wikitext(string.format('%s', lib.ternary(v['type'] == nil, "N/A", lib.ternary(v['type'] == 1 or v['type'] == 4, setHeroMainStat(v['stats']['atk_base']), v['stats']['atk_base']))))
	                 :done()
	            :tag('td')
	                 :wikitext(string.format('%s', lib.ternary(v['type'] == nil, "N/A", lib.ternary(v['type'] == 2 or v['type'] == 4, setHeroMainStat(v['stats']['wis_base']), v['stats']['wis_base']))))
	                 :done()
	            :tag('td')
	                 :wikitext(string.format('%s', lib.ternary(v['type'] == nil, "N/A", lib.ternary(v['type'] == 3, setHeroMainStat(v['stats']['agi_base']), v['stats']['agi_base']))))
	                 :done()
	        	:done()
	        tableNode:node(rowNode):newline()
	    end
    
    return frame:preprocess(tostring(tableNode))
end

function p.getHeroCategories(frame)
	local args; if frame.args == nil then args = lib.arguments(frame) else args = lib.arguments(frame.args) end
		
	local hero_data       = require ('Module:HeroData/data')
	local categories_data = require ('Module:HeroData/categories')
	local hero            = args['hero'] or args[1]
	local categories      = {}
	local str             = ""
	
	if hero_data[hero]["categories"] ~= nil then
    	for _, v in ipairs(hero_data[hero]["categories"]) do
			str = str .. mw.ustring.format('[[Категория:%s]]\n', categories_data[v])
		end
	end
	
	return frame:preprocess(tostring(str))
end

function setHeroMainStat(str)
    local spanNode = mw.html.create('span')
    
    if str == nil then
    	str = "N/A"
    end
    
    spanNode
        :addClass('rarity-glpar')
        :wikitext(mw.ustring.format('%s', str))
    :done()

    return tostring(spanNode)
end

function setStarMultiple(num, type)
	local divNode = mw.html.create('div')
	local i = 0;
	
	divNode
        :cssText('text-align: right;')
        :newline()
	
	if num == 1 then
		divNode
			:wikitext(mw.ustring.format('{{%s}}', convertStarType(type)))
			:done()
	elseif num == 2 then
		while i < 2 do
			i = i + 1
			divNode
				:wikitext(mw.ustring.format('{{%s}}',  convertStarType(type)))
				:done()
		end
	elseif num == 3 then
		while i < 3 do
			i = i + 1
			divNode
				:wikitext(mw.ustring.format('{{%s}}',  convertStarType(type)))
				:done()
		end
	elseif num == 4 then
		while i < 4 do
			i = i + 1
			divNode
				:wikitext(mw.ustring.format('{{%s}}',  convertStarType(type)))
				:done()
		end
	elseif num == 5 then
		divNode
			:wikitext(mw.ustring.format('{{%s}}',  convertStarType(type)))
			:done()
	elseif num == 6 then
		while i < 2 do
			i = i + 1
			divNode
				:wikitext(mw.ustring.format('{{%s}}',  convertStarType(type)))
				:done()
		end
	elseif num == 7 then
		while i < 3 do
			i = i + 1
			divNode
				:wikitext(mw.ustring.format('{{%s}}',  convertStarType(type)))
				:done()
		end
	elseif num == 8 then
		while i < 4 do
			i = i + 1
			divNode
				:wikitext(mw.ustring.format('{{%s}}',  convertStarType(type)))
				:done()
		end
	elseif num == 9 then
		divNode
			:wikitext(mw.ustring.format('{{%s}}',  convertStarType(type)))
			:done()
	elseif num == 10 then
		while i < 2 do
			i = i + 1
			divNode
				:wikitext(mw.ustring.format('{{%s}}',  convertStarType(type)))
				:done()
		end
	elseif num == 11 then
		while i < 3 do
			i = i + 1
			divNode
				:wikitext(mw.ustring.format('{{%s}}',  convertStarType(type)))
				:done()
		end
	elseif num == 12 then
		while i < 4 do
			i = i + 1
			divNode
				:wikitext(mw.ustring.format('{{%s}}',  convertStarType(type)))
				:done()
		end
	else
		return ""
	end
	
	return tostring(divNode)
end

function setStarMultipleMobile(num, type)
	local divNode = mw.html.create('div')
	
	divNode
        :cssText('text-align: right;')
        :newline()
	
	if num == 1 then
		divNode
			:wikitext(mw.ustring.format('{{%s}} x%d',  convertStarType(type), 1))
			:done()
	elseif num == 2 then
		divNode
			:wikitext(mw.ustring.format('{{%s}} x%d',  convertStarType(type), 2))
			:done()
	elseif num == 3 then
		divNode
			:wikitext(mw.ustring.format('{{%s}} x%d',  convertStarType(type), 3))
			:done()
	elseif num == 4 then
		divNode
			:wikitext(mw.ustring.format('{{%s}} x%d',  convertStarType(type), 4))
			:done()
	elseif num == 5 then
		divNode
			:wikitext(mw.ustring.format('{{%s}} x%d',  convertStarType(type), 1))
			:done()
	elseif num == 6 then
		divNode
			:wikitext(mw.ustring.format('{{%s}} x%d',  convertStarType(type), 2))
			:done()
	elseif num == 7 then
		divNode
			:wikitext(mw.ustring.format('{{%s}} x%d',  convertStarType(type), 3))
			:done()
	elseif num == 8 then
		divNode
			:wikitext(mw.ustring.format('{{%s}} x%d',  convertStarType(type), 4))
			:done()
	elseif num == 9 then
		divNode
			:wikitext(mw.ustring.format('{{%s}} x%d',  convertStarType(type), 1))
			:done()
	elseif num == 10 then
		divNode
			:wikitext(mw.ustring.format('{{%s}} x%d',  convertStarType(type), 2))
			:done()
	elseif num == 11 then
		divNode
			:wikitext(mw.ustring.format('{{%s}} x%d',  convertStarType(type), 3))
			:done()
	elseif num == 12 then
		divNode
			:wikitext(mw.ustring.format('{{%s}} x%d',  convertStarType(type), 4))
			:done()
	else
		return ""
	end
	
	return tostring(divNode)
end

function convertStarType(type)
	local str = ""
	if type == 0 then
		str = "Звезда"
	elseif type == 1 then
		str = "Звезда.миф"
	elseif type == 2 then
		str = "Звезда.руб"
	end
		
	return str
end

function getHeroShard(hero, shard, shard_count)
	local item_data = require ('Module:ItemData/data')
	
	if shard == "" or shard_count == nil or item_data["Осколки: " .. hero] == nil then
		return "N/A"
	end
	
	local str = "Осколки: " .. hero
	local item = item_data[str]["name"]
	
    return tostring(libItem.getItemIcon(item, "40px", shard_count))
end

function p.getHeroIcon(hero, size, tooltip, link)
	local hero_data    = require ('Module:HeroData/data')
	local rarity_data  = require ('Module:HeroData/rarities')
	
	if size == nil then
		size = "30px"
	end
	
	if tooltip == nil then
		tooltip = ""
	else
		tooltip = "true"
	end
	
	if link == nil then
		link = ""
	end

	return mw.ustring.format('{{HeroIcon|%s|%s|%s|size=%s|link=%s|tooltip=%s}}', hero, hero_data[hero]["icon"], rarity_data[hero_data[hero]["rarity"]], size, link, tooltip)
end

function p.getIconHero(frame)
	local args; if frame.args == nil then args = lib.arguments(frame) else args = lib.arguments(frame.args) end
	local hero_data    = require ('Module:HeroData/data')
	local rarity_data  = require ('Module:HeroData/rarities')
	
	if args['size'] == nil then
		size = "30px"
	else
		size = args['size']
	end
	
	if args['link'] == nil then
		link = ""
	else
		link = args['link']
	end
	
	if args['caption'] == nil then
		caption = ""
	else
		caption = args['caption']
	end
	
	if args['tooltip'] == nil then
		tooltip = ""
	else
		if args['tooltip'] == "true" then
			tooltip = args['hero']
		else
			tooltip = ""
		end
	end
	
	if lib.lookup(hero_data, args['hero']) then
		icon = hero_data[args['hero']]["icon"]
	else
		return args['hero']
	end
	
	local rarity       = rarity_data[hero_data[args['hero']]["rarity"]]
	
	return frame:preprocess(mw.ustring.format('{{HeroIcon|%s|%s|%s|size=%s|link=%s|caption=%s|tooltip=%s}}', args['hero'], icon, rarity, size, link, caption, tooltip))
end

function AllianceIcon(alliance, size)
	local icons_data = require ('Module:IconData/alliances')
	local icon       = ""
	local str        = ""
	
	if icons_data[alliance] ~= nil then
		icon = icons_data[alliance]
	else
		return "-"
	end
	
	str = mw.ustring.format('[[Файл:%s|%s|link=:Категория:%s (альянс)]]', icon, size, alliance)
	
	return tostring(str)
end

function p.getHeroCategoriesTable(frame)
	local args; if frame.args == nil then args = lib.arguments(frame) else args = lib.arguments(frame.args) end
		
	local hero_data       = require ('Module:HeroData/data')
	local categories_data = require ('Module:HeroData/categories')
	local races           = require ('Module:HeroData/races')
	local classes         = require ('Module:HeroData/classes')
	local alliances       = require ('Module:HeroData/alliances')
	local category        = args['category'] or args[1]
	local heroes          = {}
	local race            = ""
	local class           = ""
	local alliance        = ""
    local tableNode       = mw.html.create('table')
    
    for k, v in lib.pairsByAlphabeticalKeys(hero_data) do
    	if hero_data[k]['categories'] ~= nil then
	    	for k1, v1 in ipairs(hero_data[k]['categories']) do
	    		if category == categories_data[hero_data[k]['categories'][k1]] then
	    			table.insert(heroes, k)
	    		end
	    	end
	    end
    end
    
    tableNode
        :addClass('custom-table active-hover sortable')
        :cssText('width: 100%; text-align: center; display: table;')
        :newline()
    
    tableNode
        :tag('tr')
            :css('white-space', 'nowrap')
            :tag('th')
                :wikitext('Имя')
                :done()
            :tag('th')
            	:attr('class', 'unsortable')
                :css('width', '60px')
                :wikitext('Иконка')
                :done()
            :tag('th')
                :css('width', '80px')
                :wikitext('Раса')
                :done()
            :tag('th')
                :css('width', '80px')
                :wikitext('Класс')
                :done()
            :tag('th')
                :css('width', '60px')
                :wikitext('Альянс')
                :done()
            :tag('th')
                :css('width', '60px')
                :wikitext('HP')
                :done()
            :tag('th')
                :css('width', '60px')
                :wikitext('DEF')
                :done()
            :tag('th')
                :css('width', '60px')
                :wikitext('ATK')
                :done()
            :tag('th')
                :css('width', '60px')
                :wikitext('WIS')
                :done()
            :tag('th')
                :css('width', '60px')
                :wikitext('AGI')
                :done()
            :done()
    
    for k1, v1 in lib.pairsByAlphabeticalKeys(heroes) do
    	if hero_data[v1]['race'] ~= nil then
    		race = races[hero_data[v1]['race']]
    	else
    		race = "-"
    	end
    	
    	if hero_data[v1]['class'] ~= nil then
    		class = classes[hero_data[v1]['class']]
    	else
    		class = "-"
    	end
    	
    	if hero_data[v1]['alliance'] ~= nil then
    		alliance = alliances[hero_data[v1]['alliance']]
    	else
    		alliance = "-"
    	end
    		
        local rowNode = mw.html.create('tr')
        rowNode
            :tag('td')
                :attr('data-sort-value', v1)
                :wikitext(mw.ustring.format('[[%s|%s]]', v1, hero_data[v1]['name']))
                :done()
            :tag('td')
                :wikitext(mw.ustring.format('%s', p.getHeroIcon(v1, "35px")))
                :done()
            :tag('td')
                :attr('data-sort-value', race)
                :wikitext(mw.ustring.format('%s', lib.ternary(type(hero_data[v1]['race']) ~= "nil", 
                	mw.ustring.format('[[:Категория:%s (раса)|%s]]', race, race), 
                	"-")))
                :done()
            :tag('td')
                :attr('data-sort-value', class)
                :wikitext(mw.ustring.format('%s', lib.ternary(hero_data[v1]['class'] ~= nil, 
                		mw.ustring.format('[[:Категория:%s (класс)|%s]]', class, class), 
                	"-")))
                :done()
            :tag('td')
                :attr('data-sort-value', alliance)
                :wikitext(mw.ustring.format('%s',  lib.ternary(hero_data[v1]['alliance'] ~= nil, AllianceIcon(alliance, "45px"), "-")))
                :done()
            :tag('td')
                 :wikitext(mw.ustring.format('%s', lib.ternary(hero_data[v1]['stats']['hp_base'] == nil, "N/A", hero_data[v1]['stats']['hp_base'])))
                 :done()
            :tag('td')
                 :wikitext(mw.ustring.format('%s', lib.ternary(hero_data[v1]['stats']['def_base'] == nil, "N/A", hero_data[v1]['stats']['def_base'])))
                 :done()
            :tag('td')
                 :wikitext(string.format('%s', lib.ternary(hero_data[v1]['type'] == nil, "N/A", lib.ternary(hero_data[v1]['type'] == 1 or hero_data[v1]['type'] == 4, setHeroMainStat(hero_data[v1]['stats']['atk_base']), hero_data[v1]['stats']['atk_base']))))
                 :done()
            :tag('td')
                 :wikitext(string.format('%s', lib.ternary(hero_data[v1]['type'] == nil, "N/A", lib.ternary(hero_data[v1]['type'] == 2 or hero_data[v1]['type'] == 4 or hero_data[v1]['type'] == 5, setHeroMainStat(hero_data[v1]['stats']['wis_base']), hero_data[v1]['stats']['wis_base']))))
                 :done()
            :tag('td')
                 :wikitext(string.format('%s', lib.ternary(hero_data[v1]['type'] == nil, "N/A", lib.ternary(hero_data[v1]['type'] == 3 or hero_data[v1]['type'] == 5, setHeroMainStat(hero_data[v1]['stats']['agi_base']), hero_data[v1]['stats']['agi_base']))))
                 :done()
        	:done()
        tableNode:node(rowNode):newline()
    end
    
    return frame:preprocess(tostring(tableNode))
end

function p.getAllianceIcon(frame)
	local args; if frame.args == nil then args = lib.arguments(frame) else args = lib.arguments(frame.args) end
		
	local icons_data = require ('Module:IconData/alliances')
	local alliance   = args['alliance'] or args[1]
	local size       = args['size'] or args[2]
	local icon       = ""
	local str        = ""
	
	if icons_data[alliance] ~= nil then
		icon = icons_data[alliance]
	else
		return "-"
	end
	
	str = mw.ustring.format('[[Файл:%s|%s|link=:Категория:%s (альянс)]]', icon, size, alliance)
	
	return frame:preprocess(tostring(str))
end

return p