| 🌟 | 現在、 鉄壁HSは通常HSと同じダメージになります。LMG及びDMR、チャージライフル、ハンマーポイント弾を除き、すべてのダメージ値が一致していることを確認しています。 |
モジュール:Utility/TableUtil
ナビゲーションに移動
検索に移動
このモジュールについての説明文ページを モジュール:Utility/TableUtil/doc に作成できます
-- ====================
-- namespace: TableUtil
-- ====================
local tableutil = {}
-- =====
-- Config
-- =====
local aw = require('Module:Utility/Library')
local function __passthrough(num)
return num
end
-- ==========
-- type: Cell
-- ==========
local __TableUtil__CellType__Cell = 'cell'
local __TableUtil__Cell = {
__typename = __TableUtil__CellType__Cell,
}
-- [Constructor]
function __TableUtil__Cell.__new(typename, name, opts)
local obj = {
typename = typename,
name = name,
}
if opts then
obj.attributes = opts.attributes or {}
obj.cellClass = opts.cellClass
obj.headerClass = opts.headerClass
obj.headerStyle = opts.headerStyle
else
obj.attributes = {}
end
return setmetatable(obj, { __index = __TableUtil__Cell })
end
function __TableUtil__Cell.new(name, opts)
return __TableUtil__Cell.__new(__TableUtil__CellType__Cell, name, opts)
end
-- [Function] Reset context
function __TableUtil__Cell:resetContext()
end
-- [Function] Render header
function __TableUtil__Cell:renderHeader(headerRow)
local headerCell = headerRow:tag('th'):wikitext(self.name)
if type(self.headerClass) == 'string' then
headerCell:addClass(self.headerClass)
end
if type(self.headerStyle) == 'table' then
headerCell:css(self.headerStyle)
end
return headerCell
end
-- [Function] Render
function __TableUtil__Cell:render(row)
local cell = row:tag('td'):attr(self.attributes)
if type(self.cellClass) == 'string' then
cell:addClass(self.cellClass)
end
return cell
end
-- [Export]
tableutil.Cell = __TableUtil__Cell
-- =====================
-- type: ValueCell: Cell
-- =====================
local __TableUtil__CellType__ValueCell = 'value'
local __TableUtil__ValueCell = {
__typename = __TableUtil__CellType__ValueCell,
}
setmetatable(__TableUtil__ValueCell, { __index = __TableUtil__Cell })
-- [Constructor]
function __TableUtil__ValueCell.__new(typename, name, dataIndex, opts)
local obj = __TableUtil__Cell.__new(typename, name, opts)
obj.__cell__render = obj.render
obj.dataIndex = dataIndex
if type(opts) == 'table' then
obj.format = opts.format or __passthrough
else
obj.format = __passthrough
end
return setmetatable(obj, { __index = __TableUtil__ValueCell })
end
function __TableUtil__ValueCell.new(name, dataIndex, opts)
return __TableUtil__ValueCell.__new(__TableUtil__CellType__ValueCell, name, dataIndex, opts)
end
-- [Function] Render
function __TableUtil__ValueCell:render(row, dataset, i, datainfo)
local value = dataset[self.dataIndex]
local formattedValue = self.format(value)
local cell = self:__cell__render(row, dataset, i, datainfo)
:attr('data-sort-value', value)
:wikitext(formattedValue)
return cell
end
-- [Export]
tableutil.ValueCell = __TableUtil__ValueCell
-- =========================
-- type: RankCell: ValueCell
-- =========================
local __TableUtil__CellType__RankCell = 'rank'
local __TableUtil__RankCell = {
__typename = __TableUtil__CellType__RankCell,
}
setmetatable(__TableUtil__RankCell, { __index = __TableUtil__ValueCell })
-- [Constructor]
function __TableUtil__RankCell.new(name, dataIndex, descending)
local obj = __TableUtil__ValueCell.__new(__TableUtil__CellType__RankCell, name, dataIndex)
obj.currentRank = 0
obj.currentValue = -1
obj.descending = descending
return setmetatable(obj, { __index = __TableUtil__RankCell })
end
-- [Property] Is descending?
function __TableUtil__RankCell:isDescending()
return self.descending
end
-- [Function] Reset context
function __TableUtil__RankCell:resetContext()
self.currentRank = 0
self.currentValue = -1
end
-- [Function] Render
function __TableUtil__RankCell:render(row, dataset, i)
local value = dataset[self.dataIndex]
if self.currentValue ~= value then
self.currentRank = i
self.currentValue = value
end
local cell = row:tag('th')
:attr('data-sort-value', value)
:wikitext(self.currentRank)
return cell
end
-- [Export]
tableutil.RankCell = __TableUtil__RankCell
-- ====================
-- type: LineCell: Cell
-- ====================
local __TableUtil__CellType__LineCell = 'line'
local __TableUtil__LineCell = {
__typename = __TableUtil__CellType__LineCell,
}
setmetatable(__TableUtil__LineCell, { __index = __TableUtil__ValueCell })
-- [Constructor]
function __TableUtil__LineCell.__new(typename, name, dataIndex, opts)
local obj = __TableUtil__Cell.__new(typename, name, opts)
obj.__cell__render = obj.render
obj.dataIndex = dataIndex
if type(opts) == 'table' then
obj.colorStops = opts.colorStops or '#A7D7F9'
obj.height = opts.height or 1.2
obj.minimumValue = opts.minimumValue or 0
obj.maximumRate = opts.maximumRate or 1.05
else
obj.colorStops = '#A7D7F9'
obj.height = 1.2
obj.minimumValue = 0
obj.maximumRate = 1.05
end
return setmetatable(obj, { __index = __TableUtil__LineCell })
end
function __TableUtil__LineCell.new(name, dataIndex, opts)
return __TableUtil__LineCell.__new(__TableUtil__CellType__LineCell, name, dataIndex, opts)
end
-- [Property] Height
function __TableUtil__LineCell:setHeight(value)
self.height = value
return self
end
-- [Function] Render
function __TableUtil__LineCell:render(row, dataset, i, datainfo)
local gradientFormat
if type(self.colorStops) == 'table' then
if self.mixinValue then
gradientFormat = function(percentage, value)
return string.format(
'linear-gradient(to right,transparent,%s %s%%,%s %s%%,transparent %s%%)',
self.colorStops[1],
percentage,
self.colorStops[2],
percentage,
percentage)
end
else
gradientFormat = function(percentage, value)
return string.format(
'linear-gradient(to right,transparent,%s %s%%,%s %s%%,transparent %s%%)!important',
self.colorStops[1],
percentage,
self.colorStops[2],
percentage,
percentage)
end
end
else
if self.mixinValue then
gradientFormat = function(percentage, value)
return string.format(
'linear-gradient(to right,%s %s%%,transparent %s%%)',
self.colorStops,
percentage,
percentage)
end
else
gradientFormat = function(percentage, value)
return string.format(
'linear-gradient(to right,%s %s%%,transparent %s%%)!important',
self.colorStops,
percentage,
percentage)
end
end
end
local value = dataset[self.dataIndex]
local targetDataInfo = datainfo[self.dataIndex]
local minimumValue = self.minimumValue or targetDataInfo.minValue
local percentage
if value == math.huge then
percentage = 100
else
percentage = 0.001 * aw.round(100000 * (value - minimumValue) / (self.maximumRate * (targetDataInfo.maxValue - minimumValue)))
end
local cell = self:__cell__render(row, dataset, i, datainfo)
:addClass('stattable-line')
:addClass(string.format('stattable-line-h%d', 10 * self.height))
:attr('data-sort-value', value)
:css('background-image', gradientFormat(percentage, value))
return cell
end
-- [Export]
tableutil.LineCell = __TableUtil__LineCell
-- =================
-- type: Value+XCell
-- =================
local function transformValueCell(superklass, klasstype)
local valuetype = string.format('value+%s', klasstype)
local valueKlass = {
__typename = valuetype,
}
setmetatable(valueKlass, { __index = superklass })
function valueKlass.new(name, dataIndex, opts)
local obj = superklass.__new(valuetype, name, dataIndex, opts)
obj.__super__render = obj.render
obj.mixinValue = true
if type(opts) == 'table' then
obj.format = opts.format or __passthrough
else
obj.format = __passthrough
end
return setmetatable(obj, { __index = valueKlass })
end
function valueKlass:render(row, dataset, i, datainfo)
local value = dataset[self.dataIndex]
local formattedValue = self.format(value)
local cell = self:__super__render(row, dataset, i, datainfo)
return cell:wikitext(formattedValue)
end
return valueKlass
end
-- [Export]
tableutil.LineValueCell = transformValueCell(__TableUtil__LineCell, __TableUtil__CellType__LineCell)
-- ===================
-- func: specifyUICell
-- ===================
function tableutil.specifyUICell(klasstype, renderFunction, propNames)
local specifictype = string.format('ui+%s', klasstype)
local specificKlass = {
__typename = specifictype,
}
setmetatable(specificKlass, { __index = __TableUtil__Cell })
function specificKlass.new(name, dataIndex, opts)
local obj = __TableUtil__Cell.__new(specifictype, name, opts)
obj.__cell__render = obj.render
obj.dataIndex = dataIndex
if propNames and opts then
for _, name in ipairs(propNames) do
obj[name] = opts[name]
end
end
return setmetatable(obj, { __index = specificKlass })
end
specificKlass.render = renderFunction
return specificKlass
end
-- =================
-- func: createTable
-- =================
function tableutil.createTable(dataset, metadata)
local tbl = mw.html.create('table')
:addClass('numbertable')
:addClass('sortable')
:addClass('stattable')
:addClass('wikitable')
-- Build header
local headerRow = tbl:tag('tr'):addClass('row-sticky')
local sortIndex = 0
local isDesc = false
for _, m in ipairs(metadata) do
-- Reset context for building process
m:resetContext()
if m.typename == tableutil.RankCell.__typename then
sortIndex = m.dataIndex
isDesc = m:isDescending()
end
-- Render header
m:renderHeader(headerRow)
end
-- Sort data
if sortIndex ~= 0 then
local sortFunction
if isDesc then
sortFunction = function(a, b)
return a[sortIndex] > b[sortIndex]
end
else
sortFunction = function(a, b)
return a[sortIndex] < b[sortIndex]
end
end
table.sort(dataset, sortFunction)
end
-- Preprocess data
local datainfo = {}
for _, ary in ipairs(dataset) do
for key, d in pairs(ary) do
if type(d) == 'number' and d ~= math.huge then
if not datainfo[key] then
datainfo[key] = {
minValue = d,
maxValue = d,
}
else
if datainfo[key].minValue > d then
datainfo[key].minValue = d
end
if datainfo[key].maxValue < d then
datainfo[key].maxValue = d
end
end
end
end
end
-- Build cell
for i, d in ipairs(dataset) do
local row = tbl:tag('tr')
for k, m in ipairs(metadata) do
m:render(row, d, i, datainfo)
end
end
return tbl
end
-- =================
-- test: Simple test
-- =================
function tableutil.__test()
local metadata = {
tableutil.RankCell.new('', 1),
tableutil.ValueCell.new('Value', 1),
tableutil.LineCell.new('Line', 1),
tableutil.LineCell.new('LineGradient', 1, { colorStops = { '#F8B3BC', '#F26D7D' }, height = 1.4 }),
tableutil.LineValueCell.new('LineValue', 2, { cellClass = 'stattable-graph-both' }),
}
local node = tableutil.createTable({{ 45, 110 }, { 40, 60 }, { 40, 120 }, { 50, 90 }}, metadata)
return tostring(node)
end
return tableutil