🌟 | 現在、 鉄壁ヘッドショットには対応済みです。 鉄壁HSは通常HSと同じダメージになります。LMG及びDMR、チャージライフル、ハンマーポイント弾を除き、すべてのダメージ値が一致していることを確認しています。 |
「モジュール:DamageTable」の版間の差分
ナビゲーションに移動
検索に移動
(不要な記述の削除) |
(確殺数に応じたカラーリングの実装) |
||
5行目: | 5行目: | ||
local function round(num) | local function round(num) | ||
return math.floor(tonumber(string.format("%.3f", num)) + 0.5) | return math.floor(tonumber(string.format("%.3f", num)) + 0.5) | ||
end | |||
local function convertHslToRgb(hue, saturation, lightness) | |||
hue = math.max(0, math.min(1, hue)) | |||
saturation = math.max(0, math.min(1, saturation)) | |||
lightness = math.max(0, math.min(1, lightness)) | |||
if saturation == 0 then | |||
return lightness, lightness, lightness | |||
else | |||
local function to(p, q, t) | |||
if t < 0 then t = t + 1 end | |||
if t > 1 then t = t - 1 end | |||
if t < 1/6 then | |||
return p + (q - p) * 6 * t | |||
elseif t < 3/6 then | |||
return q | |||
elseif t < 4/6 then | |||
return p + (q - p) * (2/3 - t) * 6 | |||
else | |||
return p | |||
end | |||
end | |||
local q | |||
if lightness < 0.5 then | |||
q = lightness * (1 + saturation) | |||
else | |||
q = lightness + saturation - lightness * saturation | |||
end | |||
local p = 2 * lightness - q | |||
return to(p, q, hue + 1/3), to(p, q, hue), to(p, q, hue - 1/3) | |||
end | |||
end | |||
local function getColorAsString(hue) | |||
local r, g, b = convertHslToRgb(hue, 0.91, 0.89) | |||
return '#' | |||
.. string.format('%02X', 255 * r) | |||
.. string.format('%02X', 255 * g) | |||
.. string.format('%02X', 255 * b) | |||
end | |||
local function getShotCount(damage, health) | |||
return math.ceil(health / damage) | |||
end | end | ||
36行目: | 83行目: | ||
end | end | ||
local function renderRowForSTK(row, damage, pellet, offset) | local function renderCell(row, allDamage, health, minCount, maxCount, offset) | ||
local shotCount = getShotCount(allDamage, health) | |||
local ratio = (shotCount + offset - minCount) / (maxCount - minCount) | |||
row:tag('td') | |||
:attr('align', 'right') | |||
:css('background-color', getColorAsString(ratio - 0.1)) | |||
:wikitext(offset + shotCount) | |||
end | |||
local function renderRowForSTK(row, damage, pellet, minCount, maxCount, offset) | |||
offset = offset or 0 | offset = offset or 0 | ||
local allDamage = pellet * damage | local allDamage = pellet * damage | ||
row | renderCell(row, allDamage, 100, minCount, maxCount, offset) | ||
row | renderCell(row, allDamage, 150, minCount, maxCount, offset) | ||
row | renderCell(row, allDamage, 175, minCount, maxCount, offset) | ||
row | renderCell(row, allDamage, 200, minCount, maxCount, offset) | ||
row | renderCell(row, allDamage, 225, minCount, maxCount, offset) | ||
end | end | ||
local function renderRow(table, name, damage, pellet, rowspan) | local function renderRow(table, name, damage, pellet, minCount, maxCount, rowspan) | ||
rowspan = rowspan or 0 | rowspan = rowspan or 0 | ||
73行目: | 129行目: | ||
row:tag('td'):attr('align', 'right'):wikitext(damage) | row:tag('td'):attr('align', 'right'):wikitext(damage) | ||
end | end | ||
renderRowForSTK(row, damage, pellet) | renderRowForSTK(row, damage, pellet, minCount, maxCount) | ||
end | end | ||
local function renderRowForGunShiled(table, damage, baseDamage, pellet) | local function renderRowForGunShiled(table, damage, baseDamage, pellet, minCount, maxCount) | ||
local row = table:tag('tr') | local row = table:tag('tr') | ||
row:tag('th') | row:tag('th') | ||
85行目: | 141行目: | ||
:wikitext('+ガンシールド') | :wikitext('+ガンシールド') | ||
local countForGunShiled = | local countForGunShiled = getShotCount(pellet * baseDamage, 50) | ||
if pellet > 1 then | if pellet > 1 then | ||
row:tag('td'):attr('align', 'right'):wikitext((baseDamage * pellet) .. '<small> (' .. baseDamage .. ' × ' .. pellet .. ')</small>') | row:tag('td'):attr('align', 'right'):wikitext((baseDamage * pellet) .. '<small> (' .. baseDamage .. ' × ' .. pellet .. ')</small>') | ||
91行目: | 147行目: | ||
row:tag('td'):attr('align', 'right'):wikitext(baseDamage) | row:tag('td'):attr('align', 'right'):wikitext(baseDamage) | ||
end | end | ||
renderRowForSTK(row, damage, pellet, countForGunShiled) | renderRowForSTK(row, damage, pellet, minCount, maxCount, countForGunShiled) | ||
end | end | ||
local function renderTable(args) | local function renderTable(args) | ||
local damage = args.damage or 20 | |||
local baseDamage | local baseDamage | ||
if args.amped then | if args.amped then | ||
baseDamage = round(1.2 * | baseDamage = round(1.2 * damage) | ||
else | else | ||
baseDamage = | baseDamage = damage | ||
end | end | ||
107行目: | 164行目: | ||
local headDamage = round(headMul * baseDamage) | local headDamage = round(headMul * baseDamage) | ||
local legMul = args.leg or 0.8 | local legMul = args.leg or 0.8 | ||
local legDamage = round(mul * round(legMul * baseDamage)) | |||
local minCount = getShotCount(round(1.05 * round(headMul * round(1.2 * damage))), 100) | |||
local maxCount = getShotCount(round(0.85 * round(legMul * damage)), 225) | |||
local table = mw.html.create('table') | local table = mw.html.create('table') | ||
115行目: | 175行目: | ||
"頭 (x" .. headMul .. ")", | "頭 (x" .. headMul .. ")", | ||
round(mul * headDamage), | round(mul * headDamage), | ||
pellet, | pellet, minCount, maxCount, | ||
4) | 4) | ||
123行目: | 183行目: | ||
'<span class="text-rarity text-rarity-common">Lv.1 (x' .. hlmLv1Mul .. ')</span>', | '<span class="text-rarity text-rarity-common">Lv.1 (x' .. hlmLv1Mul .. ')</span>', | ||
round(mul * round(hlmLv1Mul * baseDamage)), | round(mul * round(hlmLv1Mul * baseDamage)), | ||
pellet) | pellet, minCount, maxCount) | ||
local hlmLv2Mul = 0.4 + 0.6 * headMul | local hlmLv2Mul = 0.4 + 0.6 * headMul | ||
130行目: | 190行目: | ||
'<span class="text-rarity text-rarity-rare">Lv.2 (x' .. hlmLv2Mul .. ')</span>', | '<span class="text-rarity text-rarity-rare">Lv.2 (x' .. hlmLv2Mul .. ')</span>', | ||
round(mul * round(hlmLv2Mul * baseDamage)), | round(mul * round(hlmLv2Mul * baseDamage)), | ||
pellet) | pellet, minCount, maxCount) | ||
local hlmLv3Mul = 0.5 + 0.5 * headMul | local hlmLv3Mul = 0.5 + 0.5 * headMul | ||
137行目: | 197行目: | ||
'<span class="text-rarity text-rarity-epic">Lv.3</span>/<span class="text-rarity text-rarity-legendary">4 (x' .. hlmLv3Mul .. ')</span>', | '<span class="text-rarity text-rarity-epic">Lv.3</span>/<span class="text-rarity text-rarity-legendary">4 (x' .. hlmLv3Mul .. ')</span>', | ||
round(mul * round(hlmLv3Mul * baseDamage)), | round(mul * round(hlmLv3Mul * baseDamage)), | ||
pellet) | pellet, minCount, maxCount) | ||
local bodyDamage = round(mul * baseDamage) | local bodyDamage = round(mul * baseDamage) | ||
if legMul == 1 then | if legMul == 1 then | ||
if mul == 0.85 then | if mul == 0.85 then | ||
renderRow(table, "胴・脚", bodyDamage, pellet, 2) | renderRow(table, "胴・脚", bodyDamage, pellet, minCount, maxCount, 2) | ||
renderRowForGunShiled(table, bodyDamage, baseDamage, pellet) | renderRowForGunShiled(table, bodyDamage, baseDamage, pellet, minCount, maxCount) | ||
else | else | ||
renderRow(table, "胴・脚", bodyDamage, pellet, 1) | renderRow(table, "胴・脚", bodyDamage, pellet, minCount, maxCount, 1) | ||
end | end | ||
else | else | ||
if mul == 1.05 then | if mul == 1.05 then | ||
renderRow(table, "胴・脚", bodyDamage, pellet, 1) | renderRow(table, "胴・脚", bodyDamage, pellet, minCount, maxCount, 1) | ||
elseif mul == 0.85 then | elseif mul == 0.85 then | ||
renderRow(table, "胴", bodyDamage, pellet, 2) | renderRow(table, "胴", bodyDamage, pellet, minCount, maxCount, 2) | ||
renderRowForGunShiled(table, bodyDamage, baseDamage, pellet) | renderRowForGunShiled(table, bodyDamage, baseDamage, pellet, minCount, maxCount) | ||
renderRow(table, "脚 (x" .. legMul .. ")", legDamage, pellet, 1) | renderRow(table, "脚 (x" .. legMul .. ")", legDamage, pellet, minCount, maxCount, 1) | ||
else | else | ||
renderRow(table, "胴", bodyDamage, pellet, 1) | renderRow(table, "胴", bodyDamage, pellet, minCount, maxCount, 1) | ||
renderRow(table, "脚 (x" .. legMul .. ")", legDamage, pellet, 1) | renderRow(table, "脚 (x" .. legMul .. ")", legDamage, pellet, minCount, maxCount, 1) | ||
end | end | ||
end | end |
2021年1月23日 (土) 11:28時点における版
このモジュールについての説明文ページを モジュール:DamageTable/doc に作成できます
local p = {} local getArgs -- lazily initialized local function round(num) return math.floor(tonumber(string.format("%.3f", num)) + 0.5) end local function convertHslToRgb(hue, saturation, lightness) hue = math.max(0, math.min(1, hue)) saturation = math.max(0, math.min(1, saturation)) lightness = math.max(0, math.min(1, lightness)) if saturation == 0 then return lightness, lightness, lightness else local function to(p, q, t) if t < 0 then t = t + 1 end if t > 1 then t = t - 1 end if t < 1/6 then return p + (q - p) * 6 * t elseif t < 3/6 then return q elseif t < 4/6 then return p + (q - p) * (2/3 - t) * 6 else return p end end local q if lightness < 0.5 then q = lightness * (1 + saturation) else q = lightness + saturation - lightness * saturation end local p = 2 * lightness - q return to(p, q, hue + 1/3), to(p, q, hue), to(p, q, hue - 1/3) end end local function getColorAsString(hue) local r, g, b = convertHslToRgb(hue, 0.91, 0.89) return '#' .. string.format('%02X', 255 * r) .. string.format('%02X', 255 * g) .. string.format('%02X', 255 * b) end local function getShotCount(damage, health) return math.ceil(health / damage) end local function renderHeader(table, mul) local row = table:tag('tr') local cell = row:tag('th') :attr('colspan', 2) :attr('rowspan', 2) if mul == 1 then cell:wikitext('部位') elseif mul == 1.05 then cell:wikitext('部位 (小柄)') elseif mul == 0.85 then cell:wikitext('部位 (鉄壁)') else cell:wikitext('部位 (x' .. mul .. ')') end row:tag('th') :attr('rowspan', 2) :wikitext('ダメージ') row:tag('th') :attr('colspan', 5) :wikitext('確殺数') row = table:tag('tr') row:tag('th'):wikitext('100<small> HP</small>') row:tag('th'):wikitext('<span class="text-rarity text-rarity-common">150<small> HP</small></span>') row:tag('th'):wikitext('<span class="text-rarity text-rarity-rare">175<small> HP</small></span>') row:tag('th'):wikitext('<span class="text-rarity text-rarity-epic">200<small> HP</small></span>') row:tag('th'):wikitext('<span class="text-rarity text-rarity-heirloom">225<small> HP</small></span>') end local function renderCell(row, allDamage, health, minCount, maxCount, offset) local shotCount = getShotCount(allDamage, health) local ratio = (shotCount + offset - minCount) / (maxCount - minCount) row:tag('td') :attr('align', 'right') :css('background-color', getColorAsString(ratio - 0.1)) :wikitext(offset + shotCount) end local function renderRowForSTK(row, damage, pellet, minCount, maxCount, offset) offset = offset or 0 local allDamage = pellet * damage renderCell(row, allDamage, 100, minCount, maxCount, offset) renderCell(row, allDamage, 150, minCount, maxCount, offset) renderCell(row, allDamage, 175, minCount, maxCount, offset) renderCell(row, allDamage, 200, minCount, maxCount, offset) renderCell(row, allDamage, 225, minCount, maxCount, offset) end local function renderRow(table, name, damage, pellet, minCount, maxCount, rowspan) rowspan = rowspan or 0 local row = table:tag('tr') if rowspan > 1 then row:tag('th') :attr('colspan', 2) :css('border-bottom', "0 none transparent") :wikitext(name) elseif rowspan == 1 then row:tag('th') :attr('colspan', 2) :wikitext(name) else row:tag('th') :css('border-top', "0 none transparent") :css('border-bottom', "0 none transparent") :wikitext(' ') row:tag('th') :wikitext(name) end if pellet > 1 then row:tag('td'):attr('align', 'right'):wikitext((damage * pellet) .. '<small> (' .. damage .. ' × ' .. pellet .. ')</small>') else row:tag('td'):attr('align', 'right'):wikitext(damage) end renderRowForSTK(row, damage, pellet, minCount, maxCount) end local function renderRowForGunShiled(table, damage, baseDamage, pellet, minCount, maxCount) local row = table:tag('tr') row:tag('th') :css('border-top', "0 none transparent") :css('border-bottom', "0 none transparent") :wikitext(' ') row:tag('th') :wikitext('+ガンシールド') local countForGunShiled = getShotCount(pellet * baseDamage, 50) if pellet > 1 then row:tag('td'):attr('align', 'right'):wikitext((baseDamage * pellet) .. '<small> (' .. baseDamage .. ' × ' .. pellet .. ')</small>') else row:tag('td'):attr('align', 'right'):wikitext(baseDamage) end renderRowForSTK(row, damage, pellet, minCount, maxCount, countForGunShiled) end local function renderTable(args) local damage = args.damage or 20 local baseDamage if args.amped then baseDamage = round(1.2 * damage) else baseDamage = damage end local pellet = args.pellet or 1 local mul = args.mul or 1 local headMul = args.head or 2 local headDamage = round(headMul * baseDamage) local legMul = args.leg or 0.8 local legDamage = round(mul * round(legMul * baseDamage)) local minCount = getShotCount(round(1.05 * round(headMul * round(1.2 * damage))), 100) local maxCount = getShotCount(round(0.85 * round(legMul * damage)), 225) local table = mw.html.create('table') :addClass('wikitable') renderHeader(table, mul) renderRow( table, "頭 (x" .. headMul .. ")", round(mul * headDamage), pellet, minCount, maxCount, 4) local hlmLv1Mul = 0.2 + 0.8 * headMul renderRow( table, '<span class="text-rarity text-rarity-common">Lv.1 (x' .. hlmLv1Mul .. ')</span>', round(mul * round(hlmLv1Mul * baseDamage)), pellet, minCount, maxCount) local hlmLv2Mul = 0.4 + 0.6 * headMul renderRow( table, '<span class="text-rarity text-rarity-rare">Lv.2 (x' .. hlmLv2Mul .. ')</span>', round(mul * round(hlmLv2Mul * baseDamage)), pellet, minCount, maxCount) local hlmLv3Mul = 0.5 + 0.5 * headMul renderRow( table, '<span class="text-rarity text-rarity-epic">Lv.3</span>/<span class="text-rarity text-rarity-legendary">4 (x' .. hlmLv3Mul .. ')</span>', round(mul * round(hlmLv3Mul * baseDamage)), pellet, minCount, maxCount) local bodyDamage = round(mul * baseDamage) if legMul == 1 then if mul == 0.85 then renderRow(table, "胴・脚", bodyDamage, pellet, minCount, maxCount, 2) renderRowForGunShiled(table, bodyDamage, baseDamage, pellet, minCount, maxCount) else renderRow(table, "胴・脚", bodyDamage, pellet, minCount, maxCount, 1) end else if mul == 1.05 then renderRow(table, "胴・脚", bodyDamage, pellet, minCount, maxCount, 1) elseif mul == 0.85 then renderRow(table, "胴", bodyDamage, pellet, minCount, maxCount, 2) renderRowForGunShiled(table, bodyDamage, baseDamage, pellet, minCount, maxCount) renderRow(table, "脚 (x" .. legMul .. ")", legDamage, pellet, minCount, maxCount, 1) else renderRow(table, "胴", bodyDamage, pellet, minCount, maxCount, 1) renderRow(table, "脚 (x" .. legMul .. ")", legDamage, pellet, minCount, maxCount, 1) end end return table end function p._main(args) return tostring(renderTable(args)) end function p.main(frame) if not getArgs then getArgs = require('Module:Arguments').getArgs end args = getArgs(frame) -- fix arguments args.damage = tonumber(args.damage) args.pellet = tonumber(args.pellet) args.head = tonumber(args.head) args.leg = tonumber(args.leg) args.mul = tonumber(args.mul) args.amped = args.amped == 'true' return p._main(args) end return p