Ejemplo n.º 1
0
// Updates the user's avatar's appearance
void LLWearable::writeToAvatar( BOOL set_by_user )
{
	LLVOAvatar* avatar = gAgent.getAvatarObject();
	llassert( avatar );
	if( !avatar )
	{
		return;
	}

	ESex old_sex = avatar->getSex();

	// Pull params
	for( LLVisualParam* param = avatar->getFirstVisualParam(); param; param = avatar->getNextVisualParam() )
	{
		if (((LLViewerVisualParam*)param)->getWearableType() == mType && param->isTweakable())
		{
			S32 param_id = param->getID();
			F32 weight = get_if_there(mVisualParamMap, param_id, param->getDefaultWeight());
			// only animate with user-originated changes
			if (set_by_user)
			{
				param->setAnimationTarget(weight, set_by_user);
			}
			else
			{
				avatar->setVisualParamWeight( param_id, weight, set_by_user );
			}
		}
	}

	// only interpolate with user-originated changes
	if (set_by_user)
	{
		avatar->startAppearanceAnimation(TRUE, TRUE);
	}

	// Pull texture entries
	for( S32 te = 0; te < TEX_NUM_INDICES; te++ )
	{
		if( LLVOAvatar::getTEWearableType((ETextureIndex) te ) == mType )
		{
			const LLUUID& image_id = get_if_there(mTEMap, te, LLVOAvatar::getDefaultTEImageID((ETextureIndex) te ) );
			LLViewerImage* image = gImageList.getImage( image_id );
			avatar->setLocTexTE( te, image, set_by_user );
		}
	}

	avatar->updateVisualParams();

	if( gFloaterCustomize )
	{
		LLViewerInventoryItem* item;
		item = (LLViewerInventoryItem*)gInventory.getItem(gAgent.getWearableItem(mType));
		U32 perm_mask = PERM_NONE;
		BOOL is_complete = FALSE;
		if(item)
		{
			perm_mask = item->getPermissions().getMaskOwner();
			is_complete = item->isComplete();
			if(!is_complete)
			{
				item->fetchFromServer();
			}
		}
		gFloaterCustomize->setWearable(mType, this, perm_mask, is_complete);
		LLFloaterCustomize::setCurrentWearableType( mType );
	}

	ESex new_sex = avatar->getSex();
	if( old_sex != new_sex )
	{
		avatar->updateSexDependentLayerSets( set_by_user );
	}	
	
	avatar->updateMeshTextures();

//	if( set_by_user )
//	{
//		gAgent.sendAgentSetAppearance();
//	}
}
Ejemplo n.º 2
0
// Creates new parameters for the given wearable and applies them to the avatar.
void LLGenePool::spawn( EWearableType type )
{
	LLVOAvatar* avatar = gAgent.getAvatarObject();
	if( !avatar )
	{
		return;
	}
	
	if( !mLoaded )
	{
		if( !load() )
		{
			return;
		}
	}

	if( mArchetypes.count() < 1 )
	{
		return;
	}

	// Only consider archetypes that have the same sex as you have already.
	LLVisualParam* male_param = avatar->getVisualParam( "male" );

	if (!male_param)
	{
		llwarns << "The hard coded \'male\' parameter passed to avatar->getVisualParam() in LLGenePool::spawn() is no longer valid."
				<< llendl;
		return;
	}

	S32 male_param_id = male_param->getID();
	F32 sex_weight = male_param->getWeight();

	S32 i = 0;
	S32 j = 0;
	S32 k = 0;
	const S32 MAX_CYCLES = 1000;
	S32 cycles = 0;

	F32 cur_sex_weight = 0.f;
	do
	{
		i = rand() % mArchetypes.count();
		cur_sex_weight = mArchetypes[i]->getParam(male_param_id, 0.f);
		cycles++;
		if (cur_sex_weight != sex_weight)
		{
			break;
		}
	} while((cycles < MAX_CYCLES));

	if( cycles >= MAX_CYCLES )
	{
		return;
	}

	LLAppearance* arch1 = mArchetypes[i];
	LLAppearance* arch2 = NULL;
	LLAppearance* arch3 = NULL;

	if( mArchetypes.count() > 1 )
	{
		cycles = 0;
    	do
    	{
    		j = rand() % mArchetypes.count();
			cur_sex_weight = mArchetypes[j]->getParam(male_param_id, 0.f);

			cycles++;
		} while( 
			(cycles < MAX_CYCLES) && 
			( (i == j) || (cur_sex_weight != sex_weight) )
		);

		if( cycles >= MAX_CYCLES )
		{
			return;
		}

    	arch2 = mArchetypes[j];
	}

	if( mArchetypes.count() > 2 )
	{
		cycles = 0;
    	do
    	{
    		k = rand() % mArchetypes.count();
			cur_sex_weight = mArchetypes[k]->getParam(male_param_id, 0.f);
			cycles++;
		} while( 
			(cycles < MAX_CYCLES) && 
			( (i == k) || (j == k) || (cur_sex_weight != sex_weight) )
		);

		if( cycles >= MAX_CYCLES )
		{
			return;
		}

    	arch3 = mArchetypes[k];
	}

	// Lame generation of barycentric coordinates
	F32 b1 = F32( rand() ) / RAND_MAX;
	F32 b2 = (F32( rand() ) / RAND_MAX) * (1.f - b1);
	F32 b3 = 1.f - b1 - b2;

//	ESex old_sex = avatar->getSex();

	// Pull params
	for( LLVisualParam* param = avatar->getFirstVisualParam(); param; param = avatar->getNextVisualParam() )
	{
		if( (((LLViewerVisualParam*)param)->getWearableType() == type) && (param->getGroup() == VISUAL_PARAM_GROUP_TWEAKABLE) )
		{
			S32 param_id = param->getID();

			// don't try to blend male/female param...as fp innaccuracy will break the [0 | 1] semantics
			if (param_id != male_param_id)
			{

				F32 weight1 = arch1->getParam( param_id, param->getDefaultWeight() );
				F32 net_weight = weight1;
				
				if( arch2 && arch3 )
				{
    				F32 weight2 = arch2->getParam( param_id, param->getDefaultWeight() );
    				F32 weight3 = arch3->getParam( param_id, param->getDefaultWeight() );
					net_weight = b1 * weight1 + b2 * weight2 + b3 * weight3;
				}
			
				param->setAnimationTarget(net_weight, TRUE);
			}
		}
	}

	// Find the archetype with the greatest influence
	LLAppearance* dominant_arch = arch1;
	if( (b2 > b1) && (b2 > b3) )
	{
		dominant_arch = arch2;
	}
	else
	if( (b3 > b1) && (b3 > b2) )
	{
		dominant_arch = arch3;
	}


	// Pull Textures from the dominant archetype
	for( S32 te = 0; te < LLVOAvatar::TEX_NUM_ENTRIES; te++ )
	{
		if( LLVOAvatar::isTextureIndexBaked( te ) )
		{
			continue;
		}

		if( LLVOAvatar::getTEWearableType( te ) == type )
		{
			LLUUID image_id = dominant_arch->getTexture( te );
			if( image_id.isNull() )
			{
				image_id = LLVOAvatar::getDefaultTEImageID( te );
			}

			LLViewerImage* image = gImageList.getImage( image_id );
			if( image )
			{
				avatar->setLocTexTE( te, image, TRUE );
			}
		}
	}

//	avatar->setVisualParamWeight( "male", sex_weight );

	avatar->startAppearanceAnimation(TRUE, TRUE);
	avatar->updateVisualParams();

// 	ESex new_sex = avatar->getSex();
//	if( old_sex != new_sex )
//	{
//		avatar->updateSexDependentLayerSets( TRUE );
//	}	
	
	avatar->updateMeshTextures();
    gAgent.sendAgentSetAppearance();
}