added formspecs for simple trade
This commit is contained in:
		
							parent
							
								
									4c4992f985
								
							
						
					
					
						commit
						53496c7369
					
				@ -24,6 +24,8 @@ yl_speak_up.npc_was_changed = {}
 | 
			
		||||
-- format: yl_speak_up.npc_owner[ npc_id ] = owner_name
 | 
			
		||||
yl_speak_up.npc_owner = {}
 | 
			
		||||
 | 
			
		||||
-- store the current trade between player and npc
 | 
			
		||||
yl_speak_up.trade = {}
 | 
			
		||||
 | 
			
		||||
function yl_speak_up.init_mob_table()
 | 
			
		||||
    return false
 | 
			
		||||
@ -2772,7 +2774,7 @@ yl_speak_up.input_talk = function(player, formname, fields)
 | 
			
		||||
	if(edit_mode and fields.show_inventory) then
 | 
			
		||||
		local dialog = yl_speak_up.speak_to[pname].dialog
 | 
			
		||||
		-- the inventory is just an inventory with a back button; come back to this dialog here
 | 
			
		||||
		minetest.show_formspec(pname, "yl_speak_up:inventory", yl_speak_up.get_fs_inventory(player, n_id, dialog.n_npc))
 | 
			
		||||
		minetest.show_formspec(pname, "yl_speak_up:inventory", yl_speak_up.get_fs_inventory(player))
 | 
			
		||||
		return
 | 
			
		||||
	end
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
							
								
								
									
										5
									
								
								init.lua
									
									
									
									
									
								
							
							
						
						
									
										5
									
								
								init.lua
									
									
									
									
									
								
							@ -19,8 +19,13 @@ dofile(modpath .. "config.lua")
 | 
			
		||||
dofile(modpath .. "privs.lua")
 | 
			
		||||
-- inventory management, trading and handling of quest items:
 | 
			
		||||
dofile(modpath .. "inventory.lua")
 | 
			
		||||
-- trade one item(stack) against one other item(stack)
 | 
			
		||||
dofile(modpath .. "trade_simple.lua")
 | 
			
		||||
-- the main functionality of the mod
 | 
			
		||||
dofile(modpath .. "functions.lua")
 | 
			
		||||
-- the staffs (requires npc_master priv)
 | 
			
		||||
dofile(modpath .. "tools.lua")
 | 
			
		||||
-- the actual mobs, using mobs_redo
 | 
			
		||||
dofile(modpath .. "mobs.lua")
 | 
			
		||||
--dofile(modpath .. "debug.lua")
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
@ -10,14 +10,28 @@ end
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
-- access the inventory of the NPC (only possible for players with the right priv)
 | 
			
		||||
yl_speak_up.get_fs_inventory = function(player, n_id, npc_name)
 | 
			
		||||
yl_speak_up.get_fs_inventory = function(player)
 | 
			
		||||
	if(not(player)) then
 | 
			
		||||
		return ""
 | 
			
		||||
	end
 | 
			
		||||
	local pname = player:get_player_name()
 | 
			
		||||
	-- which NPC is the player talking to?
 | 
			
		||||
	local n_id = yl_speak_up.speak_to[pname].n_id
 | 
			
		||||
	local dialog = yl_speak_up.speak_to[pname].dialog
 | 
			
		||||
	-- do we have all the necessary data?
 | 
			
		||||
	if(not(n_id) or not(dialog.n_npc)) then
 | 
			
		||||
		return "size[6,2]"..
 | 
			
		||||
			"label[0.2,0.5;Ups! This NPC lacks ID or name.]"..
 | 
			
		||||
		                "button_exit[2,1.5;1,0.9;exit;Exit]"
 | 
			
		||||
 | 
			
		||||
	end
 | 
			
		||||
	return "size[12,11]" ..
 | 
			
		||||
		"label[2,-0.2;Inventory of "..minetest.formspec_escape(npc_name)..
 | 
			
		||||
		"label[2,-0.2;Inventory of "..minetest.formspec_escape(dialog.n_npc)..
 | 
			
		||||
			" (ID: "..tostring(n_id).."):]"..
 | 
			
		||||
		"list[detached:yl_npc_"..tostring(n_id)..";npc_main;0,0.3;12,6;]" ..
 | 
			
		||||
		"list[detached:yl_speak_up_npc_"..tostring(n_id)..";npc_main;0,0.3;12,6;]" ..
 | 
			
		||||
		"list[current_player;main;2,6.85;8,1;]" ..
 | 
			
		||||
		"list[current_player;main;2,8.08;8,3;8]" ..
 | 
			
		||||
		"listring[detached:yl_npc_"..tostring(n_id)..";npc_main]" ..
 | 
			
		||||
		"listring[detached:yl_speak_up_npc_"..tostring(n_id)..";npc_main]" ..
 | 
			
		||||
		"listring[current_player;main]" ..
 | 
			
		||||
		"button[10.0,10.2;2,0.9;back_from_inventory;Back]"
 | 
			
		||||
