void CEffectsController::DetachEffect(const TAttachedEffectId effectId) { CRY_ASSERT(m_pOwnerEntity); TAttachedEffects::iterator effectIt = std::find(m_attachedEffects.begin(), m_attachedEffects.end(), effectId); if (effectIt != m_attachedEffects.end()) { const SEffectInfo& effectInfo = *effectIt; if (effectInfo.entityEffectSlot >= 0) { m_pOwnerEntity->FreeSlot(effectInfo.entityEffectSlot); } else { ICharacterInstance *pCharacter = m_pOwnerEntity->GetCharacter(effectInfo.characterEffectSlot); if (pCharacter) { IAttachmentManager *pAttachmentManager = pCharacter->GetIAttachmentManager(); IAttachment *pAttachment = pAttachmentManager->GetInterfaceByName(effectInfo.helperName.c_str()); if(pAttachment) { pAttachment->ClearBinding(); } } } m_attachedEffects.erase(effectIt); } }
void CAICorpse::AboutToBeRemoved() { IItemSystem* pItemSystem = g_pGame->GetIGameFramework()->GetIItemSystem(); ICharacterInstance* pCharacter = GetEntity()->GetCharacter(0); IAttachmentManager* pAttachmentManager = (pCharacter != NULL) ? pCharacter->GetIAttachmentManager() : NULL; for (uint32 i = 0; i < (uint32)m_attachedItemsInfo.size(); ++i) { AttachedItem& attachedItem = m_attachedItemsInfo[i]; IItem* pItem = pItemSystem->GetItem( attachedItem.id ); if((pItem != NULL) && ShouldDropOnCorpseRemoval( pItem->GetEntity()->GetClass() )) { IAttachment* pAttachment = (pAttachmentManager != NULL) ? pAttachmentManager->GetInterfaceByName( attachedItem.attachmentName.c_str() ) : NULL; if(pAttachment != NULL) { pAttachment->ClearBinding(); } pItem->Drop( 1.0f, false, true ); pItem->GetEntity()->SetFlags( pItem->GetEntity()->GetFlags() & ~ENTITY_FLAG_NO_SAVE ); attachedItem.id = 0; } } }
void DetachObject(SActivationInfo *pActInfo) { IAttachment *pAttachment = GetAttachment(pActInfo); if (pAttachment) { pAttachment->ClearBinding(); ActivateOutput(pActInfo, eOP_Detached, 0); } }
void OnEntityEvent( IEntity* pEntity, SEntityEvent& event ) { if (event.event==m_event) { if (m_pNewAttachment) { m_pNewAttachment->ClearBinding(); } } }
void CKVoltEffect::Leave() { if(m_particleEmitter) { gEnv->pParticleManager->DeleteEmitter(m_particleEmitter); m_particleEmitter->Release(); m_particleEmitter = NULL; } IAttachment* screenAttachment = GetScreenAttachment(); if(screenAttachment) { screenAttachment->ClearBinding(); } }
//------------------------------------------------------------------------ void CItem::ResetCharacterAttachment(int slot, const char *name) { ICharacterInstance *pCharacter = GetEntity()->GetCharacter(slot); if (!pCharacter) return; IAttachmentManager *pAttachmentManager = pCharacter->GetIAttachmentManager(); IAttachment *pAttachment = pAttachmentManager->GetInterfaceByName(name); if (!pAttachment) { GameWarning("Item '%s' trying to reset attachment '%s' which does not exist!", GetEntity()->GetName(), name); return; } pAttachment->ClearBinding(); }
//------------------------------------------------------------------------ int CScriptBind_Actor::ResetVulnerabilityEffects(IFunctionHandler *pH, int characterSlot) { CActor *pActor = GetActor(pH); if (!pActor) return pH->EndFunction(); IEntity* pEntity = pActor->GetEntity(); ICharacterInstance* pChar = pEntity->GetCharacter(characterSlot); if (pChar) { IAttachmentManager* pMan = pChar->GetIAttachmentManager(); for (int i=0; i<pMan->GetAttachmentCount(); ++i) { IAttachment* pAtt = pMan->GetInterfaceByIndex(i); if (strstr(pAtt->GetName(), "vulnerable")) pAtt->ClearBinding(); } } return pH->EndFunction(); }
void CAICorpse::HandleEvent( const SGameObjectEvent& gameObjectEvent ) { if(gameObjectEvent.event == eCGE_ItemTakenFromCorpse) { assert(gameObjectEvent.param != NULL); bool matchFound = false; const EntityId itemId = *static_cast<const EntityId*>(gameObjectEvent.param); for (uint32 i = 0; i < m_attachedItemsInfo.size(); ++i) { if(m_attachedItemsInfo[i].id == itemId) { ICharacterInstance* pCharacter = GetEntity()->GetCharacter(0); if(pCharacter != NULL) { IAttachment* pAttachment = pCharacter->GetIAttachmentManager()->GetInterfaceByName( m_attachedItemsInfo[i].attachmentName.c_str() ); if(pAttachment != NULL) { pAttachment->ClearBinding(); } } m_attachedItemsInfo.removeAt(i); matchFound = true; break; } } if(matchFound) { if(m_attachedItemsInfo.empty()) { m_priority = 0; //Lower the priority once all attached items have been removed } } } }
void CHandGrenades::UpdateStowedWeapons() { CActor *pOwnerActor = GetOwnerActor(); if (!pOwnerActor) return; ICharacterInstance *pOwnerCharacter = pOwnerActor->GetEntity()->GetCharacter(0); if (!pOwnerCharacter) return; IStatObj *pTPObj = GetEntity()->GetStatObj(eIGS_ThirdPerson); if (!pTPObj) return; int ammoCount = m_fm ? pOwnerActor->GetInventory()->GetAmmoCount(m_fm->GetAmmoType()) : 0; if (IsSelected() && (ammoCount > 0)) { ammoCount--; } if (!pOwnerActor->IsThirdPerson()) { ammoCount = 0; } int numGrenDiff = ammoCount - m_numStowedCopies; if(numGrenDiff != 0) { if (m_stowSlot < 0) { m_stowSlot = PickStowSlot(pOwnerCharacter->GetIAttachmentManager(), m_sharedparams->params.bone_attachment_01.c_str(), m_sharedparams->params.bone_attachment_02.c_str()); } if (m_stowSlot >= 0) { bool attach = numGrenDiff > 0; int tot = abs(numGrenDiff); IAttachmentManager *pAttachmentManager = pOwnerCharacter->GetIAttachmentManager(); IAttachment *pAttachment = NULL; for (int i=0; i<tot; i++) { //--- Generate the secondary slot from the first by adding one to the attachment name, is all we need at present... const char *attach1 = (m_stowSlot == 0) ? m_sharedparams->params.bone_attachment_01.c_str() : m_sharedparams->params.bone_attachment_02.c_str(); int lenAttachName = strlen(attach1); stack_string attach2(attach1, lenAttachName-1); attach2 += (attach1[lenAttachName-1]+1); if (attach) { pAttachment = pAttachmentManager->GetInterfaceByName(attach1); if(pAttachment && pAttachment->GetIAttachmentObject()) { pAttachment = pAttachmentManager->GetInterfaceByName(attach2); } if (pAttachment && !pAttachment->GetIAttachmentObject()) { CCGFAttachment *pCGFAttachment = new CCGFAttachment(); pCGFAttachment->pObj = pTPObj; pAttachment->AddBinding(pCGFAttachment); pAttachment->HideAttachment(0); pAttachment->HideInShadow(0); m_numStowedCopies++; } } else { pAttachment = pAttachmentManager->GetInterfaceByName(attach2); if(!pAttachment || !pAttachment->GetIAttachmentObject()) { pAttachment = pAttachmentManager->GetInterfaceByName(attach1); } if (pAttachment && pAttachment->GetIAttachmentObject()) { pAttachment->ClearBinding(); m_numStowedCopies--; } } } } } }
//------------------------------------------------------------------------ //Above function is almost the same, just some special stuff for flashlight //------------------------------------------------------------------------ uint32 CItem::AttachLightEx(int slot, uint32 id, bool attach, bool fakeLight /*= false */, bool castShadows /*= false*/, IRenderNode* pCasterException, float radius, const Vec3 &color, const float fSpecularMult, const char *projectTexture, float projectFov, const char *helper, const Vec3 &offset, const Vec3 &dir, const char* material, float fHDRDynamic) { if (m_stats.mounted) slot=eIGS_FirstPerson; if (radius<0.1f) return 0; if (attach) { CDLight light; light.SetLightColor(ColorF(color.x, color.y, color.z, 1.0f)); light.SetSpecularMult( fSpecularMult ); light.m_nLightStyle = 0; light.m_fLightFrustumAngle = 45.0f; light.m_fRadius = radius; light.m_fLightFrustumAngle = projectFov*0.5f; light.m_fHDRDynamic = fHDRDynamic; if(fakeLight) light.m_Flags |= DLF_FAKE; //Only on hight/very hight spec if(castShadows && (g_pGameCVars->i_lighteffects!=0)) light.m_Flags |= DLF_CASTSHADOW_MAPS; if (projectTexture && projectTexture[0]) { int flags = 0; light.m_pLightImage = gEnv->pRenderer->EF_LoadTexture(projectTexture, flags); if (!light.m_pLightImage || !light.m_pLightImage->IsTextureLoaded()) { GameWarning("Item '%s' failed to load projecting light texture '%s'!", GetEntity()->GetName(), projectTexture); return 0; } } if (light.m_fLightFrustumAngle && (light.m_pLightImage != NULL) && light.m_pLightImage->IsTextureLoaded()) light.m_Flags |= DLF_PROJECT; else { if (light.m_pLightImage) light.m_pLightImage->Release(); light.m_pLightImage = 0; light.m_Flags |= DLF_POINT; } IMaterial* pMaterial = 0; if (material && material[0]) pMaterial = gEnv->p3DEngine->GetMaterialManager()->LoadMaterial(material); // generate id ++m_effectGenId; while (!m_effectGenId || (m_effects.find(m_effectGenId) != m_effects.end())) ++m_effectGenId; SEntitySlotInfo slotInfo; SEffectInfo effectInfo; effectInfo.slot = -1; bool validSlot = GetEntity()->GetSlotInfo(slot, slotInfo) && (slotInfo.pCharacter || slotInfo.pStatObj); if (!validSlot || slotInfo.pStatObj) { // get helper position Vec3 position(0,0,0); if (validSlot) { IStatObj *pStatsObj = slotInfo.pStatObj; position = pStatsObj->GetHelperPos(helper); position = GetEntity()->GetSlotLocalTM(slot, false).TransformPoint(position); } position+=offset; // find a free slot SEntitySlotInfo dummy; int i=0; while (GetEntity()->GetSlotInfo(eIGS_Last+i, dummy)) i++; // move light slot to the helper position+offset effectInfo.helper = helper; effectInfo.slot = GetEntity()->LoadLight(eIGS_Last+i, &light); if (effectInfo.slot != -1 && pMaterial) GetEntity()->SetSlotMaterial(effectInfo.slot, pMaterial); Matrix34 tm = Matrix34(Matrix33::CreateRotationVDir(dir)); tm.SetTranslation(position); GetEntity()->SetSlotLocalTM(effectInfo.slot, tm); } else if (slotInfo.pCharacter) // bone attachment { effectInfo.helper = helper; effectInfo.characterSlot = slot; ICharacterInstance *pCharacter = slotInfo.pCharacter; IAttachmentManager *pAttachmentManager = pCharacter->GetIAttachmentManager(); IAttachment *pAttachment = pAttachmentManager->GetInterfaceByName(helper); if (!pAttachment) { GameWarning("Item '%s' trying to attach light to attachment '%s' which does not exist!", GetEntity()->GetName(), helper); return 0; } CLightAttachment *pLightAttachment = new CLightAttachment(); pLightAttachment->LoadLight(light); if (pMaterial) { if (ILightSource* pLightSource = pLightAttachment->GetLightSource()) pLightSource->SetMaterial(pMaterial); } if(light.m_Flags&DLF_CASTSHADOW_MAPS) { if (ILightSource* pLightSource = pLightAttachment->GetLightSource()) pLightSource->SetCastingException(pCasterException); } Matrix34 tm =Matrix34(Matrix33::CreateRotationVDir(dir)); tm.SetTranslation(offset); pAttachment->AddBinding(pLightAttachment); pAttachment->SetAttRelativeDefault(QuatT(tm)); } m_effects.insert(TEffectInfoMap::value_type(m_effectGenId, effectInfo)); return m_effectGenId; } else if (id) { TEffectInfoMap::iterator it = m_effects.find(id); if (it == m_effects.end()) return 0; SEffectInfo &info = it->second; if (info.slot>-1) { GetEntity()->FreeSlot(info.slot); } else { ICharacterInstance *pCharacter = GetEntity()->GetCharacter(info.characterSlot); if (pCharacter) { IAttachmentManager *pAttachmentManager = pCharacter->GetIAttachmentManager(); IAttachment *pAttachment = pAttachmentManager->GetInterfaceByName(info.helper.c_str()); pAttachment->ClearBinding(); } } m_effects.erase(it); } return 0; }
//------------------------------------------------------------------------ uint32 CItem::AttachEffect(int slot, uint32 id, bool attach, const char *effectName, const char *helper, const Vec3 &offset, const Vec3 &dir, float scale, bool prime) { if (m_stats.mounted) slot=eIGS_FirstPerson; if (attach) { if (!g_pGameCVars->i_particleeffects) return 0; IParticleEffect *pParticleEffect = gEnv->pParticleManager->FindEffect(effectName); if (!pParticleEffect) return 0; // generate id ++m_effectGenId; while (!m_effectGenId || (m_effects.find(m_effectGenId) != m_effects.end())) ++m_effectGenId; SEntitySlotInfo slotInfo; SEffectInfo effectInfo; bool validSlot = GetEntity()->GetSlotInfo(slot, slotInfo) && (slotInfo.pCharacter || slotInfo.pStatObj); if (!validSlot || slotInfo.pStatObj || (!helper || !helper[0])) { // get helper position Vec3 position(0,0,0); if (validSlot && helper && helper[0]) { IStatObj *pStatsObj = slotInfo.pStatObj; position = pStatsObj->GetHelperPos(helper); position = GetEntity()->GetSlotLocalTM(slot, false).TransformPoint(position); } position+=offset; // find a free slot SEntitySlotInfo dummy; int i=0; while (GetEntity()->GetSlotInfo(eIGS_Last+i, dummy)) i++; // move particle slot to the helper position+offset effectInfo.helper = helper; effectInfo.slot = GetEntity()->LoadParticleEmitter(eIGS_Last+i, pParticleEffect, 0, prime, true); Matrix34 tm = IParticleEffect::ParticleLoc(position, dir, scale); GetEntity()->SetSlotLocalTM(effectInfo.slot, tm); } else if (slotInfo.pCharacter) // bone attachment { effectInfo.helper = helper; effectInfo.characterSlot = slot; ICharacterInstance *pCharacter = slotInfo.pCharacter; IAttachmentManager *pAttachmentManager = pCharacter->GetIAttachmentManager(); IAttachment *pAttachment = pAttachmentManager->GetInterfaceByName(helper); if (!pAttachment) { GameWarning("Item '%s' trying to attach effect '%s' to attachment '%s' which does not exist!", GetEntity()->GetName(), effectName, helper); return 0; } CEffectAttachment *pEffectAttachment = new CEffectAttachment(effectName, Vec3(0,0,0), Vec3(0,1,0), scale); Matrix34 tm = Matrix34(Matrix33::CreateRotationVDir(dir)); tm.SetTranslation(offset); pAttachment->AddBinding(pEffectAttachment); pAttachment->SetAttRelativeDefault(QuatT(tm)); pEffectAttachment->UpdateAttachment(pAttachment); if (pEffectAttachment->GetEmitter()) { if (prime) pEffectAttachment->GetEmitter()->Prime(); } } m_effects.insert(TEffectInfoMap::value_type(m_effectGenId, effectInfo)); return m_effectGenId; } else if (id) { TEffectInfoMap::iterator it = m_effects.find(id); if (it == m_effects.end()) return 0; SEffectInfo &info = it->second; if (info.slot>-1) { GetEntity()->FreeSlot(info.slot); } else { ICharacterInstance *pCharacter = GetEntity()->GetCharacter(info.characterSlot); if (pCharacter) { IAttachmentManager *pAttachmentManager = pCharacter->GetIAttachmentManager(); IAttachment *pAttachment = pAttachmentManager->GetInterfaceByName(info.helper.c_str()); if(pAttachment) pAttachment->ClearBinding(); } } m_effects.erase(it); } return 0; }
//------------------------------------------------------------------------ bool CC4Projectile::StickToCharacter(bool stick,IEntity *pActor) { if(!pActor) return false; //Check for friendly AI if(pActor->GetAI()) { if(CWeapon *pWeapon = GetWeapon()) { if(CActor *pPlayer = pWeapon->GetOwnerActor()) { if(IAIObject *pPlayerAI = pPlayer->GetEntity()->GetAI()) { if(pActor->GetAI()->IsFriendly(pPlayerAI, false)) { return false; } } } } } ICharacterInstance *pCharacter = pActor->GetCharacter(0); if(!pCharacter) return false; //Actors doesn't support constraints, try to stick as character attachment IAttachmentManager *pAttachmentManager = pCharacter->GetIAttachmentManager(); IAttachment *pAttachment = NULL; //Select one of the attachment points Vec3 charOrientation = pActor->GetRotation().GetColumn1(); Vec3 c4ToChar = pActor->GetWorldPos() - GetEntity()->GetWorldPos(); c4ToChar.Normalize(); //if(c4ToChar.Dot(charOrientation)>0.0f) //pAttachment = pAttachmentManager->GetInterfaceByName("c4_back"); //else pAttachment = pAttachmentManager->GetInterfaceByName("c4_front"); if(!pAttachment) { GameWarning("No c4 face attachment found in actor"); if(!pAttachment) return false; } if(stick) { //Check if there's already one if(IAttachmentObject *pAO = pAttachment->GetIAttachmentObject()) return false; CEntityAttachment *pEntityAttachment = new CEntityAttachment(); pEntityAttachment->SetEntityId(GetEntityId()); pAttachment->AddBinding(pEntityAttachment); pAttachment->HideAttachment(0); m_stuck = true; } else { pAttachment->ClearBinding(); m_stuck = false; } return true; }