organizing stuff.
This commit is contained in:
		
							parent
							
								
									3b0bff2f74
								
							
						
					
					
						commit
						3f5bad938a
					
				| @ -368,7 +368,7 @@ void Client::step(float dtime) | ||||
| 			try | ||||
| 			{ | ||||
| 				block = m_env.getMap().getBlockNoCreate(p); | ||||
| 				block->stepObjects(dtime, false); | ||||
| 				block->stepObjects(dtime, false, m_env.getDayNightRatio()); | ||||
| 			} | ||||
| 			catch(InvalidPositionException &e) | ||||
| 			{ | ||||
| @ -946,7 +946,7 @@ void Client::ProcessData(u8 *data, u32 datasize, u16 sender_peer_id) | ||||
| 				NOTE: Be sure this is done in the main thread. | ||||
| 			*/ | ||||
| 			block->updateObjects(is, m_server_ser_ver, | ||||
| 					m_device->getSceneManager()); | ||||
| 					m_device->getSceneManager(), m_env.getDayNightRatio()); | ||||
| 		} | ||||
| 		 | ||||
| 		/*dstream<<"Final delete queue size: "<<abs_to_delete.size()
 | ||||
|  | ||||
| @ -17,11 +17,6 @@ with this program; if not, write to the Free Software Foundation, Inc., | ||||
| 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA. | ||||
| */ | ||||
| 
 | ||||
| 
 | ||||
| /*
 | ||||
| 	Debug stuff | ||||
| */ | ||||
| 
 | ||||
| #ifndef DEBUG_HEADER | ||||
| #define DEBUG_HEADER | ||||
| 
 | ||||
| @ -31,11 +26,14 @@ with this program; if not, write to the Free Software Foundation, Inc., | ||||
| #include <iostream> | ||||
| #include "common_irrlicht.h" | ||||
| #include "threads.h" | ||||
| #include "gettime.h" | ||||
| 
 | ||||
| /*
 | ||||
| 	Debug output | ||||
| */ | ||||
| 
 | ||||
| #define DTIME (getTimestamp()+": ") | ||||
| 
 | ||||
| #define DEBUGSTREAM_COUNT 2 | ||||
| 
 | ||||
| extern FILE *g_debugstreams[DEBUGSTREAM_COUNT]; | ||||
|  | ||||
| @ -41,7 +41,7 @@ void set_default_settings() | ||||
| 	// Server stuff
 | ||||
| 	g_settings.setDefault("creative_mode", "false"); | ||||
| 	g_settings.setDefault("heightmap_blocksize", "32"); | ||||
| 	g_settings.setDefault("height_randmax", "constant 50.0"); | ||||
| 	g_settings.setDefault("height_randmax", "constant 45.0"); | ||||
| 	g_settings.setDefault("height_randfactor", "constant 0.6"); | ||||
| 	g_settings.setDefault("height_base", "linear 0 0 0"); | ||||
| 	g_settings.setDefault("plants_amount", "1.0"); | ||||
|  | ||||
							
								
								
									
										55
									
								
								src/gettime.h
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										55
									
								
								src/gettime.h
									
									
									
									
									
										Normal file
									
								
							| @ -0,0 +1,55 @@ | ||||
| /*
 | ||||
| Minetest-c55 | ||||
| Copyright (C) 2010 celeron55, Perttu Ahola <celeron55@gmail.com> | ||||
| 
 | ||||
| This program is free software; you can redistribute it and/or modify | ||||
| it under the terms of the GNU General Public License as published by | ||||
| the Free Software Foundation; either version 2 of the License, or | ||||
| (at your option) any later version. | ||||
| 
 | ||||
| This program 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 General Public License for more details. | ||||
| 
 | ||||
| You should have received a copy of the GNU General Public License along | ||||
| with this program; if not, write to the Free Software Foundation, Inc., | ||||
| 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA. | ||||
| */ | ||||
| 
 | ||||
| #ifndef GETTIME_HEADER | ||||
| #define GETTIME_HEADER | ||||
| 
 | ||||
| #include "common_irrlicht.h" | ||||
| 
 | ||||
| /*
 | ||||
| 	Get a millisecond counter value. | ||||
| 	Precision depends on implementation. | ||||
| 	Overflows at any value above 10000000. | ||||
| 
 | ||||
| 	Implementation of this is done in: | ||||
| 		Normal build: main.cpp | ||||
| 		Server build: servermain.cpp | ||||
| */ | ||||
| extern u32 getTimeMs(); | ||||
| 
 | ||||
| /*
 | ||||
| 	Timestamp stuff | ||||
| */ | ||||
| 
 | ||||
| #include <time.h> | ||||
| #include <string> | ||||
| 
 | ||||
| inline std::string getTimestamp() | ||||
| { | ||||
| 	time_t t = time(NULL); | ||||
| 	// This is not really thread-safe but it won't break anything
 | ||||
| 	// except its own output, so just go with it.
 | ||||
| 	struct tm *tm = localtime(&t); | ||||
| 	char cs[20]; | ||||
| 	strftime(cs, 20, "%H:%M:%S", tm); | ||||
| 	return cs; | ||||
| } | ||||
| 
 | ||||
| 
 | ||||
| #endif | ||||
| @ -76,7 +76,7 @@ InventoryItem* InventoryItem::deSerialize(std::istream &is) | ||||
| /*
 | ||||
| 	MapBlockObjectItem | ||||
| */ | ||||
| 
 | ||||
| #ifndef SERVER | ||||
| video::ITexture * MapBlockObjectItem::getImage() | ||||
| { | ||||
| 	if(m_inventorystring.substr(0,3) == "Rat") | ||||
| @ -89,6 +89,7 @@ video::ITexture * MapBlockObjectItem::getImage() | ||||
| 
 | ||||
| 	return NULL; | ||||
| } | ||||
| #endif | ||||
| std::string MapBlockObjectItem::getText() | ||||
| { | ||||
| 	if(m_inventorystring.substr(0,3) == "Rat") | ||||
|  | ||||
| @ -46,8 +46,10 @@ public: | ||||
| 	virtual void serialize(std::ostream &os) = 0; | ||||
| 	// Shall make an exact clone of the item
 | ||||
| 	virtual InventoryItem* clone() = 0; | ||||
| #ifndef SERVER | ||||
| 	// Shall return an image to show in the GUI (or NULL)
 | ||||
| 	virtual video::ITexture * getImage() { return NULL; } | ||||
| #endif | ||||
| 	// Shall return a text to show in the GUI
 | ||||
| 	virtual std::string getText() { return ""; } | ||||
| 
 | ||||
| @ -175,7 +177,9 @@ public: | ||||
| 		return new MapBlockObjectItem(m_inventorystring); | ||||
| 	} | ||||
| 
 | ||||
| #ifndef SERVER | ||||
| 	video::ITexture * getImage(); | ||||
| #endif | ||||
| 	std::string getText(); | ||||
| 
 | ||||
| 	/*
 | ||||
|  | ||||
							
								
								
									
										86
									
								
								src/main.cpp
									
									
									
									
									
								
							
							
						
						
									
										86
									
								
								src/main.cpp
									
									
									
									
									
								
							| @ -99,8 +99,6 @@ SUGG: A version number to blocks, which increments when the block is | ||||
| 	  - This can then be used to make sure the most recent version of | ||||
| 	    a block has been sent to client | ||||
| 
 | ||||
| TODO: Stop player if focus of window is taken away (go to pause mode) | ||||
| 
 | ||||
| TODO: Combine MapBlock's face caches to so big pieces that VBO | ||||
|       gets used | ||||
|       - That is >500 vertices | ||||
| @ -110,16 +108,6 @@ TODO: Cliffs, arcs | ||||
| 
 | ||||
| TODO: Menus | ||||
| 
 | ||||
| TODO: Mobs | ||||
|       - Server: | ||||
|         - One single map container with ids as keys | ||||
|       - Client: | ||||
| 	    - ? | ||||
| TODO: - Keep track of the place of the mob in the last few hundreth's | ||||
|         of a second - then, if a player hits it, take the value that is | ||||
| 		avg_rtt/2 before the moment the packet is received. | ||||
| TODO: - Scripting | ||||
| 
 | ||||
| TODO: Moving players more smoothly. Calculate moving animation | ||||
|       in a way that doesn't make the player jump to the right place | ||||
| 	  immediately when the server sends a new position | ||||
| @ -158,8 +146,6 @@ Block object server side: | ||||
| 	    - TODO: For incoming blocks, time difference is calculated and | ||||
| 	      objects are stepped according to it. | ||||
| 
 | ||||
| TODO: Add config parameters for server's sending and generating distance | ||||
| 
 | ||||
| TODO: Copy the text of the last picked sign to inventory in creative | ||||
|       mode | ||||
| 
 | ||||
| @ -172,13 +158,20 @@ TODO: Check what goes wrong with caching map to disk (Kray) | ||||
| 
 | ||||
| TODO: Remove LazyMeshUpdater. It is not used as supposed. | ||||
| 
 | ||||
| TODO: Add server unused sector deletion settings to settings | ||||
| 
 | ||||
| TODO: TOSERVER_LEAVE | ||||
| 
 | ||||
| TODO: Better handling of objects and mobs | ||||
|       - Update brightness according to day-night blended light of node | ||||
| 	    in position | ||||
|       - Scripting? | ||||
| 
 | ||||
| Doing now: | ||||
| ====================================================================== | ||||
| 
 | ||||
| TODO: Get rid of g_irrlicht for server build | ||||
| 
 | ||||
| TODO: Implement getGlobalTime for server build | ||||
|       - It is needed for controlling the time used for flowing water | ||||
| 
 | ||||
| ====================================================================== | ||||
| 
 | ||||
| @ -226,7 +219,6 @@ Doing now: | ||||
| 
 | ||||
| #include <iostream> | ||||
| #include <fstream> | ||||
| #include <time.h> | ||||
| #include <jmutexautolock.h> | ||||
| #include <locale.h> | ||||
| #include "common_irrlicht.h" | ||||
| @ -243,6 +235,8 @@ Doing now: | ||||
| #include "strfnd.h" | ||||
| #include "porting.h" | ||||
| #include "guiPauseMenu.h" | ||||
| #include "irrlichtwrapper.h" | ||||
| #include "gettime.h" | ||||
| 
 | ||||
| IrrlichtWrapper *g_irrlicht; | ||||
| 
 | ||||
| @ -266,7 +260,6 @@ bool g_viewing_range_all = false; | ||||
| // inhibits glitches (dtime jitter) in the main loop.
 | ||||
| //float g_freetime_ratio = FREETIME_RATIO_MAX;
 | ||||
| 
 | ||||
| 
 | ||||
| /*
 | ||||
| 	Settings. | ||||
| 	These are loaded from the config file. | ||||
| @ -311,25 +304,19 @@ std::ostream *derr_server_ptr = &dstream; | ||||
| std::ostream *dout_client_ptr = &dstream; | ||||
| std::ostream *derr_client_ptr = &dstream; | ||||
| 
 | ||||
| 
 | ||||
| /*
 | ||||
| 	Timestamp stuff | ||||
| 	gettime.h implementation | ||||
| */ | ||||
| 
 | ||||
| JMutex g_timestamp_mutex; | ||||
| //std::string g_timestamp;
 | ||||
| 
 | ||||
| std::string getTimestamp() | ||||
| u32 getTimeMs() | ||||
| { | ||||
| 	if(g_timestamp_mutex.IsInitialized()==false) | ||||
| 		return ""; | ||||
| 	JMutexAutoLock lock(g_timestamp_mutex); | ||||
| 	//return g_timestamp;
 | ||||
| 	time_t t = time(NULL); | ||||
| 	struct tm *tm = localtime(&t); | ||||
| 	char cs[20]; | ||||
| 	strftime(cs, 20, "%H:%M:%S", tm); | ||||
| 	return cs; | ||||
| 	/*
 | ||||
| 		Use irrlicht because it is more precise than porting.h's | ||||
| 		getTimeMs() | ||||
| 	*/ | ||||
| 	if(g_irrlicht == NULL) | ||||
| 		return 0; | ||||
| 	return g_irrlicht->getTime(); | ||||
| } | ||||
| 
 | ||||
