541 lines
20 KiB
Lua
541 lines
20 KiB
Lua
local RecipeGui = {
|
||
classname = "FNRecipeGui",
|
||
name = "recipe",
|
||
}
|
||
|
||
local recipe_gui_template
|
||
|
||
function RecipeGui.init_template()
|
||
local cont = Controller.get_cont(RecipeGui.name)
|
||
|
||
recipe_gui_template = {
|
||
{ type = "frame", name = "main-frame", style = "fnei_recipe_main_frame", children = {
|
||
{ type = "table", name = "main-table", style = "fnei_recipe_main_table", column_count = 1, children = {
|
||
|
||
------------------ header ------------------
|
||
|
||
{ type = "frame", name = "header-frame", style = "fnei_recipe_header_frame", direction = "horizontal", children = {
|
||
{ type = "table", name = "header-table", style = "fnei_recipe_header_table", column_count = 8, children = {
|
||
{ type = "flow", name = "header-icon", style = "fnei_default_horizontal_flow" },
|
||
{ type = "label", name = "header-label", style = "fnei_recipe_title_label", align = "center", vertical_align = "center", caption = "recipe_name" },
|
||
--{ type = "empty-widget", name = "" , style = "fnei_main_header-sprite-widget", caption = {"fnei.FNEI"} },
|
||
{ type = "empty-widget", name = "drag-widget", style = "fnei_recipe_header-drag-widget", drag_target = true},
|
||
{ type = "flow", name = "favorite-flow", style = "fnei_recipe_favorite_flow", children = {
|
||
{ type = "sprite-button", name = "favorite-key", tooltip = {"fnei.favorite-button"}, event = cont.favorite_key_event },
|
||
}},
|
||
{ type = "sprite-button", name = "back-key", style = "fnei_back_button_style", tooltip = {"gui.cancel"}, event = cont.back_key_event },
|
||
{ type = "sprite-button", name = "settings-key", style = "fnei_settings_button_style", tooltip = {"gui-menu.settings"}, event = cont.settings_key_event },
|
||
{ type = "sprite-button", name = "exit-key", style = "fnei_exit_button_style", tooltip = {"gui.exit"}, event = Controller.main_key_event },
|
||
}}
|
||
}},
|
||
|
||
------------------ paging ------------------
|
||
|
||
{ type = "frame", name = "paging-frame", style = "fnei_recipe_paging_frame", children = {
|
||
{ type = "table", name = "paging-table", style = "fnei_recipe_paging_table", column_count = 5, children = {
|
||
{ type = "flow", name = "left-arrow-flow", style = "fnei_recipe_arrow_flow" },
|
||
{ type = "label", name = "type-label", style = "fnei_recipe_type_label", vertical_align = "center", align = "right", caption = "" },
|
||
{ type = "flow", name = "prot-icon", style = "fnei_recipe_header_icon_flow" },
|
||
{ type = "label", name = "paging-label", style = "fnei_recipe_paging_label", vertical_align = "center", align = "left", caption = "" },
|
||
{ type = "flow", name = "right-arrow-flow", style = "fnei_recipe_arrow_flow" },
|
||
}},
|
||
}},
|
||
|
||
------------------ content ------------------
|
||
|
||
{ type = "table", name = "prod-table", style = "fnei_recipe_products_table", column_count = 2, children = {
|
||
{ type = "frame", name = "ingr-frame", style = "fnei_recipe_ingr_frame", children = {
|
||
{ type = "label", name = "ingr-label", style = "fnei_default_label", caption = {"fnei.ingredients"} },
|
||
}},
|
||
{ type = "frame", name = "res-frame", style = "fnei_recipe_res_frame", children = {
|
||
{ type = "label", name = "res-label", style = "fnei_default_label", caption = {"fnei.results"} },
|
||
}},
|
||
{ type = "frame", name = "list-ingr-frame", style = "fnei_recipe_list_ingr_frame", children = {
|
||
{ type = "scroll-pane", name = "ingr-scroll", style = "fnei_recipe_products_scroll_pane", direction = "vertical", children = {
|
||
{ type = "table", name = "list-ingr", style = "fnei_recipe_list_elements_table", column_count = 1 }
|
||
}}
|
||
}},
|
||
{ type = "frame", name = "list-res-frame", style = "fnei_recipe_list_res_frame", children = {
|
||
{ type = "scroll-pane", name = "res-scroll", style = "fnei_recipe_products_scroll_pane", direction = "vertical", children = {
|
||
{ type = "table", name = "list-res", style = "fnei_recipe_list_elements_table", column_count = 1 }
|
||
}}
|
||
}},
|
||
}},
|
||
|
||
------------------- madein --------------------
|
||
|
||
{ type = "frame", name = "madein-frame", style = "fnei_recipe_paging_frame", direction = "horizontal", children = {
|
||
{ type = "label", name = "madein-lable", style = "fnei_recipe_madein_label", caption = {"fnei.made-in"} },
|
||
{ type = "table", name = "madein-table", style = "fnei_recipe_made_in_table", column_count = 7 }
|
||
}},
|
||
|
||
------------------- techs --------------------
|
||
|
||
{ type = "flow", name = "tech-flow", style = "fnei_default_horizontal_flow" },
|
||
|
||
}}
|
||
}}
|
||
}
|
||
end
|
||
|
||
function RecipeGui.init_events()
|
||
RecipeGui.init_template()
|
||
Events.init_temp_events(RecipeGui.name, recipe_gui_template)
|
||
end
|
||
|
||
|
||
function RecipeGui.is_gui_open()
|
||
local val = Gui.get_gui(Gui.get_pos(), recipe_gui_template[1].name)
|
||
if val and next(val) and val.valid then
|
||
return true
|
||
else
|
||
return false
|
||
end
|
||
end
|
||
|
||
function RecipeGui.open_window()
|
||
RecipeGui.close_window()
|
||
local gui = Gui.add_gui_template(Gui.get_pos(), recipe_gui_template)
|
||
gui.location = Gui.get_location()
|
||
return gui
|
||
end
|
||
|
||
function RecipeGui.close_window()
|
||
if RecipeGui.is_gui_open() then
|
||
local gui = Gui.get_gui(Gui.get_pos(), recipe_gui_template[1].name)
|
||
Gui.set_location(gui.location)
|
||
gui.destroy()
|
||
end
|
||
end
|
||
|
||
function RecipeGui.draw_favorite_state(state)
|
||
local favorite_button = Gui.get_gui(Gui.get_pos(), "favorite-flow")
|
||
|
||
if favorite_button and favorite_button.valid then
|
||
local style = (state and "fnei_recipe_selected_favorive_button") or "fnei_recipe_favorive_button"
|
||
|
||
clear_gui(favorite_button)
|
||
Gui.add_gui_template(favorite_button, {{
|
||
type = "sprite-button",
|
||
name = "favorite-key",
|
||
style = style,
|
||
tooltip = {"fnei.favorite-button"},
|
||
}})
|
||
end
|
||
end
|
||
|
||
function RecipeGui.set_recipe_time(energy)
|
||
local time = Gui.get_gui(Gui.get_pos(), "fnei_time_label")
|
||
time.caption = round_to_str(energy, 3)
|
||
end
|
||
|
||
function RecipeGui.set_recipe_name(recipe)
|
||
local name = Gui.get_gui(Gui.get_pos(), "header-label")
|
||
name.caption = get_localised_name( recipe )
|
||
name.tooltip = name.caption
|
||
|
||
local style = "fnei_recipe_title_label"
|
||
|
||
if recipe and recipe.hidden then
|
||
style = "fnei_recipe_grey_title_label"
|
||
elseif recipe and not recipe.enabled then
|
||
style = "fnei_recipe_red_title_label"
|
||
end
|
||
|
||
name.style = style
|
||
end
|
||
|
||
function RecipeGui.set_recipe_icon(recipe)
|
||
local icon_flow = Gui.get_gui(Gui.get_pos(), "header-icon")
|
||
local value = recipe.name
|
||
local type = "recipe"
|
||
|
||
if rawget(recipe, 'impostor') then
|
||
local _,pos = string.find(value, "impostor[-]minable:")
|
||
|
||
if not pos then
|
||
_,pos = string.find(value, "impostor[-]pumped:")
|
||
end
|
||
|
||
value = string.sub(value, (pos or -1) + 1)
|
||
type = "entity"
|
||
end
|
||
|
||
clear_gui(icon_flow)
|
||
Gui.add_choose_button(icon_flow, { type = "choose-elem-button", name = "selected-recipe", style = "fnei_default_button", elem_type = type, elem_value = value, locked = true })
|
||
end
|
||
|
||
function RecipeGui.set_ingredients(list, dif_prot)
|
||
local ingr_tb = Gui.get_gui(Gui.get_pos(), "list-ingr")
|
||
local template = {}
|
||
|
||
table.insert(template,
|
||
{ type = "flow", name = "time-flow", style = "fnei_recipe_list_elements_flow", direction = "horizontal", children = {
|
||
{ type = "sprite-button", name = "fnei_time", style = "slot_button", tooltip = {"fnei.crafting-time"}, sprite = "fnei_time_icon" },
|
||
{ type = "label", name = "fnei_time_label", style = "fnei_recipe_element_label", vertical_align = "center", align = "left", caption = {"fnei.crafting-time"} },
|
||
}})
|
||
|
||
for _,ingr in pairs(list) do
|
||
table.insert(template, { type = "flow", name = ingr.name .. "-flow", style = "fnei_recipe_list_elements_flow", direction = "horizontal", children = {
|
||
{ type = "choose-elem-button", name = ingr.type .. "\t" .. ingr.name, style = "fnei_default_button", elem_type = ingr.type, elem_value = ingr.name, locked = true },
|
||
{ type = "label", name = ingr.name .. "-label", style = "fnei_recipe_element_label", single_line = true, vertical_align = "center", align = "left", caption = RecipeGui.get_element_caption(ingr) }
|
||
}})
|
||
end
|
||
|
||
local scroll = Gui.get_gui(Gui.get_pos(), "ingr-scroll") or {}
|
||
if list and #list < 7 then
|
||
scroll.vertical_scroll_policy = "never"
|
||
else
|
||
scroll.vertical_scroll_policy = "auto"
|
||
end
|
||
|
||
for i = 1, dif_prot do
|
||
table.insert(template, { type = "flow", name = "empty_flow" .. i, style = "fnei_recipe_list_elements_flow" })
|
||
end
|
||
|
||
clear_gui(ingr_tb)
|
||
Gui.add_gui_template(ingr_tb, template)
|
||
end
|
||
|
||
function RecipeGui.set_products(list, dif_prot)
|
||
local res_tb = Gui.get_gui(Gui.get_pos(), "list-res")
|
||
local template = {}
|
||
|
||
for _,res in pairs(list) do
|
||
table.insert(template, { type = "flow", name = res.name .. "-flow", style = "fnei_recipe_list_elements_flow", direction = "horizontal", children = {
|
||
{ type = "choose-elem-button", name = res.type .. "\t" .. res.name, style = "fnei_default_button", elem_type = res.type, elem_value = res.name, locked = true },
|
||
{ type = "label", name = res.name .. "-label", style = "fnei_recipe_element_label", single_line = true, vertical_align = "center", align = "left", caption = RecipeGui.get_element_caption(res) }
|
||
}})
|
||
end
|
||
|
||
local scroll = Gui.get_gui(Gui.get_pos(), "res-scroll") or {}
|
||
if list and #list < 8 then
|
||
scroll.vertical_scroll_policy = "never"
|
||
else
|
||
scroll.vertical_scroll_policy = "auto"
|
||
end
|
||
|
||
for i = 1, dif_prot do
|
||
table.insert(template, { type = "flow", name = "empty_flow" .. i, style = "fnei_recipe_list_elements_flow" })
|
||
end
|
||
|
||
clear_gui(res_tb)
|
||
Gui.add_gui_template(res_tb, template)
|
||
end
|
||
|
||
function RecipeGui.set_made_in_list(recipe)
|
||
local gui_tabel = Gui.get_gui(Gui.get_pos(), "madein-table")
|
||
local craft_cat_list = get_crafting_categories_list()
|
||
local item_list = get_full_item_list()
|
||
|
||
clear_gui(gui_tabel)
|
||
|
||
if recipe and Settings.get_val("show-recipes", "categories", recipe.category) then
|
||
local cat_list = craft_cat_list[recipe.category]
|
||
|
||
for _, cat in pairs(cat_list) do
|
||
local caption = Settings.get_val("show-craft-time-label")
|
||
local element
|
||
|
||
local ing_cnt = 0
|
||
local in_fluidbox_cnt = 0
|
||
local out_fluidbox_cnt = 0
|
||
|
||
for _,prot in pairs(recipe.ingredients) do
|
||
if prot.type == "item" then
|
||
ing_cnt = ing_cnt + 1
|
||
elseif prot.type == "fluid" then
|
||
in_fluidbox_cnt = in_fluidbox_cnt + 1
|
||
end
|
||
end
|
||
|
||
for _,prot in pairs(recipe.products) do
|
||
if prot.type == "fluid" then
|
||
out_fluidbox_cnt = out_fluidbox_cnt + 1
|
||
end
|
||
end
|
||
|
||
if cat.type == "player" and Settings.get_val("show-recipes", "buildings", cat.val.name) then
|
||
if in_fluidbox_cnt <= (cat.ifbox or 0) and out_fluidbox_cnt <= (cat.ofbox or 0) then
|
||
local player = Player.get()
|
||
local tooltip = {"", {"fnei.handcraft"}}
|
||
|
||
if caption and player and cat.val.name == "handcraft" then
|
||
local crafting_speed = (player.character_crafting_speed_modifier + 1) * (player.force.manual_crafting_speed_modifier + 1)
|
||
if crafting_speed ~= 0 then
|
||
caption = round_to_str(recipe.energy / crafting_speed, 3)
|
||
end
|
||
end
|
||
|
||
if caption and player and cat.val.name == "handmine" then
|
||
local mining_speed = (player.character_mining_speed_modifier + 1) * (player.force.manual_mining_speed_modifier + 1) * cat.val.mining_speed
|
||
if mining_speed ~= 0 then
|
||
caption = round_to_str(recipe.mining_time / mining_speed, 3)
|
||
end
|
||
tooltip = {"", {"fnei.handmining"}}
|
||
end
|
||
|
||
element = {
|
||
type = "sprite-button",
|
||
name = cat.val.name,
|
||
style = "fnei_default_button",
|
||
tooltip = tooltip,
|
||
sprite = "fnei_hand_icon"
|
||
}
|
||
end
|
||
elseif cat.type == "building" and cat.ingredient_count and Settings.get_val("show-recipes", "buildings", cat.val.name) then
|
||
if cat.ingredient_count >= ing_cnt and in_fluidbox_cnt <= (cat.ifbox or 0) and out_fluidbox_cnt <= (cat.ofbox or 0) then
|
||
local entity = item_list[cat.val.name].place_result
|
||
|
||
if caption and entity and entity.crafting_speed ~= nil then
|
||
caption = round_to_str(recipe.energy / entity.crafting_speed, 3)
|
||
end
|
||
|
||
if caption and entity and entity.pumping_speed then
|
||
caption = round_to_str(recipe.energy / entity.pumping_speed, 3)
|
||
end
|
||
|
||
element = {
|
||
type = "choose-elem-button",
|
||
name = "item\t" .. cat.val.name,
|
||
style = "fnei_default_button",
|
||
elem_type = "item",
|
||
elem_value = cat.val.name,
|
||
locked = true
|
||
}
|
||
end
|
||
elseif cat.type == 'resource-miner' and cat.mining_speed and Settings.get_val("show-recipes", "buildings", cat.val.name) then
|
||
if in_fluidbox_cnt <= (cat.ifbox or 0) and out_fluidbox_cnt <= (cat.ofbox or 0) then
|
||
element = {
|
||
type = "choose-elem-button",
|
||
name = "item\t" .. cat.val.name,
|
||
style = "fnei_default_button",
|
||
elem_type = "item",
|
||
elem_value = cat.val.name,
|
||
locked = true
|
||
}
|
||
-- https://wiki.factorio.com/Mining
|
||
caption = round_to_str(recipe.mining_time / (cat.mining_speed), 3)
|
||
end
|
||
end
|
||
|
||
if element then
|
||
local label
|
||
|
||
if caption then
|
||
label = {
|
||
type = "label",
|
||
name = cat.val.name .. "-label",
|
||
style = "fnei_recipe_craft_time_for_building_label",
|
||
vertical_align = "top",
|
||
align = "center",
|
||
caption = caption,
|
||
tooltip = {"", {"fnei.craft-time-in-building"}, ": ", caption}
|
||
}
|
||
end
|
||
|
||
Gui.add_gui_template(gui_tabel, {
|
||
{ type = "flow", name = cat.val.name .. "-flow", style = "fnei_recipe_building_flow", direction = "vertical", children = {
|
||
element,
|
||
label
|
||
}}
|
||
})
|
||
end
|
||
end
|
||
end
|
||
|
||
end
|
||
|
||
function RecipeGui.set_techs( recipe )
|
||
local tech_list = get_technologies_for_recipe(recipe.name)
|
||
local gui_flow = Gui.get_gui(Gui.get_pos(), "tech-flow")
|
||
|
||
clear_gui(gui_flow)
|
||
|
||
local new_tech_list = {}
|
||
if Settings.get_val("show-disable-techs") then
|
||
new_tech_list = tech_list
|
||
else
|
||
for _, tech in pairs(tech_list) do
|
||
if tech.enabled then
|
||
table.insert(new_tech_list, tech)
|
||
end
|
||
end
|
||
end
|
||
|
||
if new_tech_list and #new_tech_list > 0 then
|
||
local techs = {}
|
||
|
||
for _, tech in pairs(new_tech_list) do
|
||
table.insert(techs, {
|
||
type = "sprite-button",
|
||
name = "tech\t".. tech.name,
|
||
style = RecipeGui.get_tech_style( tech ),
|
||
tooltip = get_localised_name(tech),
|
||
sprite = "technology/" .. tech.name
|
||
})
|
||
end
|
||
|
||
local template = {
|
||
{ type = "frame", name = "tech-frame", style = "fnei_recipe_paging_frame", direction = "horizontal", children = {
|
||
{ type = "label", name = "tech-label", style = "fnei_recipe_technologies_label", caption = {"fnei.technology"} },
|
||
{ type = "table", name = "tach-table", style = "fnei_recipe_tech_table", column_count = 3, children = techs },
|
||
}}
|
||
}
|
||
|
||
Gui.add_gui_template(gui_flow, template)
|
||
end
|
||
end
|
||
|
||
function RecipeGui.get_tech_style( tech )
|
||
if not tech.enabled then
|
||
return "fnei_recipe_grey_tech_button"
|
||
elseif tech.researched then
|
||
return "fnei_recipe_green_tech_button"
|
||
else
|
||
local preq = tech.prerequisites
|
||
for _,tec in pairs(preq) do
|
||
if tec and not tec.researched then
|
||
return "fnei_recipe_red_tech_button"
|
||
end
|
||
end
|
||
return "fnei_recipe_yellow_tech_button"
|
||
end
|
||
end
|
||
|
||
function RecipeGui.set_crafting_type( action_type )
|
||
local label = Gui.get_gui(Gui.get_pos(), "type-label")
|
||
|
||
if action_type == "usage" then
|
||
label.caption = {"fnei.usage-for"}
|
||
elseif action_type == "craft" then
|
||
label.caption = {"fnei.recipe-for"}
|
||
else
|
||
label.caption = "unknown "
|
||
end
|
||
end
|
||
|
||
function RecipeGui.draw_cur_prot(type, name)
|
||
local prot_flow = Gui.get_gui(Gui.get_pos(), "prot-icon")
|
||
clear_gui(prot_flow)
|
||
if name then
|
||
Gui.add_choose_button(prot_flow, { type = "choose-elem-button", name = type .. "\t" .. name, style = "fnei_default_button", elem_type = type, elem_value = name, locked = true })
|
||
end
|
||
end
|
||
|
||
function RecipeGui.get_element_caption(element)
|
||
if not element then
|
||
return "unknown name"
|
||
end
|
||
|
||
local prot
|
||
if element.type == "item" then
|
||
prot = get_full_item_list()[element.name]
|
||
elseif element.type == "fluid" then
|
||
prot = get_full_fluid_list()[element.name]
|
||
elseif element.type == 'entity' then
|
||
prot = game.entity_prototypes[element.name]
|
||
end
|
||
|
||
local loc_str = nil
|
||
local prob = element.probability
|
||
local amnt = element.amount
|
||
|
||
|
||
if not Settings.get_val("detail-chance") and prob ~= nil then
|
||
if element.amount then
|
||
loc_str = round_to_str(element.amount * prob, 3)
|
||
else
|
||
local min = element.amount_min or 0
|
||
local max = element.amount_max or 0
|
||
|
||
loc_str = round_to_str((min + max) / 2 * prob, 3)
|
||
end
|
||
|
||
loc_str = {"", loc_str, " × ", get_localised_name(prot)}
|
||
else
|
||
-- get amoutn for product
|
||
|
||
if amnt ~= nil then
|
||
loc_str = element.amount
|
||
else
|
||
local min = element.amount_min or 0
|
||
local max = element.amount_max or 0
|
||
|
||
if not Settings.get_val("detail-chance") and prob ~= nil then
|
||
loc_str = round_to_str((min + max) / 2 * prob, 3)
|
||
else
|
||
if min == max then
|
||
loc_str = max
|
||
else
|
||
loc_str = {"", "[" .. min .. " - " .. max .. "]"}
|
||
end
|
||
end
|
||
end
|
||
|
||
-- if not single output then add " × "
|
||
|
||
if loc_str ~= 1 or prob == nil or prob == 1 then
|
||
loc_str = {"", loc_str, " × "}
|
||
else
|
||
loc_str = ""
|
||
end
|
||
|
||
-- add probability for product if exists
|
||
|
||
if prob ~= nil and prob ~= 1 then
|
||
loc_str = {"", loc_str, "" .. round_to_str(prob * 100, 3) .. "% "}
|
||
end
|
||
|
||
-- add localised name
|
||
|
||
loc_str = {"", loc_str, get_localised_name(prot)}
|
||
end
|
||
|
||
-- add temperature for fluid
|
||
local function is_number(value) return "number" == type(value) end
|
||
-- Excludes lowest/greatest number that can still be represented on a double
|
||
-- value-(value-1) == 1 and value-(value+1) == -1 excludes numbers that are not huge enough such that n-1 or n+1 overflow
|
||
local function is_finite(value) return is_number(value) and value-(value-1) == 1 and value-(value+1) == -1 and -math.huge ~= value and math.huge ~= value end
|
||
|
||
if element.type == "fluid" and Settings.get_val("show-temperature-of-fluids") then
|
||
if element.temperature then -- product
|
||
loc_str = {"", loc_str, " (" .. element.temperature .. "°C)"}
|
||
elseif element.minimum_temperature and not is_finite(element.maximum_temperature) then -- ingredient
|
||
loc_str = {"", loc_str, " ( ≥" .. element.minimum_temperature .. "°C)"}
|
||
elseif element.maximum_temperature and not is_finite(element.minimum_temperature) then -- ingredient
|
||
loc_str = {"", loc_str, " ( ≤" .. element.maximum_temperature .. "°C)"}
|
||
elseif element.minimum_temperature and element.maximum_temperature then -- ingredient; must be after each of the single temperature value test
|
||
if element.minimum_temperature == element.maximum_temperature then
|
||
loc_str = {"", loc_str, " (" .. element.minimum_temperature .. "°C)"}
|
||
else
|
||
loc_str = {"", loc_str, " (" .. element.minimum_temperature .. "°C - " .. element.maximum_temperature .. "°C)"}
|
||
end
|
||
end
|
||
end
|
||
|
||
return loc_str
|
||
end
|
||
|
||
function RecipeGui.draw_paging(page)
|
||
local page_gui = Gui.get_gui(Gui.get_pos(), "paging-table")
|
||
local label = Gui.get_gui(page_gui, "paging-label")
|
||
local amnt = page:amount_page()
|
||
|
||
local arrow = Gui.get_gui(page_gui, "right-arrow-flow")
|
||
if arrow and arrow.style then
|
||
page:draw_forward_arrow( arrow )
|
||
arrow.style.vertical_align = "center"
|
||
end
|
||
|
||
local arrow = Gui.get_gui(page_gui, "left-arrow-flow")
|
||
if arrow and arrow.style then
|
||
page:draw_back_arrow( arrow )
|
||
arrow.style.vertical_align = "center"
|
||
end
|
||
|
||
if amnt == 0 then amnt = 1 end
|
||
label.caption = {"", {"fnei.page"}, ": " .. page:get_cur_page() .. "/".. amnt}
|
||
end
|
||
|
||
return RecipeGui |