emeraldbank/functions.lua
2023-08-25 17:06:28 +02:00

261 lines
8.0 KiB
Lua

-- Copyright (C) 2021, 2022 Ale
-- This file is part of Emeraldbank Minetest Mod.
-- Emeraldbank is free software: you can redistribute it and/or modify
-- it under the terms of the GNU Affero General Public License as
-- published by the Free Software Foundation, either version 3 of the
-- License, or (at your option) any later version.
-- Emeraldbank is distributed in the hope that it will be useful,
-- but WITHOUT ANY WARRANTY; without even the implied warranty of
-- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
-- GNU Affero General Public License for more details.
-- You should have received a copy of the GNU Affero General Public License
-- along with Emeraldbank. If not, see <https://www.gnu.org/licenses/>.
local S = core.get_translator(core.get_current_modname())
function atm.ensure_init(name)
-- Ensure the atm account for the placer specified by name exists
atm.readaccounts()
if not atm.balance[name] then
atm.balance[name] = atm.startbalance
end
end
-- banking accounts storage
function atm.readaccounts ()
local b = atm.balance
local file = io.open(atm.pth, "r")
if file then
repeat
local balance = file:read("*n")
if balance == nil then
break
end
local name = file:read("*l")
b[name:sub(2)] = balance
until file:read(0) == nil
io.close(file)
end
end
function atm.saveaccounts()
if not atm.balance then
return
end
local data = {}
for k, v in pairs(atm.balance) do
table.insert(data, string.format("%d %s\n", v, k))
end
local output = io.open(atm.pth, "w")
output:write(table.concat(data))
io.close(output)
end
function emeraldbank.update_account()
atm.readaccounts()
for _, player in ipairs(core.get_connected_players()) do
if not player or player.is_fake_player then return end
local meta = player:get_meta()
local bankemeralds = meta:get_int("emeraldbank:emerald")
local name = player:get_player_name()
if atm.balance[name] then
atm.balance[name] = math.floor(atm.balance[name] + bankemeralds)
else
atm.balance[name] = bankemeralds
end
meta:set_int("emeraldbank:emerald", 0)
-- backup
meta:set_int("emeraldbank:emerald_backup", bankemeralds)
end
atm.saveaccounts()
end
function emeraldbank.old_add_emeralds(player, num)
if not player then return false end
local meta = player:get_meta()
local bankemeralds = meta:get_int("emeraldbank:emerald") -- if nil "get_int()" return 0 Magic!
local name = player:get_player_name()
if num then
meta:set_int("emeraldbank:emerald", bankemeralds+num)
mcl_title.set(player, "actionbar", {text=S("Emeralds in Bank: @1", bankemeralds+num), color="yellow"})
return true
end
return false
end
function emeraldbank.add_emeralds(player, num)
atm.readaccounts()
if not player then return false end
local meta = player:get_meta()
local name = player:get_player_name()
if num then
if atm.balance[name] then
atm.balance[name] = math.floor(atm.balance[name] + num)
else
atm.balance[name] = num
end
mcl_title.set(player, "actionbar", {text=S("Emeralds in Bank: @1", atm.balance[name]), color="yellow"})
atm.saveaccounts()
return true
end
return false
end
function emeraldbank.transfer_emeralds(player1, player2, num)
atm.readaccounts()
local name = player1:get_player_name()
local name2 = player2:get_player_name()
local bankemeralds1 = atm.balance[name]
if num > 0 then
if bankemeralds1 and bankemeralds1 >= num then
core.chat_send_player(name, S("Pay Successfully! You have transferred @1 Emeralds." , num))
core.chat_send_player(name2, S("Pay Successfully! You've gotten @1 Emeralds.", num))
if core.get_modpath("irc") then
irc.say(name.." has transferred "..num.." emeralds to "..name2)
end
if core.get_modpath("yl_matterbridge") then
yl_matterbridge.send_to_bridge("", name.." has transferred "..num.." emeralds to "..name2)
end
emeraldbank.add_emeralds(player1, -num)
emeraldbank.add_emeralds(player2, num)
core.sound_play("cash", {
to_player = name2,
gain = 1.0,
fade = 0.0,
pitch = 1.0,
})
else
core.chat_send_player(name, S("Not enough Emeralds in your account"))
end
else
core.chat_send_player(name, S("Invalid pay"))
end
end
function emeraldbank.keep(player, itemstack)
local itemname = itemstack:get_name()
local itemcount = itemstack:get_count()
local name = player:get_player_name()
if itemname == "mcl_core:emerald" then
itemstack:take_item(itemcount)
emeraldbank.add_emeralds(player, itemcount)
return true
end
if itemname == "mcl_core:emeraldblock" then
itemstack:take_item(itemcount)
emeraldbank.add_emeralds(player, itemcount*9)
return true
end
mcl_title.set(player, "actionbar", {text=S("You need keep emeralds or emeraldblocks in your hand!"), color="dark_red"})
return false
end
function emeraldbank.take(player)
local meta = player:get_meta()
local bankemeralds = meta:get_int("emeraldbank:emerald")
local name = player:get_player_name()
local pos = player:get_pos()
local num = 1
if bankemeralds >= 1 then
if bankemeralds >= 10 then
num = 10
end
emeraldbank.add_emeralds(player, -num)
core.add_item(pos, "mcl_core:emerald "..num)
return true
end
mcl_title.set(player, "actionbar", {text=S("Not enough Emeralds in your account"), color="dark_red"})
return false
end
-- wire transfer data storage
function atm.read_transactions()
local file = io.open(atm.pth_wt, "r")
if file then
local data = file:read("*all")
atm.completed_transactions = minetest.deserialize(data)
end
end
function atm.write_transactions()
if not atm.completed_transactions then
return
end
local file = io.open(atm.pth_wt, "w")
local data = minetest.serialize(atm.completed_transactions)
file:write(data)
io.close(file)
end
minetest.register_on_joinplayer(atm.readaccounts)
minetest.register_on_joinplayer(emeraldbank.update_account)
function emeraldbank.upgrade_shop(pos)
local oldnode = core.get_node(pos)
local old_meta = core.get_meta(pos)
local old_meta_table = core.get_meta(pos):to_table()
local nodename = core.get_node(pos).name
-- set the new shop node
core.swap_node(pos, {name = "fancy_vend:player_vendor"})
-- setup the new shop node
-- Set variables for access later (for various checks, etc.)
local owner = old_meta:get_string("owner") or ""
pos.y = pos.y + 1
local above_node = minetest.get_node(pos).name
-- If node above is air or the display node, and it is not protected, attempt to place the vendor. If vendor sucessfully places, place display node above, otherwise alert the user
if (minetest.registered_nodes[above_node].buildable_to or above_node == "fancy_vend:display_node") and not minetest.is_protected(pos, owner) then
if above_node ~= "fancy_vend:display_node" then
minetest.set_node(pos, minetest.registered_nodes["fancy_vend:display_node"])
end
-- Set owner
local meta = minetest.get_meta(pos)
meta:set_string("owner", owner or "")
-- Set default meta
meta:set_string("log", minetest.serialize({"Vendor placed by "..owner,}))
emeraldbank.reset_vendor_settings(pos)
emeraldbank.refresh_vendor(pos)
else
minetest.chat_send_player(owner, S("Vendors require 2 nodes of space."))
end
if minetest.get_modpath("pipeworks") then
pipeworks.after_place(pos)
end
-- copy old metadata in new node
core.get_meta(pos):from_table(old_meta_table)
-- new node
local node = core.get_node(pos)
local meta = core.get_meta(pos)
local count = meta:get_int("count")
local price = meta:get_int("price")
local shop_item = meta:get_string("shop_item")
local minv = meta:get_inventory()
local settings = emeraldbank.get_vendor_settings(pos)
settings.input_item = "mcl_core:emerald"
settings.input_item_qty = price
settings.output_item = shop_item
settings.output_item_qty = count
emeraldbank.refresh_vendor(pos)
end