| class MyEventReceiver : public IEventReceiver | ||||
| @ -1066,9 +1053,6 @@ int main(int argc, char *argv[]) | ||||
| 	sockets_init(); | ||||
| 	atexit(sockets_cleanup); | ||||
| 	 | ||||
| 	// Initialize timestamp mutex
 | ||||
| 	g_timestamp_mutex.Init(); | ||||
| 
 | ||||
| 	/*
 | ||||
| 		Initialization | ||||
| 	*/ | ||||
| @ -1580,7 +1564,7 @@ int main(int argc, char *argv[]) | ||||
| 		// Info text
 | ||||
| 		std::wstring infotext; | ||||
| 
 | ||||
| 		//TimeTaker //timer1("//timer1", g_irrlicht);
 | ||||
| 		//TimeTaker //timer1("//timer1");
 | ||||
| 		 | ||||
| 		// Time of frame without fps limit
 | ||||
| 		float busytime; | ||||
| @ -1770,20 +1754,20 @@ int main(int argc, char *argv[]) | ||||
| 		*/ | ||||
| 		 | ||||
| 		{ | ||||
| 			//TimeTaker timer("client.step(dtime)", g_irrlicht);
 | ||||
| 			//TimeTaker timer("client.step(dtime)");
 | ||||
| 			client.step(dtime); | ||||
| 			//client.step(dtime_avg1);
 | ||||
| 		} | ||||
| 
 | ||||
| 		if(server != NULL) | ||||
| 		{ | ||||
| 			//TimeTaker timer("server->step(dtime)", g_irrlicht);
 | ||||
| 			//TimeTaker timer("server->step(dtime)");
 | ||||
| 			server->step(dtime); | ||||
| 		} | ||||
| 
 | ||||
| 		v3f player_position = client.getPlayerPosition(); | ||||
| 		 | ||||
| 		//TimeTaker //timer2("//timer2", g_irrlicht);
 | ||||
| 		//TimeTaker //timer2("//timer2");
 | ||||
| 
 | ||||
| 		/*
 | ||||
| 			Mouse and camera control | ||||
| @ -1837,12 +1821,12 @@ int main(int argc, char *argv[]) | ||||
| 		} | ||||
| 		else{ | ||||
| 			//client.m_env.getMap().updateCamera(camera_position, camera_direction);
 | ||||
| 			//TimeTaker timer("client.updateCamera", g_irrlicht);
 | ||||
| 			//TimeTaker timer("client.updateCamera");
 | ||||
| 			client.updateCamera(camera_position, camera_direction); | ||||
| 		} | ||||
| 		 | ||||
| 		//timer2.stop();
 | ||||
| 		//TimeTaker //timer3("//timer3", g_irrlicht);
 | ||||
| 		//TimeTaker //timer3("//timer3");
 | ||||
| 
 | ||||
| 		/*
 | ||||
| 			Calculate what block is the crosshair pointing to | ||||
| @ -2118,7 +2102,7 @@ int main(int argc, char *argv[]) | ||||
| 					dig_time_complete = 1.5; | ||||
| 
 | ||||
| 				u16 dig_index = (u16)(3.99*dig_time/dig_time_complete); | ||||
| 				if(dig_time > 0.2) | ||||
| 				if(dig_time > 0.125) | ||||
| 				{ | ||||
| 					//dstream<<"dig_index="<<dig_index<<std::endl;
 | ||||
| 					client.setTempMod(nodepos, NodeMod(NODEMOD_CRACK, dig_index)); | ||||
| @ -2194,7 +2178,7 @@ int main(int argc, char *argv[]) | ||||
| 			Update gui stuff (0ms) | ||||
| 		*/ | ||||
| 
 | ||||
| 		//TimeTaker guiupdatetimer("Gui updating", g_irrlicht);
 | ||||
| 		//TimeTaker guiupdatetimer("Gui updating");
 | ||||
