mirror of
				https://github.com/luanti-org/luanti.git
				synced 2025-11-04 01:05:48 +01:00 
			
		
		
		
	A bunch of fixes
No longer hide players who are dead. With models, a death animation should be used instead Some changes requested by celeron55 Rename a lot of things in the code, and use better lua api function names Minor code corrections Bump protocol version up, since the models / animations / attachments code creates new client<->server messages
This commit is contained in:
		
				
					committed by
					
						
						Perttu Ahola
					
				
			
			
				
	
			
			
			
						parent
						
							fa67b46c04
						
					
				
				
					commit
					756db8174a
				
			@@ -1103,10 +1103,10 @@ methods:
 | 
			
		||||
- get_wielded_item() -> ItemStack
 | 
			
		||||
- set_wielded_item(item): replaces the wielded item, returns true if successful
 | 
			
		||||
- set_armor_groups({group1=rating, group2=rating, ...})
 | 
			
		||||
- set_animations({x=1,y=1}, frame_speed=15, frame_blend=0)
 | 
			
		||||
- set_attachment(parent, "", {x=0,y=0,z=0}, {x=0,y=0,z=0})
 | 
			
		||||
- set_detachment()
 | 
			
		||||
- set_bone_posrot("", {x=0,y=0,z=0}, {x=0,y=0,z=0})
 | 
			
		||||
- set_animation({x=1,y=1}, frame_speed=15, frame_blend=0)
 | 
			
		||||
- set_attach(parent, "", {x=0,y=0,z=0}, {x=0,y=0,z=0})
 | 
			
		||||
- set_detach()
 | 
			
		||||
- set_bone_position("", {x=0,y=0,z=0}, {x=0,y=0,z=0})
 | 
			
		||||
- set_properties(object property table)
 | 
			
		||||
LuaEntitySAO-only: (no-op for other objects)
 | 
			
		||||
- setvelocity({x=num, y=num, z=num})
 | 
			
		||||
 
 | 
			
		||||
@@ -821,8 +821,8 @@ bool Client::loadMedia(const std::string &data, const std::string &filename)
 | 
			
		||||
	name = removeStringEnd(filename, image_ext);
 | 
			
		||||
	if(name != "")
 | 
			
		||||
	{
 | 
			
		||||
		verbosestream<<"Client: Storing image into Irrlicht: "
 | 
			
		||||
				<<"\""<<filename<<"\""<<std::endl;
 | 
			
		||||
		verbosestream<<"Client: Attempting to load image "
 | 
			
		||||
		<<"file \""<<filename<<"\""<<std::endl;
 | 
			
		||||
 | 
			
		||||
		io::IFileSystem *irrfs = m_device->getFileSystem();
 | 
			
		||||
		video::IVideoDriver *vdrv = m_device->getVideoDriver();
 | 
			
		||||
@@ -855,8 +855,8 @@ bool Client::loadMedia(const std::string &data, const std::string &filename)
 | 
			
		||||
	name = removeStringEnd(filename, sound_ext);
 | 
			
		||||
	if(name != "")
 | 
			
		||||
	{
 | 
			
		||||
		verbosestream<<"Client: Storing sound into Irrlicht: "
 | 
			
		||||
				<<"\""<<filename<<"\""<<std::endl;
 | 
			
		||||
		verbosestream<<"Client: Attempting to load sound "
 | 
			
		||||
		<<"file \""<<filename<<"\""<<std::endl;
 | 
			
		||||
		m_sound->loadSoundData(name, data);
 | 
			
		||||
		return true;
 | 
			
		||||
	}
 | 
			
		||||
 
 | 
			
		||||
@@ -61,7 +61,7 @@ public:
 | 
			
		||||
	virtual scene::IBillboardSceneNode *getSpriteSceneNode(){return NULL;}
 | 
			
		||||
	virtual bool isPlayer(){return false;}
 | 
			
		||||
	virtual bool isLocalPlayer(){return false;}
 | 
			
		||||
	virtual void updateParent(){}
 | 
			
		||||
	virtual void setAttachments(){}
 | 
			
		||||
	virtual bool doShowSelectionBox(){return true;}
 | 
			
		||||
	
 | 
			
		||||
	// Step object in time
 | 
			
		||||
 
 | 
			
		||||
@@ -67,9 +67,14 @@ with this program; if not, write to the Free Software Foundation, Inc.,
 | 
			
		||||
		TOCLIENT_DETACHED_INVENTORY
 | 
			
		||||
	PROTOCOL_VERSION 13:
 | 
			
		||||
		InventoryList field "Width" (deserialization fails with old versions)
 | 
			
		||||
	PROTOCOL_VERSION 14:
 | 
			
		||||
		New messages for mesh and bone animation, as well as attachments
 | 
			
		||||
		GENERIC_CMD_SET_ANIMATION
 | 
			
		||||
		GENERIC_CMD_SET_BONE_POSITION
 | 
			
		||||
		GENERIC_CMD_SET_ATTACHMENT
 | 
			
		||||
*/
 | 
			
		||||
 | 
			
		||||
#define PROTOCOL_VERSION 13
 | 
			
		||||
#define PROTOCOL_VERSION 14
 | 
			
		||||
 | 
			
		||||
#define PROTOCOL_ID 0x4f457403
 | 
			
		||||
 | 
			
		||||
 
 | 
			
		||||
@@ -52,8 +52,6 @@ struct ToolCapabilities;
 | 
			
		||||
 | 
			
		||||
core::map<u16, ClientActiveObject::Factory> ClientActiveObject::m_types;
 | 
			
		||||
 | 
			
		||||
std::vector<core::vector2d<int> > attachment_list; // X is child ID, Y is parent ID
 | 
			
		||||
 | 
			
		||||
/*
 | 
			
		||||
	SmoothTranslator
 | 
			
		||||
*/
 | 
			
		||||
@@ -580,10 +578,10 @@ private:
 | 
			
		||||
	v2s16 m_tx_basepos;
 | 
			
		||||
	bool m_initial_tx_basepos_set;
 | 
			
		||||
	bool m_tx_select_horiz_by_yawpitch;
 | 
			
		||||
	v2f m_frames;
 | 
			
		||||
	int m_frame_speed;
 | 
			
		||||
	int m_frame_blend;
 | 
			
		||||
	std::map<std::string, core::vector2d<v3f> > m_bone_posrot; // stores position and rotation for each bone name
 | 
			
		||||
	v2f m_animation_range;
 | 
			
		||||
	int m_animation_speed;
 | 
			
		||||
	int m_animation_blend;
 | 
			
		||||
	std::map<std::string, core::vector2d<v3f> > m_bone_position; // stores position and rotation for each bone name
 | 
			
		||||
	std::string m_attachment_bone;
 | 
			
		||||
	v3f m_attachment_position;
 | 
			
		||||
	v3f m_attachment_rotation;
 | 
			
		||||
@@ -623,10 +621,10 @@ public:
 | 
			
		||||
		m_tx_basepos(0,0),
 | 
			
		||||
		m_initial_tx_basepos_set(false),
 | 
			
		||||
		m_tx_select_horiz_by_yawpitch(false),
 | 
			
		||||
		m_frames(v2f(0,0)),
 | 
			
		||||
		m_frame_speed(15),
 | 
			
		||||
		m_frame_blend(0),
 | 
			
		||||
		m_bone_posrot(std::map<std::string, core::vector2d<v3f> >()),
 | 
			
		||||
		m_animation_range(v2f(0,0)),
 | 
			
		||||
		m_animation_speed(15),
 | 
			
		||||
		m_animation_blend(0),
 | 
			
		||||
		m_bone_position(std::map<std::string, core::vector2d<v3f> >()),
 | 
			
		||||
		m_attachment_bone(""),
 | 
			
		||||
		m_attachment_position(v3f(0,0,0)),
 | 
			
		||||
		m_attachment_rotation(v3f(0,0,0)),
 | 
			
		||||
@@ -709,7 +707,7 @@ public:
 | 
			
		||||
				return m_animated_meshnode->getAbsolutePosition();
 | 
			
		||||
			if(m_spritenode)
 | 
			
		||||
				return m_spritenode->getAbsolutePosition();
 | 
			
		||||
			return v3f(0,0,0); // Just in case
 | 
			
		||||
			return m_position;
 | 
			
		||||
		}
 | 
			
		||||
		return pos_translator.vect_show;
 | 
			
		||||
	}
 | 
			
		||||
