//-----------------------------------------------------------------------------
// purgeExcessMotion()
//-----------------------------------------------------------------------------
void LLMotionController::purgeExcessMotions()
{
	if (mLoadedMotions.size() > MAX_MOTION_INSTANCES)
	{
		// clean up deprecated motions
		for (motion_set_t::iterator deprecated_motion_it = mDeprecatedMotions.begin(); 
			 deprecated_motion_it != mDeprecatedMotions.end(); )
		{
			motion_set_t::iterator cur_iter = deprecated_motion_it++;
			LLMotion* cur_motionp = *cur_iter;
			if (!isMotionActive(cur_motionp))
			{
				// Motion is deprecated so we know it's not cannonical,
				//  we can safely remove the instance
				removeMotionInstance(cur_motionp); // modifies mDeprecatedMotions
				mDeprecatedMotions.erase(cur_iter);
			}
		}
	}

	std::set<LLUUID> motions_to_kill;
	if (mLoadedMotions.size() > MAX_MOTION_INSTANCES)
	{
		// too many motions active this frame, kill all blenders
		mPoseBlender.clearBlenders();
		for (motion_set_t::iterator loaded_motion_it = mLoadedMotions.begin(); 
			 loaded_motion_it != mLoadedMotions.end(); 
			 ++loaded_motion_it)
		{
			LLMotion* cur_motionp = *loaded_motion_it;
			// motion isn't playing, delete it
			if (!isMotionActive(cur_motionp))
			{
				motions_to_kill.insert(cur_motionp->getID());
			}
		}
	}
	
	// clean up all inactive, loaded motions
	for (std::set<LLUUID>::iterator motion_it = motions_to_kill.begin();
		motion_it != motions_to_kill.end();
		++motion_it)
	{
		// look up the motion again by ID to get canonical instance
		// and kill it only if that one is inactive
		LLUUID motion_id = *motion_it;
		LLMotion* motionp = findMotion(motion_id);
		if (motionp && !isMotionActive(motionp))
		{
			removeMotion(motion_id);
		}
	}

	if (mLoadedMotions.size() > 2*MAX_MOTION_INSTANCES)
	{
		LL_WARNS_ONCE("Animation") << "> " << 2*MAX_MOTION_INSTANCES << " Loaded Motions" << llendl;
	}
}
//-----------------------------------------------------------------------------
// purgeExcessMotion()
//-----------------------------------------------------------------------------
void LLMotionController::purgeExcessMotions()
{
	//<singu>
	// The old code attempted to remove non-active motions from mDeprecatedMotions,
	// but that is nonsense: there are no motions in mDeprecatedMotions that are not active.
	if (mLoadedMotions.size() <= MAX_MOTION_INSTANCES)
	{
		// Speed up, no need to create motions_to_kill.
		return;
	}
	//</singu>

	std::set<LLUUID> motions_to_kill;

	if (1)	// Singu: leave indentation alone...
	{
		// too many motions active this frame, kill all blenders
		mPoseBlender.clearBlenders();
		for (motion_set_t::iterator loaded_motion_it = mLoadedMotions.begin(); 
			 loaded_motion_it != mLoadedMotions.end(); 
			 ++loaded_motion_it)
		{
			LLMotion* cur_motionp = *loaded_motion_it;
			// motion isn't playing, delete it
			if (!isMotionActive(cur_motionp))
			{
				motions_to_kill.insert(cur_motionp->getID());
			}
		}
	}
	
	// clean up all inactive, loaded motions
	for (std::set<LLUUID>::iterator motion_it = motions_to_kill.begin();
		motion_it != motions_to_kill.end();
		++motion_it)
	{
		// look up the motion again by ID to get canonical instance
		// and kill it only if that one is inactive
		LLUUID motion_id = *motion_it;
		LLMotion* motionp = findMotion(motion_id);
		if (motionp && !isMotionActive(motionp))
		{
			removeMotion(motion_id);
		}
	}

	if (mLoadedMotions.size() > 2*MAX_MOTION_INSTANCES)
	{
		LL_WARNS_ONCE("Animation") << "> " << 2*MAX_MOTION_INSTANCES << " Loaded Motions" << llendl;
	}
}
BOOL LLMotionController::stopMotionInstance(LLMotion* motion, BOOL stop_immediate)
{
	if (!motion)
	{
		return FALSE;
	}

	// If on active list, stop it
	if (isMotionActive(motion) && !motion->isStopped())
	{
		motion->setStopTime(mAnimTime);
		if (stop_immediate)
		{
			deactivateMotionInstance(motion);
		}
		return TRUE;
	}
	else if (isMotionLoading(motion))
	{
		motion->setStopped(TRUE);
		return TRUE;
	}

	return FALSE;
}
Beispiel #4
0
//-----------------------------------------------------------------------------
// stopMotionLocally()
//-----------------------------------------------------------------------------
BOOL LLMotionController::stopMotionLocally(const LLUUID &id, BOOL stop_immediate)
{
	// if already inactive, return false
	LLMotion *motion = findMotion(id);
	if (!motion)
	{
		return FALSE;
	}

	// If on active list, stop it
	if (isMotionActive(motion) && !motion->isStopped())
	{
		// when using timesteps, set stop time to last frame's time, otherwise grab current timer value
		// *FIX: should investigate this inconsistency...hints of obscure bugs

		F32 stop_time = (mTimeStep != 0.f || mPaused) ? (mTime) : mTimeOffset + (mTimer.getElapsedTimeF32() * mTimeFactor);
		motion->setStopTime(stop_time);

		if (stop_immediate)
		{
			deactivateMotion(motion, false);
		}
		return TRUE;
	}
	else if (isMotionLoading(motion))
	{
		motion->setStopped(TRUE);
		return TRUE;
	}

	return FALSE;
}
Beispiel #5
0
//-----------------------------------------------------------------------------
// startMotion()
//-----------------------------------------------------------------------------
BOOL LLMotionController::startMotion(const LLUUID &id, F32 start_offset)
{
	// look for motion in our list of created motions
	LLMotion *motion = createMotion(id);

	if (!motion)
	{
		return FALSE;
	}
	//if the motion is already active, then we're done
	else if (isMotionActive(motion)) // motion is playing and...
	{	
		if (motion->isStopped()) // motion has been stopped
		{
			deactivateMotion(motion, false);
		}
		else if (mTime < motion->mSendStopTimestamp)	// motion is still active
		{
			return TRUE;
		}
	}

//	llinfos << "Starting motion " << name << llendl;
	return activateMotion(motion, mTime - start_offset);
}
Beispiel #6
0
//-----------------------------------------------------------------------------
// addLoadedMotion()
//-----------------------------------------------------------------------------
void LLMotionController::addLoadedMotion(LLMotion* motionp)
{
	if (mLoadedMotions.size() > MAX_MOTION_INSTANCES)
	{
		// too many motions active this frame, kill all blenders
		mPoseBlender.clearBlenders();

		for (U32 i = 0; i < mLoadedMotions.size(); i++)
		{
			LLMotion* cur_motionp = mLoadedMotions.front();
			mLoadedMotions.pop_front();
			
			// motion isn't playing, delete it
			if (!isMotionActive(cur_motionp))
			{
				mCharacter->requestStopMotion(cur_motionp);
				mAllMotions.erase(cur_motionp->getID());
				delete cur_motionp;
				if (mLoadedMotions.size() <= MAX_MOTION_INSTANCES)
				{
					break;
				}
			}
			else
			{
				// put active motion on back
				mLoadedMotions.push_back(cur_motionp);
			}
		}
	}
	mLoadedMotions.push_back(motionp);
}
//-----------------------------------------------------------------------------
// startMotion()
//-----------------------------------------------------------------------------
BOOL LLMotionController::startMotion(const LLUUID &id, F32 start_offset)
{
	// do we have an instance of this motion for this character?
	LLMotion *motion = findMotion(id);

	// motion that is stopping will be allowed to stop but
	// replaced by a new instance of that motion
	if (motion
		&& !mPaused
		&& motion->canDeprecate()
		&& motion->isActive()											// singu: do not deprecate motions that are not active.
		&& motion->getFadeWeight() > 0.01f // not LOD-ed out
		&& (motion->isBlending() || motion->getStopTime() != 0.f))
	{
		deprecateMotionInstance(motion);
		// force creation of new instance
		motion = NULL;
	}

	// create new motion instance
	if (!motion)
	{
		motion = createMotion(id);
	}

	if (!motion)
	{
		return FALSE;
	}
	//if the motion is already active and allows deprecation, then let it keep playing
	else if (motion->canDeprecate() && isMotionActive(motion))
	{	
		return TRUE;
	}

//	llinfos << "Starting motion " << name << llendl;
	//<singu>
	F32 start_time = mAnimTime - start_offset;
	if (!mDisableSyncing)
	{
	  start_time = motion->syncActivationTime(start_time);
	}
	++mDisableSyncing;
	//</singu>
	BOOL res = activateMotionInstance(motion, start_time);
	//<singu>
	--mDisableSyncing;
	//</singu>
	return res;
}