| 		 | ||||
| 		{ | ||||
| 			wchar_t temptext[150]; | ||||
| @ -2304,11 +2288,11 @@ int main(int argc, char *argv[]) | ||||
| 			Drawing begins | ||||
| 		*/ | ||||
| 
 | ||||
| 		TimeTaker drawtimer("Drawing", g_irrlicht); | ||||
| 		TimeTaker drawtimer("Drawing"); | ||||
| 
 | ||||
| 		 | ||||
| 		{ | ||||
| 			TimeTaker timer("beginScene", g_irrlicht); | ||||
| 			TimeTaker timer("beginScene"); | ||||
| 			driver->beginScene(true, true, bgcolor); | ||||
| 			//driver->beginScene(false, true, bgcolor);
 | ||||
| 			beginscenetime = timer.stop(true); | ||||
| @ -2319,13 +2303,13 @@ int main(int argc, char *argv[]) | ||||
| 		//std::cout<<DTIME<<"smgr->drawAll()"<<std::endl;
 | ||||
| 		 | ||||
| 		{ | ||||
| 			TimeTaker timer("smgr", g_irrlicht); | ||||
| 			TimeTaker timer("smgr"); | ||||
| 			smgr->drawAll(); | ||||
| 			scenetime = timer.stop(true); | ||||
| 		} | ||||
| 		 | ||||
| 		{ | ||||
| 		//TimeTaker timer9("auxiliary drawings", g_irrlicht);
 | ||||
| 		//TimeTaker timer9("auxiliary drawings");
 | ||||
| 		// 0ms
 | ||||
| 
 | ||||
| 		driver->draw2DLine(displaycenter - core::vector2d<s32>(10,0), | ||||
| @ -2336,7 +2320,7 @@ int main(int argc, char *argv[]) | ||||
| 				video::SColor(255,255,255,255)); | ||||
| 
 | ||||
| 		//timer9.stop();
 | ||||
| 		//TimeTaker //timer10("//timer10", g_irrlicht);
 | ||||
| 		//TimeTaker //timer10("//timer10");
 | ||||
| 		 | ||||
| 		video::SMaterial m; | ||||
| 		m.Thickness = 10; | ||||
| @ -2359,7 +2343,7 @@ int main(int argc, char *argv[]) | ||||
| 		} | ||||
| 
 | ||||
| 		//timer10.stop();
 | ||||
| 		//TimeTaker //timer11("//timer11", g_irrlicht);
 | ||||
| 		//TimeTaker //timer11("//timer11");
 | ||||
| 
 | ||||
| 		/*
 | ||||
| 			Draw gui | ||||
| @ -2369,7 +2353,7 @@ int main(int argc, char *argv[]) | ||||
| 		 | ||||
| 		// End drawing
 | ||||
| 		{ | ||||
| 			TimeTaker timer("endScene", g_irrlicht); | ||||
| 			TimeTaker timer("endScene"); | ||||
| 			driver->endScene(); | ||||
| 			endscenetime = timer.stop(true); | ||||
| 		} | ||||
|  | ||||
							
								
								
									
										22
									
								
								src/main.h
									
									
									
									
									
								
							
							
						
						
									
										22
									
								
								src/main.h
									
									
									
									
									
								
							| @ -20,18 +20,19 @@ with this program; if not, write to the Free Software Foundation, Inc., | ||||
| #ifndef MAIN_HEADER | ||||
| #define MAIN_HEADER | ||||
| 
 | ||||
| #include <string> | ||||
| extern std::string getTimestamp(); | ||||
| #define DTIME (getTimestamp()+": ") | ||||
| 
 | ||||
| #include <jmutex.h> | ||||
| #include "irrlichtwrapper.h" | ||||
| 
 | ||||
| // Settings
 | ||||
| extern Settings g_settings; | ||||
| 
 | ||||
| #include <fstream> | ||||
| // A thread safe wrapper to irrlicht
 | ||||
| // On a server build, this is always NULL.
 | ||||
| extern IrrlichtWrapper *g_irrlicht; | ||||
| 
 | ||||
| // Debug streams
 | ||||
| 
 | ||||
| #include <fstream> | ||||
| 
 | ||||
| extern std::ostream *dout_con_ptr; | ||||
| extern std::ostream *derr_con_ptr; | ||||
| extern std::ostream *dout_client_ptr; | ||||
| @ -46,14 +47,5 @@ extern std::ostream *derr_server_ptr; | ||||
| #define dout_server (*dout_server_ptr) | ||||
| #define derr_server (*derr_server_ptr) | ||||
| 
 | ||||
| /*#ifndef SERVER
 | ||||
| 	#include "utility.h" | ||||
| 	extern TextureCache g_texturecache; | ||||
| #endif*/ | ||||
| 
 | ||||
| #include "irrlichtwrapper.h" | ||||
| //extern IrrlichtDevice *g_device;
 | ||||
| extern IrrlichtWrapper *g_irrlicht; | ||||
| 
 | ||||
| #endif | ||||
| 
 | ||||
|  | ||||
							
								
								
									
										156
									
								
								src/map.cpp
									
									
									
									
									
								
							
							
						
						
									
										156
									
								
								src/map.cpp
									
									
									
									
									
								
							| @ -152,6 +152,21 @@ MapBlock * Map::getBlockNoCreate(v3s16 p3d) | ||||
| 	return block; | ||||
| } | ||||
| 
 | ||||
| MapBlock * Map::getBlockNoCreateNoEx(v3s16 p3d) | ||||
| { | ||||
| 	try | ||||
| 	{ | ||||
| 		v2s16 p2d(p3d.X, p3d.Z); | ||||
| 		MapSector * sector = getSectorNoGenerate(p2d); | ||||
| 		MapBlock *block = sector->getBlockNoCreate(p3d.Y); | ||||
| 		return block; | ||||
| 	} | ||||
| 	catch(InvalidPositionException &e) | ||||
| 	{ | ||||
| 		return NULL; | ||||
| 	} | ||||
| } | ||||
| 
 | ||||
| f32 Map::getGroundHeight(v2s16 p, bool generate) | ||||
| { | ||||
| 	try{ | ||||
| @ -740,7 +755,7 @@ void Map::updateLighting(enum LightBank bank, | ||||
| 	} | ||||
| 	 | ||||
| 	{ | ||||
| 		//TimeTaker timer("unspreadLight", g_irrlicht);
 | ||||
| 		//TimeTaker timer("unspreadLight");
 | ||||
| 		unspreadLight(bank, unlight_from, light_sources, modified_blocks); | ||||
| 	} | ||||
| 	 | ||||
| @ -759,7 +774,7 @@ void Map::updateLighting(enum LightBank bank, | ||||
| 	//       - Find out why it works
 | ||||
| 
 | ||||
| 	{ | ||||
| 		//TimeTaker timer("spreadLight", g_irrlicht);
 | ||||
| 		//TimeTaker timer("spreadLight");
 | ||||
| 		spreadLight(bank, light_sources, modified_blocks); | ||||
| 	} | ||||
| 	 | ||||
| @ -813,6 +828,7 @@ void Map::addNodeAndUpdate(v3s16 p, MapNode n, | ||||
| 	*/ | ||||
| 
 | ||||
| 	v3s16 toppos = p + v3s16(0,1,0); | ||||
| 	v3s16 bottompos = p + v3s16(0,-1,0); | ||||
| 
 | ||||
| 	bool node_under_sunlight = true; | ||||
| 	core::map<v3s16, bool> light_sources; | ||||
| @ -832,6 +848,26 @@ void Map::addNodeAndUpdate(v3s16 p, MapNode n, | ||||
| 	catch(InvalidPositionException &e) | ||||
| 	{ | ||||
| 	} | ||||
| 	 | ||||
| 	if(n.d != CONTENT_TORCH) | ||||
| 	{ | ||||
| 		/*
 | ||||
| 			If there is grass below, change it to mud | ||||
| 		*/ | ||||
| 		try{ | ||||
| 			MapNode bottomnode = getNode(bottompos); | ||||
| 			 | ||||
| 			if(bottomnode.d == CONTENT_GRASS | ||||
| 					|| bottomnode.d == CONTENT_GRASS_FOOTSTEPS) | ||||
| 			{ | ||||
| 				bottomnode.d = CONTENT_MUD; | ||||
| 				setNode(bottompos, bottomnode); | ||||
| 			} | ||||
| 		} | ||||
| 		catch(InvalidPositionException &e) | ||||
| 		{ | ||||
| 		} | ||||
| 	} | ||||
| 
 | ||||
| 	enum LightBank banks[] = | ||||
| 	{ | ||||
| @ -1065,7 +1101,7 @@ void Map::removeNodeAndUpdate(v3s16 p, | ||||
| #ifndef SERVER | ||||
| void Map::expireMeshes(bool only_daynight_diffed) | ||||
| { | ||||
| 	TimeTaker timer("expireMeshes()", g_irrlicht); | ||||
| 	TimeTaker timer("expireMeshes()"); | ||||
| 
 | ||||
| 	core::map<v2s16, MapSector*>::Iterator si; | ||||
| 	si = m_sectors.getIterator(); | ||||
| @ -1109,6 +1145,7 @@ void Map::updateMeshes(v3s16 blockpos, u32 daynight_ratio) | ||||
| 		b->updateMesh(daynight_ratio); | ||||
| 	} | ||||
| 	catch(InvalidPositionException &e){} | ||||
| 	// Leading edge
 | ||||
| 	try{ | ||||
| 		v3s16 p = blockpos + v3s16(-1,0,0); | ||||
| 		MapBlock *b = getBlockNoCreate(p); | ||||
| @ -1127,6 +1164,25 @@ void Map::updateMeshes(v3s16 blockpos, u32 daynight_ratio) | ||||
| 		b->updateMesh(daynight_ratio); | ||||
| 	} | ||||
| 	catch(InvalidPositionException &e){} | ||||
| 	/*// Trailing edge
 | ||||
| 	try{ | ||||
| 		v3s16 p = blockpos + v3s16(1,0,0); | ||||
| 		MapBlock *b = getBlockNoCreate(p); | ||||
| 		b->updateMesh(daynight_ratio); | ||||
| 	} | ||||
| 	catch(InvalidPositionException &e){} | ||||
| 	try{ | ||||
| 		v3s16 p = blockpos + v3s16(0,1,0); | ||||
| 		MapBlock *b = getBlockNoCreate(p); | ||||
| 		b->updateMesh(daynight_ratio); | ||||
| 	} | ||||
| 	catch(InvalidPositionException &e){} | ||||
| 	try{ | ||||
| 		v3s16 p = blockpos + v3s16(0,0,1); | ||||
| 		MapBlock *b = getBlockNoCreate(p); | ||||
| 		b->updateMesh(daynight_ratio); | ||||
| 	} | ||||
| 	catch(InvalidPositionException &e){}*/ | ||||
| } | ||||
| 
 | ||||
| #endif | ||||
| @ -1140,6 +1196,7 @@ bool Map::dayNightDiffed(v3s16 blockpos) | ||||
| 			return true; | ||||
| 	} | ||||
| 	catch(InvalidPositionException &e){} | ||||
| 	// Leading edges
 | ||||
| 	try{ | ||||
| 		v3s16 p = blockpos + v3s16(-1,0,0); | ||||
| 		MapBlock *b = getBlockNoCreate(p); | ||||
| @ -1161,6 +1218,28 @@ bool Map::dayNightDiffed(v3s16 blockpos) | ||||
| 			return true; | ||||
| 	} | ||||
| 	catch(InvalidPositionException &e){} | ||||
| 	// Trailing edges
 | ||||
| 	try{ | ||||
| 		v3s16 p = blockpos + v3s16(1,0,0); | ||||
| 		MapBlock *b = getBlockNoCreate(p); | ||||
| 		if(b->dayNightDiffed()) | ||||
| 			return true; | ||||
| 	} | ||||
| 	catch(InvalidPositionException &e){} | ||||
| 	try{ | ||||
| 		v3s16 p = blockpos + v3s16(0,1,0); | ||||
| 		MapBlock *b = getBlockNoCreate(p); | ||||
| 		if(b->dayNightDiffed()) | ||||
| 			return true; | ||||
| 	} | ||||
| 	catch(InvalidPositionException &e){} | ||||
| 	try{ | ||||
| 		v3s16 p = blockpos + v3s16(0,0,1); | ||||
| 		MapBlock *b = getBlockNoCreate(p); | ||||
| 		if(b->dayNightDiffed()) | ||||
| 			return true; | ||||
| 	} | ||||
| 	catch(InvalidPositionException &e){} | ||||
| 
 | ||||
| 	return false; | ||||
| } | ||||
| @ -2567,7 +2646,7 @@ void ServerMap::loadBlock(std::string sectordir, std::string blockfile, MapSecto | ||||
| 	*/ | ||||
| 	if(version >= 9) | ||||
| 	{ | ||||
| 		block->updateObjects(is, version, NULL); | ||||
| 		block->updateObjects(is, version, NULL, 0); | ||||
| 	} | ||||
| 
 | ||||
| 	if(created_new) | ||||
| @ -2985,21 +3064,56 @@ void ClientMap::renderMap(video::IVideoDriver* driver, s32 pass) | ||||
| 
 | ||||
| v3s16 ClientMap::setTempMod(v3s16 p, NodeMod mod) | ||||
| { | ||||
| 	v3s16 blockpos = getNodeBlockPos(p); | ||||
| 	MapBlock * blockref = getBlockNoCreate(blockpos); | ||||
| 	v3s16 relpos = p - blockpos*MAP_BLOCKSIZE; | ||||
| 
 | ||||
| 	blockref->setTempMod(relpos, mod); | ||||
| 	return blockpos; | ||||
| 	/*
 | ||||
| 		Add it to all blocks touching it | ||||
| 	*/ | ||||
| 	v3s16 dirs[7] = { | ||||
| 		v3s16(0,0,0), // this
 | ||||
| 		v3s16(0,0,1), // back
 | ||||
| 		v3s16(0,1,0), // top
 | ||||
| 		v3s16(1,0,0), // right
 | ||||
| 		v3s16(0,0,-1), // front
 | ||||
| 		v3s16(0,-1,0), // bottom
 | ||||
| 		v3s16(-1,0,0), // left
 | ||||
| 	}; | ||||
| 	for(u16 i=0; i<7; i++) | ||||
| 	{ | ||||
| 		v3s16 p2 = p + dirs[i]; | ||||
| 		// Block position of neighbor (or requested) node
 | ||||
| 		v3s16 blockpos = getNodeBlockPos(p2); | ||||
| 		MapBlock * blockref = getBlockNoCreateNoEx(blockpos); | ||||
| 		if(blockref == NULL) | ||||
| 			continue; | ||||
| 		// Relative position of requested node
 | ||||
| 		v3s16 relpos = p - blockpos*MAP_BLOCKSIZE; | ||||
| 		blockref->setTempMod(relpos, mod); | ||||
| 	} | ||||
| 	return getNodeBlockPos(p); | ||||
| } | ||||
| v3s16 ClientMap::clearTempMod(v3s16 p) | ||||
| { | ||||
| 	v3s16 blockpos = getNodeBlockPos(p); | ||||
| 	MapBlock * blockref = getBlockNoCreate(blockpos); | ||||
| 	v3s16 relpos = p - blockpos*MAP_BLOCKSIZE; | ||||
| 
 | ||||
| 	blockref->clearTempMod(relpos); | ||||
| 	return blockpos; | ||||
| 	v3s16 dirs[7] = { | ||||
| 		v3s16(0,0,0), // this
 | ||||
| 		v3s16(0,0,1), // back
 | ||||
| 		v3s16(0,1,0), // top
 | ||||
| 		v3s16(1,0,0), // right
 | ||||
| 		v3s16(0,0,-1), // front
 | ||||
| 		v3s16(0,-1,0), // bottom
 | ||||
| 		v3s16(-1,0,0), // left
 | ||||
| 	}; | ||||
| 	for(u16 i=0; i<7; i++) | ||||
| 	{ | ||||
| 		v3s16 p2 = p + dirs[i]; | ||||
| 		// Block position of neighbor (or requested) node
 | ||||
| 		v3s16 blockpos = getNodeBlockPos(p2); | ||||
| 		MapBlock * blockref = getBlockNoCreateNoEx(blockpos); | ||||
| 		if(blockref == NULL) | ||||
| 			continue; | ||||
| 		// Relative position of requested node
 | ||||
| 		v3s16 relpos = p - blockpos*MAP_BLOCKSIZE; | ||||
| 		blockref->clearTempMod(relpos); | ||||
| 	} | ||||
| 	return getNodeBlockPos(p); | ||||
| } | ||||
| 
 | ||||
| void ClientMap::PrintInfo(std::ostream &out) | ||||
| @ -3027,7 +3141,7 @@ MapVoxelManipulator::~MapVoxelManipulator() | ||||
| #if 1 | ||||
| void MapVoxelManipulator::emerge(VoxelArea a, s32 caller_id) | ||||
| { | ||||
| 	TimeTaker timer1("emerge", g_irrlicht, &emerge_time); | ||||
| 	TimeTaker timer1("emerge", &emerge_time); | ||||
| 
 | ||||
| 	// Units of these are MapBlocks
 | ||||
| 	v3s16 p_min = getNodeBlockPos(a.MinEdge); | ||||
| @ -3051,7 +3165,7 @@ void MapVoxelManipulator::emerge(VoxelArea a, s32 caller_id) | ||||
| 		bool block_data_inexistent = false; | ||||
| 		try | ||||
| 		{ | ||||
| 			TimeTaker timer1("emerge load", g_irrlicht, &emerge_load_time); | ||||
| 			TimeTaker timer1("emerge load", &emerge_load_time); | ||||
| 
 | ||||
| 			/*dstream<<"Loading block (caller_id="<<caller_id<<")"
 | ||||
| 					<<" ("<<p.X<<","<<p.Y<<","<<p.Z<<")" | ||||
| @ -3092,7 +3206,7 @@ void MapVoxelManipulator::emerge(VoxelArea a, s32 caller_id) | ||||
| #if 0 | ||||
| void MapVoxelManipulator::emerge(VoxelArea a) | ||||
| { | ||||
| 	TimeTaker timer1("emerge", g_irrlicht, &emerge_time); | ||||
| 	TimeTaker timer1("emerge", &emerge_time); | ||||
| 	 | ||||
| 	v3s16 size = a.getExtent(); | ||||
| 	 | ||||
| @ -3111,7 +3225,7 @@ void MapVoxelManipulator::emerge(VoxelArea a) | ||||
| 			continue; | ||||
| 		try | ||||
| 		{ | ||||
| 			TimeTaker timer1("emerge load", g_irrlicht, &emerge_load_time); | ||||
| 			TimeTaker timer1("emerge load", &emerge_load_time); | ||||
| 			MapNode n = m_map->getNode(a.MinEdge + p); | ||||
| 			m_data[i] = n; | ||||
| 			m_flags[i] = 0; | ||||
| @ -3136,7 +3250,7 @@ void MapVoxelManipulator::blitBack | ||||
| 	if(m_area.getExtent() == v3s16(0,0,0)) | ||||
| 		return; | ||||
| 	 | ||||
| 	//TimeTaker timer1("blitBack", g_irrlicht);
 | ||||
| 	//TimeTaker timer1("blitBack");
 | ||||
| 	 | ||||
| 	/*
 | ||||
| 		Initialize block cache | ||||
|  | ||||
| @ -274,7 +274,8 @@ public: | ||||
| 	 | ||||
| 	// Returns InvalidPositionException if not found
 | ||||
| 	MapBlock * getBlockNoCreate(v3s16 p); | ||||
| 	//virtual MapBlock * getBlock(v3s16 p, bool generate=true);
 | ||||
| 	// Returns NULL if not found
 | ||||
| 	MapBlock * getBlockNoCreateNoEx(v3s16 p); | ||||
| 	 | ||||
| 	// Returns InvalidPositionException if not found
 | ||||
| 	f32 getGroundHeight(v2s16 p, bool generate=false); | ||||
| @ -386,7 +387,7 @@ public: | ||||
| #endif | ||||
| 
 | ||||
| 	/*
 | ||||
| 		Takes the blocks at the leading edges into account | ||||
| 		Takes the blocks at the edges into account | ||||
| 	*/ | ||||
| 	bool dayNightDiffed(v3s16 blockpos); | ||||
| 
 | ||||
|  | ||||
| @ -40,6 +40,8 @@ MapBlock::MapBlock(NodeContainer *parent, v3s16 pos, bool dummy): | ||||
| 	data = NULL; | ||||
| 	if(dummy == false) | ||||
| 		reallocate(); | ||||
| 	 | ||||
| 	m_spawn_timer = -10000; | ||||
| 
 | ||||
| #ifndef SERVER | ||||
| 	m_mesh_expired = false; | ||||
| @ -237,8 +239,8 @@ void MapBlock::makeFastFace(TileSpec tile, u8 light, v3f p, | ||||
| 
 | ||||
| 	v3f zerovector = v3f(0,0,0); | ||||
| 	 | ||||
| 	u8 li = decode_light(light); | ||||
| 	//u8 li = 150;
 | ||||
| 	//u8 li = decode_light(light);
 | ||||
| 	u8 li = light; | ||||
| 
 | ||||
| 	u8 alpha = 255; | ||||
| 
 | ||||
| @ -435,14 +437,14 @@ void MapBlock::updateFastFaceRow( | ||||
| 				// If node at sp (tile0) is more solid
 | ||||
| 				if(mf == 1) | ||||
| 				{ | ||||
| 					makeFastFace(tile0, light, | ||||
| 					makeFastFace(tile0, decode_light(light), | ||||
| 							sp, face_dir, scale, | ||||
| 							posRelative_f, dest); | ||||
| 				} | ||||
| 				// If node at sp is less solid (mf == 2)
 | ||||
| 				else | ||||
| 				{ | ||||
| 					makeFastFace(tile1, light, | ||||
| 					makeFastFace(tile1, decode_light(light), | ||||
| 							sp+face_dir_f, -face_dir, scale, | ||||
| 							posRelative_f, dest); | ||||
| 				} | ||||
| @ -992,6 +994,52 @@ void MapBlock::copyTo(VoxelManipulator &dst) | ||||
| 		core::array<DistanceSortedObject> &dest) | ||||
| { | ||||
| }*/ | ||||
| void MapBlock::stepObjects(float dtime, bool server, u32 daynight_ratio) | ||||
| { | ||||
| 	/*
 | ||||
| 		Step objects | ||||
| 	*/ | ||||
| 	m_objects.step(dtime, server, daynight_ratio); | ||||
| 	 | ||||
| 	/*
 | ||||
| 		Spawn some objects at random. | ||||
| 
 | ||||
| 		Use dayNightDiffed() to approximate being near ground level | ||||
| 	*/ | ||||
| 	if(m_spawn_timer < -999) | ||||
| 	{ | ||||
| 		m_spawn_timer = 60; | ||||
| 	} | ||||
| 	if(dayNightDiffed() == true && getObjectCount() == 0) | ||||
| 	{ | ||||
| 		m_spawn_timer -= dtime; | ||||
| 		if(m_spawn_timer <= 0.0) | ||||
| 		{ | ||||
| 			m_spawn_timer += rand() % 300; | ||||
| 			 | ||||
| 			v2s16 p2d( | ||||
| 				(rand()%(MAP_BLOCKSIZE-1))+0, | ||||
| 				(rand()%(MAP_BLOCKSIZE-1))+0 | ||||
| 			); | ||||
| 
 | ||||
| 			s16 y = getGroundLevel(p2d); | ||||
| 			 | ||||
| 			if(y >= 0) | ||||
| 			{ | ||||
| 				v3s16 p(p2d.X, y+1, p2d.Y); | ||||
| 
 | ||||
| 				if(getNode(p).d == CONTENT_AIR | ||||
| 						&& getNode(p).getLightBlend(daynight_ratio) <= 11) | ||||
| 				{ | ||||
| 					RatObject *obj = new RatObject(NULL, -1, intToFloat(p)); | ||||
| 					addObject(obj); | ||||
| 				} | ||||
| 			} | ||||
| 		} | ||||
| 	} | ||||
| 
 | ||||
| 	setChangedFlag(); | ||||
| } | ||||
| 
 | ||||
| 
 | ||||
| void MapBlock::updateDayNightDiff() | ||||
| @ -1041,6 +1089,31 @@ void MapBlock::updateDayNightDiff() | ||||
| 	m_day_night_differs = differs; | ||||
| } | ||||
| 
 | ||||
| s16 MapBlock::getGroundLevel(v2s16 p2d) | ||||
| { | ||||
| 	if(isDummy()) | ||||
| 		return -3; | ||||
| 	try | ||||
| 	{ | ||||
| 		s16 y = MAP_BLOCKSIZE-1; | ||||
| 		for(; y>=0; y--) | ||||
| 		{ | ||||
| 			if(is_ground_content(getNodeRef(p2d.X, y, p2d.Y).d)) | ||||
| 			{ | ||||
| 				if(y == MAP_BLOCKSIZE-1) | ||||
| 					return -2; | ||||
| 				else | ||||
| 					return y; | ||||
| 			} | ||||
| 		} | ||||
| 		return -1; | ||||
| 	} | ||||
| 	catch(InvalidPositionException &e) | ||||
| 	{ | ||||
| 		return -3; | ||||
| 	} | ||||
| } | ||||
| 
 | ||||
| /*
 | ||||
| 	Serialization | ||||
| */ | ||||
|  | ||||
| @ -281,6 +281,7 @@ public: | ||||
| 	} | ||||
| 	 | ||||
| #ifndef SERVER | ||||
| 	// light = 0...255
 | ||||
| 	static void makeFastFace(TileSpec tile, u8 light, v3f p, | ||||
| 			v3s16 dir, v3f scale, v3f posRelative_f, | ||||
| 			core::array<FastFace> &dest); | ||||
| @ -325,9 +326,9 @@ public: | ||||
| 	} | ||||
| 	// If smgr!=NULL, new objects are added to the scene
 | ||||
| 	void updateObjects(std::istream &is, u8 version, | ||||
| 			scene::ISceneManager *smgr) | ||||
| 			scene::ISceneManager *smgr, u32 daynight_ratio) | ||||
| 	{ | ||||
| 		m_objects.update(is, version, smgr); | ||||
| 		m_objects.update(is, version, smgr, daynight_ratio); | ||||
| 
 | ||||
| 		setChangedFlag(); | ||||
| 	} | ||||
| @ -358,12 +359,11 @@ public: | ||||
| 	{ | ||||
| 		return m_objects.getLock(); | ||||
| 	} | ||||
| 	void stepObjects(float dtime, bool server) | ||||
| 	{ | ||||
| 		m_objects.step(dtime, server); | ||||
| 
 | ||||
| 		setChangedFlag(); | ||||
| 	} | ||||
| 	/*
 | ||||
| 		Moves objects, deletes objects and spawns new objects | ||||
| 	*/ | ||||
| 	void stepObjects(float dtime, bool server, u32 daynight_ratio); | ||||
| 
 | ||||
| 	/*void wrapObject(MapBlockObject *object)
 | ||||
| 	{ | ||||
| @ -427,6 +427,20 @@ public: | ||||
| 		return m_day_night_differs; | ||||
| 	} | ||||
| 
 | ||||
| 	/*
 | ||||
| 		Miscellaneous stuff | ||||
| 	*/ | ||||
| 	 | ||||
| 	/*
 | ||||
| 		Tries to measure ground level. | ||||
| 		Return value: | ||||
| 			-1 = only air | ||||
| 			-2 = only ground | ||||
| 			-3 = random fail | ||||
| 			0...MAP_BLOCKSIZE-1 = ground level | ||||
| 	*/ | ||||
| 	s16 getGroundLevel(v2s16 p2d); | ||||
| 
 | ||||
| 	/*
 | ||||
| 		Serialization | ||||
| 	*/ | ||||
| @ -454,6 +468,8 @@ private: | ||||
| 
 | ||||
| 	MapNode & getNodeRef(s16 x, s16 y, s16 z) | ||||
| 	{ | ||||
| 		if(data == NULL) | ||||
| 			throw InvalidPositionException(); | ||||
| 		if(x < 0 || x >= MAP_BLOCKSIZE) throw InvalidPositionException(); | ||||
| 		if(y < 0 || y >= MAP_BLOCKSIZE) throw InvalidPositionException(); | ||||
| 		if(z < 0 || z >= MAP_BLOCKSIZE) throw InvalidPositionException(); | ||||
| @ -491,6 +507,9 @@ private: | ||||
| 	bool m_day_night_differs; | ||||
| 	 | ||||
| 	MapBlockObjectList m_objects; | ||||
| 
 | ||||
| 	// Object spawning stuff
 | ||||
| 	float m_spawn_timer; | ||||
| 	 | ||||
| #ifndef SERVER | ||||
| 	bool m_mesh_expired; | ||||
|  | ||||
| @ -46,6 +46,17 @@ void MapBlockObject::setBlockChanged() | ||||
| /*
 | ||||
| 	MovingObject | ||||
| */ | ||||
| 
 | ||||
| v3f MovingObject::getAbsoluteShowPos() | ||||
| { | ||||
| 	if(m_block == NULL) | ||||
| 		return m_pos; | ||||
| 	 | ||||
| 	// getPosRelative gets nodepos relative to map origin
 | ||||
| 	v3f blockpos = intToFloat(m_block->getPosRelative()); | ||||
| 	return blockpos + m_showpos; | ||||
| } | ||||
| 
 | ||||
| void MovingObject::move(float dtime, v3f acceleration) | ||||
| { | ||||
| 	DSTACK("%s: typeid=%i, pos=(%f,%f,%f), speed=(%f,%f,%f)" | ||||
| @ -97,7 +108,7 @@ void MovingObject::move(float dtime, v3f acceleration) | ||||
| 	float speedlength = m_speed.getLength(); | ||||
| 	f32 dtime_max_increment; | ||||
| 	if(fabs(speedlength) > 0.001) | ||||
| 		dtime_max_increment = 0.1*BS / speedlength; | ||||
| 		dtime_max_increment = 0.05*BS / speedlength; | ||||
| 	else | ||||
| 		dtime_max_increment = 0.5; | ||||
| 	 | ||||
| @ -151,14 +162,14 @@ void MovingObject::move(float dtime, v3f acceleration) | ||||
| 			} | ||||
| 			catch(InvalidPositionException &e) | ||||
| 			{ | ||||
| 				// Doing nothing here will block the player from
 | ||||
| 				// Doing nothing here will block the object from
 | ||||
| 				// walking over map borders
 | ||||
| 			} | ||||
| 
 | ||||
| 			core::aabbox3d<f32> nodebox = Map::getNodeBox( | ||||
| 					v3s16(x,y,z)); | ||||
| 			 | ||||
| 			// See if the player is touching ground
 | ||||
| 			// See if the object is touching ground
 | ||||
| 			if( | ||||
| 					fabs(nodebox.MaxEdge.Y-objectbox.MinEdge.Y) < d | ||||
| 					&& nodebox.MaxEdge.X-d > objectbox.MinEdge.X | ||||
| @ -227,6 +238,60 @@ void MovingObject::move(float dtime, v3f acceleration) | ||||
| 	m_pos = position; | ||||
| } | ||||
| 
 | ||||
| void MovingObject::simpleMove(float dtime) | ||||
| { | ||||
| 	m_pos_animation_time_counter += dtime; | ||||
| 	m_pos_animation_counter += dtime; | ||||
| 	v3f movevector = m_pos - m_oldpos; | ||||
| 	f32 moveratio; | ||||
| 	if(m_pos_animation_time < 0.001) | ||||
| 		moveratio = 1.0; | ||||
| 	else | ||||
| 		moveratio = m_pos_animation_counter / m_pos_animation_time; | ||||
| 	if(moveratio > 1.5) | ||||
| 		moveratio = 1.5; | ||||
| 	m_showpos = m_oldpos + movevector * moveratio; | ||||
| } | ||||
| 
 | ||||
| #ifndef SERVER | ||||
| /*
 | ||||
| 	RatObject | ||||
| */ | ||||
| void RatObject::addToScene(scene::ISceneManager *smgr) | ||||
| { | ||||
| 	if(m_node != NULL) | ||||
| 		return; | ||||
| 	 | ||||
| 	video::IVideoDriver* driver = smgr->getVideoDriver(); | ||||
| 	 | ||||
| 	scene::SMesh *mesh = new scene::SMesh(); | ||||
| 	scene::IMeshBuffer *buf = new scene::SMeshBuffer(); | ||||
| 	video::SColor c(255,255,255,255); | ||||
| 	video::S3DVertex vertices[4] = | ||||
| 	{ | ||||
| 		video::S3DVertex(-BS/2,-BS/4,0, 0,0,0, c, 0,1), | ||||
| 		video::S3DVertex(BS/2,-BS/4,0, 0,0,0, c, 1,1), | ||||
| 		video::S3DVertex(BS/2,BS/4,0, 0,0,0, c, 1,0), | ||||
| 		video::S3DVertex(-BS/2,BS/4,0, 0,0,0, c, 0,0), | ||||
| 	}; | ||||
| 	u16 indices[] = {0,1,2,2,3,0}; | ||||
| 	buf->append(vertices, 4, indices, 6); | ||||
| 	// Set material
 | ||||
| 	buf->getMaterial().setFlag(video::EMF_LIGHTING, false); | ||||
| 	buf->getMaterial().setFlag(video::EMF_BACK_FACE_CULLING, false); | ||||
| 	buf->getMaterial().setTexture | ||||
| 			(0, driver->getTexture("../data/rat.png")); | ||||
| 	buf->getMaterial().setFlag(video::EMF_BILINEAR_FILTER, false); | ||||
| 	buf->getMaterial().MaterialType = video::EMT_TRANSPARENT_ALPHA_CHANNEL; | ||||
| 	// Add to mesh
 | ||||
| 	mesh->addMeshBuffer(buf); | ||||
| 	buf->drop(); | ||||
| 	m_node = smgr->addMeshSceneNode(mesh, NULL); | ||||
| 	mesh->drop(); | ||||
| 	updateNodePos(); | ||||
| } | ||||
| #endif | ||||
| 
 | ||||
| /*
 | ||||
| 	MapBlockObjectList | ||||
| */ | ||||
| @ -265,7 +330,7 @@ void MapBlockObjectList::serialize(std::ostream &os, u8 version) | ||||
| } | ||||
| 
 | ||||
| void MapBlockObjectList::update(std::istream &is, u8 version, | ||||
| 		scene::ISceneManager *smgr) | ||||
| 		scene::ISceneManager *smgr, u32 daynight_ratio) | ||||
| { | ||||
| 	JMutexAutoLock lock(m_mutex); | ||||
| 
 | ||||
| @ -349,11 +414,14 @@ void MapBlockObjectList::update(std::istream &is, u8 version, | ||||
| 			} | ||||
| 			else | ||||
| 			{ | ||||
| 				// This is fatal because we cannot know the length
 | ||||
| 				// of the object's data
 | ||||
| 				throw SerializationError | ||||
| 				("MapBlockObjectList::update(): Unknown MapBlockObject type"); | ||||
| 			} | ||||
| 
 | ||||
| 			if(smgr != NULL) | ||||
| 				//obj->addToScene(smgr, daynight_ratio);
 | ||||
| 				obj->addToScene(smgr); | ||||
| 
 | ||||
| 			n->setValue(obj); | ||||
| @ -362,6 +430,11 @@ void MapBlockObjectList::update(std::istream &is, u8 version, | ||||
| 		{ | ||||
| 			obj = n->getValue(); | ||||
| 			obj->updatePos(pos); | ||||
| 			/*if(daynight_ratio != m_last_update_daynight_ratio)
 | ||||
| 			{ | ||||
| 				obj->removeFromScene(); | ||||
| 				obj->addToScene(smgr, daynight_ratio); | ||||
| 			}*/ | ||||
| 		} | ||||
| 
 | ||||
| 		// Now there is an object in obj.
 | ||||
| @ -369,6 +442,21 @@ void MapBlockObjectList::update(std::istream &is, u8 version, | ||||
| 		 | ||||
| 		obj->update(is, version); | ||||
| 		 | ||||
| 		/*
 | ||||
| 			Update light on client | ||||
| 		*/ | ||||
| 		if(smgr != NULL) | ||||
| 		{ | ||||
| 			u8 light = LIGHT_MAX; | ||||
| 			try{ | ||||
| 				v3s16 relpos_i = floatToInt(obj->m_pos); | ||||
| 				MapNode n = m_block->getNodeParent(relpos_i); | ||||
| 				light = n.getLightBlend(daynight_ratio); | ||||
| 			} | ||||
| 			catch(InvalidPositionException &e) {} | ||||
| 			obj->updateLight(light); | ||||
| 		} | ||||
| 		 | ||||
| 		// Remove from deletion list
 | ||||
| 		if(ids_to_delete.find(id) != NULL) | ||||
| 			ids_to_delete.remove(id); | ||||
| @ -390,6 +478,8 @@ void MapBlockObjectList::update(std::istream &is, u8 version, | ||||
| 		delete obj; | ||||
| 		m_objects.remove(id); | ||||
| 	} | ||||
| 
 | ||||
| 	m_last_update_daynight_ratio = daynight_ratio; | ||||
| } | ||||
| 
 | ||||
| s16 MapBlockObjectList::getFreeId() throw(ContainerFullException) | ||||
| @ -492,7 +582,7 @@ MapBlockObject * MapBlockObjectList::get(s16 id) | ||||
| 		return n->getValue(); | ||||
| } | ||||
| 
 | ||||
| void MapBlockObjectList::step(float dtime, bool server) | ||||
| void MapBlockObjectList::step(float dtime, bool server, u32 daynight_ratio) | ||||
| { | ||||
| 	DSTACK(__FUNCTION_NAME); | ||||
| 	 | ||||
| @ -514,7 +604,17 @@ void MapBlockObjectList::step(float dtime, bool server) | ||||
| 
 | ||||
| 			if(server) | ||||
| 			{ | ||||
| 				bool to_delete = obj->serverStep(dtime); | ||||
| 				// Update light
 | ||||
| 				u8 light = LIGHT_MAX; | ||||
| 				try{ | ||||
| 					v3s16 relpos_i = floatToInt(obj->m_pos); | ||||
| 					MapNode n = m_block->getNodeParent(relpos_i); | ||||
| 					light = n.getLightBlend(daynight_ratio); | ||||
| 				} | ||||
| 				catch(InvalidPositionException &e) {} | ||||
| 				obj->updateLight(light); | ||||
| 				 | ||||
| 				bool to_delete = obj->serverStep(dtime, daynight_ratio); | ||||
| 
 | ||||
| 				if(to_delete) | ||||
| 					ids_to_delete.insert(obj->m_id, true); | ||||
| @ -669,7 +769,7 @@ void MapBlockObjectList::getObjects(v3f origin, f32 max_d, | ||||
| 	{ | ||||
| 		MapBlockObject *obj = i.getNode()->getValue(); | ||||
| 
 | ||||
| 		f32 d = (obj->m_pos - origin).getLength(); | ||||
| 		f32 d = (obj->getRelativeShowPos() - origin).getLength(); | ||||
| 
 | ||||
| 		if(d > max_d) | ||||
| 			continue; | ||||
|  | ||||
| @ -33,7 +33,7 @@ with this program; if not, write to the Free Software Foundation, Inc., | ||||
| #define MAPBLOCKOBJECT_TYPE_SIGN 2 | ||||
| #define MAPBLOCKOBJECT_TYPE_RAT 3 | ||||
| // Used for handling selecting special stuff
 | ||||
| //#define MAPBLOCKOBJECT_TYPE_PSEUDO 4
 | ||||
| //#define MAPBLOCKOBJECT_TYPE_PSEUDO 1000
 | ||||
| 
 | ||||
| class MapBlock; | ||||
| 
 | ||||
| @ -81,6 +81,11 @@ public: | ||||
| 		os.write((char*)buf, 2); | ||||
| 	} | ||||
| 	 | ||||
| 	// Position where the object is drawn relative to block
 | ||||
| 	virtual v3f getRelativeShowPos() | ||||
| 	{ | ||||
| 		return m_pos; | ||||
| 	} | ||||
| 	// Get floating point position on map
 | ||||
| 	v3f getAbsolutePos(); | ||||
| 
 | ||||
| @ -134,12 +139,14 @@ public: | ||||
| 	// Typical dtimes are 0.2 and 10000.
 | ||||
| 	// A return value of true requests deletion of the object by the caller.
 | ||||
| 	// NOTE: Only server calls this.
 | ||||
| 	virtual bool serverStep(float dtime) { return false; }; | ||||
| 	virtual bool serverStep(float dtime, u32 daynight_ratio) | ||||
| 	{ return false; }; | ||||
| 
 | ||||
| #ifdef SERVER | ||||
| 	void clientStep(float dtime) {}; | ||||
| 	void addToScene(void *smgr) {}; | ||||
| 	void removeFromScene() {}; | ||||
| 	void updateLight(u8 light_at_pos) {}; | ||||
| #else | ||||
| 	// This should do slight animations only or so
 | ||||
| 	virtual void clientStep(float dtime) {}; | ||||
| @ -148,11 +155,14 @@ public: | ||||
| 	//       same as the current state
 | ||||
| 	// Shall add and remove relevant scene nodes for rendering the
 | ||||
| 	// object in the game world
 | ||||
| 	virtual void addToScene(scene::ISceneManager *smgr) {}; | ||||
| 	virtual void addToScene(scene::ISceneManager *smgr) = 0; | ||||
| 	// Shall remove stuff from the scene
 | ||||
| 	// Should return silently if there is nothing to remove
 | ||||
| 	// NOTE: This has to be called before calling destructor
 | ||||
| 	virtual void removeFromScene() {}; | ||||
| 	virtual void removeFromScene() = 0; | ||||
| 	 | ||||
| 	// 0 <= light_at_pos <= LIGHT_SUN
 | ||||
| 	virtual void updateLight(u8 light_at_pos) {}; | ||||
| #endif | ||||
| 
 | ||||
| 	virtual std::string infoText() { return ""; } | ||||
| @ -209,7 +219,7 @@ public: | ||||
| 	{ | ||||
| 		assert(0); | ||||
| 	} | ||||
| 	virtual bool serverStep(float dtime) | ||||
| 	virtual bool serverStep(float dtime, u32 daynight_ratio) | ||||
| 	{ | ||||
| 		assert(0); | ||||
| 	} | ||||
| @ -233,7 +243,10 @@ public: | ||||
| 	// The constructor of every MapBlockObject should be like this
 | ||||
| 	MovingObject(MapBlock *block, s16 id, v3f pos): | ||||
| 		MapBlockObject(block, id, pos), | ||||
| 		m_speed(0,0,0) | ||||
| 		m_speed(0,0,0), | ||||
| 		m_oldpos(pos), | ||||
| 		m_pos_animation_time(0), | ||||
| 		m_showpos(pos) | ||||
| 	{ | ||||
| 		m_touching_ground = false; | ||||
| 	} | ||||
| @ -273,9 +286,34 @@ public: | ||||
| 
 | ||||
| 		m_speed = speed; | ||||
| 	} | ||||
| 	 | ||||
| 	// Reimplementation shall call this.
 | ||||
| 	virtual void updatePos(v3f pos) | ||||
| 	{ | ||||
| 		m_oldpos = m_showpos; | ||||
| 		m_pos = pos; | ||||
| 		 | ||||
| 		if(m_pos_animation_time < 0.001 || m_pos_animation_time > 1.0) | ||||
| 			m_pos_animation_time = m_pos_animation_time_counter; | ||||
| 		else | ||||
| 			m_pos_animation_time = m_pos_animation_time * 0.9 | ||||
| 					+ m_pos_animation_time_counter * 0.1; | ||||
| 		m_pos_animation_time_counter = 0; | ||||
| 		m_pos_animation_counter = 0; | ||||
| 	} | ||||
| 	 | ||||
| 	// Position where the object is drawn relative to block
 | ||||
| 	virtual v3f getRelativeShowPos() | ||||
| 	{ | ||||
| 		return m_showpos; | ||||
| 	} | ||||
| 	// Returns m_showpos relative to whole map
 | ||||
| 	v3f getAbsoluteShowPos(); | ||||
| 
 | ||||
| 	virtual bool serverStep(float dtime) { return false; }; | ||||
| 	virtual void clientStep(float dtime) {}; | ||||
| 	virtual bool serverStep(float dtime, u32 daynight_ratio) | ||||
| 	{ return false; }; | ||||
| 	virtual void clientStep(float dtime) | ||||
| 	{}; | ||||
| 	 | ||||
| 	/*virtual void addToScene(scene::ISceneManager *smgr) = 0;
 | ||||
| 	virtual void removeFromScene() = 0;*/ | ||||
| @ -284,182 +322,21 @@ public: | ||||
| 		Special methods | ||||
| 	*/ | ||||
| 	 | ||||
| 	// Moves with collision detection
 | ||||
| 	// Move with collision detection, server side
 | ||||
| 	void move(float dtime, v3f acceleration); | ||||
| 
 | ||||
| 	// Move from old position to new position, client side
 | ||||
| 	void simpleMove(float dtime); | ||||
| 	 | ||||
| protected: | ||||
| 	v3f m_speed; | ||||
| 	bool m_touching_ground; | ||||
| }; | ||||
| 
 | ||||
| class RatObject : public MovingObject | ||||
| { | ||||
| public: | ||||
| 	RatObject(MapBlock *block, s16 id, v3f pos): | ||||
| 		MovingObject(block, id, pos), | ||||
| 		m_node(NULL) | ||||
| 	{ | ||||
| 		m_collision_box = new core::aabbox3d<f32> | ||||
| 				(-BS*0.3,0,-BS*0.3, BS*0.3,BS*0.5,BS*0.3); | ||||
| 		m_selection_box = new core::aabbox3d<f32> | ||||
| 				(-BS*0.3,0,-BS*0.3, BS*0.3,BS*0.5,BS*0.3); | ||||
| 
 | ||||
| 		m_counter1 = 0; | ||||
| 		m_counter2 = 0; | ||||
| 	} | ||||
| 	virtual ~RatObject() | ||||
| 	{ | ||||
| 		delete m_collision_box; | ||||
| 		delete m_selection_box; | ||||
| 	} | ||||
| 	 | ||||
| 	/*
 | ||||
| 		Implementation interface | ||||
| 	*/ | ||||
| 	virtual u16 getTypeId() const | ||||
| 	{ | ||||
| 		return MAPBLOCKOBJECT_TYPE_RAT; | ||||
| 	} | ||||
| 	virtual void serialize(std::ostream &os, u8 version) | ||||
| 	{ | ||||
| 		MovingObject::serialize(os, version); | ||||
| 		u8 buf[2]; | ||||
| 
 | ||||
| 		// Write yaw * 10
 | ||||
| 		writeS16(buf, m_yaw * 10); | ||||
| 		os.write((char*)buf, 2); | ||||
| 
 | ||||
| 	} | ||||
| 	virtual void update(std::istream &is, u8 version) | ||||
| 	{ | ||||
| 		MovingObject::update(is, version); | ||||
| 		u8 buf[2]; | ||||
| 		 | ||||
| 		// Read yaw * 10
 | ||||
| 		is.read((char*)buf, 2); | ||||
| 		s16 yaw_i = readS16(buf); | ||||
| 		m_yaw = (f32)yaw_i / 10; | ||||
| 
 | ||||
| 		updateNodePos(); | ||||
| 	} | ||||
| 
 | ||||
| 	virtual bool serverStep(float dtime) | ||||
| 	{ | ||||
| 		v3f dir(cos(m_yaw/180*PI),0,sin(m_yaw/180*PI)); | ||||
| 
 | ||||
| 		f32 speed = 2*BS; | ||||
| 
 | ||||
| 		m_speed.X = speed * dir.X; | ||||
| 		m_speed.Z = speed * dir.Z; | ||||
| 
 | ||||
| 		if(m_touching_ground && (m_oldpos - m_pos).getLength() < dtime*speed/2) | ||||
| 		{ | ||||
| 			m_counter1 -= dtime; | ||||
| 			if(m_counter1 < 0.0) | ||||
| 			{ | ||||
| 				m_counter1 += 1.0; | ||||
| 				m_speed.Y = 5.0*BS; | ||||
| 			} | ||||
| 		} | ||||
| 
 | ||||
| 		{ | ||||
| 			m_counter2 -= dtime; | ||||
| 			if(m_counter2 < 0.0) | ||||
| 			{ | ||||
| 				m_counter2 += (float)(rand()%100)/100*3.0; | ||||
| 				m_yaw += ((float)(rand()%200)-100)/100*180; | ||||
| 				m_yaw = wrapDegrees(m_yaw); | ||||
| 			} | ||||
| 		} | ||||
| 
 | ||||
| 		m_oldpos = m_pos; | ||||
| 
 | ||||
| 		//m_yaw += dtime*90;
 | ||||
| 
 | ||||
| 		move(dtime, v3f(0, -9.81*BS, 0)); | ||||
| 
 | ||||
| 		updateNodePos(); | ||||
| 
 | ||||
| 		return false; | ||||
| 	} | ||||
| #ifndef SERVER | ||||
| 	virtual void clientStep(float dtime) | ||||
| 	{ | ||||
| 		m_pos += m_speed * dtime; | ||||
| 
 | ||||
| 		updateNodePos(); | ||||
| 	} | ||||
| 	 | ||||
| 	virtual void addToScene(scene::ISceneManager *smgr) | ||||
| 	{ | ||||
| 		if(m_node != NULL) | ||||
| 			return; | ||||
| 		 | ||||
| 		video::IVideoDriver* driver = smgr->getVideoDriver(); | ||||
| 		 | ||||
| 		scene::SMesh *mesh = new scene::SMesh(); | ||||
| 		scene::IMeshBuffer *buf = new scene::SMeshBuffer(); | ||||
| 		video::SColor c(255,255,255,255); | ||||
| 		video::S3DVertex vertices[4] = | ||||
| 		{ | ||||
| 			video::S3DVertex(-BS/2,0,0, 0,0,0, c, 0,1), | ||||
| 			video::S3DVertex(BS/2,0,0, 0,0,0, c, 1,1), | ||||
| 			video::S3DVertex(BS/2,BS/2,0, 0,0,0, c, 1,0), | ||||
| 			video::S3DVertex(-BS/2,BS/2,0, 0,0,0, c, 0,0), | ||||
| 		}; | ||||
| 		u16 indices[] = {0,1,2,2,3,0}; | ||||
| 		buf->append(vertices, 4, indices, 6); | ||||
| 		// Set material
 | ||||
| 		buf->getMaterial().setFlag(video::EMF_LIGHTING, false); | ||||
| 		buf->getMaterial().setFlag(video::EMF_BACK_FACE_CULLING, false); | ||||
| 		buf->getMaterial().setTexture | ||||
| 				(0, driver->getTexture("../data/rat.png")); | ||||
| 		buf->getMaterial().setFlag(video::EMF_BILINEAR_FILTER, false); | ||||
| 		buf->getMaterial().MaterialType = video::EMT_TRANSPARENT_ALPHA_CHANNEL; | ||||
| 		// Add to mesh
 | ||||
| 		mesh->addMeshBuffer(buf); | ||||
| 		buf->drop(); | ||||
| 		m_node = smgr->addMeshSceneNode(mesh, NULL); | ||||
| 		mesh->drop(); | ||||
| 		m_node->setPosition(getAbsolutePos()); | ||||
| 	} | ||||
| 	virtual void removeFromScene() | ||||
| 	{ | ||||
| 		if(m_node != NULL) | ||||
| 		{ | ||||
| 			m_node->remove(); | ||||
| 			m_node = NULL; | ||||
| 		} | ||||
| 	} | ||||
| #endif | ||||
| 
 | ||||
| 	virtual std::string getInventoryString() | ||||
| 	{ | ||||
| 		// There must be a space after the name
 | ||||
| 		// Or does there?
 | ||||
| 		return std::string("Rat "); | ||||
| 	} | ||||
| 
 | ||||
| 	/*
 | ||||
| 		Special methods | ||||
| 	*/ | ||||
| 	 | ||||
| 	void updateNodePos() | ||||
| 	{ | ||||
| 		if(m_node != NULL) | ||||
| 		{ | ||||
| 			m_node->setPosition(getAbsolutePos()); | ||||
| 			m_node->setRotation(v3f(0, -m_yaw+180, 0)); | ||||
| 		} | ||||
| 	} | ||||
| 	 | ||||
| protected: | ||||
| 	scene::IMeshSceneNode *m_node; | ||||
| 	float m_yaw; | ||||
| 
 | ||||
| 	float m_counter1; | ||||
| 	float m_counter2; | ||||
| 	// Client-side moving
 | ||||
| 	v3f m_oldpos; | ||||
| 	f32 m_pos_animation_counter; | ||||
| 	f32 m_pos_animation_time; | ||||
| 	f32 m_pos_animation_time_counter; | ||||
| 	v3f m_showpos; | ||||
| }; | ||||
| 
 | ||||
| class SignObject : public MapBlockObject | ||||
| @ -524,7 +401,7 @@ public: | ||||
| 
 | ||||
| 		updateSceneNode(); | ||||
| 	} | ||||
| 	virtual bool serverStep(float dtime) | ||||
| 	virtual bool serverStep(float dtime, u32 daynight_ratio) | ||||
| 	{ | ||||
| 		return false; | ||||
| 	} | ||||
| @ -596,6 +473,28 @@ public: | ||||
| 			m_node = NULL; | ||||
| 		} | ||||
| 	} | ||||
| 	virtual void updateLight(u8 light_at_pos) | ||||
| 	{ | ||||
| 		if(m_node == NULL) | ||||
| 			return; | ||||
| 
 | ||||
| 		u8 li = decode_light(light_at_pos); | ||||
| 		video::SColor color(255,li,li,li); | ||||
| 
 | ||||
| 		scene::IMesh *mesh = m_node->getMesh(); | ||||
| 		 | ||||
| 		u16 mc = mesh->getMeshBufferCount(); | ||||
| 		for(u16 j=0; j<mc; j++) | ||||
| 		{ | ||||
| 			scene::IMeshBuffer *buf = mesh->getMeshBuffer(j); | ||||
| 			video::S3DVertex *vertices = (video::S3DVertex*)buf->getVertices(); | ||||
| 			u16 vc = buf->getVertexCount(); | ||||
| 			for(u16 i=0; i<vc; i++) | ||||
| 			{ | ||||
| 				vertices[i].Color = color; | ||||
| 			} | ||||
| 		} | ||||
| 	} | ||||
| #endif | ||||
| 
 | ||||
| 	virtual std::string infoText() | ||||
| @ -644,6 +543,177 @@ protected: | ||||
| 	f32 m_yaw; | ||||
| }; | ||||
| 
 | ||||
| class RatObject : public MovingObject | ||||
| { | ||||
| public: | ||||
| 	RatObject(MapBlock *block, s16 id, v3f pos): | ||||
| 		MovingObject(block, id, pos), | ||||
| 		m_node(NULL) | ||||
| 	{ | ||||
| 		m_collision_box = new core::aabbox3d<f32> | ||||
| 				(-BS*0.3,-BS*.25,-BS*0.3, BS*0.3,BS*0.25,BS*0.3); | ||||
| 		m_selection_box = new core::aabbox3d<f32> | ||||
| 				(-BS*0.3,-BS*.25,-BS*0.3, BS*0.3,BS*0.25,BS*0.3); | ||||
| 
 | ||||
| 		m_counter1 = 0; | ||||
| 		m_counter2 = 0; | ||||
| 		m_age = 0; | ||||
| 	} | ||||
| 	virtual ~RatObject() | ||||
| 	{ | ||||
| 		delete m_collision_box; | ||||
| 		delete m_selection_box; | ||||
| 	} | ||||
| 	 | ||||
| 	/*
 | ||||
| 		Implementation interface | ||||
| 	*/ | ||||
| 	virtual u16 getTypeId() const | ||||
| 	{ | ||||
| 		return MAPBLOCKOBJECT_TYPE_RAT; | ||||
| 	} | ||||
| 	virtual void serialize(std::ostream &os, u8 version) | ||||
| 	{ | ||||
| 		MovingObject::serialize(os, version); | ||||
| 		u8 buf[2]; | ||||
| 
 | ||||
| 		// Write yaw * 10
 | ||||
| 		writeS16(buf, m_yaw * 10); | ||||
| 		os.write((char*)buf, 2); | ||||
| 
 | ||||
| 	} | ||||
| 	virtual void update(std::istream &is, u8 version) | ||||
| 	{ | ||||
| 		MovingObject::update(is, version); | ||||
| 		u8 buf[2]; | ||||
| 		 | ||||
| 		// Read yaw * 10
 | ||||
| 		is.read((char*)buf, 2); | ||||
| 		s16 yaw_i = readS16(buf); | ||||
| 		m_yaw = (f32)yaw_i / 10; | ||||
| 
 | ||||
| 		updateNodePos(); | ||||
| 	} | ||||
| 
 | ||||
| 	virtual bool serverStep(float dtime, u32 daynight_ratio) | ||||
| 	{ | ||||
| 		m_age += dtime; | ||||
| 		if(m_age > 60) | ||||
| 			// Die
 | ||||
| 			return true; | ||||
| 
 | ||||
| 		v3f dir(cos(m_yaw/180*PI),0,sin(m_yaw/180*PI)); | ||||
| 
 | ||||
| 		f32 speed = 2*BS; | ||||
| 
 | ||||
| 		m_speed.X = speed * dir.X; | ||||
| 		m_speed.Z = speed * dir.Z; | ||||
| 
 | ||||
| 		if(m_touching_ground && (m_oldpos - m_pos).getLength() < dtime*speed/2) | ||||
| 		{ | ||||
| 			m_counter1 -= dtime; | ||||
| 			if(m_counter1 < 0.0) | ||||
| 			{ | ||||
| 				m_counter1 += 1.0; | ||||
| 				m_speed.Y = 5.0*BS; | ||||
| 			} | ||||
| 		} | ||||
| 
 | ||||
| 		{ | ||||
| 			m_counter2 -= dtime; | ||||
| 			if(m_counter2 < 0.0) | ||||
| 			{ | ||||
| 				m_counter2 += (float)(rand()%100)/100*3.0; | ||||
| 				m_yaw += ((float)(rand()%200)-100)/100*180; | ||||
| 				m_yaw = wrapDegrees(m_yaw); | ||||
| 			} | ||||
| 		} | ||||
| 
 | ||||
| 		m_oldpos = m_pos; | ||||
| 
 | ||||
| 		//m_yaw += dtime*90;
 | ||||
| 
 | ||||
| 		move(dtime, v3f(0, -9.81*BS, 0)); | ||||
| 
 | ||||
| 		//updateNodePos();
 | ||||
| 
 | ||||
| 		return false; | ||||
| 	} | ||||
| #ifndef SERVER | ||||
| 	virtual void clientStep(float dtime) | ||||
| 	{ | ||||
| 		//m_pos += m_speed * dtime;
 | ||||
| 		MovingObject::simpleMove(dtime); | ||||
| 
 | ||||
| 		updateNodePos(); | ||||
| 	} | ||||
| 	 | ||||
| 	virtual void addToScene(scene::ISceneManager *smgr); | ||||
| 
 | ||||
| 	virtual void removeFromScene() | ||||
| 	{ | ||||
| 		if(m_node == NULL) | ||||
| 			return; | ||||
| 
 | ||||
| 		m_node->remove(); | ||||
| 		m_node = NULL; | ||||
| 	} | ||||
| 
 | ||||
| 	virtual void updateLight(u8 light_at_pos) | ||||
| 	{ | ||||
| 		if(m_node == NULL) | ||||
| 			return; | ||||
| 
 | ||||
| 		u8 li = decode_light(light_at_pos); | ||||
| 		video::SColor color(255,li,li,li); | ||||
| 
 | ||||
| 		scene::IMesh *mesh = m_node->getMesh(); | ||||
| 		 | ||||
| 		u16 mc = mesh->getMeshBufferCount(); | ||||
| 		for(u16 j=0; j<mc; j++) | ||||
| 		{ | ||||
| 			scene::IMeshBuffer *buf = mesh->getMeshBuffer(j); | ||||
| 			video::S3DVertex *vertices = (video::S3DVertex*)buf->getVertices(); | ||||
| 			u16 vc = buf->getVertexCount(); | ||||
| 			for(u16 i=0; i<vc; i++) | ||||
| 			{ | ||||
| 				vertices[i].Color = color; | ||||
| 			} | ||||
| 		} | ||||
| 	} | ||||
| 	 | ||||
| #endif | ||||
| 
 | ||||
| 	virtual std::string getInventoryString() | ||||
| 	{ | ||||
| 		// There must be a space after the name
 | ||||
| 		// Or does there?
 | ||||
| 		return std::string("Rat "); | ||||
| 	} | ||||
| 
 | ||||
| 	/*
 | ||||
| 		Special methods | ||||
| 	*/ | ||||
| 	 | ||||
| 	void updateNodePos() | ||||
| 	{ | ||||
| 		if(m_node == NULL) | ||||
| 			return; | ||||
| 
 | ||||
| 		m_node->setPosition(getAbsoluteShowPos()); | ||||
| 		m_node->setRotation(v3f(0, -m_yaw+180, 0)); | ||||
| 	} | ||||
| 	 | ||||
| protected: | ||||
| 	scene::IMeshSceneNode *m_node; | ||||
| 	float m_yaw; | ||||
| 
 | ||||
| 	float m_counter1; | ||||
| 	float m_counter2; | ||||
| 	v3f m_oldpos; | ||||
| 	float m_age; | ||||
| }; | ||||
| 
 | ||||
| struct DistanceSortedObject | ||||
| { | ||||
| 	DistanceSortedObject(MapBlockObject *a_obj, f32 a_d) | ||||
| @ -666,12 +736,16 @@ class MapBlockObjectList | ||||
| public: | ||||
| 	MapBlockObjectList(MapBlock *block); | ||||
| 	~MapBlockObjectList(); | ||||
| 
 | ||||
| 	// Writes the count, id, the type id and the parameters of all objects
 | ||||
| 	void serialize(std::ostream &os, u8 version); | ||||
| 
 | ||||
| 	// Reads ids, type_ids and parameters.
 | ||||
| 	// Creates, updates and deletes objects.
 | ||||
| 	// If smgr!=NULL, new objects are added to the scene
 | ||||
| 	void update(std::istream &is, u8 version, scene::ISceneManager *smgr); | ||||
| 	void update(std::istream &is, u8 version, scene::ISceneManager *smgr, | ||||
| 			u32 daynight_ratio); | ||||
| 
 | ||||
| 	// Finds a new unique id
 | ||||
| 	s16 getFreeId() throw(ContainerFullException); | ||||
| 	/*
 | ||||
| @ -706,7 +780,7 @@ public: | ||||
| 
 | ||||
| 	// Steps all objects and if server==true, removes those that
 | ||||
| 	// want to be removed
 | ||||
| 	void step(float dtime, bool server); | ||||
| 	void step(float dtime, bool server, u32 daynight_ratio); | ||||
| 
 | ||||
| 	// Wraps an object that wants to move onto this block from an another
 | ||||
| 	// Returns true if wrapping was impossible
 | ||||
| @ -727,6 +801,8 @@ private: | ||||
| 	// Key is id
 | ||||
| 	core::map<s16, MapBlockObject*> m_objects; | ||||
| 	MapBlock *m_block; | ||||
| 
 | ||||
| 	u32 m_last_update_daynight_ratio; | ||||
| }; | ||||
| 
 | ||||
| 
 | ||||
|  | ||||
| @ -399,6 +399,7 @@ struct MapNode | ||||
| 	} | ||||
| 	 | ||||
| 	// 0 <= daylight_factor <= 1000
 | ||||
| 	// 0 <= return value <= LIGHT_SUN
 | ||||
| 	u8 getLightBlend(u32 daylight_factor) | ||||
| 	{ | ||||
| 		u8 l = ((daylight_factor * getLight(LIGHTBANK_DAY) | ||||
| @ -411,6 +412,17 @@ struct MapNode | ||||
| 			l = max; | ||||
| 		return l; | ||||
| 	} | ||||
| 	/*// 0 <= daylight_factor <= 1000
 | ||||
| 	// 0 <= return value <= 255
 | ||||
| 	u8 getLightBlend(u32 daylight_factor) | ||||
| 	{ | ||||
| 		u8 daylight = decode_light(getLight(LIGHTBANK_DAY)); | ||||
| 		u8 nightlight = decode_light(getLight(LIGHTBANK_NIGHT)); | ||||
| 		u8 mix = ((daylight_factor * daylight | ||||
| 			+ (1000-daylight_factor) * nightlight) | ||||
| 			)/1000; | ||||
| 		return mix; | ||||
| 	}*/ | ||||
| 
 | ||||
| 	void setLight(enum LightBank bank, u8 a_light) | ||||
| 	{ | ||||
|  | ||||
| @ -24,11 +24,48 @@ with this program; if not, write to the Free Software Foundation, Inc., | ||||
| #ifndef PORTING_HEADER | ||||
| #define PORTING_HEADER | ||||
| 
 | ||||
| // Included for u64 and such
 | ||||
| #include "common_irrlicht.h" | ||||
| 
 | ||||
| #ifdef _WIN32 | ||||
| 	#define SWPRINTF_CHARSTRING L"%S" | ||||
| #else | ||||
| 	#define SWPRINTF_CHARSTRING L"%s" | ||||
| #endif | ||||
| 
 | ||||
| #ifdef _WIN32 | ||||
| 	#include <windows.h> | ||||
| 	#define sleep_ms(x) Sleep(x) | ||||
| #else | ||||
| 	#include <unistd.h> | ||||
| 	#define sleep_ms(x) usleep(x*1000) | ||||
| #endif | ||||
| 
 | ||||
| namespace porting | ||||
| { | ||||
| 
 | ||||
| /*
 | ||||
| 	Resolution is 10-20ms. | ||||
| 	Remember to check for overflows. | ||||
| 	Overflow can occur at any value higher than 10000000. | ||||
| */ | ||||
| #ifdef _WIN32 // Windows
 | ||||
| 	#include <windows.h> | ||||
| 	inline u32 getTimeMs() | ||||
| 	{ | ||||
| 		return GetTickCount(); | ||||
| 	} | ||||
| #else // Posix
 | ||||
| 	#include <sys/timeb.h> | ||||
| 	inline u32 getTimeMs() | ||||
| 	{ | ||||
| 		struct timeb tb; | ||||
| 		ftime(&tb); | ||||
| 		return tb.time * 1000 + tb.millitm; | ||||
| 	} | ||||
| #endif | ||||
| 
 | ||||
| } // namespace porting
 | ||||
| 
 | ||||
| #endif | ||||
| 
 | ||||
|  | ||||
| @ -663,8 +663,6 @@ void RemoteClient::SendObjectData( | ||||
| 		- Add blocks to emerge queue if they are not found | ||||
| 
 | ||||
| 		SUGGESTION: These could be ignored from the backside of the player | ||||
| 
 | ||||
| 		TODO: Keep track of total size of packet and stop when it is too big | ||||
| 	*/ | ||||
| 
 | ||||
| 	Player *player = server->m_env.getPlayer(peer_id); | ||||
| @ -675,13 +673,11 @@ void RemoteClient::SendObjectData( | ||||
| 	v3s16 center_nodepos = floatToInt(playerpos); | ||||
| 	v3s16 center = getNodeBlockPos(center_nodepos); | ||||
| 
 | ||||
| 	//s16 d_max = ACTIVE_OBJECT_D_BLOCKS;
 | ||||
| 	s16 d_max = g_settings.getS16("active_object_range"); | ||||
| 	 | ||||
| 	// Number of blocks whose objects were written to bos
 | ||||
| 	u16 blockcount = 0; | ||||
| 
 | ||||
| 	//core::map<v3s16, MapBlock*> blocks;
 | ||||
| 	std::ostringstream bos(std::ios_base::binary); | ||||
| 
 | ||||
| 	for(s16 d = 0; d <= d_max; d++) | ||||
| @ -710,18 +706,20 @@ void RemoteClient::SendObjectData( | ||||
| 			// Get block
 | ||||
| 			MapBlock *block = server->m_env.getMap().getBlockNoCreate(p); | ||||
| 
 | ||||
| 			// Skip block if there are no objects
 | ||||
| 			if(block->getObjectCount() == 0) | ||||
| 				continue; | ||||
| 			 | ||||
| 			// Step block if not in stepped_blocks and add to stepped_blocks
 | ||||
| 			/*
 | ||||
| 				Step block if not in stepped_blocks and add to stepped_blocks. | ||||
| 			*/ | ||||
| 			if(stepped_blocks.find(p) == NULL) | ||||
| 			{ | ||||
| 				block->stepObjects(dtime, true); | ||||
| 				block->stepObjects(dtime, true, server->getDayNightRatio()); | ||||
| 				stepped_blocks.insert(p, true); | ||||
| 				block->setChangedFlag(); | ||||
| 			} | ||||
| 
 | ||||
| 			// Skip block if there are no objects
 | ||||
| 			if(block->getObjectCount() == 0) | ||||
| 				continue; | ||||
| 			 | ||||
| 			/*
 | ||||
| 				Write objects | ||||
| 			*/ | ||||
|  | ||||
							
								
								
									
										12
									
								
								src/server.h
									
									
									
									
									
								
							
							
						
						
									
										12
									
								
								src/server.h
									
									
									
									
									
								
							| @ -398,6 +398,18 @@ public: | ||||
| 	//void SendSectorMeta(u16 peer_id, core::list<v2s16> ps, u8 ver);
 | ||||
| 
 | ||||
| 	core::list<PlayerInfo> getPlayerInfo(); | ||||
| 
 | ||||
| 	u32 getDayNightRatio() | ||||
| 	{ | ||||
| 		s32 d = 8; | ||||
| 		s32 t = (((m_time_of_day.get() + 24000/d/2)%24000)/(24000/d)); | ||||
| 		if(t == d/4 || t == (d-d/4)) | ||||
| 			return 600; | ||||
| 		else if(t < d/4 || t > (d-d/4)) | ||||
| 			return 300; | ||||
| 		else | ||||
| 			return 1000; | ||||
| 	} | ||||
| 	 | ||||
| private: | ||||
| 
 | ||||
|  | ||||
| @ -20,7 +20,6 @@ with this program; if not, write to the Free Software Foundation, Inc., | ||||
| /*
 | ||||
| =============================== NOTES ============================== | ||||
| 
 | ||||
| TODO: Move the default settings into some separate file | ||||
| 
 | ||||
| */ | ||||
| 
 | ||||
| @ -49,15 +48,6 @@ TODO: Move the default settings into some separate file | ||||
| #pragma comment(lib, "zlibwapi.lib") | ||||
| #endif | ||||
| 
 | ||||
| #ifdef _WIN32 | ||||
| 	#define WIN32_LEAN_AND_MEAN | ||||
| 	#include <windows.h> | ||||
| 	#define sleep_ms(x) Sleep(x) | ||||
| #else | ||||
| 	#include <unistd.h> | ||||
| 	#define sleep_ms(x) usleep(x*1000) | ||||
| #endif | ||||
| 
 | ||||
| #include <iostream> | ||||
| #include <fstream> | ||||
| #include <time.h> | ||||
| @ -75,9 +65,7 @@ TODO: Move the default settings into some separate file | ||||
| #include "constants.h" | ||||
| #include "strfnd.h" | ||||
| #include "porting.h" | ||||
| 
 | ||||
| // Dummy variable
 | ||||
| IrrlichtDevice *g_device = NULL; | ||||
| //#include "irrlichtwrapper.h"
 | ||||
| 
 | ||||
| /*
 | ||||
| 	Settings. | ||||
| @ -106,21 +94,15 @@ std::ostream *derr_client_ptr = &dstream; | ||||
| 
 | ||||
| 
 | ||||
| /*
 | ||||
| 	Timestamp stuff | ||||
| 	gettime.h implementation | ||||
| */ | ||||
| 
 | ||||
| JMutex g_timestamp_mutex; | ||||
| 
 | ||||
| std::string getTimestamp() | ||||
| u32 getTimeMs() | ||||
| { | ||||
| 	if(g_timestamp_mutex.IsInitialized()==false) | ||||
| 		return ""; | ||||
| 	JMutexAutoLock lock(g_timestamp_mutex); | ||||
| 	time_t t = time(NULL); | ||||
| 	struct tm *tm = localtime(&t); | ||||
| 	char cs[20]; | ||||
| 	strftime(cs, 20, "%H:%M:%S", tm); | ||||
| 	return cs; | ||||
| 	/*
 | ||||
| 		Use imprecise system calls directly (from porting.h) | ||||
| 	*/ | ||||
| 	return porting::getTimeMs(); | ||||
| } | ||||
| 
 | ||||
| int main(int argc, char *argv[]) | ||||
| @ -211,9 +193,6 @@ int main(int argc, char *argv[]) | ||||
| 	sockets_init(); | ||||
| 	atexit(sockets_cleanup); | ||||
| 	 | ||||
| 	// Initialize timestamp mutex
 | ||||
| 	g_timestamp_mutex.Init(); | ||||
| 
 | ||||
| 	/*
 | ||||
| 		Initialization | ||||
| 	*/ | ||||
|  | ||||
| @ -18,7 +18,7 @@ with this program; if not, write to the Free Software Foundation, Inc., | ||||
| */ | ||||
| 
 | ||||
| #include "tile.h" | ||||
| #include "irrlichtwrapper.h" | ||||
| #include "main.h" | ||||
| 
 | ||||
| // A mapping from tiles to paths of textures
 | ||||
| const char * g_tile_texture_paths[TILES_COUNT] = | ||||
|  | ||||
| @ -23,33 +23,21 @@ with this program; if not, write to the Free Software Foundation, Inc., | ||||
| 
 | ||||
| #include "utility.h" | ||||
| #include "irrlichtwrapper.h" | ||||
| #include "gettime.h" | ||||
| 
 | ||||
| TimeTaker::TimeTaker(const char *name, IrrlichtWrapper *irrlicht, u32 *result) | ||||
| TimeTaker::TimeTaker(const char *name, u32 *result) | ||||
| { | ||||
| 	m_name = name; | ||||
| 	m_irrlicht = irrlicht; | ||||
| 	m_result = result; | ||||
| 	m_running = true; | ||||
| 	if(irrlicht == NULL) | ||||
| 	{ | ||||
| 		m_time1 = 0; | ||||
| 		return; | ||||
| 	} | ||||
| 	m_time1 = m_irrlicht->getTime(); | ||||
| 	m_time1 = getTimeMs(); | ||||
| } | ||||
| 
 | ||||
| u32 TimeTaker::stop(bool quiet) | ||||
| { | ||||
| 	if(m_running) | ||||
| 	{ | ||||
| 		if(m_irrlicht == NULL) | ||||
| 		{ | ||||
| 			/*if(quiet == false)
 | ||||
| 				std::cout<<"Couldn't measure time for "<<m_name | ||||
| 						<<": irrlicht==NULL"<<std::endl;*/ | ||||
| 			return 0; | ||||
| 		} | ||||
| 		u32 time2 = m_irrlicht->getTime(); | ||||
| 		u32 time2 = getTimeMs(); | ||||
| 		u32 dtime = time2 - m_time1; | ||||
| 		if(m_result != NULL) | ||||
| 		{ | ||||
|  | ||||
| @ -28,18 +28,11 @@ with this program; if not, write to the Free Software Foundation, Inc., | ||||
| #include <jmutex.h> | ||||
| #include <jmutexautolock.h> | ||||
| 
 | ||||
| #ifdef _WIN32 | ||||
| 	#include <windows.h> | ||||
| 	#define sleep_ms(x) Sleep(x) | ||||
| #else | ||||
| 	#include <unistd.h> | ||||
| 	#define sleep_ms(x) usleep(x*1000) | ||||
| #endif | ||||
| 
 | ||||
| #include "common_irrlicht.h" | ||||
| #include "debug.h" | ||||
| #include "strfnd.h" | ||||
| #include "exceptions.h" | ||||
| #include "porting.h" | ||||
| 
 | ||||
| extern const v3s16 g_26dirs[26]; | ||||
| 
 | ||||
| @ -404,7 +397,7 @@ class IrrlichtWrapper; | ||||
| class TimeTaker | ||||
| { | ||||
| public: | ||||
| 	TimeTaker(const char *name, IrrlichtWrapper *irrlicht, u32 *result=NULL); | ||||
| 	TimeTaker(const char *name, u32 *result=NULL); | ||||
| 
 | ||||
| 	~TimeTaker() | ||||
| 	{ | ||||
| @ -415,7 +408,6 @@ public: | ||||
| 
 | ||||
| private: | ||||
| 	const char *m_name; | ||||
| 	IrrlichtWrapper *m_irrlicht; | ||||
| 	u32 m_time1; | ||||
| 	bool m_running; | ||||
| 	u32 *m_result; | ||||
|  | ||||
| @ -21,8 +21,8 @@ with this program; if not, write to the Free Software Foundation, Inc., | ||||
| #include "map.h" | ||||
| 
 | ||||
| // For TimeTaker
 | ||||
| #include "main.h" | ||||
| #include "utility.h" | ||||
| #include "gettime.h" | ||||
| 
 | ||||
| /*
 | ||||
| 	Debug stuff | ||||
| @ -138,7 +138,7 @@ void VoxelManipulator::addArea(VoxelArea area) | ||||
| 	if(m_area.contains(area)) | ||||
| 		return; | ||||
| 	 | ||||
| 	TimeTaker timer("addArea", g_irrlicht, &addarea_time); | ||||
| 	TimeTaker timer("addArea", &addarea_time); | ||||
| 
 | ||||
| 	// Calculate new area
 | ||||
| 	VoxelArea new_area; | ||||
| @ -290,7 +290,7 @@ void VoxelManipulator::interpolate(VoxelArea area) | ||||
| void VoxelManipulator::clearFlag(u8 flags) | ||||
| { | ||||
| 	// 0-1ms on moderate area
 | ||||
| 	TimeTaker timer("clearFlag", g_irrlicht, &clearflag_time); | ||||
| 	TimeTaker timer("clearFlag", &clearflag_time); | ||||
| 
 | ||||
| 	v3s16 s = m_area.getExtent(); | ||||
| 
 | ||||
| @ -539,8 +539,7 @@ void VoxelManipulator::updateAreaWaterPressure(VoxelArea a, | ||||
| 		core::map<v3s16, u8> &active_nodes, | ||||
| 		bool checked3_is_clear) | ||||
| { | ||||
| 	TimeTaker timer("updateAreaWaterPressure", g_irrlicht, | ||||
| 			&updateareawaterpressure_time); | ||||
| 	TimeTaker timer("updateAreaWaterPressure", &updateareawaterpressure_time); | ||||
| 
 | ||||
| 	emerge(a, 3); | ||||
| 	 | ||||
| @ -653,7 +652,7 @@ bool VoxelManipulator::flowWater(v3s16 removed_pos, | ||||
| 	//dstream<<"s1="<<s1<<", s2="<<s2<<std::endl;
 | ||||
| 
 | ||||
| 	{ | ||||
| 	TimeTaker timer1("flowWater pre", g_irrlicht, &flowwater_pre_time); | ||||
| 	TimeTaker timer1("flowWater pre", &flowwater_pre_time); | ||||
| 	 | ||||
| 	// Load neighboring nodes
 | ||||
| 	emerge(VoxelArea(removed_pos - v3s16(1,1,1), removed_pos + v3s16(1,1,1)), 4); | ||||
| @ -802,9 +801,9 @@ bool VoxelManipulator::flowWater(v3s16 removed_pos, | ||||
| 				debugprint, stoptime); | ||||
| 	} | ||||
| 	 | ||||
| 	if(stoptime != 0 && g_irrlicht != NULL) | ||||
| 	if(stoptime != 0) | ||||
| 	{ | ||||
| 		u32 timenow = g_irrlicht->getTime(); | ||||
| 		u32 timenow = getTimeMs(); | ||||
| 		if(timenow >= stoptime || | ||||
| 				(stoptime < 0x80000000 && timenow > 0x80000000)) | ||||
| 		{ | ||||
| @ -876,10 +875,7 @@ void VoxelManipulator::flowWater( | ||||
| 
 | ||||
| 
 | ||||
| 	u32 stoptime = 0; | ||||
| 	if(g_irrlicht != NULL) | ||||
| 	{ | ||||
| 		stoptime = g_irrlicht->getTime() + timelimit; | ||||
| 	} | ||||
| 	stoptime = getTimeMs() + timelimit; | ||||
| 
 | ||||
| 	// Count of handled active nodes
 | ||||
| 	u32 handled_count = 0; | ||||
|  | ||||
		Loading…
	
		Reference in New Issue
	
	Block a user