void GroupObjectImplementation::addGroupModifiers(CreatureObject* player) {
	if (player == NULL)
		return;

	Reference<CreatureObject*> leader = getLeader();

	if (leader == NULL)
		return;

	if (!leader->isPlayerCreature())
		return;

	int duration = 300;

	String action = "squadleader";

	if (player->hasBuff(action.hashCode()))
		player->removeBuff(action.hashCode());

	ManagedReference<SquadLeaderBuff*> buff = new SquadLeaderBuff(player, leader, action.hashCode(), duration);

	Locker locker(buff);

	buff->setSkillModifier("slope_move", leader->getSkillMod("group_slope_move"));
	buff->setSkillModifier("private_group_ranged_defense", leader->getSkillMod("group_ranged_defense"));
	buff->setSkillModifier("private_group_melee_defense", leader->getSkillMod("group_melee_defense"));
	buff->setSkillModifier("burst_run", leader->getSkillMod("group_burst_run"));
	player->addBuff(buff);

	buff->addObservers();
}
Reference<SceneObject*> SceneObjectImplementation::getCraftedComponentsSatchel() {
    
	Reference<SceneObject*> sceno = asSceneObject();
	if (sceno == NULL)
		return NULL;

	Reference<ZoneServer*> zServer = getZoneServer();

	if(zServer == NULL)
		return NULL;
	
	ManagedReference<SceneObject*> craftingComponents = sceno->getSlottedObject("crafted_components");
	ManagedReference<SceneObject*> craftingComponentsSatchel = NULL;
	
    
	if(craftingComponents == NULL) {

		/// Add Components to crafted object
		String craftingComponentsPath = "object/tangible/crafting/crafting_components_container.iff";
		craftingComponents = zServer->createObject(craftingComponentsPath.hashCode(), 1);

		Locker componentsLocker(craftingComponents);
		
		craftingComponents->setSendToClient(false);
		sceno->transferObject(craftingComponents, 4, false);

		craftingComponents->setContainerDefaultDenyPermission(ContainerPermissions::OPEN + ContainerPermissions::MOVEIN + ContainerPermissions::MOVEOUT + ContainerPermissions::MOVECONTAINER);
		craftingComponents->setContainerDefaultAllowPermission(0);
		craftingComponents->setContainerDenyPermission("owner", ContainerPermissions::OPEN + ContainerPermissions::MOVEIN + ContainerPermissions::MOVEOUT + ContainerPermissions::MOVECONTAINER);
		craftingComponents->setContainerDenyPermission("admin", ContainerPermissions::OPEN + ContainerPermissions::MOVEIN + ContainerPermissions::MOVEOUT + ContainerPermissions::MOVECONTAINER);
		craftingComponents->setContainerAllowPermission("owner", 0);
		craftingComponents->setContainerAllowPermission("admin", 0);
		craftingComponents->setContainerInheritPermissionsFromParent(false);

		//String craftingComponentsSatchelPath = "object/tangible/container/base/base_container_volume.iff";
		String craftingComponentsSatchelPath = "object/tangible/hopper/crafting_station_hopper/crafting_station_ingredient_hopper_large.iff";
		craftingComponentsSatchel = zServer->createObject(craftingComponentsSatchelPath.hashCode(), 1);

		Locker satchelLocker(craftingComponentsSatchel, craftingComponents);
		
		craftingComponentsSatchel->setContainerInheritPermissionsFromParent(false);
		craftingComponentsSatchel->setContainerDefaultDenyPermission(ContainerPermissions::OPEN + ContainerPermissions::MOVEIN + ContainerPermissions::MOVEOUT + ContainerPermissions::MOVECONTAINER);
		craftingComponentsSatchel->setContainerDefaultAllowPermission(0);
		craftingComponentsSatchel->setContainerAllowPermission("admin", ContainerPermissions::OPEN);
		craftingComponentsSatchel->setContainerDenyPermission("admin", ContainerPermissions::MOVEIN + ContainerPermissions::MOVEOUT + ContainerPermissions::MOVECONTAINER);
		craftingComponentsSatchel->setContainerAllowPermission("owner", 0);
		craftingComponentsSatchel->setContainerDenyPermission("owner", ContainerPermissions::OPEN + ContainerPermissions::MOVEIN + ContainerPermissions::MOVEOUT + ContainerPermissions::MOVECONTAINER);

		craftingComponents->transferObject(craftingComponentsSatchel, -1, false);

	} else {
		craftingComponentsSatchel = craftingComponents->getContainerObject(0);
	}
	
	return craftingComponentsSatchel;
}
CreatureObject* CreatureManagerImplementation::spawnCreatureAsBaby(uint32 templateCRC, float x, float z, float y, uint64 parentID) {
	CreatureTemplate* creoTempl = creatureTemplateManager->getTemplate(templateCRC);

	if (creoTempl == NULL || creoTempl->getTame() <= 0)
		return NULL;

	CreatureObject* creo = NULL;

	String templateToSpawn = getTemplateToSpawn(templateCRC);
	uint32 objectCRC = templateToSpawn.hashCode();

	creo = createCreature(objectCRC, false, templateCRC);

	if (creo != NULL && creo->isCreature()) {
		Creature* creature = cast<Creature*>(creo);
		creature->loadTemplateDataForBaby(creoTempl);
	} else {
		error("could not spawn template " + templateToSpawn + " as baby.");
		creo = NULL;
	}

	placeCreature(creo, x, z, y, parentID);

	if (creo != NULL && creo->isAiAgent())
		cast<AiAgent*>(creo)->activateLoad("");
	else {
		error("could not spawn template " + templateToSpawn + " as baby with AI.");
		creo = NULL;
	}

	return creo;
}
CreatureObject* CreatureManagerImplementation::spawnCreatureAsEventMob(uint32 templateCRC, float x, float z, float y, uint64 parentID) {
	CreatureTemplate* creoTempl = creatureTemplateManager->getTemplate(templateCRC);

	if (creoTempl == NULL)
		return NULL;

	CreatureObject* creo = NULL;

	String templateToSpawn = getTemplateToSpawn(templateCRC);
	uint32 objectCRC = templateToSpawn.hashCode();

	creo = createCreature(objectCRC, false, templateCRC);

	if (creo != NULL && creo->isAiAgent()) {
		AiAgent* creature = cast<AiAgent*>(creo);
		creature->loadTemplateData(creoTempl);

		UnicodeString eventName;
		eventName = creature->getDisplayedName() + " (event)";
		creature->setCustomObjectName(eventName, false);

	} else if (creo == NULL) {
		error("could not spawn template " + templateToSpawn);
	}

	placeCreature(creo, x, z, y, parentID);

	if (creo != NULL && creo->isAiAgent())
		cast<AiAgent*>(creo)->activateLoad("");

	return creo;
}
CreatureObject* CreatureManagerImplementation::spawnCreature(uint32 templateCRC, uint32 objectCRC, float x, float z, float y, uint64 parentID, bool persistent) {
	CreatureTemplate* creoTempl = creatureTemplateManager->getTemplate(templateCRC);

	if (creoTempl == NULL)
		return spawnCreature(objectCRC, x, z, y, parentID);

	CreatureObject* creature = NULL;

	String templateToSpawn;

	if (objectCRC == 0) {
		templateToSpawn = getTemplateToSpawn(templateCRC);
		objectCRC = templateToSpawn.hashCode();
	}

	creature = createCreature(objectCRC, persistent, templateCRC);

	if (creature != NULL && creature->isAiAgent()) {
		AiAgent* npc = cast<AiAgent*>(creature);
		npc->loadTemplateData(creoTempl);
	} else if (creature == NULL) {
		error("could not spawn template " + templateToSpawn);
	}

	placeCreature(creature, x, z, y, parentID);

	return creature;
}
Reference<ResourceContainer*> ResourceSpawnImplementation::createResource(int units) {
   	Reference<ResourceContainer*> newResource = NULL;

   	newResource = (getZoneServer()->createObject(containerCRC, 2)).castTo<ResourceContainer*>();

   	if(newResource == NULL) {
   		error("Unable to create resource container, using generic.  CRC attempted was: " + String::valueOf(containerCRC));
   		print();
   		String genericContainer = "object/resource_container/organic_food.iff";
   		newResource = (getZoneServer()->createObject(genericContainer.hashCode(), 2)).castTo<ResourceContainer*>();
   	}

   	Locker locker(newResource);

   	newResource->setSpawnObject(_this.getReferenceUnsafeStaticCast());

   	if (units != 0)
   		newResource->setQuantity(units);

   	String resourceName = getFinalClass() + " (" + getName() + ")"; 
    	newResource->setCustomObjectName(resourceName, false);

   	++containerReferenceCount;

   	return newResource;
}
void ScavengerDroidImplementation::sendItemListSUI(CreatureObject* player) {
	PlayerObject* ghost = player->getPlayerObject();

	if (ghost == NULL)
		return;

	if (itemList.size() == 0) {
		player->sendSystemMessage("@event_perk:scavenger_no_items");
		return;
	}

	ManagedReference<SuiListBox*> listbox = new SuiListBox(player, SuiWindowType::SCAVENGER_ITEM_LIST);
	listbox->setPromptTitle("@event_perk:scavenger_list_t"); // Scavenger Hunt List
	listbox->setPromptText("@event_perk:scavenger_list_d"); // Below you will find the list of items you need to find for the scavenger hunt. Good luck!
	listbox->setUsingObject(_this.getReferenceUnsafeStaticCast());
	listbox->setForceCloseDistance(32.f);
	listbox->setCancelButton(true, "@cancel");

	for (int i = 0; i < itemList.size(); i++) {
		String itemTemplate = itemList.get(i);
		listbox->addMenuItem(TemplateManager::instance()->getTemplate(itemTemplate.hashCode())->getObjectName());
	}

	ghost->addSuiBox(listbox);
	player->sendMessage(listbox->generateMessage());
}
int LuaPlayerObject::hasSchematic(lua_State* L) {
	String templateString = lua_tostring(L, -1);
	DraftSchematic* schematic = SchematicMap::instance()->get(templateString.hashCode());

	lua_pushboolean(L, realObject->hasSchematic(schematic));

	return 1;
}
Example #9
0
bool ImageDesignManager::validateCustomizationString(CustomizationVariables* data, const String& appearanceFilename, int skillLevel) {
	VectorMap<String, Reference<CustomizationVariable*> > variables;
	variables.setNullValue(NULL);
	AssetCustomizationManagerTemplate::instance()->getCustomizationVariables(appearanceFilename.hashCode(), variables, false);

	if (variables.size() == 0) {
		instance()->error("no customization data found for " + appearanceFilename);
		return false;
	}

	for (int i = 0; i < data->size(); ++i) {
		uint8 id = data->elementAt(i).getKey();
		int16 val = data->elementAt(i).getValue();

		String name = CustomizationIdManager::instance()->getCustomizationVariable(id);

		//instance()->info("validating " + name + " with value " + String::valueOf(val), true);

		CustomizationVariable* customizationVariable = variables.get(name).get();

		if (customizationVariable == NULL) {
			instance()->error("customization variable id " + String::valueOf(id) + " not found in the appearance file " + appearanceFilename + " with value " + String::valueOf(val));

			continue;
		}

		PaletteColorCustomizationVariable* palette = dynamic_cast<PaletteColorCustomizationVariable*>(customizationVariable);

		if (palette != NULL) {
			if (!validatePalette(palette, val, skillLevel))
				return false;
		} else {
			BasicRangedIntCustomizationVariable* range = dynamic_cast<BasicRangedIntCustomizationVariable*>(customizationVariable);

			if (range == NULL) {
				instance()->error("unkown customization variable type " + name);
				return false;
			} else {
				int maxExcl = range->getMaxValueExclusive();
				int minIncl = range->getMinValueInclusive();

				if (val >= maxExcl || val < minIncl) {
					instance()->error("variable outside bounds " + name + " value " + val + " outside bounds [" + String::valueOf(minIncl) + "," + String::valueOf(maxExcl) + ")");

					return false;
				} else {
					//instance()->info("variable " + name + " value " + String::valueOf(val) + " inside bounds [" + String::valueOf(minIncl) + "," + String::valueOf(maxExcl) + ")", true);
				}

			}
		}


		//info("setting variable:" + name + " to " + String::valueOf(val), true);
	}

	return true;
}
bool CreatureManagerImplementation::addWearableItem(CreatureObject* creature, TangibleObject* clothing) {

	if (!clothing->isWearableObject() && !clothing->isWeaponObject())
		return false;

	ChatManager* chatMan = zoneServer->getChatManager();

	SharedTangibleObjectTemplate* tanoData = dynamic_cast<SharedTangibleObjectTemplate*>(clothing->getObjectTemplate());
	Vector<uint32>* races = tanoData->getPlayerRaces();
	String race = creature->getObjectTemplate()->getFullTemplateString();

	if(clothing->isWearableObject()) {
		if (!races->contains(race.hashCode())) {
			UnicodeString message;

			if(creature->getObjectTemplate()->getFullTemplateString().contains("ithorian"))
				message = "@player_structure:wear_not_ithorian";
			else
				message = "@player_structure:wear_no";

			chatMan->broadcastMessage(creature, message, clothing->getObjectID(), creature->getMoodID(), 0);

			return false;
		}
	}

	ManagedReference<SceneObject*> clothingParent = clothing->getParent();

	if (clothingParent == NULL)
		return false;

	for (int i = 0; i < clothing->getArrangementDescriptorSize(); ++i) {
		Vector<String> descriptors = clothing->getArrangementDescriptor(i);

		for (int j = 0; j < descriptors.size(); ++j) {
			ManagedReference<SceneObject*> slot = creature->getSlottedObject(descriptors.get(j));

			if (slot != NULL) {
				slot->destroyObjectFromWorld(true);
				slot->destroyObjectFromDatabase(true);
			}
		}
	}

	creature->transferObject(clothing, 4, false);
	creature->doAnimation("pose_proudly");
	creature->broadcastObject(clothing, true);

	UnicodeString message;
	if(clothing->isWeaponObject())
		message = "@player_structure:wear_yes_weapon";
	else
		message = "@player_structure:wear_yes";

	chatMan->broadcastMessage(creature, message, clothing->getObjectID(), creature->getMoodID(), 0);

	return true;
}
Example #11
0
MusInputStream(CodecMus MusInputStream::codecmus, URL url, InputStream inputstream) 
{
        codec = codecmus;
        buffer = new byte[1];
        inputStream = inputstream;
        String s = url.getPath();
        s = s.substring(s.lastIndexOf("/") + 1);
        hash_00 = s.hashCode();
}
SceneObject* CreatureManagerImplementation::spawnLair(unsigned int lairTemplate, int difficultyLevel, int difficulty, float x, float z, float y, float size) {
	LairTemplate* lairTmpl = creatureTemplateManager->getLairTemplate(lairTemplate);

	if (lairTmpl == NULL || lairTmpl->getBuildingType() != LairTemplate::LAIR)
		return NULL;

 	String buildingToSpawn;

 	Vector<String>* mobiles = lairTmpl->getWeightedMobiles();

 	if (mobiles->size() == 0)
 		return NULL;

 	buildingToSpawn = lairTmpl->getBuilding((uint32)difficulty);

 	if (buildingToSpawn.isEmpty()) {
 		error("error spawning " + buildingToSpawn);
 		return NULL;
 	}

 	ManagedReference<LairObject*> building = zoneServer->createObject(buildingToSpawn.hashCode(), 0).castTo<LairObject*>();

 	if (building == NULL) {
 		error("error spawning " + buildingToSpawn);
 		return NULL;
 	}

 	Locker blocker(building);

 	building->setFaction(lairTmpl->getFaction());
 	building->setPvpStatusBitmask(CreatureFlag::ATTACKABLE);
 	building->setOptionsBitmask(0, false);
 	building->setMaxCondition(difficultyLevel * (900 + System::random(200)));
 	building->setConditionDamage(0, false);
 	building->initializePosition(x, z, y);
 	building->setDespawnOnNoPlayersInRange(true);

 	ManagedReference<LairObserver*> lairObserver = new LairObserver();
 	lairObserver->deploy();
 	lairObserver->setLairTemplate(lairTmpl);
 	lairObserver->setDifficulty(difficulty);
 	lairObserver->setObserverType(ObserverType::LAIR);
 	lairObserver->setSize(size);

 	building->registerObserver(ObserverEventType::OBJECTDESTRUCTION, lairObserver);
 	building->registerObserver(ObserverEventType::DAMAGERECEIVED, lairObserver);
 	building->registerObserver(ObserverEventType::AIMESSAGE, lairObserver);
 	building->registerObserver(ObserverEventType::OBJECTREMOVEDFROMZONE, lairObserver);

 	zone->transferObject(building, -1, false);

	lairObserver->checkForNewSpawns(building, NULL, true);

 	return building;
}
int LuaPlayerObject::removeRewardedSchematic(lua_State* L){
	String templateString = lua_tostring(L, -2);
	bool notifyClient = lua_toboolean(L, -1);

	DraftSchematic* schematic = SchematicMap::instance()->get(templateString.hashCode());

	if (schematic != nullptr)
		realObject->removeRewardedSchematic(schematic, notifyClient);

	return 0;
}
void ChatManagerImplementation::broadcastGalaxy(const String& message, const String& faction) {
	Locker locker(_this.getReferenceUnsafeStaticCast());

	playerMap->resetIterator(false);

	uint32 factionCRC = faction.hashCode();

	while (playerMap->hasNext(false)) {
		ManagedReference<CreatureObject*> playerObject = playerMap->getNextValue(false);

		if (playerObject->getFaction() == factionCRC || playerObject->getPlayerObject()->isPrivileged())
			playerObject->sendSystemMessage(message);
	}
}
void PlayerCreationManager::addStartingItems(CreatureObject* creature,
		const String& clientTemplate, bool equipmentOnly) {
	SortedVector < String > *items = NULL;

	if (!defaultCharacterEquipment.contains(clientTemplate))
		items = &defaultCharacterEquipment.get(0);
	else
		items = &defaultCharacterEquipment.get(clientTemplate);

	for (int i = 0; i < items->size(); ++i) {
		String itemTemplate = items->get(i);

		//instance()->info("Add Starting Items: " + itemTemplate, true);

		ManagedReference<SceneObject*> item = zoneServer->createObject(
				itemTemplate.hashCode(), 1);

		if (item != NULL) {
			String error;
			if (creature->canAddObject(item, 4, error) == 0) {
				creature->transferObject(item, 4, false);
			} else {
				item->destroyObjectFromDatabase(true);
			}
		}

	}

	// Get inventory.
	if (!equipmentOnly) {
		SceneObject* inventory = creature->getSlottedObject("inventory");
		if (inventory == NULL) {
			return;
		}

		//Add common starting items.
		for (int itemNumber = 0; itemNumber < commonStartingItems.size();
				itemNumber++) {
			ManagedReference<SceneObject*> item = zoneServer->createObject(
					commonStartingItems.get(itemNumber).hashCode(), 1);
			if (item != NULL) {
				if (!inventory->transferObject(item, -1, false)) {
					item->destroyObjectFromDatabase(true);
				}
			}
		}
	}
}
Example #16
0
void ImageDesignManager::updateColorVariable(const Vector<String>& fullVariables, uint32 value, TangibleObject* tano, int skillLevel) {
	String appearanceFilename = tano->getObjectTemplate()->getAppearanceFilename();

	VectorMap<String, Reference<CustomizationVariable*> > variableLimits;

	AssetCustomizationManagerTemplate::instance()->getCustomizationVariables(appearanceFilename.hashCode(), variableLimits, false);

	for (int i = 0; i < fullVariables.size(); ++i) {
		String var = fullVariables.get(i);

		for (int j = 0; j < variableLimits.size(); ++j) {
			String fullVariableNameLimit = variableLimits.elementAt(j).getKey();

			//info("checking customization variable " + fullVariableNameLimit + " for " + var, true);

			if (fullVariableNameLimit.contains(var)) {
				BasicRangedIntCustomizationVariable* ranged = dynamic_cast<BasicRangedIntCustomizationVariable*>(variableLimits.elementAt(j).getValue().get());
				PaletteColorCustomizationVariable* palette = NULL;
				uint32 currentVal = value;

				if (ranged != NULL) {
					int min = ranged->getMinValueInclusive();
					int max = ranged->getMaxValueExclusive();

					if (value < min)
						currentVal = min;

					if (value >= max)
						currentVal = max - 1;
				} else {
					palette = dynamic_cast<PaletteColorCustomizationVariable*>(variableLimits.elementAt(j).getValue().get());

					if (palette != NULL) {
						if (!validatePalette(palette, currentVal, skillLevel))
							currentVal = palette->getDefaultValue();
					}
				}

				Locker locker(tano);
				tano->setCustomizationVariable(fullVariableNameLimit, currentVal, true);

				//info("setting " + fullVariableNameLimit + " to " + String::valueOf(currentVal), true);
			}
		}
	}
}
SceneObject* CreatureManagerImplementation::spawnTheater(unsigned int lairTemplate, int difficulty, float x, float z, float y, float size) {
	LairTemplate* lairTmpl = creatureTemplateManager->getLairTemplate(lairTemplate);

	if (lairTmpl == NULL || lairTmpl->getBuildingType() != LairTemplate::THEATER)
		return NULL;

 	Vector<String>* mobiles = lairTmpl->getWeightedMobiles();

 	if (mobiles->size() == 0)
 		return NULL;

 	String buildingToSpawn = lairTmpl->getBuilding((uint32)difficulty);

 	if (buildingToSpawn.isEmpty()) {
 		error("error spawning " + buildingToSpawn);
 		return NULL;
 	}

 	ManagedReference<TangibleObject*> building = zoneServer->createObject(buildingToSpawn.hashCode(), 0).castTo<TangibleObject*>();

 	if (building == NULL) {
 		error("error spawning " + buildingToSpawn);
 		return NULL;
 	}

 	Locker blocker(building);

 	building->initializePosition(x, z, y);

 	ManagedReference<DynamicSpawnObserver*> theaterObserver = new DynamicSpawnObserver();
 	theaterObserver->deploy();
 	theaterObserver->setLairTemplate(lairTmpl);
 	theaterObserver->setDifficulty(difficulty);
 	theaterObserver->setObserverType(ObserverType::LAIR);
 	theaterObserver->setSize(size);

 	building->registerObserver(ObserverEventType::CREATUREDESPAWNED, theaterObserver);


 	zone->transferObject(building, -1, false);

 	theaterObserver->spawnInitialMobiles(building);

 	return building;
}
int LuaPlayerObject::addRewardedSchematic(lua_State* L){
	String templateString = lua_tostring(L, -4);
	short type = lua_tointeger(L, -3);
	int quantity = lua_tointeger(L, -2);
	bool notifyClient = lua_toboolean(L, -1);

	DraftSchematic* schematic = SchematicMap::instance()->get(templateString.hashCode());

	if (schematic == nullptr) {
		lua_pushboolean(L, false);
		return 1;
	}

	bool result = realObject->addRewardedSchematic(schematic, type, quantity, notifyClient);

	lua_pushboolean(L, result);

	return 1;
}
void GroupObjectImplementation::removeGroupModifiers(CreatureObject* player) {
	if (player == NULL)
		return;

	Reference<CreatureObject*> leader = getLeader();

	if (leader == NULL)
		return;

	if (!leader->isPlayerCreature())
		return;

	Locker clocker(player, _this.getReferenceUnsafeStaticCast());
	String action = "squadleader";

	if (player->hasBuff(action.hashCode()))
		player->removeBuff(action.hashCode());

	player->updateTerrainNegotiation();
}
void DroidObjectImplementation::notifyInsertToZone(Zone* zone) {
	SceneObjectImplementation::notifyInsertToZone(zone);

	if( this->linkedCreature == NULL )
		return;

	ManagedReference<CreatureObject* > linkedCreature = this->linkedCreature.get();
	if( linkedCreature == NULL )
		return;

	// Decay customized paint (if any)
	if (paintCount > 0){

		// Paint starts to fade when there are 4 calls left
		if (paintCount <= 4){

			// Send player notification of decay
			if( paintCount == 1 ){
				linkedCreature->sendSystemMessage("@pet/pet_menu:customization_gone"); // "Your droid's customization has completely faded away."
			}
			else{
				linkedCreature->sendSystemMessage("@pet/pet_menu:customization_fading"); // "Your droid's customization is fading away."
			}

			// Fade color to white
			String appearanceFilename = getObjectTemplate()->getAppearanceFilename();
			VectorMap<String, Reference<CustomizationVariable*> > variables;
			AssetCustomizationManagerTemplate::instance()->getCustomizationVariables(appearanceFilename.hashCode(), variables, false);
			for(int i = 0; i< variables.size(); ++i){
				String varkey = variables.elementAt(i).getKey();
				if (varkey.contains("color")){
					setCustomizationVariable(varkey, paintCount-1, true); // Palette values 3,2,1,0 are grey->white
				}
			}
		}
		--paintCount;
	}

}
void PlayerCreationManager::addProfessionStartingItems(CreatureObject* creature,
		const String& profession, const String& clientTemplate,
		bool equipmentOnly) {
	ProfessionDefaultsInfo* professionData = professionDefaultsInfo.get(
			profession);

	if (professionData == NULL)
		professionData = professionDefaultsInfo.get(0);

	Reference<Skill*> startingSkill = professionData->getSkill();
	//Reference<Skill*> startingSkill = SkillManager::instance()->getSkill("crafting_artisan_novice");

	//Starting skill.
	SkillManager::instance()->awardSkill(startingSkill->getSkillName(),
			creature, false, true, true);

	//Set the hams.
	for (int i = 0; i < 6; i++) {
			int mod = 1000; // All stats start at 1k.
			creature->setBaseHAM(i, mod, false);
			creature->setHAM(i, mod, false);
			creature->setMaxHAM(i, mod, false);
		}

	SortedVector < String > *itemTemplates = professionData->getProfessionItems(
			clientTemplate);

	if (itemTemplates == NULL)
		return;

	for (int i = 0; i < itemTemplates->size(); ++i) {
		String itemTemplate = itemTemplates->get(i);

		//instance()->info("Add Profession Starting Items: " + itemTemplate, true);

		ManagedReference<SceneObject*> item;

		try {
			item = zoneServer->createObject(itemTemplate.hashCode(), 1);
		} catch (Exception& e) {
		}

		if (item != NULL) {
			String error;
			if (creature->canAddObject(item, 4, error) == 0) {
				creature->transferObject(item, 4, false);
			} else {
				item->destroyObjectFromDatabase(true);
			}
		} else {
			error(
					"could not create item in PlayerCreationManager::addProfessionStartingItems: "
							+ itemTemplate);
		}
	}

	// Get inventory.
	if (!equipmentOnly) {
		SceneObject* inventory = creature->getSlottedObject("inventory");
		if (inventory == NULL) {
			return;
		}

		//Add profession specific items.
		for (int itemNumber = 0;
				itemNumber < professionData->getStartingItems()->size();
				itemNumber++) {
			String itemTemplate = professionData->getStartingItems()->get(
					itemNumber);

			ManagedReference<SceneObject*> item = zoneServer->createObject(
					itemTemplate.hashCode(), 1);

			if (item != NULL) {
				if (!inventory->transferObject(item, -1, false)) {
					item->destroyObjectFromDatabase(true);
				}
			} else if (item == NULL) {
				error("could not create profession item " + itemTemplate);
			}
		}
	}
}
bool PlayerCreationManager::createCharacter(MessageCallback* data) {
	TemplateManager* templateManager = TemplateManager::instance();

	ClientCreateCharacterCallback* callback = cast<
			ClientCreateCharacterCallback*>(data);
	ZoneClientSession* client = data->getClient();

	if (client->getCharacterCount(zoneServer.get()->getGalaxyID()) >= 10) {
		ErrorMessage* errMsg = new ErrorMessage("Create Error", "You are limited to 10 characters per galaxy.", 0x0);
		client->sendMessage(errMsg);

		return false;
	}

	PlayerManager* playerManager = zoneServer.get()->getPlayerManager();

	SkillManager* skillManager = SkillManager::instance();

	//Get all the data and validate it.
	UnicodeString characterName;
	callback->getCharacterName(characterName);

	//TODO: Replace this at some point?
	if (!playerManager->checkPlayerName(callback))
		return false;

	String raceFile;
	callback->getRaceFile(raceFile);

	uint32 serverObjectCRC = raceFile.hashCode();

	PlayerCreatureTemplate* playerTemplate =
			dynamic_cast<PlayerCreatureTemplate*>(templateManager->getTemplate(
					serverObjectCRC));

	if (playerTemplate == NULL) {
		error("Unknown player template selected: " + raceFile);
		return false;
	}

	int raceID = playerTemplate->getRace();


	String fileName = playerTemplate->getTemplateFileName();
	String clientTemplate = templateManager->getTemplateFile(
			playerTemplate->getClientObjectCRC());

	RacialCreationData* raceData = racialCreationData.get(fileName);

	if (raceData == NULL)
		raceData = racialCreationData.get(0); //Just get the first race, since they tried to create a race that doesn't exist.

	String profession, customization, hairTemplate, hairCustomization;
	callback->getSkill(profession);

	if (profession.contains("jedi"))
		profession = "crafting_artisan";

	callback->getCustomizationString(customization);
	callback->getHairObject(hairTemplate);
	callback->getHairCustomization(hairCustomization);

	float height = callback->getHeight();
	height = MAX(MIN(height, playerTemplate->getMaxScale()),
			playerTemplate->getMinScale());

	//validate biography
	UnicodeString bio;
	callback->getBiography(bio);

	bool doTutorial = callback->getTutorialFlag();
	//bool doTutorial = false;

	ManagedReference<CreatureObject*> playerCreature =
			zoneServer.get()->createObject(
					serverObjectCRC, 2).castTo<CreatureObject*>();

	if (playerCreature == NULL) {
		error("Could not create player with template: " + raceFile);
		return false;
	}

	Locker playerLocker(playerCreature);

	playerCreature->createChildObjects();
	playerCreature->setHeight(height);
	playerCreature->setCustomObjectName(characterName, false); //TODO: Validate with Name Manager.

	client->setPlayer(playerCreature);
	playerCreature->setClient(client);

	// Set starting cash and starting bank
	playerCreature->setCashCredits(startingCash, false);
	playerCreature->setBankCredits(startingBank, false);

	ManagedReference<PlayerObject*> ghost = playerCreature->getPlayerObject();

	if (ghost != NULL) {
		//Set skillpoints before adding any skills.
		ghost->setSkillPoints(skillPoints);
		ghost->setStarterProfession(profession);
	}

	addCustomization(playerCreature, customization,
			playerTemplate->getAppearanceFilename());
	addHair(playerCreature, hairTemplate, hairCustomization);
	if (!doTutorial) {
		addProfessionStartingItems(playerCreature, profession, clientTemplate,
				false);
		addStartingItems(playerCreature, clientTemplate, false);
		addRacialMods(playerCreature, fileName,
				playerTemplate->getStartingSkills(),
				playerTemplate->getStartingItems(), false);
	} else {
		addProfessionStartingItems(playerCreature, profession, clientTemplate,
				true);
		addStartingItems(playerCreature, clientTemplate, true);
		addRacialMods(playerCreature, fileName,
				playerTemplate->getStartingSkills(),
				playerTemplate->getStartingItems(), true);
	}

	// Set starting cash and starting bank
	playerCreature->setCashCredits(startingCash, false);
	playerCreature->setBankCredits(startingBank, false);

	if (ghost != NULL) {

		ghost->setAccountID(client->getAccountID());

		if (!freeGodMode) {
			try {
				uint32 accID = client->getAccountID();

				ManagedReference<Account*> playerAccount = playerManager->getAccount(accID);

				if (playerAccount == NULL) {
					playerCreature->destroyPlayerCreatureFromDatabase(true);
					return false;
				}

				int accountPermissionLevel = playerAccount->getAdminLevel();
				String accountName = playerAccount->getUsername();

				if(accountPermissionLevel > 0 && (accountPermissionLevel == 9 || accountPermissionLevel == 10 || accountPermissionLevel == 12 || accountPermissionLevel == 15)) {
					playerManager->updatePermissionLevel(playerCreature, accountPermissionLevel);

					/*
					Reference<ShipControlDevice*> shipControlDevice = zoneServer->createObject(STRING_HASHCODE("object/intangible/ship/sorosuub_space_yacht_pcd.iff"), 1).castTo<ShipControlDevice*>();
					//ShipObject* ship = (ShipObject*) server->createObject(STRING_HASHCODE("object/ship/player/player_sorosuub_space_yacht.iff"), 1);
					Reference<ShipObject*> ship = zoneServer->createObject(STRING_HASHCODE("object/ship/player/player_basic_tiefighter.iff"), 1).castTo<ShipObject*>();

					shipControlDevice->setControlledObject(ship);

					if (!shipControlDevice->transferObject(ship, 4))
						info("Adding of ship to device failed");

					ManagedReference<SceneObject*> datapad = playerCreature->getSlottedObject("datapad");

					if (datapad != NULL) {
						if (!datapad->transferObject(shipControlDevice, -1)) {
							shipControlDevice->destroyObjectFromDatabase(true);
						}
					} else {
						shipControlDevice->destroyObjectFromDatabase(true);
						error("could not get datapad from player");
					}
					*/
				}

				if (accountPermissionLevel < 9) {
					try {
						StringBuffer query;
						//query << "SELECT UNIX_TIMESTAMP(creation_date) FROM characters c WHERE galaxy_id = " << zoneServer.get()->getGalaxyID() << " AND account_id = " << client->getAccountID() << " ORDER BY creation_date desc;";
						uint32 galaxyId = zoneServer.get()->getGalaxyID();
						uint32 accountId = client->getAccountID();
						query << "(SELECT UNIX_TIMESTAMP(c.creation_date) as t FROM characters as c WHERE c.account_id = " << accountId << " AND c.galaxy_id = " << galaxyId << " ORDER BY c.creation_date DESC) UNION (SELECT UNIX_TIMESTAMP(d.creation_date) FROM deleted_characters as d WHERE d.account_id = " << accountId << " AND d.galaxy_id = " << galaxyId << " ORDER BY d.creation_date DESC) ORDER BY t DESC LIMIT 1";

						Reference<ResultSet*> res = ServerDatabase::instance()->executeQuery(query);

						if (res != NULL && res->next()) {
							uint32 sec = res->getUnsignedInt(0);

							Time timeVal(sec);

							if (timeVal.miliDifference() < 86400000) {
								ErrorMessage* errMsg = new ErrorMessage("Create Error", "You are only permitted to create one character every 24 hours. Repeat attempts prior to 24 hours elapsing will reset the timer.", 0x0);
								client->sendMessage(errMsg);

								playerCreature->destroyPlayerCreatureFromDatabase(true);
								return false;
							}
							//timeVal.se
						}
					} catch (DatabaseException& e) {
						error(e.getMessage());
					}

					Locker locker(&charCountMutex);

					if (lastCreatedCharacter.containsKey(accID)) {
						Time lastCreatedTime = lastCreatedCharacter.get(accID);

						if (lastCreatedTime.miliDifference() < 86400000) {
							ErrorMessage* errMsg = new ErrorMessage("Create Error", "You are only permitted to create one character every 24 hours. Repeat attempts prior to 24 hours elapsing will reset the timer.", 0x0);
							client->sendMessage(errMsg);

							playerCreature->destroyPlayerCreatureFromDatabase(true);
							return false;
						} else {
							lastCreatedTime.updateToCurrentTime();

							lastCreatedCharacter.put(accID, lastCreatedTime);
						}
					} else {
						lastCreatedCharacter.put(accID, Time());
					}
				}

			} catch (Exception& e) {
				error(e.getMessage());
			}
		} else {
			playerManager->updatePermissionLevel(playerCreature, PermissionLevelList::instance()->getLevelNumber("admin"));
		}

		if (doTutorial)
			playerManager->createTutorialBuilding(playerCreature);
		else
			playerManager->createSkippedTutorialBuilding(playerCreature);

		ValidatedPosition* lastValidatedPosition =
				ghost->getLastValidatedPosition();
		lastValidatedPosition->update(playerCreature);

		ghost->setBiography(bio);
		ghost->setRaceID(raceID);

		ghost->setLanguageID(playerTemplate->getDefaultLanguage());
	}

	playerCreature->setLevel(1);

	ClientCreateCharacterSuccess* msg = new ClientCreateCharacterSuccess(
			playerCreature->getObjectID());
	playerCreature->sendMessage(msg);

	ChatManager* chatManager = zoneServer.get()->getChatManager();
	chatManager->addPlayer(playerCreature);

	String firstName = playerCreature->getFirstName();
	String lastName = playerCreature->getLastName();

	try {
		StringBuffer query;
		query
				<< "INSERT INTO `characters_dirty` (`character_oid`, `account_id`, `galaxy_id`, `firstname`, `surname`, `race`, `gender`, `template`)"
				<< " VALUES (" << playerCreature->getObjectID() << ","
				<< client->getAccountID() << "," << zoneServer.get()->getGalaxyID()
				<< "," << "'" << firstName.escapeString() << "','"
				<< lastName.escapeString() << "'," << raceID << "," << 0 << ",'"
				<< raceFile.escapeString() << "')";

		ServerDatabase::instance()->executeStatement(query);
	} catch (DatabaseException& e) {
		error(e.getMessage());
	}

	playerManager->addPlayer(playerCreature);

	// Copy claimed veteran rewards from player's alt character
	uint32 accID = client->getAccountID();
	ManagedReference<Account*> playerAccount = playerManager->getAccount(accID);
	if (playerAccount != NULL && ghost != NULL) {

		// Find the first alt character
		ManagedReference<CreatureObject*> altPlayer = NULL;
		CharacterList* characters = playerAccount->getCharacterList();
		for(int i = 0; i < characters->size(); ++i) {
			CharacterListEntry* entry = &characters->get(i);
			if(entry->getGalaxyID() == zoneServer.get()->getGalaxyID() &&
		       entry->getFirstName() != playerCreature->getFirstName() ) {

				altPlayer = playerManager->getPlayer(entry->getFirstName());
				if( altPlayer != NULL ){
					break;
				}
			}
		}

		// Record the rewards if alt player was found
		if( altPlayer != NULL && altPlayer->getPlayerObject() != NULL){

			Locker alocker( altPlayer );
			for( int i = 0; i < playerManager->getNumVeteranRewardMilestones(); i++ ){
				int milestone = playerManager->getVeteranRewardMilestone(i);
				String claimedReward = altPlayer->getPlayerObject()->getChosenVeteranReward(milestone);
				if( !claimedReward.isEmpty() ){
					ghost->addChosenVeteranReward(milestone,claimedReward);
				}
			}
		}
	}

	client->addCharacter(playerCreature->getObjectID(), zoneServer.get()->getGalaxyID());

	JediManager::instance()->onPlayerCreated(playerCreature);

	ManagedReference<SuiMessageBox*> box = new SuiMessageBox(playerCreature, SuiWindowType::NONE);
	box->setPromptTitle("PLEASE NOTE");
	box->setPromptText("You are limited to creating one character every 24 hours. Attempting to create another character or deleting your character before the 24 hour timer expires will reset the timer.");

	ghost->addSuiBox(box);
	playerCreature->sendMessage(box->generateMessage());
	ghost->recalculateCombatLevel(playerCreature);

	return true;
}
int ForceShrineMenuComponent::handleObjectMenuSelect(SceneObject* sceneObject, CreatureObject* creature, byte selectedID) {
	if (selectedID != 213)
		return 0;

	if (creature->getPosture() != CreaturePosture::CROUCHED){
		creature->sendSystemMessage("@jedi_trials:show_respect"); // Must show respect
		return 0;
	}

	ManagedReference<PlayerObject*> ghost = creature->getPlayerObject();

	if (ghost == NULL)
		return 0;

	if (creature->getScreenPlayState("VillageJediProgression") && !creature->hasSkill("force_title_jedi_rank_02")){
		ManagedReference<SuiMessageBox*> box = new SuiMessageBox(creature, SuiWindowType::NONE);
		box->setPromptTitle("@jedi_trials:padawan_trials_title"); // Jedi Trials
		box->setPromptText("@jedi_trials:padawan_trials_completed");

		ghost->addSuiBox(box);
		creature->sendMessage(box->generateMessage());

		SkillManager::instance()->awardSkill("force_title_jedi_rank_02", creature, true, true, true);

		creature->playEffect("clienteffect/entertainer_dazzle_level_3.cef", ""); // Not sure if it's the right one for this.

		PlayMusicMessage* pmm = new PlayMusicMessage("sound/intro.snd");
		creature->sendMessage(pmm);

		ghost->setJediState(2);

		// Trainer number. Pick a random trainer, there are at least 600 in the galaxy.

		ZoneServer* zoneServer = ghost->getZoneServer();
		int randomZone = System::random(zoneServer->getZoneCount() - 1);

		ManagedReference<Zone*> zone = zoneServer->getZone(randomZone);
		Vector3 randomTrainer = zone->getCreatureManager()->getRandomJediTrainer();

		if ((randomTrainer.getX() == 0) && (randomTrainer.getY() == 0)) { // No trainers on the zone.
			ManagedReference<Zone*> zone = zoneServer->getZone(0);
			Vector3 randomTrainer = zone->getCreatureManager()->getRandomJediTrainer();
		}

		Vector3 trainerPositionFinal(randomTrainer.getX(), randomTrainer.getY(), 0);

		String zoneName = zone->getZoneName();

		ghost->setTrainerCoordinates(trainerPositionFinal);
		ghost->setTrainerZoneName(zoneName); // For the Waypoint.


		ManagedReference<SceneObject*> inventory = creature->getSlottedObject("inventory");

		//Check if inventory is full.
		if (inventory->hasFullContainerObjects()) {
			creature->sendSystemMessage("@jedi_spam:inventory_full_jedi_robe"); //	You have too many items in your inventory. In order to get your Padawan Robe you must clear out at least one free slot.
			return 0;
		}

		ZoneServer* zserv = creature->getZoneServer();

		String PadawanRobe = "object/tangible/wearables/robe/robe_jedi_padawan.iff";
		ManagedReference<SceneObject*> padawanRobe = zserv->createObject(PadawanRobe.hashCode(), 1);
		if (inventory->transferObject(padawanRobe, -1)) {
			inventory->broadcastObject(padawanRobe, true);
		} else {
			padawanRobe->destroyObjectFromDatabase(true);
		}
	}

	else if (!creature->hasSkill("force_title_jedi_novice")){

		int rand = System::random(14) + 1;

		StringBuffer sysmsg;

		sysmsg << "@jedi_trials:force_shrine_wisdom_" << rand;

		creature->sendSystemMessage(sysmsg.toString());

	}

	else if (creature->hasSkill("force_title_jedi_rank_02")){

		ManagedReference<SceneObject*> inventory = creature->getSlottedObject("inventory");

		//Check if inventory is full.
		if (inventory->hasFullContainerObjects()) {
			creature->sendSystemMessage("@jedi_spam:inventory_full_jedi_robe"); //	You have too many items in your inventory. In order to get your Padawan Robe you must clear out at least one free slot.
			return 0;
		}

		ZoneServer* zserv = creature->getZoneServer();

		String PadawanRobe = "object/tangible/wearables/robe/robe_jedi_padawan.iff";
		ManagedReference<SceneObject*> padawanRobe = zserv->createObject(PadawanRobe.hashCode(), 1);
		if (inventory->transferObject(padawanRobe, -1)) {
			inventory->broadcastObject(padawanRobe, true);
		} else {
			padawanRobe->destroyObjectFromDatabase(true);
		}

	}

	return 0;


}
Example #24
0
void ImageDesignManager::updateCustomization(CreatureObject* imageDesigner, const String& customizationName, float value, CreatureObject* creo) {
	if (creo == NULL)
		return;

	if (value < 0 || value > 1)
		return;

	String speciesGender = getSpeciesGenderString(creo);

	ManagedReference<CreatureObject*> creatureObject = creo;

	CustomizationData* customData = getCustomizationData(speciesGender, customizationName);

	if (customData == NULL) {
		//System::out << "Unable to get CustomizationData for " + speciesGender + "_" + customizationName << endl;
		return;
	}

	String variables = customData->getVariables();
	String type = customData->getType();

	String skillMod = customData->getImageDesignSkillMod();

	if (imageDesigner->getSkillMod(skillMod) < customData->getSkillModValue())
		return;

	if (customData->getIsScale()) {
		float minScale = customData->getMinScale();
		float maxScale = customData->getMaxScale();

		float height = minScale + value * (maxScale - minScale);

		creatureObject->setHeight(MAX(MIN(height, maxScale), minScale));

		return;
	}

	Vector<String> fullVariables;
	StringTokenizer tokenizer(variables);
	tokenizer.setDelimeter(",");

	while (tokenizer.hasMoreTokens()) {
		String var;
		tokenizer.getStringToken(var);

		fullVariables.add(var);
	}

	String appearanceFilename = creo->getObjectTemplate()->getAppearanceFilename();

	VectorMap<String, Reference<CustomizationVariable*> > variableLimits;

	AssetCustomizationManagerTemplate::instance()->getCustomizationVariables(appearanceFilename.hashCode(), variableLimits, false);

	for (int i = 0; i < fullVariables.size(); ++i) {
		String var = fullVariables.get(i);

		for (int j = 0; j < variableLimits.size(); ++j) {
			String fullVariableNameLimit = variableLimits.elementAt(j).getKey();

			if (fullVariableNameLimit.contains(var)) {
				BasicRangedIntCustomizationVariable* ranged = dynamic_cast<BasicRangedIntCustomizationVariable*>(variableLimits.elementAt(j).getValue().get());

				if (ranged == NULL) {
					error("variable " + fullVariableNameLimit + " is not ranged");

					continue;
				}

				int min = ranged->getMinValueInclusive();
				int max = ranged->getMaxValueExclusive();

				int count = max - min;

				int setVal;

				float currentValue = value;

				if (fullVariables.size() > 1) {
					// examples for var count = 2
					// ex: received value 0 is for i == 0 -> 1.0, i == 1 -> 0.0
					// ex: received value 0.5 is for i == 0 -> 0.0, i == 1 -> 0.0
					// ex: received value 1 is for i == 0 -> 0.0, i == 1 -> 1.0

					// pre: i � [0, 1] && value � [0, 1]
					// post f � [0, 1]
					currentValue = MAX(0, ((value - 0.5) * 2) * (-1 + (i * 2)));
				}

				if (customData->getReverse()) {
					setVal = float(max - 1) - currentValue * (float(count) - 1);
				} else {
					setVal = float(min) + currentValue * (float(count) - 1);
				}

				creatureObject->setCustomizationVariable(fullVariableNameLimit, setVal, true);

				//info("setting " + fullVariableNameLimit + " to " + String::valueOf(setVal), true);
			}
		}
	}

}
int CampKitMenuComponent::handleObjectMenuSelect(SceneObject* sceneObject,
		CreatureObject* player, byte selectedID) const {
	if (!sceneObject->isTangibleObject())
		return 0;

	TangibleObject* tano = cast<TangibleObject*>(sceneObject);

	if (tano == NULL || !player->isPlayerCreature())
		return 0;

	if (player->getZone() == NULL)
		return 0;

	if (!sceneObject->isASubChildOf(player))
		return 0;

	if (selectedID == 20) {

		/// Get Camp Kit Template
		CampKitTemplate* campKitData = cast<CampKitTemplate*> (sceneObject->getObjectTemplate());
		if (campKitData == NULL) {
			error("No CampKitTemplate for: " + String::valueOf(sceneObject->getServerObjectCRC()));
			return 0;
		}

		/// Get Camp Template
		SharedObjectTemplate* templateData = TemplateManager::instance()->getTemplate(campKitData->getSpawnObjectTemplate().hashCode());
		CampStructureTemplate* campStructureData = cast<CampStructureTemplate*> (templateData);
		if (campStructureData == NULL) {
			error("No CampStructureTemplate for: " + campKitData->getSpawnObjectTemplate());
			return 0;
		}

		ManagedReference<ZoneServer*> zoneServer = player->getZoneServer();
		if (zoneServer == NULL) {
			error("ZoneServer is null when trying to create camp");
			return 0;
		}

		ManagedReference<Zone*> zone = player->getZone();
		if (zone == NULL) {
			error("Zone is null when trying to create camp");
			return 0;
		}

		ManagedReference<PlanetManager*> planetManager = zone->getPlanetManager();
		if (planetManager == NULL) {
			error("Unable to get PlanetManager when placing camp");
			return 0;
		}


		/// Get Ghost
		Reference<PlayerObject*> ghost = player->getSlottedObject("ghost").castTo<PlayerObject*>();
		if (ghost == NULL) {
			error("PlayerCreature has no ghost: " + String::valueOf(player->getObjectID()));
			return 0;
		}

		int playerSkill = player->getSkillMod("camp");

		if(playerSkill < campStructureData->getSkillRequired()) {
			player->sendSystemMessage("@camp:sys_nsf_skill");
			return 0;
		}

		if(player->isInCombat()) {
			player->sendSystemMessage("@camp:sys_not_in_combat");
			return 0;
		}

		if(player->getParent() != NULL && player->getParent().get()->isCellObject()) {
			player->sendSystemMessage("@camp:error_inside");
			return 0;
		}

		if(!sceneObject->isASubChildOf(player)) {
			player->sendSystemMessage("@camp:sys_not_in_inventory");
			return 0;
		}

		if(!player->isStanding() || player->isRidingMount()) {
			player->sendSystemMessage("@camp:error_cmd_fail");
			return 0;
		}

		ManagedReference<CityRegion*> region = player->getCityRegion().get();
		if(region != NULL) {
			player->sendSystemMessage("@camp:error_muni_true");
			return 0;
		}

		/// Check for water
		if(player->isSwimming() || player->isInWater()) {
			player->sendSystemMessage("@camp:error_in_water");
			return 0;
		}

		/// Make sure player doesn't already have a camp setup somewhere else
		for (int i = 0; i < ghost->getTotalOwnedStructureCount(); ++i) {
			uint64 oid = ghost->getOwnedStructure(i);

			ManagedReference<StructureObject*> structure = ghost->getZoneServer()->getObject(oid).castTo<StructureObject*>();

			if (structure != NULL && structure->isCampStructure()) {
				player->sendSystemMessage("@camp:sys_already_camping");
				return 0;
			}
		}

		/// Check if player is in another camp
		if(player->getCurrentCamp() != NULL) {
			player->sendSystemMessage("@camp:error_camp_exists");
			return 0;
		}

		/// Check if player is elevated, on a building or porch

		/// Check camps/lairs nearby
		SortedVector<ManagedReference<QuadTreeEntry* > > nearbyObjects;
		zone->getInRangeObjects(player->getPositionX(), player->getPositionY(),
				512, &nearbyObjects, true, false);

		for(int i = 0; i < nearbyObjects.size(); ++i) {
			SceneObject* scno = cast<SceneObject*>(nearbyObjects.get(i).get());
			if (scno != NULL && scno->isCampStructure() && scno->getDistanceTo(
					player) <= scno->getObjectTemplate()->getNoBuildRadius() + campStructureData->getRadius()) {
				player->sendSystemMessage("@camp:error_camp_too_close");
				return 0;
			}

			if (scno != NULL && !scno->isCampStructure() && scno->isStructureObject() &&
					scno->getDistanceTo(player) <= 100) {
				player->sendSystemMessage("@camp:error_building_too_close");
				return 0;
			}

			if(scno != NULL && scno->getDistanceTo(player) <= scno->getObjectTemplate()->getNoBuildRadius() + campStructureData->getRadius()) {

				if (scno->getObserverCount(ObserverEventType::OBJECTDESTRUCTION) > 0) {
					SortedVector<ManagedReference<Observer* > > observers = scno->getObservers(ObserverEventType::OBJECTDESTRUCTION);
					for(int j = 0; j < observers.size(); ++j) {
						if(observers.get(j)->isObserverType(ObserverType::LAIR)) {
							player->sendSystemMessage("@camp:error_lair_too_close");
							return 0;
						}
					}
				}

				if (scno->getObserverCount(ObserverEventType::CREATUREDESPAWNED) > 0) {
					SortedVector<ManagedReference<Observer* > > observers2 = scno->getObservers(ObserverEventType::CREATUREDESPAWNED);
					for(int j = 0; j < observers2.size(); ++j) {
						if(observers2.get(j)->isObserverType(ObserverType::LAIR)) {
							player->sendSystemMessage("@camp:error_lair_too_close");
							return 0;
						}
					}
				}
			}
		}

		/// Check to see if you can camp here (Allows building in city no-build zone but not within city limits which are checked above)
		if (!planetManager->isCampingPermittedAt(player->getPositionX(), player->getPositionY(), campStructureData->getRadius())) {
			player->sendSystemMessage("@camp:error_nobuild");
			return 0;
		}

		player->sendSystemMessage("@camp:starting_camp");

		/// Create Structure
		StructureObject* structureObject = StructureManager::instance()->placeStructure(
				player, campKitData->getSpawnObjectTemplate(),
				player->getPositionX(), player->getPositionY(),
				(int) player->getDirectionAngle());

		if (structureObject == NULL) {
			error("Unable to create camp: " + campKitData->getSpawnObjectTemplate());
			return 1;
		}

		/// Identify terminal for Active area
		Terminal* campTerminal = NULL;
		SortedVector < ManagedReference<SceneObject*> > *childObjects
				= structureObject->getChildObjects();

		for (int i = 0; i < childObjects->size(); ++i) {
			if (childObjects->get(i)->isTerminal()) {
				campTerminal = cast<Terminal*> (childObjects->get(i).get());
				break;
			}
		}

		if (campTerminal == NULL) {
			structureObject->destroyObjectFromDatabase(true);
			error("Camp does not have terminal: " + campStructureData->getTemplateFileName());
			return 1;
		}

		String campName = player->getFirstName();
		if(!player->getLastName().isEmpty())
			campName += " " + player->getLastName();
		campName += "'s Camp";
		campTerminal->setCustomObjectName(campName, true);

		/// Create active area
		String areaPath = "object/camp_area.iff";
		ManagedReference<CampSiteActiveArea*> campArea =
			(zoneServer->createObject( areaPath.hashCode(), 1)).castTo< CampSiteActiveArea*>();

		if (campArea == NULL) {
			structureObject->destroyObjectFromDatabase(true);
			return 1;
		}

		Locker areaLocker(campArea, player);

		campArea->init(campStructureData);
		campArea->setTerminal(campTerminal);
		campArea->setCamp(structureObject);
		campArea->setOwner(player);
		campArea->setNoBuildArea(true);
		campArea->initializePosition(player->getPositionX(), 0, player->getPositionY());

		if (!zone->transferObject(campArea, -1, false)) {
			structureObject->destroyObjectFromDatabase(true);
			campArea->destroyObjectFromDatabase(true);
			return 1;
		}

		campArea->setAbandoned(false);

		structureObject->addActiveArea(campArea);

		player->sendSystemMessage("@camp:camp_complete");

		/// Remove Camp
		TangibleObject* tano = cast<TangibleObject*>(sceneObject);
		if(tano != NULL)
			tano->decreaseUseCount();


		return 0;
	} else
		return TangibleObjectMenuComponent::handleObjectMenuSelect(sceneObject,
				player, selectedID);

	return 0;
}
Reference<FactoryCrate*> TangibleObjectImplementation::createFactoryCrate(bool insertSelf) {
	String file;
	uint32 type = getGameObjectType();

	if(type & SceneObjectType::ARMOR)
		file = "object/factory/factory_crate_armor.iff";
	else if(type == SceneObjectType::CHEMICAL || type == SceneObjectType::PHARMACEUTICAL || type == SceneObjectType::PETMEDECINE)
		file = "object/factory/factory_crate_chemicals.iff";
	else if(type & SceneObjectType::CLOTHING)
		file = "object/factory/factory_crate_clothing.iff";
	else if(type == SceneObjectType::ELECTRONICS)
		file = "object/factory/factory_crate_electronics.iff";
	else if(type == SceneObjectType::FOOD || type == SceneObjectType::DRINK)
		file = "object/factory/factory_crate_food.iff";
	else if(type == SceneObjectType::FURNITURE)
		file = "object/factory/factory_crate_furniture.iff";
	else if(type & SceneObjectType::INSTALLATION)
		file = "object/factory/factory_crate_installation.iff";
	else if(type & SceneObjectType::WEAPON)
		file = "object/factory/factory_crate_weapon.iff";
	else
		file = "object/factory/factory_crate_generic_items.iff";

	SharedTangibleObjectTemplate* tanoData = dynamic_cast<SharedTangibleObjectTemplate*>(templateObject.get());

	if (tanoData == NULL)
		return NULL;

	ObjectManager* objectManager = ObjectManager::instance();

	Reference<FactoryCrate*> crate = (getZoneServer()->createObject(file.hashCode(), 2)).castTo<FactoryCrate*>();

	if (crate == NULL)
		return NULL;

	Locker locker(crate);

	crate->setMaxCapacity(tanoData->getFactoryCrateSize());

	if (insertSelf) {
		if (!crate->transferObject(asTangibleObject(), -1, false)) {
			crate->destroyObjectFromDatabase(true);
			return NULL;
		}
	} else {

		ManagedReference<TangibleObject*> protoclone = cast<TangibleObject*>( objectManager->cloneObject(asTangibleObject()));

		if (protoclone == NULL) {
			crate->destroyObjectFromDatabase(true);
			return NULL;
		}

		protoclone->setParent(NULL);
		if (!crate->transferObject(protoclone, -1, false)) {
			protoclone->destroyObjectFromDatabase(true);
			crate->destroyObjectFromDatabase(true);
			return NULL;
		}
	}

	crate->setCustomObjectName(getCustomObjectName(), false);

	crate->setUseCount(1);

	return crate;
}
int PlayerContainerComponent::canAddObject(SceneObject* sceneObject, SceneObject* object, int containmentType, String& errorDescription) const {
	CreatureObject* creo = dynamic_cast<CreatureObject*>(sceneObject);

	if (creo == NULL) {
		return TransferErrorCode::PLAYERUSEMASKERROR;
	}

	if (object->isTangibleObject() && containmentType == 4) {
		TangibleObject* wearable = cast<TangibleObject*>(object);

		SharedTangibleObjectTemplate* tanoData = dynamic_cast<SharedTangibleObjectTemplate*>(wearable->getObjectTemplate());

		if (tanoData != NULL) {
			Vector<uint32>* races = tanoData->getPlayerRaces();
			String race = creo->getObjectTemplate()->getFullTemplateString();

			if (!races->contains(race.hashCode())) {
				errorDescription = "You lack the necessary requirements to wear this object";

				return TransferErrorCode::PLAYERUSEMASKERROR;
			}
		}

		if (creo->isPlayerCreature()) {
			if (!wearable->isNeutral()) {
				if (wearable->isImperial() && (creo->getFactionStatus() == FactionStatus::ONLEAVE || !creo->isImperial())) {
					errorDescription = "You lack the necessary requirements to wear this object";

					return TransferErrorCode::PLAYERUSEMASKERROR;
				}

				if (wearable->isRebel() && (creo->getFactionStatus() == FactionStatus::ONLEAVE || !creo->isRebel())) {
					errorDescription = "You lack the necessary requirements to wear this object";

					return TransferErrorCode::PLAYERUSEMASKERROR;
				}
			}
		}

		if (object->isArmorObject()) {
			PlayerManager* playerManager = sceneObject->getZoneServer()->getPlayerManager();

			if (!playerManager->checkEncumbrancies(creo, cast<ArmorObject*>(object))) {
				errorDescription = "You lack the necessary secondary stats to equip this item";

				return TransferErrorCode::NOTENOUGHENCUMBRANCE;
			}
		}

		if (object->isWearableObject()) {
			if (tanoData != NULL) {
				const Vector<String>& skillsRequired = tanoData->getCertificationsRequired();

				if (skillsRequired.size() > 0) {
					bool hasSkill = false;

					for (int i = 0; i < skillsRequired.size(); i++) {
						const String& skill = skillsRequired.get(i);

						if (!skill.isEmpty() && creo->hasSkill(skill)) {
							hasSkill = true;
							break;
						}
					}

					if (!hasSkill) {
						errorDescription = "@error_message:insufficient_skill"; // You lack the skill to use this item.

						return TransferErrorCode::PLAYERUSEMASKERROR;
					}
				}
			}
		}

		if (object->isWeaponObject()) {
			WeaponObject* weapon = cast<WeaponObject*>(object);
			int bladeColor = weapon->getBladeColor();
			PlayerObject* ghost = creo->getPlayerObject();

			if (weapon->isJediWeapon()) {
				if (bladeColor == 31) {
					errorDescription = "@jedi_spam:lightsaber_no_color";
					return TransferErrorCode::PLAYERUSEMASKERROR;
				}

				if (weapon->getCraftersName() != creo->getFirstName() && !ghost->isPrivileged()) {
					errorDescription = "@jedi_spam:not_your_lightsaber";
					return TransferErrorCode::PLAYERUSEMASKERROR;
				}
			}
		}
	}

	return ContainerComponent::canAddObject(sceneObject, object, containmentType, errorDescription);
}
void PlayerCreationManager::addHair(CreatureObject* creature,
		const String& hairTemplate, const String& hairCustomization) {
	if (hairTemplate.isEmpty())
		return;

	HairStyleInfo* hairInfo = hairStyleInfo.get(hairTemplate);

	if (hairInfo == NULL)
		hairInfo = hairStyleInfo.get(0);

	HairAssetData* hairAssetData =
			CustomizationIdManager::instance()->getHairAssetData(hairTemplate);

	if (hairAssetData == NULL) {
		error("no hair asset data detected for " + hairTemplate);
		return;
	}

	if (hairAssetData->getServerPlayerTemplate()
			!= creature->getObjectTemplate()->getFullTemplateString()) {
		error(
				"hair " + hairTemplate
						+ " is not compatible with this creature player "
						+ creature->getObjectTemplate()->getFullTemplateString());
		return;
	}

	if (!hairAssetData->isAvailableAtCreation()) {
		error("hair " + hairTemplate + " not available at creation");
		return;
	}

	ManagedReference<SceneObject*> hair = zoneServer->createObject(
			hairTemplate.hashCode(), 1);

	//TODO: Validate hairCustomization
	if (hair == NULL) {
		return;
	}

	Locker locker(hair);

	if (!hair->isTangibleObject()) {
		hair->destroyObjectFromDatabase(true);
		return;
	}

	TangibleObject* tanoHair = cast<TangibleObject*>(hair.get());
	tanoHair->setContainerDenyPermission("owner",
			ContainerPermissions::MOVECONTAINER);
	tanoHair->setContainerDefaultDenyPermission(
			ContainerPermissions::MOVECONTAINER);

	String appearanceFilename =
			tanoHair->getObjectTemplate()->getAppearanceFilename();

	CustomizationVariables data;

	data.parseFromClientString(hairCustomization);

	if (ImageDesignManager::validateCustomizationString(&data,
			appearanceFilename, -1))
		tanoHair->setCustomizationString(hairCustomization);

	creature->transferObject(tanoHair, 4);
}
int PetDeedImplementation::handleObjectMenuSelect(CreatureObject* player, byte selectedID) {
	if (selectedID == 21) {
		if(generated || !player->hasSkill("outdoors_bio_engineer_novice") || !isASubChildOf(player))
			return 1;
		if (player->isRidingMount()) {
			player->sendSystemMessage("You cannot sample DNA while mounted");
			return 1;
		}

		if(player->getPendingTask("sampledeed") != NULL) {
			player->sendSystemMessage("@bio_engineer:harvest_dna_already_harvesting");
			return 1;
		}
		int skillMod = player->getSkillMod("dna_harvesting");
		if (skillMod < 1 || level > skillMod + 15) {
			player->sendSystemMessage("@bio_engineer:harvest_dna_skill_too_low");
			return 1;
		}

		Locker clocker(_this.get());

		ManagedReference<SampleDeedTask*> task = new SampleDeedTask(_this.get(), player);
		player->addPendingTask("sampledeed",task,0);
		return 0;
	}
	if (selectedID == 20) {

		if (generated || !isASubChildOf(player))
			return 1;

		if (player->isInCombat() || player->getParentRecursively(SceneObjectType::BUILDING) != NULL) {
			player->sendSystemMessage("@pet/pet_menu:cant_call"); //You can only unpack vehicles while Outside and not in Combat.
			return 1;
		}

		ManagedReference<SceneObject*> datapad = player->getSlottedObject("datapad");

		if (datapad == NULL) {
			player->sendSystemMessage("Datapad doesn't exist when trying to call pet");
			return 1;
		}
		if (datapad->getContainerObjectsSize() >= datapad->getContainerVolumeLimit()) {
			player->sendSystemMessage("@faction_recruiter:datapad_full"); // Your datapad is full. You must first free some space.
			return 1;
		}
		// Does the player have room
		ManagedReference<PlayerManager*> playerManager = player->getZoneServer()->getPlayerManager();

		int numberStored = 0;
		int maxStoredPets = playerManager->getBaseStoredCreaturePets() + player->getSkillMod("stored_pets");

		for (int i = 0; i < datapad->getContainerObjectsSize(); ++i) {
			ManagedReference<SceneObject*> object = datapad->getContainerObject(i);

			if (object != NULL && object->isPetControlDevice()) {
				PetControlDevice* device = cast<PetControlDevice*>( object.get());

				if (device->getPetType() == PetManager::CREATUREPET) {
					if (++numberStored >= maxStoredPets) {
						player->sendSystemMessage("@pet/pet_menu:sys_too_many_stored"); // There are too many pets stored in this container. Release some of them to make room for more.
						return 1;
					}

				}
			}
		}
		// Can the player control it
		ManagedReference<PlayerObject*> ghost = player->getPlayerObject();

		int currentlySpawned = 0;
		int spawnedLevel = 0;
		int cLevel = level;
		int maxPets = player->getSkillMod("keep_creature");
		int maxLevelofPets = player->getSkillMod("tame_level");

		for (int i = 0; i < ghost->getActivePetsSize(); ++i) {
			ManagedReference<AiAgent*> object = ghost->getActivePet(i);

			if (object != NULL && object->isCreature()) {
				if (++currentlySpawned >= maxPets) {
					player->sendSystemMessage("@pet/pet_menu:too_many"); // You can't control any more pets. Store one first
					return 1;
				}

				spawnedLevel += object->getLevel();

				if ((spawnedLevel + cLevel) > maxLevelofPets) {
					player->sendSystemMessage("Taming this pet would exceed your control level ability.");
					return 1;
				}
			}
		}

		Reference<CreatureManager*> creatureManager = player->getZone()->getCreatureManager();
		if( creatureManager == NULL ){
			player->sendSystemMessage("Internal Pet Deed Error #307");
			return 1;
		}

		CreatureTemplateManager* creatureTemplateManager = CreatureTemplateManager::instance();
		ManagedReference<CreatureTemplate*> petTemplate = creatureTemplateManager->getTemplate( mobileTemplate.hashCode() );

		if (petTemplate == NULL) {
			player->sendSystemMessage("wrong pet template;mobileTemplate=[" + mobileTemplate + "]" );
			return 1;
		}

		bool isVicious = petTemplate->getPvpBitmask() & CreatureFlag::AGGRESSIVE;

		if (level > 10 || isVicious) {
			if (!player->hasSkill("outdoors_creaturehandler_novice") || (level > maxLevelofPets)) {
				player->sendSystemMessage("@pet/pet_menu:sys_lack_skill"); // You lack the skill to be able to tame that creature.
				return 1;
			}

			if (isVicious && player->getSkillMod("tame_aggro") < 1) {
				player->sendSystemMessage("@pet/pet_menu:sys_lack_skill"); // You lack the skill to be able to tame that creature.
				return 1;
			}
		}

		// All checks complete, lets setup the control device and do it.
		ManagedReference<PetControlDevice*> controlDevice = (server->getZoneServer()->createObject(controlDeviceObjectTemplate.hashCode(), 1)).castTo<PetControlDevice*>();

		if (controlDevice == NULL) {
			player->sendSystemMessage("wrong pet control device;controlDevice=[" + controlDeviceObjectTemplate + "]" );
			return 1;
		}

		Locker locker(controlDevice);

		String templateToSpawn = creatureManager->getTemplateToSpawn(mobileTemplate.hashCode());
		ManagedReference<CreatureObject*> creatureObject = creatureManager->createCreature(templateToSpawn.hashCode(), true, 0 );
		if( creatureObject == NULL ) {
			controlDevice->destroyObjectFromDatabase(true);
			player->sendSystemMessage("wrong pet template;mobileTemplate=[" + mobileTemplate + "]" );
			return 1;
		}

		Locker clocker(creatureObject, player);

		ManagedReference<Creature*> pet = creatureObject.castTo<Creature*>();
		if( pet == NULL ) {
			controlDevice->destroyObjectFromDatabase(true);
			creatureObject->destroyObjectFromDatabase(true);
			player->sendSystemMessage("Internal Pet Deed Error #348" );
			return 1;
		}

		ObjectManager* objectManager = server->getZoneServer()->getObjectManager();
		pet->setPetDeed(_this.get());
		pet->loadTemplateData( petTemplate );
		pet->setCustomObjectName(StringIdManager::instance()->getStringId(*pet->getObjectName()), true);
		pet->createChildObjects();
		pet->setBaby(false);
		// update base stats on the pet now
		// We will store the deed pointer to the aiagent before serialization

		// Copy color customization from deed to pet
		CustomizationVariables* customVars = getCustomizationVariables();
		if( customVars != NULL ){
			for (int i = 0; i < customVars->size(); ++i) {
				uint8 id = customVars->elementAt(i).getKey();
				int16 val = customVars->elementAt(i).getValue();

				String name = CustomizationIdManager::instance()->getCustomizationVariable(id);
				pet->setCustomizationVariable( name, val, true );
			}
		}
		// then this is complete
		StringId s;
		s.setStringId(pet->getObjectName()->getFullPath());
		controlDevice->setControlledObject(pet);
		controlDevice->setObjectName(s);
		controlDevice->setPetType(PetManager::CREATUREPET);
		controlDevice->setMaxVitality(100);
		controlDevice->setVitality(100);
		controlDevice->setGrowthStage(1);
		controlDevice->updateStatus(1);

		if (!datapad->transferObject(controlDevice, -1)) {
			controlDevice->destroyObjectFromDatabase(true);
			return 1;
		}

		datapad->broadcastObject(controlDevice, true);
		controlDevice->growPet(player,true);
		controlDevice->callObject(player);

		//Remove the deed from it's container.
		ManagedReference<SceneObject*> deedContainer = getParent().get();

		if (deedContainer != NULL) {
			destroyObjectFromWorld(true);
		}

		generated = true;
		player->sendSystemMessage("@pet/pet_menu:device_added"); // "A control device has been added to your datapad."
		return 0;
	}

	return DeedImplementation::handleObjectMenuSelect(player, selectedID);
}
void DestroyMissionObjectiveImplementation::spawnLair() {
	ManagedReference<MissionObject* > mission = this->mission.get();

	ManagedReference<MissionSpawnActiveArea* > spawnActiveArea = this->spawnActiveArea;

	if (spawnActiveArea == NULL)
		return;

	if (lairObject != NULL && lairObject->getZone() != NULL)
		return;

	Zone* zone = spawnActiveArea->getZone();

	Locker locker(spawnActiveArea);

	spawnActiveArea->destroyObjectFromWorld(true);

	Vector3 pos = findValidSpawnPosition(zone);

	ManagedReference<WaypointObject*> waypoint = mission->getWaypointToMission();

	if (waypoint == NULL) {
		waypoint = mission->createWaypoint();
	}

	waypoint->setPosition(pos.getX(), 0, pos.getY());
	mission->updateMissionLocation();

	mission->setStartPosition(pos.getX(), pos.getY());

	//TODO: find correct string id
	ManagedReference<CreatureObject*> player = getPlayerOwner();

	if (player != NULL) {
		player->sendSystemMessage("Transmission Received: Mission Target has been located.  Mission waypoint has been updated to exact location");
	}

	LairTemplate* lair = CreatureTemplateManager::instance()->getLairTemplate(lairTemplate.hashCode());

	if (lair == NULL) {
		error("incorrect lair template in destroy mission objective " + lairTemplate);
		abort();
		return;
	}

	if (lairObject == NULL) {
		String buildingToSpawn = lair->getMissionBuilding(difficulty);

	 	if (buildingToSpawn.isEmpty()) {
	 		error("error spawning " + buildingToSpawn);
	 		abort();
	 		return;
	 	}

		lairObject = zone->getZoneServer()->createObject(buildingToSpawn.hashCode(), 0).castTo<LairObject*>();

	 	if (lairObject == NULL) {
	 		error("error spawning " + buildingToSpawn);
	 		abort();
	 		return;
	 	}

	 	Locker locker(lairObject);

	 	lairObject->setFaction(lair->getFaction());
	 	lairObject->setPvpStatusBitmask(CreatureFlag::ATTACKABLE);
	 	lairObject->setOptionsBitmask(0, false);
	 	lairObject->setMaxCondition(difficultyLevel * (900 + System::random(200)));
	 	lairObject->setConditionDamage(0, false);
	 	lairObject->initializePosition(pos.getX(), pos.getZ(), pos.getY());
	 	lairObject->setDespawnOnNoPlayersInRange(false);

		ManagedReference<MissionObserver*> observer = new MissionObserver(_this.get());
		addObserver(observer, true);

		lairObject->registerObserver(ObserverEventType::OBJECTDESTRUCTION, observer);

	 	ManagedReference<DestroyMissionLairObserver*> lairObserver = new DestroyMissionLairObserver();
	 	lairObserver->deploy();
	 	lairObserver->setLairTemplate(lair);
	 	lairObserver->setDifficulty(difficulty);
	 	lairObserver->setObserverType(ObserverType::LAIR);
	 	lairObserver->setSize(mission->getSize());

	 	lairObject->registerObserver(ObserverEventType::OBJECTDESTRUCTION, lairObserver);
	 	lairObject->registerObserver(ObserverEventType::DAMAGERECEIVED, lairObserver);
	 	lairObject->registerObserver(ObserverEventType::AIMESSAGE, lairObserver);
	 	lairObject->registerObserver(ObserverEventType::OBJECTREMOVEDFROMZONE, lairObserver);

		zone->transferObject(lairObject, -1, true);

		lairObserver->checkForNewSpawns(lairObject, NULL, true);
	}

	if (lairObject != NULL && lairObject->getZone() == NULL) {
		zone->transferObject(lairObject, -1, true);
	}
}