mirror of
https://github.com/PHIDIAS0303/ExpCluster.git
synced 2026-11-12 07:54:52 +09:00
transfer
This commit is contained in:
1 parent
48f86959d9
commit
c64a6201d9
5 files changed
+384
-4
No files matched your search
@@ -79,6 +79,7 @@ add(require("modules/exp_scenario/gui/player_bonus"))
|
||||
add(require("modules/exp_scenario/gui/player_list"))
|
||||
add(require("modules/exp_scenario/gui/player_stats"))
|
||||
add(require("modules/exp_scenario/gui/production_stats"))
|
||||
add(require("modules/exp_scenario/gui/calculator"))
|
||||
add(require("modules/exp_scenario/gui/quick_actions"))
|
||||
add(require("modules/exp_scenario/gui/readme"))
|
||||
add(require("modules/exp_scenario/gui/research_milestones"))
|
||||
|
||||
@@ -0,0 +1,327 @@
|
||||
--[[-- Gui - Calculator
|
||||
Add a calculator to do quick calculation.
|
||||
]]
|
||||
|
||||
local Gui = require("modules/exp_gui")
|
||||
local Roles = require("modules/exp_roles")
|
||||
|
||||
--- @class ExpGui_Calculator.elements
|
||||
local Elements = {}
|
||||
|
||||
local calc_function = setmetatable({
|
||||
ln = math.log,
|
||||
log = function(x, b) return math.log(x, b or 10) end,
|
||||
round = function(x) return x >= 0 and math.floor(x + 0.5) or math.ceil(x - 0.5) end,
|
||||
trunc = function(x) return (math.modf(x)) end,
|
||||
sign = function(x) return x > 0 and 1 or (x < 0 and -1 or 0) end,
|
||||
pi = function(_) return math.pi end,
|
||||
}, {
|
||||
__index = math
|
||||
})
|
||||
|
||||
local calc_function_operation = {
|
||||
["+"] = {1, function(a, b) return a + b end},
|
||||
["-"] = {1, function(a, b) return a - b end},
|
||||
["*"] = {2, function(a, b) return a * b end},
|
||||
["/"] = {2, function(a, b) if b == 0 then error({"", {"exp-gui_calculator.error"}, {"exp-gui_calculator.div_zero"}}, 0) end return a / b end},
|
||||
["%"] = {2, function(a, b) if b == 0 then error({"", {"exp-gui_calculator.error"}, {"exp-gui_calculator.mod_zero"}}, 0) end return a % b end},
|
||||
}
|
||||
|
||||
local calc_si_suffix = {
|
||||
k = 1e3,
|
||||
m = 1e6,
|
||||
g = 1e9,
|
||||
t = 1e12,
|
||||
p = 1e15
|
||||
}
|
||||
|
||||
local calc_number_base = {
|
||||
x = {value = 16, digits = "%x"},
|
||||
b = {value = 2, digits = "[01]"},
|
||||
o = {value = 8, digits = "[0-7]"},
|
||||
}
|
||||
|
||||
--- Input textfield
|
||||
Elements.calculator_input_textfield = Gui.define("calculator/input_textfield")
|
||||
:draw{
|
||||
type = "textfield",
|
||||
name = "calculator_input_textfield",
|
||||
style = "console_input_textfield",
|
||||
}
|
||||
:style{
|
||||
width = 320,
|
||||
}
|
||||
|
||||
--- Output label
|
||||
Elements.calculator_result_label = Gui.define("calculator/result_label")
|
||||
:draw{
|
||||
type = "label",
|
||||
name = "calculator_result_label",
|
||||
style = "heading_2_label",
|
||||
}
|
||||
:style{
|
||||
horizontal_align = "right"
|
||||
}
|
||||
|
||||
--- Empty new line label
|
||||
Elements.calculator_label_1 = Gui.define("calculator/label_1")
|
||||
:draw{
|
||||
type = "label",
|
||||
name = "calculator_label_1",
|
||||
style = "heading_2_label",
|
||||
}
|
||||
|
||||
--- Container added to the screen
|
||||
Elements.container = Gui.define("exp-gui_calculatorulator/container")
|
||||
:draw(function(def, parent)
|
||||
local screen_frame = Gui.elements.screen_frame(parent, nil, true)
|
||||
local button_flow = Gui.elements.screen_frame.get_button_flow(screen_frame)
|
||||
|
||||
Elements.calculator_input_textfield(screen_frame)
|
||||
Elements.calculator_result_label(screen_frame)
|
||||
Elements.calculator_label_1(screen_frame)
|
||||
|
||||
return Gui.elements.screen_frame.get_root_element(screen_frame)
|
||||
end)
|
||||
|
||||
--- Add a button to create the container
|
||||
Gui.toolbar.create_button{
|
||||
name = "open_calculator",
|
||||
sprite = "entity/arithmetic-combinator",
|
||||
tooltip = { "exp-gui_calculator.tooltip" },
|
||||
visible = function(player, element)
|
||||
return Roles.player_has_permission(player, "exp-gui_calculator")
|
||||
end
|
||||
}:on_click(function(def, player, element, event)
|
||||
Elements.container(player.gui.screen)
|
||||
end)
|
||||
|
||||
--- Parse Value
|
||||
function Elements.calculator.parse(expression)
|
||||
local cursor = 1
|
||||
|
||||
local function skip_space()
|
||||
while expression:sub(cursor, cursor) == " " do
|
||||
cursor = cursor + 1
|
||||
end
|
||||
end
|
||||
|
||||
local function factorial(n)
|
||||
if n < 0 then
|
||||
return error({"", {"exp-gui_calculator.error"}, {"exp-gui_calculator.factorial_neg", n}}, 0)
|
||||
|
||||
elseif n > 170 then
|
||||
return error({"", {"exp-gui_calculator.error"}, {"exp-gui_calculator.factorial_large", n}}, 0)
|
||||
end
|
||||
|
||||
if n ~= math.floor(n) then
|
||||
return error({"", {"exp-gui_calculator.error"}, {"exp-gui_calculator.factorial_int", n}}, 0)
|
||||
end
|
||||
|
||||
local result = 1
|
||||
|
||||
for i = 2, n do
|
||||
result = result * i
|
||||
end
|
||||
|
||||
return result
|
||||
end
|
||||
|
||||
local parse_expr
|
||||
|
||||
local function parse_atom()
|
||||
skip_space()
|
||||
local character = expression:sub(cursor, cursor)
|
||||
|
||||
if character == "|" then
|
||||
cursor = cursor + 1
|
||||
local value = parse_expr(1)
|
||||
skip_space()
|
||||
|
||||
if expression:sub(cursor, cursor) ~= "|" then
|
||||
return error({"", {"exp-gui_calculator.error"}, {"exp-gui_calculator.expected_bar"}}, 0)
|
||||
end
|
||||
|
||||
cursor = cursor + 1
|
||||
return math.abs(value)
|
||||
|
||||
elseif character == "(" then
|
||||
cursor = cursor + 1
|
||||
local value = parse_expr(1)
|
||||
skip_space()
|
||||
|
||||
if expression:sub(cursor, cursor) ~= ")" then
|
||||
return error({"", {"exp-gui_calculator.error"}, {"exp-gui_calculator.expected_paren"}}, 0)
|
||||
end
|
||||
|
||||
cursor = cursor + 1
|
||||
return value
|
||||
|
||||
elseif character == "" then
|
||||
return error({"", {"exp-gui_calculator.error"}, {"exp-gui_calculator.unexpected_end"}}, 0)
|
||||
|
||||
elseif character:match("%a") then
|
||||
skip_space()
|
||||
local start = cursor
|
||||
|
||||
while expression:sub(cursor, cursor):match("%w") do
|
||||
cursor = cursor + 1
|
||||
end
|
||||
|
||||
local name = expression:sub(start, cursor - 1)
|
||||
local fn = calc_function[name]
|
||||
skip_space()
|
||||
|
||||
if expression:sub(cursor, cursor) == "(" then
|
||||
if not fn then
|
||||
return error({"", {"exp-gui_calculator.error"}, {"exp-gui_calculator.unknown_fn"}}, 0)
|
||||
end
|
||||
|
||||
cursor = cursor + 1
|
||||
local argument = parse_expr(1)
|
||||
skip_space()
|
||||
|
||||
if expression:sub(cursor, cursor) ~= ")" then
|
||||
return error({"", {"exp-gui_calculator.error"}, {"exp-gui_calculator.expected_paren"}}, 0)
|
||||
end
|
||||
|
||||
cursor = cursor + 1
|
||||
return fn(argument)
|
||||
end
|
||||
|
||||
if fn then
|
||||
return error({"", {"exp-gui_calculator.error"}, {"exp-gui_calculator.expected_open", name}}, 0)
|
||||
end
|
||||
|
||||
return error({"", {"exp-gui_calculator.error"}, {"exp-gui_calculator.unknown_id", name}}, 0)
|
||||
|
||||
else
|
||||
skip_space()
|
||||
|
||||
if expression:sub(cursor, cursor) == "0" then
|
||||
local base = calc_number_base[expression:sub(cursor + 1, cursor + 1):lower()]
|
||||
if base then
|
||||
local literal_start = cursor
|
||||
cursor = cursor + 2
|
||||
local digit_start = cursor
|
||||
|
||||
while expression:sub(cursor, cursor):match(base.digits) do
|
||||
cursor = cursor + 1
|
||||
end
|
||||
|
||||
if cursor == digit_start or expression:sub(cursor, cursor):match("%w") then
|
||||
while expression:sub(cursor, cursor):match("%w") do
|
||||
cursor = cursor + 1
|
||||
end
|
||||
|
||||
return error({"", {"exp-gui_calculator.error"}, {"exp-gui_calculator.invalid_num", expression:sub(literal_start, cursor - 1)}}, 0)
|
||||
end
|
||||
|
||||
return tonumber(expression:sub(digit_start, cursor - 1), base.value)
|
||||
end
|
||||
end
|
||||
|
||||
local literal = expression:match("^(%d+%.?%d*[eE][%+%-]?%d+)", cursor) or expression:match("^(%d+%.?%d*)", cursor)
|
||||
|
||||
if not literal then
|
||||
return error({"", {"exp-gui_calculator.error"}, {"exp-gui_calculator.expected_num"}}, 0)
|
||||
end
|
||||
|
||||
cursor = cursor + literal:len()
|
||||
local num = tonumber(literal)
|
||||
|
||||
if not num then
|
||||
return error({"", {"exp-gui_calculator.error"}, {"exp-gui_calculator.invalid_num", literal}}, 0)
|
||||
end
|
||||
|
||||
return num
|
||||
end
|
||||
end
|
||||
|
||||
local function parse_factor()
|
||||
skip_space()
|
||||
|
||||
if expression:sub(cursor, cursor) == "-" then
|
||||
cursor = cursor + 1
|
||||
return -parse_factor()
|
||||
|
||||
elseif expression:sub(cursor, cursor) == "+" then
|
||||
cursor = cursor + 1
|
||||
return parse_factor()
|
||||
end
|
||||
|
||||
local base = parse_atom()
|
||||
skip_space()
|
||||
local suffix = calc_si_suffix[expression:sub(cursor, cursor)]
|
||||
|
||||
if suffix then
|
||||
cursor = cursor + 1
|
||||
base = base * suffix
|
||||
end
|
||||
|
||||
skip_space()
|
||||
|
||||
if expression:sub(cursor, cursor) == "!" then
|
||||
cursor = cursor + 1
|
||||
base = factorial(base)
|
||||
end
|
||||
|
||||
skip_space()
|
||||
|
||||
if expression:sub(cursor, cursor + 1) == "**" then
|
||||
cursor = cursor + 2
|
||||
return base ^ parse_factor()
|
||||
|
||||
elseif expression:sub(cursor, cursor) == "^" then
|
||||
cursor = cursor + 1
|
||||
return base ^ parse_factor()
|
||||
end
|
||||
|
||||
return base
|
||||
end
|
||||
|
||||
parse_expr = function(min_prec)
|
||||
local lhs = parse_factor()
|
||||
|
||||
while true do
|
||||
skip_space()
|
||||
local entry = calc_function_operation[expression:sub(cursor, cursor)]
|
||||
|
||||
if not entry or entry[1] < min_prec then
|
||||
break
|
||||
end
|
||||
|
||||
cursor = cursor + 1
|
||||
lhs = entry[2](lhs, parse_expr(entry[1] + 1))
|
||||
end
|
||||
|
||||
return lhs
|
||||
end
|
||||
|
||||
local ok, result = pcall(function()
|
||||
local value = parse_expr(1)
|
||||
skip_space()
|
||||
|
||||
if cursor <= #expression then
|
||||
error({"", {"exp-gui_calculator.error"}, {"exp-gui_calculator.trailing", expression:sub(cursor, expression:len())}}, 0)
|
||||
end
|
||||
|
||||
return value
|
||||
end)
|
||||
|
||||
return ok and result or (type(result) == "table" and result or {"exp-gui_calculator.error", tostring(result)})
|
||||
end
|
||||
|
||||
--- Value change
|
||||
function Elements.calculator.change(event)
|
||||
Elements.calculator_result_label.caption = event.text == "" and "" or main.parse(event.text:lower())
|
||||
end
|
||||
|
||||
local e = defines.events
|
||||
|
||||
return {
|
||||
elements = Elements,
|
||||
events = {
|
||||
[e.on_gui_text_changed] = Elements.calculator.parse,
|
||||
},
|
||||
}
|
||||
@@ -258,6 +258,24 @@ tooltip-amount=Amount of items to insert into the __1__ slots
|
||||
invalid=Autofill set to maximum amount: __1__ __2__ for __3__
|
||||
inserted=Inserted __1__ __2__ into __3__
|
||||
|
||||
[exp-gui_calculator]
|
||||
tooltip=Calculator
|
||||
error=[ERROR]
|
||||
factorial_neg=Factorial of a negative number __1__
|
||||
factorial_large=Factorial too large __1__
|
||||
factorial_int=Factorial must be an integer __1__
|
||||
expected_bar=Expected closing bar
|
||||
expected_num=Expected number
|
||||
expected_open=Expected opening parenthesis __1__
|
||||
expected_paren=Expected closing parenthesis
|
||||
unexpected_end=Unexpected end of input
|
||||
unknown_fn=Unknown function __1__
|
||||
unknown_id=Unknown identifier __1__
|
||||
invalid_num=Invalid number __1__
|
||||
div_zero=Division by zero
|
||||
mod_zero=Modulo by zero
|
||||
trailing=Unexpected trailing input __1__
|
||||
|
||||
[exp-gui_module-inserter]
|
||||
tooltip-main=Module Inserter
|
||||
caption-main=Modules
|
||||
|
||||
@@ -260,6 +260,24 @@ tooltip-amount=自動填入 __1__ 的數量
|
||||
invalid=自動填入最大值 __1__ __2__ 給 __3__
|
||||
inserted=自動填入 __1__ __2__ 到 __3__
|
||||
|
||||
[exp-gui_calculator]
|
||||
tooltip=計算機
|
||||
error=[錯誤]
|
||||
factorial_neg=負數的階乘 __1__
|
||||
factorial_large=階乘太大 __1__
|
||||
factorial_int=階乘必須是整數 __1__
|
||||
expected_bar=缺少右側垂直線
|
||||
expected_num=缺少數字
|
||||
expected_open=缺少左括號 __1__
|
||||
expected_paren=缺少右括號
|
||||
unexpected_end=意外的輸入結尾
|
||||
unknown_fn=未知函數 __1__
|
||||
unknown_id=未知識別項 __1__
|
||||
invalid_num=無效的數字 __1__
|
||||
div_zero=除以零
|
||||
mod_zero=對零取餘數
|
||||
trailing=意外的尾隨輸入 __1__
|
||||
|
||||
[exp-gui_module-inserter]
|
||||
tooltip-main=模組
|
||||
caption-main=Modules
|
||||
@@ -603,7 +621,6 @@ chat-jailed=__1__ 因被多次拆除受保護物體而被禁止行動。請等
|
||||
[exp_report-jail]
|
||||
chat-jailed=__1__ 因被多次舉報而被禁止行動。請等候管理員作出下一步處理。
|
||||
|
||||
|
||||
[exp-gui_player-list]
|
||||
main-tooltip = Player List
|
||||
open-action-bar = Options
|
||||
@@ -620,4 +637,4 @@ afk-time = __1__% of total map time\nLast moved __2__ ago
|
||||
open-map = __1__ __2__\n__3__\nClick to open map
|
||||
|
||||
[exp_spectate]
|
||||
follow-label = Following __1__.\nClick here or press escape to stop following.
|
||||
follow-label = Following __1__.\nClick here or press escape to stop following.
|
||||
@@ -260,6 +260,24 @@ tooltip-amount=自動填入 __1__ 的數量
|
||||
invalid=自動填入最大值 __1__ __2__ 給 __3__
|
||||
inserted=自動填入 __1__ __2__ 到 __3__
|
||||
|
||||
[exp-gui_calculator]
|
||||
tooltip=計算機
|
||||
error=[錯誤]
|
||||
factorial_neg=負數的階乘 __1__
|
||||
factorial_large=階乘太大 __1__
|
||||
factorial_int=階乘必須是整數 __1__
|
||||
expected_bar=缺少右側垂直線
|
||||
expected_num=缺少數字
|
||||
expected_open=缺少左括號 __1__
|
||||
expected_paren=缺少右括號
|
||||
unexpected_end=意外的輸入結尾
|
||||
unknown_fn=未知函數 __1__
|
||||
unknown_id=未知識別項 __1__
|
||||
invalid_num=無效的數字 __1__
|
||||
div_zero=除以零
|
||||
mod_zero=對零取餘數
|
||||
trailing=意外的尾隨輸入 __1__
|
||||
|
||||
[exp-gui_module-inserter]
|
||||
tooltip-main=模組
|
||||
caption-main=Modules
|
||||
@@ -603,7 +621,6 @@ chat-jailed=__1__ 因被多次拆除受保護物體而被禁止行動。請等
|
||||
[exp_report-jail]
|
||||
chat-jailed=__1__ 因被多次舉報而被禁止行動。請等候管理員作出下一步處理。
|
||||
|
||||
|
||||
[exp-gui_player-list]
|
||||
main-tooltip = Player List
|
||||
open-action-bar = Options
|
||||
@@ -620,4 +637,4 @@ afk-time = __1__% of total map time\nLast moved __2__ ago
|
||||
open-map = __1__ __2__\n__3__\nClick to open map
|
||||
|
||||
[exp_spectate]
|
||||
follow-label = Following __1__.\nClick here or press escape to stop following.
|
||||
follow-label = Following __1__.\nClick here or press escape to stop following.
|
||||
Reference in new issue
Block a user