@@ -745,7 +743,7 @@ public:
 | 
			
		||||
		return m_is_local_player;
 | 
			
		||||
	}
 | 
			
		||||
 | 
			
		||||
	void updateParent()
 | 
			
		||||
	void setAttachments()
 | 
			
		||||
	{
 | 
			
		||||
		updateAttachments();
 | 
			
		||||
	}
 | 
			
		||||
@@ -753,9 +751,9 @@ public:
 | 
			
		||||
	ClientActiveObject *getParent()
 | 
			
		||||
	{
 | 
			
		||||
		ClientActiveObject *obj = NULL;
 | 
			
		||||
		for(std::vector<core::vector2d<int> >::const_iterator cii = attachment_list.begin(); cii != attachment_list.end(); cii++)
 | 
			
		||||
		for(std::vector<core::vector2d<int> >::const_iterator cii = m_env->attachment_list.begin(); cii != m_env->attachment_list.end(); cii++)
 | 
			
		||||
		{
 | 
			
		||||
			if(cii->X == this->getId()){ // This ID is our child
 | 
			
		||||
			if(cii->X == getId()){ // This ID is our child
 | 
			
		||||
				if(cii->Y > 0){ // A parent ID exists for our child
 | 
			
		||||
					if(cii->X != cii->Y){ // The parent and child ID are not the same
 | 
			
		||||
						obj = m_env->getActiveObject(cii->Y);
 | 
			
		||||
@@ -774,22 +772,22 @@ public:
 | 
			
		||||
		if(permanent) // Should be true when removing the object permanently and false when refreshing (eg: updating visuals)
 | 
			
		||||
		{
 | 
			
		||||
			// Detach this object's children
 | 
			
		||||
			for(std::vector<core::vector2d<int> >::iterator ii = attachment_list.begin(); ii != attachment_list.end(); ii++)
 | 
			
		||||
			for(std::vector<core::vector2d<int> >::iterator ii = m_env->attachment_list.begin(); ii != m_env->attachment_list.end(); ii++)
 | 
			
		||||
			{
 | 
			
		||||
				if(ii->Y == this->getId()) // Is a child of our object
 | 
			
		||||
				if(ii->Y == getId()) // Is a child of our object
 | 
			
		||||
				{
 | 
			
		||||
					ii->Y = 0;
 | 
			
		||||
					ClientActiveObject *obj = m_env->getActiveObject(ii->X); // Get the object of the child
 | 
			
		||||
					if(obj)
 | 
			
		||||
						obj->updateParent();
 | 
			
		||||
						obj->setAttachments();
 | 
			
		||||
				}
 | 
			
		||||
			}
 | 
			
		||||
			// Delete this object from the attachments list
 | 
			
		||||
			for(std::vector<core::vector2d<int> >::iterator ii = attachment_list.begin(); ii != attachment_list.end(); ii++)
 | 
			
		||||
			for(std::vector<core::vector2d<int> >::iterator ii = m_env->attachment_list.begin(); ii != m_env->attachment_list.end(); ii++)
 | 
			
		||||
			{
 | 
			
		||||
				if(ii->X == this->getId()) // Is our object
 | 
			
		||||
				if(ii->X == getId()) // Is our object
 | 
			
		||||
				{
 | 
			
		||||
					attachment_list.erase(ii);
 | 
			
		||||
					m_env->attachment_list.erase(ii);
 | 
			
		||||
					break;
 | 
			
		||||
				}
 | 
			
		||||
			}
 | 
			
		||||
@@ -983,31 +981,16 @@ public:
 | 
			
		||||
		
 | 
			
		||||
	void updateLight(u8 light_at_pos)
 | 
			
		||||
	{
 | 
			
		||||
		// Objects attached to the local player should always be hidden
 | 
			
		||||
		if(m_attached_to_local)
 | 
			
		||||
			m_is_visible = false;
 | 
			
		||||
		else
 | 
			
		||||
			m_is_visible = (m_hp != 0);
 | 
			
		||||
		u8 li = decode_light(light_at_pos);
 | 
			
		||||
 | 
			
		||||
		if(li != m_last_light){
 | 
			
		||||
			m_last_light = li;
 | 
			
		||||
			video::SColor color(255,li,li,li);
 | 
			
		||||
			if(m_meshnode){
 | 
			
		||||
			if(m_meshnode)
 | 
			
		||||
				setMeshColor(m_meshnode->getMesh(), color);
 | 
			
		||||
				m_meshnode->setVisible(m_is_visible);
 | 
			
		||||
			}
 | 
			
		||||
			if(m_animated_meshnode){
 | 
			
		||||
			if(m_animated_meshnode)
 | 
			
		||||
				setMeshColor(m_animated_meshnode->getMesh(), color);
 | 
			
		||||
				m_animated_meshnode->setVisible(m_is_visible);
 | 
			
		||||
			}
 | 
			
		||||
			if(m_spritenode){
 | 
			
		||||
			if(m_spritenode)
 | 
			
		||||
				m_spritenode->setColor(color);
 | 
			
		||||
				m_spritenode->setVisible(m_is_visible);
 | 
			
		||||
			}
 | 
			
		||||
			if(m_textnode){
 | 
			
		||||
				m_textnode->setVisible(m_is_visible);
 | 
			
		||||
			}
 | 
			
		||||
		}
 | 
			
		||||
	}
 | 
			
		||||
 | 
			
		||||
@@ -1044,9 +1027,9 @@ public:
 | 
			
		||||
			m_visuals_expired = false;
 | 
			
		||||
 | 
			
		||||
			// Attachments, part 1: All attached objects must be unparented first, or Irrlicht causes a segmentation fault
 | 
			
		||||
			for(std::vector<core::vector2d<int> >::iterator ii = attachment_list.begin(); ii != attachment_list.end(); ii++)
 | 
			
		||||
			for(std::vector<core::vector2d<int> >::iterator ii = m_env->attachment_list.begin(); ii != m_env->attachment_list.end(); ii++)
 | 
			
		||||
			{
 | 
			
		||||
				if(ii->Y == this->getId()) // This is a child of our parent
 | 
			
		||||
				if(ii->Y == getId()) // This is a child of our parent
 | 
			
		||||
				{
 | 
			
		||||
					ClientActiveObject *obj = m_env->getActiveObject(ii->X); // Get the object of the child
 | 
			
		||||
					if(obj)
 | 
			
		||||
@@ -1066,18 +1049,18 @@ public:
 | 
			
		||||
 | 
			
		||||
			removeFromScene(false);
 | 
			
		||||
			addToScene(m_smgr, m_gamedef->tsrc(), m_irr);
 | 
			
		||||
			updateAnimations();
 | 
			
		||||
			updateBonePosRot();
 | 
			
		||||
			updateAnimation();
 | 
			
		||||
			updateBonePosition();
 | 
			
		||||
			updateAttachments();
 | 
			
		||||
 | 
			
		||||
			// Attachments, part 2: Now that the parent has been refreshed, put its attachments back
 | 
			
		||||
			for(std::vector<core::vector2d<int> >::iterator ii = attachment_list.begin(); ii != attachment_list.end(); ii++)
 | 
			
		||||
			for(std::vector<core::vector2d<int> >::iterator ii = m_env->attachment_list.begin(); ii != m_env->attachment_list.end(); ii++)
 | 
			
		||||
			{
 | 
			
		||||
				if(ii->Y == this->getId()) // This is a child of our parent
 | 
			
		||||
				if(ii->Y == getId()) // This is a child of our parent
 | 
			
		||||
				{
 | 
			
		||||
					ClientActiveObject *obj = m_env->getActiveObject(ii->X); // Get the object of the child
 | 
			
		||||
					if(obj)
 | 
			
		||||
						obj->updateParent();
 | 
			
		||||
						obj->setAttachments();
 | 
			
		||||
				}
 | 
			
		||||
			}
 | 
			
		||||
		}
 | 
			
		||||
@@ -1095,12 +1078,7 @@ public:
 | 
			
		||||
		if(getParent() != NULL) // Attachments should be glued to their parent by Irrlicht
 | 
			
		||||
		{
 | 
			
		||||
			// Set these for later
 | 
			
		||||
			if(m_meshnode)
 | 
			
		||||
				m_position = m_meshnode->getAbsolutePosition();
 | 
			
		||||
			if(m_animated_meshnode)
 | 
			
		||||
				m_position = m_animated_meshnode->getAbsolutePosition();
 | 
			
		||||
			if(m_spritenode)
 | 
			
		||||
				m_position = m_spritenode->getAbsolutePosition();
 | 
			
		||||
			m_position = getPosition();
 | 
			
		||||
			m_velocity = v3f(0,0,0);
 | 
			
		||||
			m_acceleration = v3f(0,0,0);
 | 
			
		||||
			pos_translator.vect_show = m_position;
 | 
			
		||||
@@ -1405,23 +1383,23 @@ public:
 | 
			
		||||
		}
 | 
			
		||||
	}
 | 
			
		||||
 | 
			
		||||
	void updateAnimations()
 | 
			
		||||
	void updateAnimation()
 | 
			
		||||
	{
 | 
			
		||||
		if(m_animated_meshnode == NULL)
 | 
			
		||||
			return;
 | 
			
		||||
 | 
			
		||||
		m_animated_meshnode->setFrameLoop((int)m_frames.X, (int)m_frames.Y);
 | 
			
		||||
		m_animated_meshnode->setAnimationSpeed(m_frame_speed);
 | 
			
		||||
		m_animated_meshnode->setTransitionTime(m_frame_blend);
 | 
			
		||||
		m_animated_meshnode->setFrameLoop((int)m_animation_range.X, (int)m_animation_range.Y);
 | 
			
		||||
		m_animated_meshnode->setAnimationSpeed(m_animation_speed);
 | 
			
		||||
		m_animated_meshnode->setTransitionTime(m_animation_blend);
 | 
			
		||||
	}
 | 
			
		||||
 | 
			
		||||
	void updateBonePosRot()
 | 
			
		||||
	void updateBonePosition()
 | 
			
		||||
	{
 | 
			
		||||
		if(!m_bone_posrot.size() || m_animated_meshnode == NULL)
 | 
			
		||||
		if(!m_bone_position.size() || m_animated_meshnode == NULL)
 | 
			
		||||
			return;
 | 
			
		||||
 | 
			
		||||
		m_animated_meshnode->setJointMode(irr::scene::EJUOR_CONTROL); // To write positions to the mesh on render
 | 
			
		||||
		for(std::map<std::string, core::vector2d<v3f> >::const_iterator ii = m_bone_posrot.begin(); ii != m_bone_posrot.end(); ++ii){
 | 
			
		||||
		for(std::map<std::string, core::vector2d<v3f> >::const_iterator ii = m_bone_position.begin(); ii != m_bone_position.end(); ++ii){
 | 
			
		||||
			std::string bone_name = (*ii).first;
 | 
			
		||||
			v3f bone_pos = (*ii).second.X;
 | 
			
		||||
			v3f bone_rot = (*ii).second.Y;
 | 
			
		||||
@@ -1437,6 +1415,7 @@ public:
 | 
			
		||||
	void updateAttachments()
 | 
			
		||||
	{
 | 
			
		||||
		m_attached_to_local = getParent() != NULL && getParent()->isLocalPlayer();
 | 
			
		||||
		m_is_visible = !m_attached_to_local; // Objects attached to the local player should always be hidden
 | 
			
		||||
 | 
			
		||||
		if(getParent() == NULL || m_attached_to_local) // Detach or don't attach
 | 
			
		||||
		{
 | 
			
		||||
@@ -1658,35 +1637,35 @@ public:
 | 
			
		||||
 | 
			
		||||
			updateTexturePos();
 | 
			
		||||
		}
 | 
			
		||||
		else if(cmd == GENERIC_CMD_SET_ANIMATIONS)
 | 
			
		||||
		else if(cmd == GENERIC_CMD_SET_ANIMATION)
 | 
			
		||||
		{
 | 
			
		||||
			m_frames = readV2F1000(is);
 | 
			
		||||
			m_frame_speed = readF1000(is);
 | 
			
		||||
			m_frame_blend = readF1000(is);
 | 
			
		||||
			m_animation_range = readV2F1000(is);
 | 
			
		||||
			m_animation_speed = readF1000(is);
 | 
			
		||||
			m_animation_blend = readF1000(is);
 | 
			
		||||
 | 
			
		||||
			updateAnimations();
 | 
			
		||||
			updateAnimation();
 | 
			
		||||
		}
 | 
			
		||||
		else if(cmd == GENERIC_CMD_SET_BONE_POSROT)
 | 
			
		||||
		else if(cmd == GENERIC_CMD_SET_BONE_POSITION)
 | 
			
		||||
		{
 | 
			
		||||
			std::string bone = deSerializeString(is);
 | 
			
		||||
			v3f position = readV3F1000(is);
 | 
			
		||||
			v3f rotation = readV3F1000(is);
 | 
			
		||||
			m_bone_posrot[bone] = core::vector2d<v3f>(position, rotation);
 | 
			
		||||
			m_bone_position[bone] = core::vector2d<v3f>(position, rotation);
 | 
			
		||||
 | 
			
		||||
			updateBonePosRot();
 | 
			
		||||
			updateBonePosition();
 | 
			
		||||
		}
 | 
			
		||||
		else if(cmd == GENERIC_CMD_SET_ATTACHMENT)
 | 
			
		||||
		{
 | 
			
		||||
			// If an entry already exists for this object, delete it first to avoid duplicates
 | 
			
		||||
			for(std::vector<core::vector2d<int> >::iterator ii = attachment_list.begin(); ii != attachment_list.end(); ii++)
 | 
			
		||||
			for(std::vector<core::vector2d<int> >::iterator ii = m_env->attachment_list.begin(); ii != m_env->attachment_list.end(); ii++)
 | 
			
		||||
			{
 | 
			
		||||
				if(ii->X == this->getId()) // This is the ID of our object
 | 
			
		||||
				if(ii->X == getId()) // This is the ID of our object
 | 
			
		||||
				{
 | 
			
		||||
					attachment_list.erase(ii);
 | 
			
		||||
					m_env->attachment_list.erase(ii);
 | 
			
		||||
					break;
 | 
			
		||||
				}
 | 
			
		||||
			}
 | 
			
		||||
			attachment_list.push_back(core::vector2d<int>(this->getId(), readS16(is)));
 | 
			
		||||
			m_env->attachment_list.push_back(core::vector2d<int>(getId(), readS16(is)));
 | 
			
		||||
			m_attachment_bone = deSerializeString(is);
 | 
			
		||||
			m_attachment_position = readV3F1000(is);
 | 
			
		||||
			m_attachment_rotation = readV3F1000(is);
 | 
			
		||||
 
 | 
			
		||||
@@ -356,8 +356,8 @@ LuaEntitySAO::LuaEntitySAO(ServerEnvironment *env, v3f pos,
 | 
			
		||||
	m_last_sent_position_timer(0),
 | 
			
		||||
	m_last_sent_move_precision(0),
 | 
			
		||||
	m_armor_groups_sent(false),
 | 
			
		||||
	m_animations_sent(false),
 | 
			
		||||
	m_animations_bone_sent(false),
 | 
			
		||||
	m_animation_sent(false),
 | 
			
		||||
	m_bone_position_sent(false),
 | 
			
		||||
	m_attachment_sent(false)
 | 
			
		||||
{
 | 
			
		||||
	// Only register type if no environment supplied
 | 
			
		||||
@@ -537,18 +537,18 @@ void LuaEntitySAO::step(float dtime, bool send_recommended)
 | 
			
		||||
		m_messages_out.push_back(aom);
 | 
			
		||||
	}
 | 
			
		||||
 | 
			
		||||
	if(m_animations_sent == false){
 | 
			
		||||
		m_animations_sent = true;
 | 
			
		||||
		std::string str = gob_cmd_update_animations(m_animation_frames, m_animation_speed, m_animation_blend);
 | 
			
		||||
	if(m_animation_sent == false){
 | 
			
		||||
		m_animation_sent = true;
 | 
			
		||||
		std::string str = gob_cmd_update_animation(m_animation_range, m_animation_speed, m_animation_blend);
 | 
			
		||||
		// create message and add to list
 | 
			
		||||
		ActiveObjectMessage aom(getId(), true, str);
 | 
			
		||||
		m_messages_out.push_back(aom);
 | 
			
		||||
	}
 | 
			
		||||
 | 
			
		||||
	if(m_animations_bone_sent == false){
 | 
			
		||||
		m_animations_bone_sent = true;
 | 
			
		||||
		for(std::map<std::string, core::vector2d<v3f> >::const_iterator ii = m_animation_bone.begin(); ii != m_animation_bone.end(); ++ii){
 | 
			
		||||
			std::string str = gob_cmd_update_bone_posrot((*ii).first, (*ii).second.X, (*ii).second.Y);
 | 
			
		||||
	if(m_bone_position_sent == false){
 | 
			
		||||
		m_bone_position_sent = true;
 | 
			
		||||
		for(std::map<std::string, core::vector2d<v3f> >::const_iterator ii = m_bone_position.begin(); ii != m_bone_position.end(); ++ii){
 | 
			
		||||
			std::string str = gob_cmd_update_bone_position((*ii).first, (*ii).second.X, (*ii).second.Y);
 | 
			
		||||
			// create message and add to list
 | 
			
		||||
			ActiveObjectMessage aom(getId(), true, str);
 | 
			
		||||
			m_messages_out.push_back(aom);
 | 
			
		||||
@@ -575,12 +575,12 @@ std::string LuaEntitySAO::getClientInitializationData()
 | 
			
		||||
	writeF1000(os, m_yaw);
 | 
			
		||||
	writeS16(os, m_hp);
 | 
			
		||||
 | 
			
		||||
	writeU8(os, 4 + m_animation_bone.size()); // number of messages stuffed in here
 | 
			
		||||
	writeU8(os, 4 + m_bone_position.size()); // number of messages stuffed in here
 | 
			
		||||
	os<<serializeLongString(getPropertyPacket()); // message 1
 | 
			
		||||
	os<<serializeLongString(gob_cmd_update_armor_groups(m_armor_groups)); // 2
 | 
			
		||||
	os<<serializeLongString(gob_cmd_update_animations(m_animation_frames, m_animation_speed, m_animation_blend)); // 3
 | 
			
		||||
	for(std::map<std::string, core::vector2d<v3f> >::const_iterator ii = m_animation_bone.begin(); ii != m_animation_bone.end(); ++ii){
 | 
			
		||||
		os<<serializeLongString(gob_cmd_update_bone_posrot((*ii).first, (*ii).second.X, (*ii).second.Y)); // m_animation_bone.size
 | 
			
		||||
	os<<serializeLongString(gob_cmd_update_animation(m_animation_range, m_animation_speed, m_animation_blend)); // 3
 | 
			
		||||
	for(std::map<std::string, core::vector2d<v3f> >::const_iterator ii = m_bone_position.begin(); ii != m_bone_position.end(); ++ii){
 | 
			
		||||
		os<<serializeLongString(gob_cmd_update_bone_position((*ii).first, (*ii).second.X, (*ii).second.Y)); // m_bone_position.size
 | 
			
		||||
	}
 | 
			
		||||
	os<<serializeLongString(gob_cmd_update_attachment(m_attachment_parent_id, m_attachment_bone, m_attachment_position, m_attachment_rotation)); // 4
 | 
			
		||||
 | 
			
		||||
@@ -728,18 +728,18 @@ void LuaEntitySAO::setArmorGroups(const ItemGroupList &armor_groups)
 | 
			
		||||
	m_armor_groups_sent = false;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void LuaEntitySAO::setAnimations(v2f frames, float frame_speed, float frame_blend)
 | 
			
		||||
void LuaEntitySAO::setAnimation(v2f frame_range, float frame_speed, float frame_blend)
 | 
			
		||||
{
 | 
			
		||||
	m_animation_frames = frames;
 | 
			
		||||
	m_animation_range = frame_range;
 | 
			
		||||
	m_animation_speed = frame_speed;
 | 
			
		||||
	m_animation_blend = frame_blend;
 | 
			
		||||
	m_animations_sent = false;
 | 
			
		||||
	m_animation_sent = false;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void LuaEntitySAO::setBonePosRot(std::string bone, v3f position, v3f rotation)
 | 
			
		||||
void LuaEntitySAO::setBonePosition(std::string bone, v3f position, v3f rotation)
 | 
			
		||||
{
 | 
			
		||||
	m_animation_bone[bone] = core::vector2d<v3f>(position, rotation);
 | 
			
		||||
	m_animations_bone_sent = false;
 | 
			
		||||
	m_bone_position[bone] = core::vector2d<v3f>(position, rotation);
 | 
			
		||||
	m_bone_position_sent = false;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void LuaEntitySAO::setAttachment(int parent_id, std::string bone, v3f position, v3f rotation)
 | 
			
		||||
@@ -884,8 +884,8 @@ PlayerSAO::PlayerSAO(ServerEnvironment *env_, Player *player_, u16 peer_id_,
 | 
			
		||||
	m_properties_sent(true),
 | 
			
		||||
	m_privs(privs),
 | 
			
		||||
	m_is_singleplayer(is_singleplayer),
 | 
			
		||||
	m_animations_sent(false),
 | 
			
		||||
	m_animations_bone_sent(false),
 | 
			
		||||
	m_animation_sent(false),
 | 
			
		||||
	m_bone_position_sent(false),
 | 
			
		||||
	m_attachment_sent(false),
 | 
			
		||||
	// public
 | 
			
		||||
	m_moved(false),
 | 
			
		||||
@@ -914,7 +914,7 @@ PlayerSAO::PlayerSAO(ServerEnvironment *env_, Player *player_, u16 peer_id_,
 | 
			
		||||
	m_prop.colors.push_back(video::SColor(255, 255, 255, 255));
 | 
			
		||||
	m_prop.spritediv = v2s16(1,1);
 | 
			
		||||
	// end of default appearance
 | 
			
		||||
	m_prop.is_visible = (getHP() != 0); // TODO: Use a death animation instead for mesh players
 | 
			
		||||
	m_prop.is_visible = true;
 | 
			
		||||
	m_prop.makes_footstep_sound = true;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
@@ -973,12 +973,12 @@ std::string PlayerSAO::getClientInitializationData()
 | 
			
		||||
	writeF1000(os, m_player->getYaw());
 | 
			
		||||
	writeS16(os, getHP());
 | 
			
		||||
 | 
			
		||||
	writeU8(os, 4 + m_animation_bone.size()); // number of messages stuffed in here
 | 
			
		||||
	writeU8(os, 4 + m_bone_position.size()); // number of messages stuffed in here
 | 
			
		||||
	os<<serializeLongString(getPropertyPacket()); // message 1
 | 
			
		||||
	os<<serializeLongString(gob_cmd_update_armor_groups(m_armor_groups)); // 2
 | 
			
		||||
	os<<serializeLongString(gob_cmd_update_animations(m_animation_frames, m_animation_speed, m_animation_blend)); // 3
 | 
			
		||||
	for(std::map<std::string, core::vector2d<v3f> >::const_iterator ii = m_animation_bone.begin(); ii != m_animation_bone.end(); ++ii){
 | 
			
		||||
		os<<serializeLongString(gob_cmd_update_bone_posrot((*ii).first, (*ii).second.X, (*ii).second.Y)); // m_animation_bone.size
 | 
			
		||||
	os<<serializeLongString(gob_cmd_update_animation(m_animation_range, m_animation_speed, m_animation_blend)); // 3
 | 
			
		||||
	for(std::map<std::string, core::vector2d<v3f> >::const_iterator ii = m_bone_position.begin(); ii != m_bone_position.end(); ++ii){
 | 
			
		||||
		os<<serializeLongString(gob_cmd_update_bone_position((*ii).first, (*ii).second.X, (*ii).second.Y)); // m_bone_position.size
 | 
			
		||||
	}
 | 
			
		||||
	os<<serializeLongString(gob_cmd_update_attachment(m_attachment_parent_id, m_attachment_bone, m_attachment_position, m_attachment_rotation)); // 4
 | 
			
		||||
 | 
			
		||||
@@ -1137,18 +1137,18 @@ void PlayerSAO::step(float dtime, bool send_recommended)
 | 
			
		||||
		m_messages_out.push_back(aom);
 | 
			
		||||
	}
 | 
			
		||||
 | 
			
		||||
	if(m_animations_sent == false){
 | 
			
		||||
		m_animations_sent = true;
 | 
			
		||||
		std::string str = gob_cmd_update_animations(m_animation_frames, m_animation_speed, m_animation_blend);
 | 
			
		||||
	if(m_animation_sent == false){
 | 
			
		||||
		m_animation_sent = true;
 | 
			
		||||
		std::string str = gob_cmd_update_animation(m_animation_range, m_animation_speed, m_animation_blend);
 | 
			
		||||
		// create message and add to list
 | 
			
		||||
		ActiveObjectMessage aom(getId(), true, str);
 | 
			
		||||
		m_messages_out.push_back(aom);
 | 
			
		||||
	}
 | 
			
		||||
 | 
			
		||||
	if(m_animations_bone_sent == false){
 | 
			
		||||
		m_animations_bone_sent = true;
 | 
			
		||||
		for(std::map<std::string, core::vector2d<v3f> >::const_iterator ii = m_animation_bone.begin(); ii != m_animation_bone.end(); ++ii){
 | 
			
		||||
			std::string str = gob_cmd_update_bone_posrot((*ii).first, (*ii).second.X, (*ii).second.Y);
 | 
			
		||||
	if(m_bone_position_sent == false){
 | 
			
		||||
		m_bone_position_sent = true;
 | 
			
		||||
		for(std::map<std::string, core::vector2d<v3f> >::const_iterator ii = m_bone_position.begin(); ii != m_bone_position.end(); ++ii){
 | 
			
		||||
			std::string str = gob_cmd_update_bone_position((*ii).first, (*ii).second.X, (*ii).second.Y);
 | 
			
		||||
			// create message and add to list
 | 
			
		||||
			ActiveObjectMessage aom(getId(), true, str);
 | 
			
		||||
			m_messages_out.push_back(aom);
 | 
			
		||||
@@ -1285,20 +1285,20 @@ void PlayerSAO::setArmorGroups(const ItemGroupList &armor_groups)
 | 
			
		||||
	m_armor_groups_sent = false;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void PlayerSAO::setAnimations(v2f frames, float frame_speed, float frame_blend)
 | 
			
		||||
void PlayerSAO::setAnimation(v2f frame_range, float frame_speed, float frame_blend)
 | 
			
		||||
{
 | 
			
		||||
	// store these so they can be updated to clients
 | 
			
		||||
	m_animation_frames = frames;
 | 
			
		||||
	m_animation_range = frame_range;
 | 
			
		||||
	m_animation_speed = frame_speed;
 | 
			
		||||
	m_animation_blend = frame_blend;
 | 
			
		||||
	m_animations_sent = false;
 | 
			
		||||
	m_animation_sent = false;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void PlayerSAO::setBonePosRot(std::string bone, v3f position, v3f rotation)
 | 
			
		||||
void PlayerSAO::setBonePosition(std::string bone, v3f position, v3f rotation)
 | 
			
		||||
{
 | 
			
		||||
	// store these so they can be updated to clients
 | 
			
		||||
	m_animation_bone[bone] = core::vector2d<v3f>(position, rotation);
 | 
			
		||||
	m_animations_bone_sent = false;
 | 
			
		||||
	m_bone_position[bone] = core::vector2d<v3f>(position, rotation);
 | 
			
		||||
	m_bone_position_sent = false;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void PlayerSAO::setAttachment(int parent_id, std::string bone, v3f position, v3f rotation)
 | 
			
		||||
@@ -1381,7 +1381,7 @@ void PlayerSAO::disconnected()
 | 
			
		||||
 | 
			
		||||
std::string PlayerSAO::getPropertyPacket()
 | 
			
		||||
{
 | 
			
		||||
	m_prop.is_visible = (getHP() != 0);
 | 
			
		||||
	m_prop.is_visible = (true);
 | 
			
		||||
	return gob_cmd_set_properties(m_prop);
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
 
 | 
			
		||||
@@ -62,8 +62,8 @@ public:
 | 
			
		||||
	void setHP(s16 hp);
 | 
			
		||||
	s16 getHP() const;
 | 
			
		||||
	void setArmorGroups(const ItemGroupList &armor_groups);
 | 
			
		||||
	void setAnimations(v2f frames, float frame_speed, float frame_blend);
 | 
			
		||||
	void setBonePosRot(std::string bone, v3f position, v3f rotation);
 | 
			
		||||
	void setAnimation(v2f frame_range, float frame_speed, float frame_blend);
 | 
			
		||||
	void setBonePosition(std::string bone, v3f position, v3f rotation);
 | 
			
		||||
	void setAttachment(int parent_id, std::string bone, v3f position, v3f rotation);
 | 
			
		||||
	ObjectProperties* accessObjectProperties();
 | 
			
		||||
	void notifyObjectPropertiesModified();
 | 
			
		||||
@@ -101,13 +101,13 @@ private:
 | 
			
		||||
	float m_last_sent_move_precision;
 | 
			
		||||
	bool m_armor_groups_sent;
 | 
			
		||||
	
 | 
			
		||||
	v2f m_animation_frames;
 | 
			
		||||
	v2f m_animation_range;
 | 
			
		||||
	float m_animation_speed;
 | 
			
		||||
	float m_animation_blend;
 | 
			
		||||
	bool m_animations_sent;
 | 
			
		||||
	bool m_animation_sent;
 | 
			
		||||
 | 
			
		||||
	std::map<std::string, core::vector2d<v3f> > m_animation_bone;
 | 
			
		||||
	bool m_animations_bone_sent;
 | 
			
		||||
	std::map<std::string, core::vector2d<v3f> > m_bone_position;
 | 
			
		||||
	bool m_bone_position_sent;
 | 
			
		||||
 | 
			
		||||
	int m_attachment_parent_id;
 | 
			
		||||
	std::string m_attachment_bone;
 | 
			
		||||
@@ -161,8 +161,8 @@ public:
 | 
			
		||||
	void setHP(s16 hp);
 | 
			
		||||
	
 | 
			
		||||
	void setArmorGroups(const ItemGroupList &armor_groups);
 | 
			
		||||
	void setAnimations(v2f frames, float frame_speed, float frame_blend);
 | 
			
		||||
	void setBonePosRot(std::string bone, v3f position, v3f rotation);
 | 
			
		||||
	void setAnimation(v2f frame_range, float frame_speed, float frame_blend);
 | 
			
		||||
	void setBonePosition(std::string bone, v3f position, v3f rotation);
 | 
			
		||||
	void setAttachment(int parent_id, std::string bone, v3f position, v3f rotation);
 | 
			
		||||
	ObjectProperties* accessObjectProperties();
 | 
			
		||||
	void notifyObjectPropertiesModified();
 | 
			
		||||
@@ -260,13 +260,13 @@ private:
 | 
			
		||||
	std::set<std::string> m_privs;
 | 
			
		||||
	bool m_is_singleplayer;
 | 
			
		||||
 | 
			
		||||
	v2f m_animation_frames;
 | 
			
		||||
	v2f m_animation_range;
 | 
			
		||||
	float m_animation_speed;
 | 
			
		||||
	float m_animation_blend;
 | 
			
		||||
	bool m_animations_sent;
 | 
			
		||||
	bool m_animation_sent;
 | 
			
		||||
 | 
			
		||||
	std::map<std::string, core::vector2d<v3f> > m_animation_bone; // stores position and rotation for each bone name
 | 
			
		||||
	bool m_animations_bone_sent;
 | 
			
		||||
	std::map<std::string, core::vector2d<v3f> > m_bone_position; // Stores position and rotation for each bone name
 | 
			
		||||
	bool m_bone_position_sent;
 | 
			
		||||
 | 
			
		||||
	int m_attachment_parent_id;
 | 
			
		||||
	std::string m_attachment_bone;
 | 
			
		||||
 
 | 
			
		||||
@@ -463,6 +463,8 @@ public:
 | 
			
		||||
	
 | 
			
		||||
	// Get event from queue. CEE_NONE is returned if queue is empty.
 | 
			
		||||
	ClientEnvEvent getClientEvent();
 | 
			
		||||
 | 
			
		||||
	std::vector<core::vector2d<int> > attachment_list; // X is child ID, Y is parent ID
 | 
			
		||||
	
 | 
			
		||||
private:
 | 
			
		||||
	ClientMap *m_map;
 | 
			
		||||
 
 | 
			
		||||
@@ -92,11 +92,11 @@ std::string gob_cmd_set_sprite(
 | 
			
		||||
	return os.str();
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
std::string gob_cmd_update_animations(v2f frames, float frame_speed, float frame_blend)
 | 
			
		||||
std::string gob_cmd_update_animation(v2f frames, float frame_speed, float frame_blend)
 | 
			
		||||
{
 | 
			
		||||
	std::ostringstream os(std::ios::binary);
 | 
			
		||||
	// command 
 | 
			
		||||
	writeU8(os, GENERIC_CMD_SET_ANIMATIONS);
 | 
			
		||||
	writeU8(os, GENERIC_CMD_SET_ANIMATION);
 | 
			
		||||
	// parameters
 | 
			
		||||
	writeV2F1000(os, frames);
 | 
			
		||||
	writeF1000(os, frame_speed);
 | 
			
		||||
@@ -104,11 +104,11 @@ std::string gob_cmd_update_animations(v2f frames, float frame_speed, float frame
 | 
			
		||||
	return os.str();
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
std::string gob_cmd_update_bone_posrot(std::string bone, v3f position, v3f rotation)
 | 
			
		||||
std::string gob_cmd_update_bone_position(std::string bone, v3f position, v3f rotation)
 | 
			
		||||
{
 | 
			
		||||
	std::ostringstream os(std::ios::binary);
 | 
			
		||||
	// command 
 | 
			
		||||
	writeU8(os, GENERIC_CMD_SET_BONE_POSROT);
 | 
			
		||||
	writeU8(os, GENERIC_CMD_SET_BONE_POSITION);
 | 
			
		||||
	// parameters
 | 
			
		||||
	os<<serializeString(bone);
 | 
			
		||||
	writeV3F1000(os, position);
 | 
			
		||||
 
 | 
			
		||||
@@ -28,8 +28,8 @@ with this program; if not, write to the Free Software Foundation, Inc.,
 | 
			
		||||
#define GENERIC_CMD_UPDATE_POSITION 1
 | 
			
		||||
#define GENERIC_CMD_SET_TEXTURE_MOD 2
 | 
			
		||||
#define GENERIC_CMD_SET_SPRITE 3
 | 
			
		||||
#define GENERIC_CMD_SET_ANIMATIONS 4
 | 
			
		||||
#define GENERIC_CMD_SET_BONE_POSROT 5
 | 
			
		||||
#define GENERIC_CMD_SET_ANIMATION 4
 | 
			
		||||
#define GENERIC_CMD_SET_BONE_POSITION 5
 | 
			
		||||
#define GENERIC_CMD_SET_ATTACHMENT 6
 | 
			
		||||
#define GENERIC_CMD_PUNCHED 7
 | 
			
		||||
#define GENERIC_CMD_UPDATE_ARMOR_GROUPS 8
 | 
			
		||||
@@ -57,9 +57,9 @@ std::string gob_cmd_set_sprite(
 | 
			
		||||
	bool select_horiz_by_yawpitch
 | 
			
		||||
);
 | 
			
		||||
 | 
			
		||||
std::string gob_cmd_update_animations(v2f frames, float frame_speed, float frame_blend);
 | 
			
		||||
std::string gob_cmd_update_animation(v2f frames, float frame_speed, float frame_blend);
 | 
			
		||||
 | 
			
		||||
std::string gob_cmd_update_bone_posrot(std::string bone, v3f position, v3f rotation);
 | 
			
		||||
std::string gob_cmd_update_bone_position(std::string bone, v3f position, v3f rotation);
 | 
			
		||||
 | 
			
		||||
std::string gob_cmd_update_attachment(int parent_id, std::string bone, v3f position, v3f rotation);
 | 
			
		||||
 | 
			
		||||
 
 | 
			
		||||
@@ -714,6 +714,7 @@ void GUIFormSpecMenu::drawMenu()
 | 
			
		||||
		Draw backgrounds
 | 
			
		||||
	*/
 | 
			
		||||
	for(u32 i=0; i<m_backgrounds.size(); i++)
 | 
			
		||||
	{
 | 
			
		||||
		const ImageDrawSpec &spec = m_backgrounds[i];
 | 
			
		||||
		video::ITexture *texture =
 | 
			
		||||
				m_gamedef->tsrc()->getTextureRaw(spec.name);
 | 
			
		||||
@@ -727,6 +728,7 @@ void GUIFormSpecMenu::drawMenu()
 | 
			
		||||
			core::rect<s32>(core::position2d<s32>(0,0),
 | 
			
		||||
					core::dimension2di(texture->getOriginalSize())),
 | 
			
		||||
			NULL/*&AbsoluteClippingRect*/, colors, true);
 | 
			
		||||
	}
 | 
			
		||||
	
 | 
			
		||||
	/*
 | 
			
		||||
		Draw images
 | 
			
		||||
 
 | 
			
		||||
@@ -2716,8 +2716,8 @@ private:
 | 
			
		||||
		return 0;
 | 
			
		||||
	}
 | 
			
		||||
 | 
			
		||||
	// setanimations(self, frames, frame_speed, frame_blend)
 | 
			
		||||
	static int l_set_animations(lua_State *L)
 | 
			
		||||
	// set_animation(self, frame_range, frame_speed, frame_blend)
 | 
			
		||||
	static int l_set_animation(lua_State *L)
 | 
			
		||||
	{
 | 
			
		||||
		ObjectRef *ref = checkobject(L, 1);
 | 
			
		||||
		ServerActiveObject *co = getobject(ref);
 | 
			
		||||
@@ -2732,12 +2732,12 @@ private:
 | 
			
		||||
		float frame_blend = 0;
 | 
			
		||||
		if(!lua_isnil(L, 4))
 | 
			
		||||
			frame_blend = lua_tonumber(L, 4);
 | 
			
		||||
		co->setAnimations(frames, frame_speed, frame_blend);
 | 
			
		||||
		co->setAnimation(frames, frame_speed, frame_blend);
 | 
			
		||||
		return 0;
 | 
			
		||||
	}
 | 
			
		||||
 | 
			
		||||
	// setboneposrot(self, std::string bone, v3f position, v3f rotation)
 | 
			
		||||
	static int l_set_bone_posrot(lua_State *L)
 | 
			
		||||
	// set_bone_position(self, std::string bone, v3f position, v3f rotation)
 | 
			
		||||
	static int l_set_bone_position(lua_State *L)
 | 
			
		||||
	{
 | 
			
		||||
		ObjectRef *ref = checkobject(L, 1);
 | 
			
		||||
		ServerActiveObject *co = getobject(ref);
 | 
			
		||||
@@ -2752,12 +2752,12 @@ private:
 | 
			
		||||
		v3f rotation = v3f(0, 0, 0);
 | 
			
		||||
		if(!lua_isnil(L, 4))
 | 
			
		||||
			rotation = read_v3f(L, 4);
 | 
			
		||||
		co->setBonePosRot(bone, position, rotation);
 | 
			
		||||
		co->setBonePosition(bone, position, rotation);
 | 
			
		||||
		return 0;
 | 
			
		||||
	}
 | 
			
		||||
 | 
			
		||||
	// set_attachment(self, parent, bone, position, rotation)
 | 
			
		||||
	static int l_set_attachment(lua_State *L)
 | 
			
		||||
	// set_attach(self, parent, bone, position, rotation)
 | 
			
		||||
	static int l_set_attach(lua_State *L)
 | 
			
		||||
	{
 | 
			
		||||
		ObjectRef *ref = checkobject(L, 1);
 | 
			
		||||
		ObjectRef *parent_ref = checkobject(L, 2);
 | 
			
		||||
@@ -2779,8 +2779,8 @@ private:
 | 
			
		||||
		return 0;
 | 
			
		||||
	}
 | 
			
		||||
 | 
			
		||||
	// set_detachment(self)
 | 
			
		||||
	static int l_set_detachment(lua_State *L)
 | 
			
		||||
	// set_detach(self)
 | 
			
		||||
	static int l_set_detach(lua_State *L)
 | 
			
		||||
	{
 | 
			
		||||
		ObjectRef *ref = checkobject(L, 1);
 | 
			
		||||
		ServerActiveObject *co = getobject(ref);
 | 
			
		||||
@@ -3104,10 +3104,10 @@ const luaL_reg ObjectRef::methods[] = {
 | 
			
		||||
	method(ObjectRef, get_wielded_item),
 | 
			
		||||
	method(ObjectRef, set_wielded_item),
 | 
			
		||||
	method(ObjectRef, set_armor_groups),
 | 
			
		||||
	method(ObjectRef, set_animations),
 | 
			
		||||
	method(ObjectRef, set_bone_posrot),
 | 
			
		||||
	method(ObjectRef, set_attachment),
 | 
			
		||||
	method(ObjectRef, set_detachment),
 | 
			
		||||
	method(ObjectRef, set_animation),
 | 
			
		||||
	method(ObjectRef, set_bone_position),
 | 
			
		||||
	method(ObjectRef, set_attach),
 | 
			
		||||
	method(ObjectRef, set_detach),
 | 
			
		||||
	method(ObjectRef, set_properties),
 | 
			
		||||
	// LuaEntitySAO-only
 | 
			
		||||
	method(ObjectRef, setvelocity),
 | 
			
		||||
 
 | 
			
		||||
@@ -152,9 +152,9 @@ public:
 | 
			
		||||
 | 
			
		||||
	virtual void setArmorGroups(const ItemGroupList &armor_groups)
 | 
			
		||||
	{}
 | 
			
		||||
	virtual void setAnimations(v2f frames, float frame_speed, float frame_blend)
 | 
			
		||||
	virtual void setAnimation(v2f frames, float frame_speed, float frame_blend)
 | 
			
		||||
	{}
 | 
			
		||||
	virtual void setBonePosRot(std::string bone, v3f position, v3f rotation)
 | 
			
		||||
	virtual void setBonePosition(std::string bone, v3f position, v3f rotation)
 | 
			
		||||
	{}
 | 
			
		||||
	virtual void setAttachment(int parent_id, std::string bone, v3f position, v3f rotation)
 | 
			
		||||
	{}
 | 
			
		||||
 
 | 
			
		||||
		Reference in New Issue
	
	Block a user