mirror of
				https://github.com/vcmi/vcmi.git
				synced 2025-10-31 00:07:39 +02:00 
			
		
		
		
	- Fixed crash caused by randomShuffle
- Banned Magic Spring as it has 2 visitable positions
This commit is contained in:
		| @@ -6,13 +6,14 @@ | ||||
| 		"handler": "magicSpring", | ||||
| 		"types" : { | ||||
| 			"object" : { | ||||
| 				"index" : 0, | ||||
| 				"rmg" : { | ||||
| 					"zoneLimit"	: 1, | ||||
| 					"mapLimit"	: 32, | ||||
| 					"value"		: 500, | ||||
| 					"rarity"	: 50 | ||||
| 				} | ||||
| 				"index" : 0//, | ||||
| 				//"rmg" : { | ||||
| 				//	"zoneLimit"	: 1, | ||||
| 				//	"mapLimit"	: 32, | ||||
| 				//	"value"		: 500, | ||||
| 				//	"rarity"	: 50 | ||||
| 				//} | ||||
| 				//banned due to problems with 2 viistable offsets | ||||
| 			} | ||||
| 		} | ||||
| 	}, | ||||
|   | ||||
| @@ -117,7 +117,7 @@ namespace RandomGeneratorUtil | ||||
| 		int n = (container.end() - container.begin()); | ||||
| 		for (int i = n-1; i>0; --i) | ||||
| 		{ | ||||
| 			std::swap (container.begin()[i],container.begin()[rand.nextInt(i+1)]); | ||||
| 			std::swap (container.begin()[i],container.begin()[rand.nextInt(i)]); | ||||
| 		} | ||||
| 	} | ||||
| } | ||||
|   | ||||
| @@ -23,34 +23,31 @@ | ||||
|  * | ||||
|  */ | ||||
|  | ||||
| namespace vstd | ||||
| static bool isOnVisitableFromTopList(int identifier, int type) | ||||
| { | ||||
| 	static bool isVisitableFromTop(int identifier, int type) | ||||
| 	{ | ||||
| 		if(type == 2 || type == 3 || type == 4 || type == 5) //creature, hero, artifact, resource | ||||
| 			return true; | ||||
| 	if(type == 2 || type == 3 || type == 4 || type == 5) //creature, hero, artifact, resource | ||||
| 		return true; | ||||
|  | ||||
| 		static const Obj visitableFromTop[] = | ||||
| 			{Obj::FLOTSAM, | ||||
| 			Obj::SEA_CHEST, | ||||
| 			Obj::SHIPWRECK_SURVIVOR, | ||||
| 			Obj::BUOY, | ||||
| 			Obj::OCEAN_BOTTLE, | ||||
| 			Obj::BOAT, | ||||
| 			Obj::WHIRLPOOL, | ||||
| 			Obj::GARRISON, | ||||
| 			Obj::GARRISON2, | ||||
| 			Obj::SCHOLAR, | ||||
| 			Obj::CAMPFIRE, | ||||
| 			Obj::BORDERGUARD, | ||||
| 			Obj::BORDER_GATE, | ||||
| 			Obj::QUEST_GUARD, | ||||
| 			Obj::CORPSE | ||||
| 		}; | ||||
| 		if (vstd::find_pos(visitableFromTop, identifier) != -1) | ||||
| 			return true; | ||||
| 		return false; | ||||
| 	} | ||||
| 	static const Obj visitableFromTop[] = | ||||
| 		{Obj::FLOTSAM, | ||||
| 		Obj::SEA_CHEST, | ||||
| 		Obj::SHIPWRECK_SURVIVOR, | ||||
| 		Obj::BUOY, | ||||
| 		Obj::OCEAN_BOTTLE, | ||||
| 		Obj::BOAT, | ||||
| 		Obj::WHIRLPOOL, | ||||
| 		Obj::GARRISON, | ||||
| 		Obj::GARRISON2, | ||||
| 		Obj::SCHOLAR, | ||||
| 		Obj::CAMPFIRE, | ||||
| 		Obj::BORDERGUARD, | ||||
| 		Obj::BORDER_GATE, | ||||
| 		Obj::QUEST_GUARD, | ||||
| 		Obj::CORPSE | ||||
| 	}; | ||||
| 	if (vstd::find_pos(visitableFromTop, identifier) != -1) | ||||
| 		return true; | ||||
| 	return false; | ||||
| } | ||||
|  | ||||
| ObjectTemplate::ObjectTemplate(): | ||||
| @@ -109,7 +106,7 @@ void ObjectTemplate::readTxt(CLegacyConfigParser & parser) | ||||
| 	int type  = boost::lexical_cast<int>(strings[7]); | ||||
| 	printPriority = boost::lexical_cast<int>(strings[8]) * 100; // to have some space in future | ||||
|  | ||||
| 	if (vstd::isVisitableFromTop(id, type)) | ||||
| 	if (isOnVisitableFromTopList(id, type)) | ||||
| 		visitDir = 0xff; | ||||
| 	else | ||||
| 		visitDir = (8|16|32|64|128); | ||||
| @@ -171,7 +168,7 @@ void ObjectTemplate::readMap(CBinaryReader & reader) | ||||
| 	int type = reader.readUInt8(); | ||||
| 	printPriority = reader.readUInt8() * 100; // to have some space in future | ||||
|  | ||||
| 	if (vstd::isVisitableFromTop(id, type)) | ||||
| 	if (isOnVisitableFromTopList(id, type)) | ||||
| 		visitDir = 0xff; | ||||
| 	else | ||||
| 		visitDir = (8|16|32|64|128); | ||||
|   | ||||
| @@ -784,6 +784,25 @@ bool CRmgTemplateZone::createTreasurePile (CMapGenerator* gen, int3 &pos) | ||||
| 			return true; | ||||
| 		} | ||||
|  | ||||
| 		//update boundary around our objects, including knowledge about objects visitable from bottom | ||||
|  | ||||
| 		boundary.clear(); | ||||
| 		for (auto tile : info.visitableFromBottomPositions) | ||||
| 		{ | ||||
| 			gen->foreach_neighbour (tile, [tile, &boundary](int3 pos) | ||||
| 			{ | ||||
| 				if (tile.y >= pos.y) //don't block these objects from above | ||||
| 					boundary.insert(pos); | ||||
| 			}); | ||||
| 		} | ||||
| 		for (auto tile : info.visitableFromTopPositions) | ||||
| 		{ | ||||
| 			gen->foreach_neighbour (tile, [&boundary](int3 pos) | ||||
| 			{ | ||||
| 				boundary.insert(pos); | ||||
| 			}); | ||||
| 		} | ||||
|  | ||||
| 		for (auto tile : boundary) //guard must be standing there | ||||
| 		{ | ||||
| 			if (gen->isFree(tile)) //this tile could be already blocked, don't place a monster here | ||||
| @@ -1403,6 +1422,8 @@ bool CRmgTemplateZone::guardObject(CMapGenerator* gen, CGObjectInstance* object, | ||||
|  | ||||
| ObjectInfo CRmgTemplateZone::getRandomObject (CMapGenerator* gen, CTreasurePileInfo &info, ui32 value) | ||||
| { | ||||
| 	//int objectsVisitableFromBottom = 0; //for debug | ||||
|  | ||||
| 	std::vector<std::pair<ui32, ObjectInfo>> tresholds; | ||||
| 	ui32 total = 0; | ||||
|  | ||||
| @@ -1418,6 +1439,7 @@ ObjectInfo CRmgTemplateZone::getRandomObject (CMapGenerator* gen, CTreasurePileI | ||||
|  | ||||
| 			if (!oi.templ.isVisitableFromTop()) | ||||
| 			{ | ||||
| 				//objectsVisitableFromBottom++; | ||||
| 				//there must be free tiles under object | ||||
| 				if (!isAccessibleFromAnywhere(gen, oi.templ, newVisitablePos, oi.templ.getBlockedOffsets())) | ||||
| 					continue; | ||||
| @@ -1502,6 +1524,8 @@ ObjectInfo CRmgTemplateZone::getRandomObject (CMapGenerator* gen, CTreasurePileI | ||||
| 		} | ||||
| 	} | ||||
|  | ||||
| 	//logGlobal->infoStream() << boost::format ("Number of objects visitable  from bottom: %d") % objectsVisitableFromBottom; | ||||
|  | ||||
| 	//Generate pandora Box with gold if the value is extremely high | ||||
| 	ObjectInfo oi; | ||||
| 	if (tresholds.empty()) | ||||
|   | ||||
		Reference in New Issue
	
	Block a user