int CraftingSessionImplementation::cancelSession() {
	ManagedReference<CraftingTool*> craftingTool = this->craftingTool.get();
	ManagedReference<CreatureObject*> crafter = this->crafter.get();
	ManagedReference<PlayerObject*> crafterGhost = this->crafterGhost.get();
	ManagedReference<CraftingStation*> craftingStation = this->craftingStation.get();

	if(craftingTool != NULL)
		craftingTool->dropActiveSession(SessionFacadeType::CRAFTING);

	if (crafter != NULL) {
		crafter->dropActiveSession(SessionFacadeType::CRAFTING);
		// DPlay9 *****************************
		PlayerObjectDeltaMessage9* dplay9 = new PlayerObjectDeltaMessage9(
				crafter->getPlayerObject());
		dplay9->setCraftingState(0);
		dplay9->close();
		crafter->sendMessage(dplay9);
		// *************************************
	}

	if(crafterGhost != NULL && crafterGhost->getDebug()) {
		crafter->sendSystemMessage("*** Canceling crafting session ***");
	}

	return clearSession();
}
int SlicingSessionImplementation::cancelSession() {
	ManagedReference<CreatureObject*> player = this->player.get();
	ManagedReference<TangibleObject*> tangibleObject = this->tangibleObject.get();
	if (player != NULL) {
		player->dropActiveSession(SessionFacadeType::SLICING);
		player->getPlayerObject()->removeSuiBoxType(SuiWindowType::SLICING_MENU);
	}
	if (tangibleObject != NULL)
		tangibleObject->dropActiveSession(SessionFacadeType::SLICING);
	clearSession();
	return 0;
}
void EntertainingSessionImplementation::stopDancing() {
	ManagedReference<CreatureObject*> entertainer = this->entertainer.get();

	if (entertainer == NULL)
		return;

	Locker locker(entertainer);

	if (!dancing)
		return;

	dancing = false;

	entertainer->sendSystemMessage("@performance:dance_stop_self");

	performanceName = "";

	sendEntertainingUpdate(entertainer, 0.8025000095f, entertainer->getPerformanceAnimation(), 0, 0);

	if (entertainer->getPosture() == CreaturePosture::SKILLANIMATING)
		entertainer->setPosture(CreaturePosture::UPRIGHT);


	ManagedReference<PlayerManager*> playerManager = entertainer->getZoneServer()->getPlayerManager();

	while (watchers.size() > 0) {
		ManagedReference<CreatureObject*> watcher = watchers.elementAt(0).getKey();

		Locker clocker(watcher, entertainer);

		playerManager->stopWatch(watcher, entertainer->getObjectID(), true, true, false);

		if (!watcher->isWatching())
			sendEntertainmentUpdate(watcher, 0, "", true);

		watchers.drop(watcher);
	}

	if (tickTask != NULL && tickTask->isScheduled())
		tickTask->cancel();

	updateEntertainerMissionStatus(false, MissionObject::DANCER);

	entertainer->notifyObservers(ObserverEventType::STOPENTERTAIN, entertainer);

	entertainer->dropObserver(ObserverEventType::POSTURECHANGED, observer);

	if (!dancing && !playingMusic) {
		ManagedReference<PlayerObject*> entPlayer = entertainer->getPlayerObject();
		if (entPlayer != NULL && entPlayer->getPerformanceBuffTarget() != 0)
			entPlayer->setPerformanceBuffTarget(0);

		entertainer->dropActiveSession(SessionFacadeType::ENTERTAINING);
	}
}
int ImageDesignSessionImplementation::cancelSession() {
	ManagedReference<CreatureObject*> designerCreature = this->designerCreature.get();
	ManagedReference<CreatureObject*> targetCreature = this->targetCreature.get();

	if (designerCreature != NULL) {
		designerCreature->dropActiveSession(SessionFacadeType::IMAGEDESIGN);

		if (positionObserver != NULL)
			designerCreature->dropObserver(ObserverEventType::POSITIONCHANGED, positionObserver);
	}

	if (targetCreature != NULL) {
		targetCreature->dropActiveSession(SessionFacadeType::IMAGEDESIGN);

		if (positionObserver != NULL)
			targetCreature->dropObserver(ObserverEventType::POSITIONCHANGED, positionObserver);
	}

	dequeueIdTimeoutEvent();

	return 0;
}
void EntertainingSessionImplementation::stopPlayingMusic() {
	ManagedReference<CreatureObject*> entertainer = this->entertainer.get();

	Locker locker(entertainer);

	if (!playingMusic)
		return;

	playingMusic = false;
	entertainer->sendSystemMessage("@performance:music_stop_self");

	sendEntertainingUpdate(entertainer, 0.8025000095f, entertainer->getPerformanceAnimation(), 0, 0);

	performanceName = "";
	entertainer->setListenToID(0);

	if (entertainer->getPosture() == CreaturePosture::SKILLANIMATING)
		entertainer->setPosture(CreaturePosture::UPRIGHT);

	if (externalInstrument != NULL && externalInstrument->isBeingUsed())
		externalInstrument->setBeingUsed(false);

	externalInstrument = NULL;

	ManagedReference<PlayerManager*> playerManager = entertainer->getZoneServer()->getPlayerManager();

	while (listeners.size() > 0) {
		ManagedReference<CreatureObject*> listener = listeners.elementAt(0).getKey();

		Locker clocker(listener, entertainer);

		playerManager->stopListen(listener, entertainer->getObjectID(), true, true, false);

		if (!listener->isWatching())
			sendEntertainmentUpdate(listener, 0, "", true);

		listeners.drop(listener);
	}

	if (tickTask != NULL && tickTask->isScheduled())
		tickTask->cancel();

	targetInstrument = false;
	updateEntertainerMissionStatus(false, MissionObject::MUSICIAN);

	entertainer->notifyObservers(ObserverEventType::STOPENTERTAIN, entertainer);

	entertainer->dropObserver(ObserverEventType::POSTURECHANGED, observer);

	ManagedReference<GroupObject*> group = entertainer->getGroup();

	if (group != NULL) {
		bool otherPlaying = group->isOtherMemberPlayingMusic(entertainer);

		if (!otherPlaying) {
			Locker locker(group);

			group->setBandSong("");
		}
	}

	if (!dancing && !playingMusic) {
		ManagedReference<PlayerObject*> entPlayer = entertainer->getPlayerObject();
		if (entPlayer != NULL && entPlayer->getPerformanceBuffTarget() != 0)
			entPlayer->setPerformanceBuffTarget(0);

		entertainer->dropActiveSession(SessionFacadeType::ENTERTAINING);
	}
}
void ImageDesignSessionImplementation::updateImageDesign(CreatureObject* updater, uint64 designer, uint64 targetPlayer, uint64 tent, int type, const ImageDesignData& data) {
	ManagedReference<CreatureObject*> strongReferenceTarget = targetCreature.get();
	ManagedReference<CreatureObject*> strongReferenceDesigner = designerCreature.get();

	if (strongReferenceTarget == NULL || strongReferenceDesigner == NULL)
		return;

	Locker locker(strongReferenceDesigner);
	Locker clocker(strongReferenceTarget, strongReferenceDesigner);

	imageDesignData = data;

	CreatureObject* targetObject = NULL;

	if (updater == strongReferenceDesigner)
		targetObject = strongReferenceTarget;
	else
		targetObject = strongReferenceDesigner;

	//ManagedReference<SceneObject*> obj = targetObject->getParentRecursively(SceneObjectType::SALONBUILDING);
	//tent = obj != NULL ? obj->getObjectID()

	ImageDesignChangeMessage* message = new ImageDesignChangeMessage(targetObject->getObjectID(), designer, targetPlayer, tent, type);

	imageDesignData.insertToMessage(message);

	bool commitChanges = false;

	if (imageDesignData.isAcceptedByDesigner()) {
		commitChanges = true;

		if (strongReferenceDesigner != strongReferenceTarget && !imageDesignData.isAcceptedByTarget()) {
			commitChanges = false;

			if (idTimeoutEvent == NULL)
				idTimeoutEvent = new ImageDesignTimeoutEvent(_this.get());

			if (!idTimeoutEvent->isScheduled())
				idTimeoutEvent->schedule(120000); //2 minutes
		} else {
			commitChanges = doPayment();
		}
	}

	//System::out << h << endl;
	if (commitChanges) {
		//TODO: set XP Values

		int xpGranted = 0; // Minimum Image Design XP granted (base amount).

		//if (imageDesignData.mi)

		String hairTemplate = imageDesignData.getHairTemplate();

		bool statMig = imageDesignData.isStatMigrationRequested();

		if (statMig && strongReferenceDesigner->getParentRecursively(SceneObjectType::SALONBUILDING).get().get()
				&& strongReferenceDesigner->getParentRecursively(SceneObjectType::SALONBUILDING).get().get() && strongReferenceDesigner != strongReferenceTarget) {

			ManagedReference<Facade*> facade = strongReferenceTarget->getActiveSession(SessionFacadeType::MIGRATESTATS);
			ManagedReference<MigrateStatsSession*> session = dynamic_cast<MigrateStatsSession*>(facade.get());

			if (session != NULL) {
				session->migrateStats();
				xpGranted = 2000;
			}
		}

		VectorMap<String, float>* bodyAttributes = imageDesignData.getBodyAttributesMap();
		VectorMap<String, uint32>* colorAttributes = imageDesignData.getColorAttributesMap();

		ImageDesignManager* imageDesignManager = ImageDesignManager::instance();

		hairObject = strongReferenceTarget->getSlottedObject("hair").castTo<TangibleObject*>();

		if (type == 1) {
			String oldCustomization;

			if (hairObject != NULL)
				hairObject->getCustomizationString(oldCustomization);

			hairObject = imageDesignManager->createHairObject(strongReferenceDesigner, strongReferenceTarget, imageDesignData.getHairTemplate(), imageDesignData.getHairCustomizationString());

			if (hairObject != NULL)
				hairObject->setCustomizationString(oldCustomization);

			if (xpGranted < 100)
				xpGranted = 100;
		}

		if (bodyAttributes->size() > 0) {
			if (xpGranted < 300)
				xpGranted = 300;
			for (int i = 0; i < bodyAttributes->size(); ++i) {
				VectorMapEntry<String, float>* entry = &bodyAttributes->elementAt(i);
				imageDesignManager->updateCustomization(strongReferenceDesigner, entry->getKey(), entry->getValue(), strongReferenceTarget);
			}
		}


		if (colorAttributes->size() > 0) {
			if(xpGranted < 100)
				xpGranted = 100;
			for (int i = 0; i < colorAttributes->size(); ++i) {
				VectorMapEntry<String, uint32>* entry = &colorAttributes->elementAt(i);
				imageDesignManager->updateColorCustomization(strongReferenceDesigner, entry->getKey(), entry->getValue(), hairObject, strongReferenceTarget);
			}
		}

		imageDesignManager->updateHairObject(strongReferenceTarget, hairObject);

		// Add holo emote
		String holoemote = imageDesignData.getHoloEmote();
		if( !holoemote.isEmpty() ){

			PlayerObject* ghost = strongReferenceTarget->getPlayerObject();
			ghost->setInstalledHoloEmote( holoemote );  // Also resets number of uses available

			strongReferenceTarget->sendSystemMessage("@image_designer:new_holoemote"); //"Congratulations! You have purchased a new Holo-Emote generator. Type '/holoemote help' for instructions."

			if(xpGranted < 100)
				xpGranted = 100;

		}

		// Drop the Session for both the designer and the targetCreature;
		strongReferenceDesigner->dropActiveSession(SessionFacadeType::IMAGEDESIGN);
		strongReferenceTarget->dropActiveSession(SessionFacadeType::IMAGEDESIGN);

		// Award XP.
		PlayerManager* playerManager = strongReferenceDesigner->getZoneServer()->getPlayerManager();

		if (playerManager != NULL && xpGranted > 0) {
			if(strongReferenceDesigner == strongReferenceTarget)
				xpGranted /= 2;
			playerManager->awardExperience(strongReferenceDesigner, "imagedesigner", xpGranted, true);
		}

		if (idTimeoutEvent != NULL && idTimeoutEvent->isScheduled())
			dequeueIdTimeoutEvent();
	}

	targetObject->sendMessage(message);
}