end
 | 
			
		||||
@ -50,6 +64,7 @@ end
 | 
			
		||||
 | 
			
		||||
-- create and load the detached inventory in yl_speak_up.after_activate;
 | 
			
		||||
-- direct access to this inventory is only possible for players with the right privs
 | 
			
		||||
-- (this is an inventory for the *NPC*, which is stored to disk sometimes)
 | 
			
		||||
yl_speak_up.load_npc_inventory = function(n_id)
 | 
			
		||||
	if(not(n_id)) then
 | 
			
		||||
		return
 | 
			
		||||
@ -59,7 +74,7 @@ yl_speak_up.load_npc_inventory = function(n_id)
 | 
			
		||||
		return
 | 
			
		||||
	end
 | 
			
		||||
	-- create the detached inventory (it is empty for now)
 | 
			
		||||
	local npc_inv = minetest.create_detached_inventory("yl_npc_"..tostring(n_id), {
 | 
			
		||||
	local npc_inv = minetest.create_detached_inventory("yl_speak_up_npc_"..tostring(n_id), {
 | 
			
		||||
		allow_move = function(inv, from_list, from_index, to_list, to_index, count, player)
 | 
			
		||||
			if(not(yl_speak_up.may_edit_npc(player, n_id))) then
 | 
			
		||||
				return 0
 | 
			
		||||
 | 
			
		||||
							
								
								
									
										275
									
								
								trade_simple.lua
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										275
									
								
								trade_simple.lua
									
									
									
									
									
										Normal file
									
								
							@ -0,0 +1,275 @@
 | 
			
		||||
-- spimple trading: one item(stack) for another item(stack)
 | 
			
		||||
 | 
			
		||||
-- fallback message if something went wrong
 | 
			
		||||
yl_speak_up.trade_fail_fs = "size[6,2]"..
 | 
			
		||||
                "label[0.2,0.5;Ups! The trade is not possible.\nPlease notify an admin.]"..
 | 
			
		||||
		"button_exit[2,1.5;1,0.9;exit;Exit]"
 | 
			
		||||
 | 
			
		||||
-- TODO: when closing the formspec: give the items in the pay slot back
 | 
			
		||||
 | 
			
		||||
-- can this trade be made? called in allow_take
 | 
			
		||||
yl_speak_up.can_trade_simple = function(player, count)
 | 
			
		||||
	if(not(player)) then
 | 
			
		||||
		return 0
 | 
			
		||||
	end
 | 
			
		||||
	local pname = player:get_player_name()
 | 
			
		||||
	-- which trade are we talking about?
 | 
			
		||||
	local trade = yl_speak_up.trade[pname]
 | 
			
		||||
	-- do we have all the necessary data?
 | 
			
		||||
	if(not(trade) or trade.trade_type ~= "trade_simple") then
 | 
			
		||||
		return 0
 | 
			
		||||
	end
 | 
			
		||||
 | 
			
		||||
	-- the player tries to take *less* items than what his payment is;
 | 
			
		||||
	-- avoid this confusion!
 | 
			
		||||
	if(ItemStack(trade.npc_gives):get_count() ~= count) then
 | 
			
		||||
		return 0
 | 
			
		||||
	end
 | 
			
		||||
	-- buy, sell and config items need to be placed somewhere
 | 
			
		||||
	local trade_inv = minetest.get_inventory({type="detached", name="yl_speak_up_player_"..pname})
 | 
			
		||||
	-- the players' inventory
 | 
			
		||||
	local player_inv = player:get_inventory()
 | 
			
		||||
	-- the NPCs' inventory
 | 
			
		||||
	local npc_inv = minetest.get_inventory({type="detached", name="yl_speak_up_npc_"..tostring(trade.n_id)})
 | 
			
		||||
 | 
			
		||||
	-- is the payment in the payment slot?
 | 
			
		||||
	if( not(trade_inv:contains_item("pay", trade.player_gives))
 | 
			
		||||
	-- is the item to be sold in the buy slot?
 | 
			
		||||
	 or not(trade_inv:contains_item("buy", trade.npc_gives))
 | 
			
		||||
	-- has the NPC room for the payment?
 | 
			
		||||
	 or not(npc_inv:room_for_item("npc_main", trade.player_gives))
 | 
			
		||||
	-- has the player room for the sold item?
 | 
			
		||||
	 or not(player_inv:room_for_item("main", trade.npc_gives))) then
 | 
			
		||||
		-- trade not possible
 | 
			
		||||
		return 0
 | 
			
		||||
	end
 | 
			
		||||
	-- all ok; all items that are to be sold can be taken
 | 
			
		||||
	return ItemStack(trade.npc_gives):get_count()
 | 
			
		||||
end
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
-- actually execute the trade
 | 
			
		||||
yl_speak_up.do_trade_simple = function(player, count)
 | 
			
		||||
	-- can the trade be made?
 | 
			
		||||
	if(not(yl_speak_up.can_trade_simple(player, count))) then
 | 
			
		||||
		return
 | 
			
		||||
	end
 | 
			
		||||
 | 
			
		||||
	local pname = player:get_player_name()
 | 
			
		||||
	-- which trade are we talking about?
 | 
			
		||||
	local trade = yl_speak_up.trade[pname]
 | 
			
		||||
 | 
			
		||||
	-- buy, sell and config items need to be placed somewhere
 | 
			
		||||
	local trade_inv = minetest.get_inventory({type="detached", name="yl_speak_up_player_"..pname})
 | 
			
		||||
	-- the NPCs' inventory
 | 
			
		||||
	local npc_inv = minetest.get_inventory({type="detached", name="yl_speak_up_npc_"..tostring(trade.n_id)})
 | 
			
		||||
 | 
			
		||||
	-- the NPC sells these items right now, and the player is moving it to his inventory
 | 
			
		||||
	npc_inv:remove_item("npc_main", trade.npc_gives)
 | 
			
		||||
 | 
			
		||||
	-- move price items to the NPC
 | 
			
		||||
	local stack = trade_inv:remove_item("pay", trade.player_gives)
 | 
			
		||||
	npc_inv:add_item("npc_main", stack)
 | 
			
		||||
	-- save the inventory of the npc so that the payment does not get lost
 | 
			
		||||
	yl_speak_up.save_npc_inventory( trade.n_id )
 | 
			
		||||
 | 
			
		||||
	-- store for statistics how many times the player has executed this trade
 | 
			
		||||
	trade.trade_done = trade.trade_done + 1
 | 
			
		||||
end
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
-- simple trade: one item(stack) for another
 | 
			
		||||
-- handles configuration of new trades and showing the formspec for trades;
 | 
			
		||||
-- checks if payment and buying is possible
 | 
			
		||||
yl_speak_up.get_fs_trade_simple = function(player, player_gives, npc_gives)
 | 
			
		||||
	if(not(player)) then
 | 
			
		||||
		return yl_speak_up.trade_fail_fs
 | 
			
		||||
	end
 | 
			
		||||
	local pname = player:get_player_name()
 | 
			
		||||
	-- which trade are we talking about?
 | 
			
		||||
	local trade = yl_speak_up.trade[pname]
 | 
			
		||||
	-- do we have all the necessary data?
 | 
			
		||||
	if(not(trade) or trade.trade_type ~= "trade_simple") then
 | 
			
		||||
		return yl_speak_up.trade_fail_fs
 | 
			
		||||
	end
 | 
			
		||||
	-- the common formspec, shared by actual trade and configuration
 | 
			
		||||
	-- no listring here as that would make things more complicated
 | 
			
		||||
	local formspec = "size[8.5,8]"..
 | 
			
		||||
		"label[4.35,0.8;"..minetest.formspec_escape(trade.npc_name).." sells:]"..
 | 
			
		||||
		"list[current_player;main;0.2,3.85;8,1;]"..
 | 
			
		||||
		"list[current_player;main;0.2,5.08;8,3;8]"
 | 
			
		||||
 | 
			
		||||
	-- configuration of a new trade happens here
 | 
			
		||||
	if(not(trade.player_gives) or not(trade.npc_gives)) then
 | 
			
		||||
		-- is this player allowed to edit the NPC and his trades? If not abort.
 | 
			
		||||
		if(not(yl_speak_up.may_edit_npc(player, trade.n_id))) then
 | 
			
		||||
			return formspec..
 | 
			
		||||
				"label[2.0,1.8;Ups! Something went wrong.]"..
 | 
			
		||||
				"button[6.2,1.6;2.0,0.9;abort_trade_simple;Back]"
 | 
			
		||||
		end
 | 
			
		||||
		return formspec..
 | 
			
		||||
			-- show the second slot of the setup inventory in the detached player's inv
 | 
			
		||||
			"list[detached:yl_speak_up_player_"..pname..";setup;2,1.5;1,1;]"..
 | 
			
		||||
			-- show the second slot of said inventory
 | 
			
		||||
			"list[detached:yl_speak_up_player_"..pname..";setup;5,1.5;1,1;1]"..
 | 
			
		||||
			"label[2.5,0.0;Configure trade with "..minetest.formspec_escape(trade.npc_name)..":]"..
 | 
			
		||||
			"label[1.5,0.8;The customer pays:]"..
 | 
			
		||||
			"label[1.5,2.8;Put items in the two slots and click on \"Store trade\".]"..
 | 
			
		||||
			"label[1.5,3.2;You will get your items back when storing the trade.]"..
 | 
			
		||||
			"button[0.2,1.6;1.0,0.9;abort_trade_simple;Abort]"..
 | 
			
		||||
			"button[6.2,1.6;2.0,0.9;store_trade_simple;Store trade]"..
 | 
			
		||||
			"tooltip[store_trade_simple;Click here to store this as a new trade. Your "..
 | 
			
		||||
				"items will be returned to you and the trade will be shown the way "..
 | 
			
		||||
				"the customer can see it.]"..
 | 
			
		||||
			"tooltip[abort_trade_simple;Abort setting up this new trade.]"
 | 
			
		||||
	end
 | 
			
		||||
 | 
			
		||||
	-- view for the customer when actually trading
 | 
			
		||||
 | 
			
		||||
	-- buy, sell and config items need to be placed somewhere
 | 
			
		||||
	local trade_inv = minetest.get_inventory({type="detached", name="yl_speak_up_player_"..pname})
 | 
			
		||||
	-- the players' inventory
 | 
			
		||||
	local player_inv = player:get_inventory()
 | 
			
		||||
	-- the NPCs' inventory
 | 
			
		||||
	local npc_inv = minetest.get_inventory({type="detached", name="yl_speak_up_npc_"..tostring(trade.n_id)})
 | 
			
		||||
 | 
			
		||||
	-- show edit button for the owner
 | 
			
		||||
	if(yl_speak_up.may_edit_npc(player, trade.n_id)) then
 | 
			
		||||
		formspec = formspec..
 | 
			
		||||
			"button[0.2,1.6;0.8,0.9;edit_trade_simple;Edit]"..
 | 
			
		||||
			"tooltip[edit_trade_simple;Edit this trade. You can do so only "..
 | 
			
		||||
				"if you can edit the NPC as such (i.e. own it).]"
 | 
			
		||||
	end
 | 
			
		||||
 | 
			
		||||
	local trade_possible_msg = "Status of trade: Unknown."
 | 
			
		||||
	-- has the NPC room for the payment?
 | 
			
		||||
	if(not(npc_inv:room_for_item("npc_main", trade.player_gives))) then
 | 
			
		||||
		trade_possible_msg = "Sorry. "..minetest.formspec_escape(trade.npc_name)..
 | 
			
		||||
			" ran out of inventory space.\nThere is no room to store your payment!]"
 | 
			
		||||
	-- can the player pay?
 | 
			
		||||
	elseif(not(player_inv:contains_item("main", trade.player_gives))) then
 | 
			
		||||
		-- both slots will remain empty
 | 
			
		||||
		trade_possible_msg = "You cannot pay the price."
 | 
			
		||||
	-- is the slot for the payment empty?
 | 
			
		||||
	elseif not(trade_inv:is_empty("pay")) then
 | 
			
		||||
		-- both slots will remain empty
 | 
			
		||||
		-- (the slot may already contain the right things; we'll find that out later on)
 | 
			
		||||
		trade_possible_msg = "Please insert the right payment manually."
 | 
			
		||||
	-- all good so far; move the price stack to the pay slot
 | 
			
		||||
	else
 | 
			
		||||
		-- move price item to the price slot
 | 
			
		||||
		local stack = player_inv:remove_item("main", trade.player_gives)
 | 
			
		||||
		trade_inv:add_item("pay", stack)
 | 
			
		||||
	end
 | 
			
		||||
 | 
			
		||||
	-- make sure the sale slot is empty (we will fill it if the trade is possible)
 | 
			
		||||
	trade_inv:set_stack("buy", 1, "")
 | 
			
		||||
	-- after all this: does the payment slot contain the right things?
 | 
			
		||||
	if(trade_inv:contains_item("pay", trade.player_gives)) then
 | 
			
		||||
		trade_possible_msg = "Take the offered item(s) in order to buy them."
 | 
			
		||||
 | 
			
		||||
		-- can the NPC provide his part?
 | 
			
		||||
		if(not(npc_inv:contains_item("npc_main", trade.npc_gives))) then
 | 
			
		||||
			trade_possible_msg = "Sorry. "..minetest.formspec_escape(trade.npc_name)..
 | 
			
		||||
				" ran out of stock.\nPlease come back later."
 | 
			
		||||
		else
 | 
			
		||||
			-- put a *copy* of the item(stack) that is to be sold in the sale slot
 | 
			
		||||
			trade_inv:add_item("buy", trade.npc_gives)
 | 
			
		||||
		end
 | 
			
		||||
	end
 | 
			
		||||
 | 
			
		||||
	if(not(player_inv:room_for_item("main", trade.npc_gives))) then
 | 
			
		||||
		-- the player has no room for the sold item; give a warning
 | 
			
		||||
		trade_possible_msg = "Careful! You do not seem to have enough\n"..
 | 
			
		||||
				"free inventory space to store your purchase.]"
 | 
			
		||||
	end
 | 
			
		||||
 | 
			
		||||
	return formspec..
 | 
			
		||||
		"label[2.5,0.0;Trading with "..minetest.formspec_escape(trade.npc_name).."]"..
 | 
			
		||||
		"label[1.5,0.8;You pay:]"..
 | 
			
		||||
		-- show images of price and what is sold so that the player knows what
 | 
			
		||||
		-- it costs and what he will get even if the trade is not possible at
 | 
			
		||||
		-- that moment
 | 
			
		||||
		"item_image[1,1.5;1,1;"..tostring(trade.player_gives).."]"..
 | 
			
		||||
		"item_image[4,1.5;1,1;"..tostring(trade.npc_gives).."]"..
 | 
			
		||||
		-- show the pay slot from the detached player's trade inventory
 | 
			
		||||
		"list[detached:yl_speak_up_player_"..pname..";pay;2,1.5;1,1;]" ..
 | 
			
		||||
		-- show the buy slot from the same inventory
 | 
			
		||||
		"list[detached:yl_speak_up_player_"..pname..";buy;5,1.5;1,1;]" ..
 | 
			
		||||
		"label[1.5,2.8;"..trade_possible_msg.."]"..
 | 
			
		||||
		"button[6.2,1.6;2.0,0.9;finished_trading;Finish trading]"..
 | 
			
		||||
		"tooltip[finished_trading;Click here once you've traded enough with this "..
 | 
			
		||||
			"NPC and want to get back to talking.]"
 | 
			
		||||
end
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
-- create a detached inventory for the *player* for trading with the npcs
 | 
			
		||||
minetest.register_on_joinplayer(function(player, last_login)
 | 
			
		||||
	local pname = player:get_player_name()
 | 
			
		||||
 | 
			
		||||
	-- create the detached inventory;
 | 
			
		||||
	-- the functions for monitoring changes will be important later on
 | 
			
		||||
	-- only the the player owning this detached inventory may access it
 | 
			
		||||
	local trade_inv = minetest.create_detached_inventory("yl_speak_up_player_"..tostring(pname), {
 | 
			
		||||
		-- moving of items between diffrent lists is not allowed
 | 
			
		||||
		allow_move = function(inv, from_list, from_index, to_list, to_index, count, player)
 | 
			
		||||
			if(not(player) or player:get_player_name() ~= pname) then
 | 
			
		||||
				return 0
 | 
			
		||||
			end
 | 
			
		||||
			if(from_list ~= to_list) then
 | 
			
		||||
				return 0
 | 
			
		||||
			end
 | 
			
		||||
			return count
 | 
			
		||||
		end,
 | 
			
		||||
 | 
			
		||||
		-- these all require calling special functions, depending on context
 | 
			
		||||
	        allow_put = function(inv, listname, index, stack, player)
 | 
			
		||||
			if(not(player) or player:get_player_name() ~= pname) then
 | 
			
		||||
				return 0
 | 
			
		||||
			end
 | 
			
		||||
			-- the "buy" slot is managed by the NPC; the player only takes from it
 | 
			
		||||
			if(listname == "buy") then
 | 
			
		||||
				return 0
 | 
			
		||||
			end
 | 
			
		||||
			return stack:get_count()
 | 
			
		||||
		end,
 | 
			
		||||
	        allow_take = function(inv, listname, index, stack, player)
 | 
			
		||||
			if(not(player) or player:get_player_name() ~= pname) then
 | 
			
		||||
				return 0
 | 
			
		||||
			end
 | 
			
		||||
			-- can the trade be made?
 | 
			
		||||
			if(listname == "buy") then
 | 
			
		||||
				return yl_speak_up.can_trade_simple(player, stack:get_count())
 | 
			
		||||
			end
 | 
			
		||||
			return stack:get_count()
 | 
			
		||||
		end,
 | 
			
		||||
	        on_move = function(inv, from_list, from_index, to_list, to_index, count, player)
 | 
			
		||||
		end,
 | 
			
		||||
	        on_put = function(inv, listname, index, stack, player)
 | 
			
		||||
			if(listname == "pay") then
 | 
			
		||||
				local pname = player:get_player_name()
 | 
			
		||||
				-- show formspec with updated information (perhaps sale is now possible)
 | 
			
		||||
				minetest.show_formspec(pname, "yl_speak_up:talk", yl_speak_up.get_fs_trade_simple(player))
 | 
			
		||||
			end
 | 
			
		||||
		end,
 | 
			
		||||
	        on_take = function(inv, listname, index, stack, player)
 | 
			
		||||
			-- the player may have put something wrong in the payment slot
 | 
			
		||||
			-- -> show updated formspec
 | 
			
		||||
			if(listname == "pay") then
 | 
			
		||||
				local pname = player:get_player_name()
 | 
			
		||||
				-- show formspec with updated information (perhaps sale is now possible)
 | 
			
		||||
				minetest.show_formspec(pname, "yl_speak_up:talk", yl_speak_up.get_fs_trade_simple(player))
 | 
			
		||||
			elseif(listname == "buy") then
 | 
			
		||||
				yl_speak_up.do_trade_simple(player, stack:get_count())
 | 
			
		||||
				-- information may require an update (NPC might now be out of stock), or
 | 
			
		||||
				-- the player can do the trade a second time
 | 
			
		||||
				minetest.show_formspec(pname, "yl_speak_up:talk", yl_speak_up.get_fs_trade_simple(player))
 | 
			
		||||
			end
 | 
			
		||||
		end,
 | 
			
		||||
	})
 | 
			
		||||
	-- prepare the actual inventories
 | 
			
		||||
	trade_inv:set_size("pay", 1)
 | 
			
		||||
	trade_inv:set_size("buy", 1)
 | 
			
		||||
	-- for setting up new simple trades
 | 
			
		||||
	trade_inv:set_size("setup", 2*1)
 | 
			
		||||
end)
 | 
			
		||||
		Loading…
	
		Reference in New Issue
	
	Block a user