| 🌟 | 現在、 鉄壁HSは通常HSと同じダメージになります。LMG及びDMR、チャージライフル、ハンマーポイント弾を除き、すべてのダメージ値が一致していることを確認しています。 |
モジュール:WeaponInfobox
ナビゲーションに移動
検索に移動
このモジュールについての説明文ページを モジュール:WeaponInfobox/doc に作成できます
require('Module:Utility/mw.html Extensions')
local p = {}
local cfg = mw.loadData('Module:WeaponInfobox/configuration')
local aw = require('Module:Utility/Library')
local iu = require('Module:Utility/Image')
local nu = require('Module:Utility/Name')
local formatter -- lazily initialized
local getArgs -- lazily initialized
local function calcBurstAverageRPS(stat, delay)
delay = delay or stat.firerate.burst_delay
return stat.mode.burst / ((stat.mode.burst - 1) / stat.firerate.burst + delay)
end
local function createCellInRow(tbl, name)
return tbl:tag('tr')
:tag('th')
:wikitext(name)
:done()
:tag('td')
end
local function renderRow(tbl, name, item)
createCellInRow(tbl, name):wikitext(item)
end
local function renderFormatRow(tbl, name, default, common, rare, epic, opts)
opts = opts or {}
opts.separator = opts.separator or ' - '
local row = tbl:tag('tr')
:addClassIf(opts.class and type(opts.class) == 'string', opts.class)
if name ~= nil then
row:tag('th')
:attrIf(opts.headerAlign and type(opts.headerAlign) == 'string', { align = opts.headerAlign })
:wikitext(name)
end
row:tag('td')
:addClass('cell-type-number')
:attrIf(opts.align and type(opts.align) == 'string', { align = opts.align })
:wikitext(default)
if common ~= nil then
row:tag('td'):wikitext(opts.separator):done()
:tag('td')
:addClass('cell-type-number')
:attrIf(opts.align and type(opts.align) == 'string', { align = opts.align })
:wikitext(formatter:common(common))
end
if rare ~= nil then
row:tag('td'):wikitext(opts.separator):done()
:tag('td')
:addClass('cell-type-number')
:attrIf(opts.align and type(opts.align) == 'string', { align = opts.align })
:wikitext(formatter:rare(rare))
end
if epic ~= nil then
row:tag('td'):wikitext(opts.separator):done()
:tag('td')
:addClass('cell-type-number')
:attrIf(opts.align and type(opts.align) == 'string', { align = opts.align })
:wikitext(formatter:epic(epic))
end
if opts.footer ~= nil then
row:tag('td')
:attrIf(opts.footerAlign and type(opts.footerAlign) == 'string', { align = opts.footerAlign }, { align = 'left' })
:attrIf(opts.footerColspan and type(opts.footerColspan) == 'number', { colspan = opts.footerColspan })
:wikitext(opts.footer)
end
return row
end
local function renderReleaseDate(tbl, cfg, release)
local r = os.date("*t", release)
local releaseText = string.format(
'<time datetime="%04d-%02d-%02dT%02d:00:00.000+0900">%d年%d月%d日 %d時</time>~',
r.year, r.month, r.day, r.hour, r.year, r.month, r.day, r.hour)
renderRow(tbl, cfg.name, releaseText)
end
local function renderCategory(tbl, cfg, stat)
local category = nu.type(stat)
local item = string.format('[[武器#%s|%s]][[Category:%s]]', category, category, category)
renderRow(tbl, cfg.name, item)
end
local function renderAmmo(tbl, cfg, stat)
local ammo = nu.ammo(stat)
local classSuffix
if aw.stringstarts(stat, 'special_') then
classSuffix = 'special'
else
classSuffix = stat
end
local item = string.format(
'%s [[弾薬#%s|<span class="text-ammo text-ammo-%s">%s</span>]][[Category:%s]]',
iu.ammo(stat, { size = 24 }),
ammo,
classSuffix,
ammo,
ammo)
renderRow(tbl, cfg.name, item)
end
local function renderMode(tbl, cfg, stat)
local builder = require('Module:Utility/StringBuilder').new()
if stat.burst > 1 then
builder:appendFormat(cfg.burst, stat.burst)
builder:append(cfg.burst_category)
end
if stat.auto then
if not builder:isEmpty() then
builder:append(cfg.separator)
end
builder:append(cfg.auto, cfg.auto_category)
end
if stat.single then
if not builder:isEmpty() then
builder:append(cfg.separator)
end
builder:append(cfg.single, cfg.single_category)
end
renderRow(tbl, cfg.name, tostring(builder))
end
local function renderDamage(tbl, cfg, stat, ammo, pellet)
local base = stat.base
local typename = type(base)
local damageText
if pellet ~= nil then
damageText = string.format(cfg.shotgun, base, pellet)
elseif typename == 'table' then
damageText = table.concat(base, ' - ')
elseif typename == 'number' then
if stat.anvil_receiver ~= nil then
damageText = string.format(
'<span class="text-type-number">%s</span> <span class="text-separator">/</span> %s <span class="text-type-number">%s</span>',
base,
iu.hopup('アンビルレシーバー'),
formatter:legendary(stat.anvil_receiver.base))
elseif aw.isNumberAndGreaterThanZero(stat.amped) then
damageText = string.format(
'<span class="text-type-number">%s</span> <span class="text-separator">/</span> %s <span class="text-type-number">%s</span>',
base,
iu.item('シールドセル'),
stat.amped)
elseif aw.isNumberAndGreaterThanZero(stat.charged) then
damageText = string.format(
'<span class="text-type-number">%s</span> <span class="text-separator">/</span> %s <span class="text-type-number">%s</span>',
base,
iu.scope('スロット'),
stat.charged)
else
damageText = tostring(base)
end
else
return
end
renderRow(tbl, cfg.name, damageText)
local head = stat.headshot
local hlm1 = 0.2 + 0.8 * stat.headshot
local hlm2 = 0.4 + 0.6 * stat.headshot
local hlm3 = 0.5 + 0.5 * stat.headshot
local leg = stat.legshot
local sprm = stat.skullpiercer_rifling or 1
local cattext = string.format(cfg.head_category, stat.headshot)
local intable = tbl:tag('tr')
:tag('td')
:attr('colspan', 2)
:tag('table')
:addClass('condensedtable')
:addClass('listtable')
if sprm > 1 then
local spr0 = sprm
local spr1 = 0.2 + 0.8 * sprm
local spr2 = 0.4 + 0.6 * sprm
local spr3 = 0.5 + 0.5 * sprm
renderFormatRow(
intable,
cfg.head,
head, hlm1, hlm2, hlm3,
{ align = 'left', footer = cfg.unit .. cattext })
renderFormatRow(
intable,
iu.hopup('スカルピアサーライフリング') .. ' ',
spr0, spr1, spr2, spr3,
{ class = 'no-list-style', align = 'left', footer = cfg.unit })
else
renderFormatRow(
intable,
cfg.head,
head, hlm1, hlm2, hlm3,
{ align = 'left', footer = cfg.unit .. cattext })
end
local additional
if stat.anvil_receiver ~= nil then
additional = string.format(
' <span class="text-separator">/</span> %s %s',
iu.hopup('アンビルレシーバー'),
formatter:legendary('<span class="text-type-number">' .. stat.anvil_receiver.legshot .. '</span>' .. cfg.unit))
else
additional = ''
end
intable:tag('tr')
:tag('th')
:wikitext(cfg.legs)
:done()
:tag('td')
:attr('align', 'left')
:attr('colspan', 8)
:wikitext('<span class="text-type-number">' .. leg .. '</span>' .. cfg.unit .. additional)
end
local function renderFirerateRow(intbl, name, cfg, rps, opts)
opts = opts or {}
intbl:tag('tr')
:addClassIf(opts.class and type(opts.class) == 'string', opts.class)
:tag('th')
:wikitext(name)
:done()
:tag('td')
:addClass('cell-type-number')
:attr('align', 'right')
:wikitext(string.format(cfg.rps.format, rps))
:done()
:tag('td')
:wikitext(cfg.rps.unit)
:done()
:tag('td')
:tag('small')
:addClass('text-secondary')
:wikitext(cfg.rpm.name)
:done()
:done()
:tag('td')
:addClass('cell-type-number')
:attr('align', 'right')
:tag('small')
:addClass('text-secondary')
:wikitext(aw.comma(60 * rps))
:done()
:done()
:tag('td')
:tag('small')
:addClass('text-secondary')
:wikitext(cfg.rpm.unit)
end
local function renderFirerateCell(cell, cfg, rps, opts)
opts = opts or {}
opts.header = opts.header or ''
cell:wikitext(string.format(
opts.header .. '<span class="text-type-number">' .. cfg.rps.format .. '</span>' .. cfg.rps.unit .. '<span class="text-secondary"><small>(<span class="text-type-number">%s</span>' .. cfg.rpm.unit .. '</small></span>',
rps,
aw.comma(60 * rps)))
end
local function renderFirerate(tbl, cfg, stat)
local firerate = stat.firerate
if firerate == nil then
return
end
local mode = stat.mode
local cell = createCellInRow(tbl, cfg.name)
local rps
if mode.auto then
if mode.single then
if firerate.anvil_receiver then
local intbl = cell:tag('table')
:addClass('condensedtable')
:addClass('listtable')
renderFirerateRow(intbl, cfg.auto, cfg, firerate.auto)
if firerate.auto ~= firerate.single then
local singleRPS
if aw.isNumberAndGreaterThanZero(firerate.single_rechamber) then
singleRPS = 0.01 * aw.round(100 * 1 / (1 / firerate.single + firerate.single_rechamber))
else
singleRPS = firerate.single
end
renderFirerateRow(intbl, cfg.single, cfg, singleRPS)
end
if firerate.anvil_receiver then
renderFirerateRow(intbl, iu.hopup('アンビルレシーバー'), cfg, firerate.anvil_receiver)
end
return
elseif firerate.auto ~= firerate.single then
local intbl = cell:tag('table')
:addClass('condensedtable')
:addClass('listtable')
if firerate.burst then
renderFirerateRow(intbl, cfg.burst, cfg, firerate.burst)
end
renderFirerateRow(intbl, cfg.auto, cfg, firerate.auto)
local singleRPS
if aw.isNumberAndGreaterThanZero(firerate.single_rechamber) then
singleRPS = 0.01 * aw.round(100 * 1 / (1 / firerate.single + firerate.single_rechamber))
else
singleRPS = firerate.single
end
renderFirerateRow(intbl, cfg.single, cfg, singleRPS)
return
end
elseif mode.burst > 1 then
if type(firerate.auto) == 'table' then
local newcell = tbl:tag('tr')
:tag('td')
:attr('colspan', 2)
renderFirerateCell(newcell:tag('ul'):tag('li'), cfg, firerate.burst, { header = cfg.burst })
intbl = newcell:tag('table')
:addClass('condensedtable')
:addClass('listtable')
local average1 = 0.01 * aw.round(100 * calcBurstAverageRPS(stat, firerate.burst_delay[1]))
local average2 = 0.01 * aw.round(100 * calcBurstAverageRPS(stat, firerate.burst_delay[2]))
local average3 = 0.01 * aw.round(100 * calcBurstAverageRPS(stat, firerate.burst_delay[3]))
local average4 = 0.01 * aw.round(100 * calcBurstAverageRPS(stat, firerate.burst_delay[4]))
renderFormatRow(
intbl,
cfg.burst_average .. cfg.rps.name,
string.format(cfg.rps.format, average1),
string.format(cfg.rps.format, average2),
string.format(cfg.rps.format, average3),
string.format(cfg.rps.format, average4),
{ class = 'no-list-style', separator = cfg.rps.separator, footer = cfg.rps.unit })
renderFormatRow(
intbl,
cfg.rpm.name,
string.format(cfg.rpm.format, 60 * average1),
string.format(cfg.rpm.format, 60 * average2),
string.format(cfg.rpm.format, 60 * average3),
string.format(cfg.rpm.format, 60 * average4),
{ class = 'all-secondary no-list-style', headerAlign = 'right', separator = cfg.rpm.separator, footer = cfg.rpm.unit })
renderFormatRow(
intbl,
cfg.auto .. cfg.rps.name,
string.format(cfg.rps.format, firerate.auto[1]),
string.format(cfg.rps.format, firerate.auto[2]),
string.format(cfg.rps.format, firerate.auto[3]),
string.format(cfg.rps.format, firerate.auto[4]),
{ separator = cfg.rps.separator, footer = cfg.rps.unit })
renderFormatRow(
intbl,
cfg.rpm.name,
string.format(cfg.rpm.format, 60 * firerate.auto[1]),
string.format(cfg.rpm.format, 60 * firerate.auto[2]),
string.format(cfg.rpm.format, 60 * firerate.auto[3]),
string.format(cfg.rpm.format, 60 * firerate.auto[4]),
{ class = 'all-secondary no-list-style', headerAlign = 'right', separator = cfg.rpm.separator, footer = cfg.rpm.unit })
else
local intbl = cell:tag('table')
:addClass('condensedtable')
:addClass('listtable')
local average = 0.01 * aw.round(100 * calcBurstAverageRPS(stat))
renderFirerateRow(intbl, cfg.burst, cfg, firerate.burst)
renderFirerateRow(intbl, cfg.burst_average, cfg, average, { class = 'no-list-style' })
renderFirerateRow(intbl, cfg.auto, cfg, firerate.auto)
end
return
end
rps = firerate.auto
elseif mode.single then
if mode.burst > 1 then
local intbl = cell:tag('table')
:addClass('condensedtable')
:addClass('listtable')
local average = 0.01 * aw.round(100 * calcBurstAverageRPS(stat))
renderFirerateRow(intbl, cfg.burst, cfg, firerate.burst)
renderFirerateRow(intbl, cfg.burst_average, cfg, average, { class = 'no-list-style' })
local singleRPS
if aw.isNumberAndGreaterThanZero(firerate.single_rechamber) then
singleRPS = 0.01 * aw.round(100 * 1 / (1 / firerate.single + firerate.single_rechamber))
else
singleRPS = firerate.single
end
renderFirerateRow(intbl, cfg.single, cfg, singleRPS)
return
end
if aw.isNumberAndGreaterThanZero(firerate.single_rechamber) then
rps = 0.01 * aw.round(100 * 1 / (1 / firerate.single + firerate.single_rechamber))
else
rps = firerate.single
end
else
return
end
if type(rps) == 'table' then
local intable = cell:tag('table'):addClass('condensedtable')
renderFormatRow(
intable,
cfg.rps.name,
string.format(cfg.rps.format, rps[1]),
string.format(cfg.rps.format, rps[2]),
string.format(cfg.rps.format, rps[3]),
string.format(cfg.rps.format, rps[4]),
{ separator = cfg.rps.separator, footer = cfg.rps.unit })
renderFormatRow(
intable,
cfg.rpm.name,
string.format(cfg.rpm.format, 60 * rps[1]),
string.format(cfg.rpm.format, 60 * rps[2]),
string.format(cfg.rpm.format, 60 * rps[3]),
string.format(cfg.rpm.format, 60 * rps[4]),
{ class = 'all-secondary', separator = cfg.rpm.separator, footer = cfg.rpm.unit })
else
renderFirerateCell(cell, cfg, rps)
end
end
local function renderProjectileSpeed(tbl, cfg, projectile_speed)
if projectile_speed == nil then
return
end
local text
if projectile_speed == math.huge then
text = cfg.hitscan
else
text = '<span class="text-type-number">' .. string.format(cfg.format, aw.comma(0.1 * projectile_speed)) .. '</span>' .. cfg.unit
end
renderRow(tbl, cfg.name, text)
end
local function renderRowDPS(tbl, name, leg, body, head, skullpiercer, tag)
tag = tag or 'td'
local row = tbl:tag('tr')
row:tag('th'):wikitext(name)
if leg == '' then
row:tag(tag)
:attr('align', 'center')
:addClass('disabled')
:wikitext('–')
elseif leg ~= nil and leg ~= body then
row:tag(tag):wikitext(leg)
end
row
:tag(tag):wikitext(body):done()
:tag(tag):wikitext(head)
if skullpiercer ~= nil then
row:tag(tag):wikitext(skullpiercer)
end
end
local function toDPSText(dps)
return string.format("%.1f", dps)
end
local function renderDPSTable(cell, name, pellet, base, damages, firerate, useRound)
local headDamage = aw.round(damages.headshot * base)
local legDamage = aw.round(damages.legshot * base)
local skullpiercer = damages.skullpiercer_rifling
local selectiveRound = useRound and aw.round or aw.roundover
local skullpiercerHeader = nil
local commonSkullpiercerDPS = nil
local lowprofileSkullpiercerDPS = nil
local fortifiedSkullpiercerDPS = nil
if skullpiercer ~= nil then
skullpiercerHeader = iu.hopup('スカルピアサーライフリング')
local skullpiercerDamage = aw.round(skullpiercer * base)
commonSkullpiercerDPS = toDPSText(pellet * skullpiercerDamage * firerate)
lowprofileSkullpiercerDPS = toDPSText(pellet * selectiveRound(1.05 * skullpiercerDamage) * firerate)
fortifiedSkullpiercerDPS = toDPSText(pellet * aw.round(0.85 * skullpiercerDamage) * firerate)
end
if type(firerate) == 'table' then
firerate = firerate[1]
end
local intable = cell:tag('table')
:addClass('intable')
:addClass('numbertable')
local lowprofileLegDamagePlaceholder
if damages.legshot == 1 then
lowprofileLegDamagePlaceholder = nil
renderRowDPS(intable, name, nil, '胴', '頭', skullpiercerHeader, 'th')
else
lowprofileLegDamagePlaceholder = ''
renderRowDPS(intable, name, '脚', '胴', '頭', skullpiercerHeader, 'th')
end
renderRowDPS(
intable,
'通常',
toDPSText(pellet * legDamage * firerate),
toDPSText(pellet * base * firerate),
toDPSText(pellet * headDamage * firerate),
commonSkullpiercerDPS)
renderRowDPS(
intable,
'小柄',
lowprofileLegDamagePlaceholder,
toDPSText(pellet * selectiveRound(1.05 * base, useRound) * firerate),
toDPSText(pellet * selectiveRound(1.05 * headDamage, useRound) * firerate),
lowprofileSkullpiercerDPS)
renderRowDPS(
intable,
'鉄壁',
toDPSText(pellet * aw.round(0.85 * legDamage) * firerate),
toDPSText(pellet * aw.round(0.85 * base) * firerate),
toDPSText(pellet * aw.round(0.85 * headDamage) * firerate),
fortifiedSkullpiercerDPS)
end
local function renderDPS(tbl, name, stat)
if stat.firerate == nil then
return
end
local damage = stat.damage.base
renderRow(tbl, name, '')
local pellet = stat.pellet or 1
local useRound = stat.damage.round or false
local cell = tbl:tag('tr'):tag('td'):attr('colspan', 2)
if type(damage) == 'table' then
for _, damage in ipairs(damage) do
if stat.mode.single then
renderDPSTable(
cell,
'',
pellet,
damage,
stat.damage,
stat.firerate.single,
useRound)
end
end
else
if stat.mode.burst and stat.mode.burst > 1 then
local average
if type(stat.firerate.burst_delay) == 'table' then
average = calcBurstAverageRPS(stat, stat.firerate.burst_delay[1])
else
average = calcBurstAverageRPS(stat)
end
renderDPSTable(
cell,
'',
pellet,
stat.damage.base,
stat.damage,
average,
useRound)
end
if stat.mode.auto then
renderDPSTable(
cell,
'',
pellet,
stat.damage.base,
stat.damage,
stat.firerate.auto,
useRound)
end
if stat.mode.single and stat.firerate.auto ~= stat.firerate.single then
renderDPSTable(
cell,
'',
pellet,
stat.damage.base,
stat.damage,
stat.firerate.single,
useRound)
end
if stat.damage.anvil_receiver and stat.firerate.anvil_receiver then
renderDPSTable(
cell,
iu.hopup('アンビルレシーバー'),
pellet,
stat.damage.anvil_receiver.base,
stat.damage.anvil_receiver,
stat.firerate.anvil_receiver,
useRound)
end
end
end
local function renderMagazineRow(intbl, name, mag, rsvmag, cfg, opts)
opts = opts or {}
intbl:tag('tr')
:addClassIf(opts.class and type(opts.class) == 'string', opts.class)
:tag('th')
:wikitext(name)
:done()
:tag('td')
:addClass('cell-type-number')
:attr('align', 'right')
:wikitext(mag)
:done()
:tag('td')
:wikitext(cfg.unit)
:done()
:tag('td')
:addClass('text-secondary')
:wikitext(' / ')
:done()
:tag('td')
:addClass('cell-type-number')
:attr('align', 'right')
:wikitext(rsvmag == math.huge and cfg.infinity or rsvmag)
:done()
:tag('td')
:wikitext(cfg.unit)
end
local function renderMagazine(tbl, cfg, stat, isModdedLoaderAttachable)
local magazine = stat.magazine
local typename = type(magazine)
if typename == 'table' then
if isModdedLoaderAttachable then
local intable = createCellInRow(tbl, cfg.name)
:tag('table')
:addClass('condensedtable')
renderFormatRow(
intable,
'',
magazine[1], magazine[2], magazine[3], magazine[4], { footer = cfg.units })
renderFormatRow(
intable,
formatter:hopup('改造ローダー') .. ' ',
aw.round(1.15 * magazine[1]),
aw.round(1.15 * magazine[2]),
aw.round(1.15 * magazine[3]),
aw.round(1.15 * magazine[4]),
{ footer = cfg.units })
else
local text = formatter:format(magazine[1], magazine[2], magazine[3], magazine[4], cfg.units, ' - ')
renderRow(tbl, cfg.name, text)
end
elseif typename == 'number' then
local text
if magazine == math.huge then
if aw.isNumber(stat.overheat) and stat.firerate and stat.firerate.auto then
text = string.format(
'%s (<span class="text-type-number">%d</span>%s <span class="text-separator">/</span> %s <span class="text-type-number">%d</span>%s)',
cfg.infinity,
1 + math.floor(stat.overheat * stat.firerate.auto),
cfg.unit,
formatter:hopup('改造ローダー'),
1 + math.floor(1.15 * stat.overheat * stat.firerate.auto),
cfg.unit)
else
text = cfg.infinity
end
elseif stat.rounds_per_shot and stat.rounds_per_shot.single and stat.rounds_per_shot.single > 1 then
local times = magazine / stat.rounds_per_shot.single
local timesText
if type(cfg.times.format) == 'table' then
if times > 2 then
timesText = string.format(cfg.times.format[3], times)
else
timesText = cfg.times.format[times]
end
else
timesText = string.format(cfg.times.format, times)
end
text = string.format(
'<span class="text-type-number">%d</span>%s <span class="text-secondary"><small>(%s)</small></span>',
magazine, cfg.unit, timesText)
elseif aw.isNumber(stat.magazine_reserve) then
if isModdedLoaderAttachable then
local intbl = createCellInRow(tbl, cfg.name)
:tag('table')
:addClass('condensedtable')
renderMagazineRow(intbl, '', magazine, stat.magazine_reserve, cfg)
renderMagazineRow(intbl, formatter:hopup('改造ローダー') .. ' ', aw.round(1.15 * magazine), stat.magazine_reserve, cfg)
return
else
text = string.format(
'<span class="text-type-number">%d</span>%s <span class="text-separator">/</span> <span class="text-type-number">%s</span>%s',
magazine,
cfg.unit,
stat.magazine_reserve == math.huge and cfg.infinity or stat.magazine_reserve,
cfg.unit)
end
else
text = string.format('<span class="text-type-number">%d</span>%s', magazine, cfg.unit)
end
renderRow(tbl, cfg.name, text)
end
end
local function renderReload(tbl, cfg, reload, attachments, ammo, isModdedLoaderAttachable)
if reload.full == nil then
return
end
local muls
if ammo == 'heavy' or ammo == 'special_heavy' then
muls = { level2 = 0.92, level3 = 0.87 }
else
muls = { level2 = 0.95, level3 = 0.9 }
end
local incompatible = not attachments.extended_mag_or_shotgun_bolt
if incompatible or ammo == 'shotgun' or aw.stringstarts(ammo, "special_") then
if reload.tactical ~= nil and reload.tactical ~= reload.full then
local tacticalText, fullText
if incompatible or ammo == 'special_sniper' then
tacticalText = tostring(reload.tactical)
fullText = tostring(reload.full)
else
tacticalText = tostring(muls.level3 * reload.tactical)
fullText = tostring(muls.level3 * reload.full)
end
local intable = createCellInRow(tbl, cfg.name)
:tag('table')
:addClass('condensedtable')
:addClass('listtable')
renderFormatRow(
intable,
cfg.tactical.name .. ' ',
string.format(cfg.tactical.format, reload.tactical),
nil, nil, nil, { footer = cfg.tactical.unit })
if isModdedLoaderAttachable then
renderFormatRow(
intable,
formatter:hopup('改造ローダー') .. ' ',
string.format(cfg.tactical.format, 0.75 * reload.tactical),
nil, nil, nil, { class = 'no-list-style', headerAlign = 'right', footer = cfg.tactical.unit })
end
renderFormatRow(
intable,
cfg.full.name .. ' ',
string.format(cfg.full.format, reload.full),
nil, nil, nil, { footer = cfg.full.unit })
if isModdedLoaderAttachable then
renderFormatRow(
intable,
formatter:hopup('改造ローダー') .. ' ',
string.format(cfg.full.format, 0.75 * reload.full),
nil, nil, nil, { class = 'no-list-style', headerAlign = 'right', footer = cfg.full.unit })
end
elseif isModdedLoaderAttachable then
local time
if incompatible then
time = reload.full
else
time = muls.level3 * reload.full
end
local text = string.format(
cfg.full.format .. cfg.full.unit .. ' <span class="text-separator">/</span> %s ' .. cfg.full.format .. cfg.full.unit,
time,
formatter:hopup('改造ローダー'),
0.75 * time)
renderRow(tbl, cfg.name, text)
else
local time
if incompatible or ammo == 'special_sniper' then
time = reload.full
else
time = muls.level3 * reload.full
end
renderRow(tbl, cfg.name, string.format(cfg.full.format, time) .. cfg.full.unit)
end
elseif reload.tactical ~= nil and reload.tactical ~= reload.full then
renderRow(tbl, cfg.name, '')
local intable = tbl:tag('tr')
:tag('td')
:attr('colspan', 2)
:tag('table')
:addClass('condensedtable')
:addClass('listtable')
renderFormatRow(
intable,
cfg.tactical.name .. ' ',
string.format(cfg.tactical.format, reload.tactical),
nil,
string.format(cfg.tactical.format, muls.level2 * reload.tactical),
string.format(cfg.tactical.format, muls.level3 * reload.tactical),
{ footer = cfg.tactical.unit })
if isModdedLoaderAttachable then
renderFormatRow(
intable,
formatter:hopup('改造ローダー') .. ' ',
string.format(cfg.tactical.format, 0.75 * reload.tactical),
nil,
string.format(cfg.tactical.format, 0.75 * muls.level2 * reload.tactical),
string.format(cfg.tactical.format, 0.75 * muls.level3 * reload.tactical),
{ class = 'no-list-style', headerAlign = 'right', footer = cfg.tactical.unit })
end
renderFormatRow(
intable,
cfg.full.name .. ' ',
string.format(cfg.full.format, reload.full),
nil,
string.format(cfg.full.format, muls.level2 * reload.full),
string.format(cfg.full.format, muls.level3 * reload.full),
{ footer = cfg.full.unit })
if isModdedLoaderAttachable then
renderFormatRow(
intable,
formatter:hopup('改造ローダー') .. ' ',
string.format(cfg.full.format, 0.75 * reload.full),
nil,
string.format(cfg.full.format, 0.75 * muls.level2 * reload.full),
string.format(cfg.full.format, 0.75 * muls.level3 * reload.full),
{ class = 'no-list-style', headerAlign = 'right', footer = cfg.full.unit })
end
else
local text = formatter:format(
string.format(cfg.full.format, reload.full),
nil,
string.format(cfg.full.format, muls.level2 * reload.full),
string.format(cfg.full.format, muls.level3 * reload.full),
cfg.full.unit, ' - ')
renderRow(tbl, cfg.name, text)
end
end
local function renderDraw(tbl, cfg, draw, quickdraw_holster, attachments, ammo)
if draw == nil then
return
end
local muls
if ammo == 'heavy' or ammo == 'special_heavy' then
muls = { level2 = 0.92, level3 = 0.87 }
else
muls = { level2 = 0.95, level3 = 0.9 }
end
local incompatible = not attachments.stock
if incompatible or aw.stringstarts(ammo, "special_") then
local time
if incompatible or ammo == 'special_sniper' then
time = draw
else
time = 0.75 * draw
end
local text
if quickdraw_holster > 0 then
text = string.format(
cfg.format .. cfg.unit .. ' <span class="text-separator">/</span> %s ' .. formatter:epic(cfg.format .. cfg.unit),
time,
iu.hopup('クイックドローホルスター'),
quickdraw_holster * time)
else
text = string.format(cfg.format, time) .. cfg.unit
end
renderRow(tbl, cfg.name, text)
elseif quickdraw_holster > 0 then
local intable = createCellInRow(tbl, cfg.name)
:tag('table')
:addClass('condensedtable')
renderFormatRow(
intable,
'',
string.format(cfg.format, draw),
string.format(cfg.format, 0.85 * draw),
string.format(cfg.format, 0.80 * draw),
string.format(cfg.format, 0.75 * draw),
{ footer = cfg.unit })
renderFormatRow(
intable,
iu.hopup('クイックドローホルスター') .. ' ',
string.format(cfg.format, quickdraw_holster * draw),
string.format(cfg.format, 0.85 * quickdraw_holster * draw),
string.format(cfg.format, 0.80 * quickdraw_holster * draw),
string.format(cfg.format, 0.75 * quickdraw_holster * draw),
{ footer = cfg.unit })
else
local text = formatter:format(
string.format(cfg.format, draw),
string.format(cfg.format, 0.85 * draw),
string.format(cfg.format, 0.80 * draw),
string.format(cfg.format, 0.75 * draw),
cfg.unit, ' - ')
renderRow(tbl, cfg.name, text)
end
end
local function createTable(cfg, stat)
local isModdedLoaderAttachable = stat.category == 'light_machine_gun' or stat.ammo == 'minigun'
local tbl = mw.html.create('table')
renderReleaseDate(tbl, cfg.release, stat.release)
renderCategory(tbl, cfg.category, stat.category)
renderAmmo(tbl, cfg.ammo, stat.ammo)
renderMode(tbl, cfg.mode, stat.mode)
renderDamage(tbl, cfg.damage, stat.damage, stat.ammo, stat.pellet)
renderFirerate(tbl, cfg.firerate, stat)
renderProjectileSpeed(tbl, cfg.projectilespeed, stat.projectile_speed)
renderMagazine(tbl, cfg.magazine, stat, isModdedLoaderAttachable)
if stat.time then
if stat.time.draw then
renderDraw(tbl, cfg.draw, stat.time.draw, stat.time.quickdraw_holster or 0, stat.attachments, stat.ammo)
end
if stat.time.reload then
renderReload(tbl, cfg.reload, stat.time.reload, stat.attachments, stat.ammo, isModdedLoaderAttachable)
end
end
renderDPS(tbl, 'DPS', stat)
return tbl
end
local function renderInfobox(args)
local cfglang = cfg[args and args.lang or 'ja']
local stat = mw.loadData('Module:Stat/Weapon')[args.name]
local div = mw.html.create('div')
:addClass('tpl-infobox-right')
:addClass('tpl-weapon')
if aw.stringstarts(stat.ammo, "special_") then
div:addClass('tpl-weapon-special')
else
div:addClass('tpl-weapon-' .. stat.ammo)
end
div:tag('div')
:addClass('tpl-weapon-header')
:wikitext(args.name .. iu.ammo(stat.ammo, { size = 40 }))
div:node(createTable(cfglang, stat))
return div
end
function p._main(args, frame)
formatter = require('Module:Utility/Formatter').new(frame)
return tostring(renderInfobox(args))
end
function p.main(frame)
if not getArgs then
getArgs = require('Module:Arguments').getArgs
end
args = getArgs(frame)
return p._main(args, frame)
end
return p