Allow restricting detached inventories to one player
This combats the problem of sending the hundreds of "creative" / "armor" or whatever detached invs that exist on popular servers to each and every player on join or on change of said invs.
This commit is contained in:
		
							parent
							
								
									2fe3bf5a18
								
							
						
					
					
						commit
						c38985825f
					
				| @ -2,7 +2,7 @@ | ||||
| 
 | ||||
| core.detached_inventories = {} | ||||
| 
 | ||||
| function core.create_detached_inventory(name, callbacks) | ||||
| function core.create_detached_inventory(name, callbacks, player_name) | ||||
| 	local stuff = {} | ||||
| 	stuff.name = name | ||||
| 	if callbacks then | ||||
| @ -15,6 +15,6 @@ function core.create_detached_inventory(name, callbacks) | ||||
| 	end | ||||
| 	stuff.mod_origin = core.get_current_modname() or "??" | ||||
| 	core.detached_inventories[name] = stuff | ||||
| 	return core.create_detached_inventory_raw(name) | ||||
| 	return core.create_detached_inventory_raw(name, player_name) | ||||
| end | ||||
| 
 | ||||
|  | ||||
| @ -2310,8 +2310,11 @@ and `minetest.auth_reload` call the authetification handler. | ||||
|     * `{type="player", name="celeron55"}` | ||||
|     * `{type="node", pos={x=, y=, z=}}` | ||||
|     * `{type="detached", name="creative"}` | ||||
| * `minetest.create_detached_inventory(name, callbacks)`: returns an `InvRef` | ||||
| * `minetest.create_detached_inventory(name, callbacks, [player_name])`: returns an `InvRef` | ||||
|     * callbacks: See "Detached inventory callbacks" | ||||
|     * player_name: Make detached inventory available to one player exclusively, | ||||
|       by default they will be sent to every player (even if not used). | ||||
|       Note that this parameter is mostly just a workaround and will be removed in future releases. | ||||
|     * Creates a detached inventory. If it already exists, it is cleared. | ||||
| * `minetest.do_item_eat(hp_change, replace_with_item, itemstack, user, pointed_thing)`: | ||||
|    returns left over ItemStack | ||||
|  | ||||
| @ -520,16 +520,17 @@ int ModApiInventory::l_get_inventory(lua_State *L) | ||||
| 	} | ||||
| } | ||||
| 
 | ||||
| // create_detached_inventory_raw(name)
 | ||||
| // create_detached_inventory_raw(name, [player_name])
 | ||||
| int ModApiInventory::l_create_detached_inventory_raw(lua_State *L) | ||||
| { | ||||
| 	NO_MAP_LOCK_REQUIRED; | ||||
| 	const char *name = luaL_checkstring(L, 1); | ||||
| 	if(getServer(L)->createDetachedInventory(name) != NULL){ | ||||
| 	const char *player = lua_isstring(L, 2) ? lua_tostring(L, 2) : ""; | ||||
| 	if (getServer(L)->createDetachedInventory(name, player) != NULL) { | ||||
| 		InventoryLocation loc; | ||||
| 		loc.setDetached(name); | ||||
| 		InvRef::create(L, loc); | ||||
| 	}else{ | ||||
| 	} else { | ||||
| 		lua_pushnil(L); | ||||
| 	} | ||||
| 	return 1; | ||||
|  | ||||
| @ -2487,11 +2487,16 @@ void Server::sendDetachedInventory(const std::string &name, u16 peer_id) | ||||
| 	NetworkPacket pkt(TOCLIENT_DETACHED_INVENTORY, 0, peer_id); | ||||
| 	pkt.putRawString(s.c_str(), s.size()); | ||||
| 
 | ||||
| 	if (peer_id != PEER_ID_INEXISTENT) { | ||||
| 		Send(&pkt); | ||||
| 	} | ||||
| 	else { | ||||
| 		m_clients.sendToAll(0, &pkt, true); | ||||
| 	const std::string &check = m_detached_inventories_player[name]; | ||||
| 	if (peer_id == PEER_ID_INEXISTENT) { | ||||
| 		if (check == "") | ||||
| 			return m_clients.sendToAll(0, &pkt, true); | ||||
| 		RemotePlayer *p = m_env->getPlayer(check.c_str()); | ||||
| 		if (p) | ||||
| 			m_clients.send(p->peer_id, 0, &pkt, true); | ||||
| 	} else { | ||||
| 		if (check == "" || getPlayerName(peer_id) == check) | ||||
| 			Send(&pkt); | ||||
| 	} | ||||
| } | ||||
| 
 | ||||
| @ -3224,7 +3229,7 @@ void Server::deleteParticleSpawner(const std::string &playername, u32 id) | ||||
| 	SendDeleteParticleSpawner(peer_id, id); | ||||
| } | ||||
| 
 | ||||
| Inventory* Server::createDetachedInventory(const std::string &name) | ||||
| Inventory* Server::createDetachedInventory(const std::string &name, const std::string &player) | ||||
| { | ||||
| 	if(m_detached_inventories.count(name) > 0){ | ||||
| 		infostream<<"Server clearing detached inventory \""<<name<<"\""<<std::endl; | ||||
| @ -3235,6 +3240,7 @@ Inventory* Server::createDetachedInventory(const std::string &name) | ||||
| 	Inventory *inv = new Inventory(m_itemdef); | ||||
| 	sanity_check(inv); | ||||
| 	m_detached_inventories[name] = inv; | ||||
| 	m_detached_inventories_player[name] = player; | ||||
| 	//TODO find a better way to do this
 | ||||
| 	sendDetachedInventory(name,PEER_ID_INEXISTENT); | ||||
| 	return inv; | ||||
|  | ||||
| @ -270,7 +270,7 @@ public: | ||||
| 	void deleteParticleSpawner(const std::string &playername, u32 id); | ||||
| 
 | ||||
| 	// Creates or resets inventory
 | ||||
| 	Inventory* createDetachedInventory(const std::string &name); | ||||
| 	Inventory* createDetachedInventory(const std::string &name, const std::string &player=""); | ||||
| 
 | ||||
| 	// Envlock and conlock should be locked when using scriptapi
 | ||||
| 	GameScripting *getScriptIface(){ return m_script; } | ||||
| @ -647,6 +647,8 @@ private: | ||||
| 	*/ | ||||
| 	// key = name
 | ||||
| 	std::map<std::string, Inventory*> m_detached_inventories; | ||||
| 	// value = "" (visible to all players) or player name
 | ||||
| 	std::map<std::string, std::string> m_detached_inventories_player; | ||||
| 
 | ||||
| 	DISABLE_CLASS_COPY(Server); | ||||
| }; | ||||
|  | ||||
		Loading…
	
		Reference in New Issue
	
	Block a user