bool RPG_Effect::CreateSoundEffect(RPG_EffectDefinition const& effectDefinition, hkvVec3 const& position /*= hkvVec3(0.f, 0.f, 0.f)*/) { if (m_debugDisplay) { VString msg; if (m_parentEntity) { msg += m_parentEntity->GetTypeId()->m_lpszClassName; msg += " --> "; } msg += "Playing Sound Event: "; msg += effectDefinition.m_fmodEventGroupName.AsChar(); msg += "/"; msg += effectDefinition.m_fmodEventName.AsChar(); hkvLog::Info(msg.AsChar()); Vision::Message.Add(1, msg.AsChar()); } VFmodEvent* event = RPG_VisionEffectHelper::PlayFmodSoundEvent(effectDefinition.m_fmodEventGroupName, effectDefinition.m_fmodEventName, position, VFMOD_FLAG_NODISPOSE); // hang onto character events for reuse if (event) { event->AttachToParent(this); // if this is a looped sound event, we need to cache it on the character for manual shutdown. if (RPG_VisionEffectHelper::IsLoopedFmodEvent(event)) { // looped sound m_persistentFmodEvent = event; } return true; } hkvLog::Warning("Sound event failed to play: %s/%s", effectDefinition.m_fmodEventGroupName.AsChar(), effectDefinition.m_fmodEventName.AsChar()); return false; }
void PlayerUIDialog::HandleInputRelease(RPG_Character* characterEntity) { const bool primaryActionInputHeld = m_inputMap->GetTrigger(PI_PrimaryAction); const bool shiftModifierHeld = m_inputMap->GetTrigger(PI_ShiftModifier); // is player ending a primary action? if (!primaryActionInputHeld && m_wasDown_PlayerMoveOrMelee) { #ifdef _DEBUG const VString msg = "Release Primary Action."; Vision::Error.SystemMessage(msg.AsChar()); Vision::Message.Add(1, msg.AsChar()); #endif ReleaseMeleeAttack(characterEntity); m_wasDown_PlayerMoveOrMelee = false; m_wasPressedTime = -1.f; } // is player ending a ranged attack? if ((!primaryActionInputHeld || !shiftModifierHeld) && m_wasDown_PlayerRangedAttack) { #ifdef _DEBUG const VString msg = "Release Primary Action."; Vision::Error.SystemMessage(msg.AsChar()); Vision::Message.Add(1, msg.AsChar()); #endif ReleaseRangedAttack(characterEntity); m_wasDown_PlayerRangedAttack = false; m_wasPressedTime = -1.f; } }
void RPG_CharacterStats::DebugPrintCharacterEventLog() const { #ifdef _DEBUG VString msg; for (unsigned int i = 0; i < m_recentCharacterEvents.GetSize(); ++i) { const RPG_CharacterEvent event = m_recentCharacterEvents[i]; msg.Format("EventType: %i, Time: %f, Value: %i, Message: %s\n", event.m_eventType, event.m_eventTime, event.m_eventValue, "<FIXME: NO MESSAGE>"); hkvLog::Info(msg.AsChar()); } msg = "-------------------------------------------------------"; hkvLog::Info(msg.AsChar()); #endif }
void PlayerUIDialog::CheatToggleUnlimitedMana() { RPG_Character *characterEntity = static_cast<RPG_Character *>(m_playerController->GetOwner()); VASSERT(characterEntity); characterEntity->GetCharacterStats().SetUnlimitedMana(!characterEntity->GetCharacterStats().HasUnlimitedMana()); VString msg; if (characterEntity->GetCharacterStats().HasUnlimitedMana()) { msg = "CHEAT - Unlimited Mana: ON"; } else { msg = "CHEAT - Unlimited Mana: OFF"; } hkvLog::Info(msg.AsChar()); Vision::Message.Add(1, msg.AsChar()); }
bool RPG_VisionEffectHelper::LoadFmodEventGroup(VString const& eventGroupName) { VString const& eventProjectPath = RPG_GameManager::s_instance.GetFmodEventProject(); VASSERT_MSG(!eventProjectPath.IsEmpty(), "Please ensure that GameManager::FMOD_EVENT_PROJECT points to a valid FMOD project file."); VFmodEventGroup *pEventGroup = VFmodManager::GlobalManager().LoadEventGroup(eventProjectPath.AsChar(), eventGroupName.AsChar()); VASSERT_MSG(pEventGroup && pEventGroup->IsValid(), eventGroupName.AsChar()); return pEventGroup->IsValid(); }
void VRTLSupport_cl::SetText(const VString & utf8String) { // Convert to wide char as RTL support helper requires wide char strings. int iBufSize = utf8String.GetLen() + 1; wchar_t *pWCharBuf = new wchar_t[iBufSize]; V_UTF8_TO_WCHAR(utf8String.AsChar(), pWCharBuf, iBufSize); SetText(pWCharBuf); V_SAFE_DELETE(pWCharBuf); }
void VArabicSupport_cl::SetText(const VString & utf8ArabicText, bool isContextualArabic, bool duplicateSpacesDuringConversion) { // Convert to wide char as Arabic support helper requires wide char strings. int iBufSize = utf8ArabicText.GetLen() + 1; wchar_t *pWCharBuf = new wchar_t[iBufSize]; V_UTF8_TO_WCHAR(utf8ArabicText.AsChar(), pWCharBuf, iBufSize); SetText(pWCharBuf, isContextualArabic, duplicateSpacesDuringConversion); V_SAFE_DELETE(pWCharBuf); }
VScalefromModelPreview::VScalefromModelPreview(VScaleformMovieInstance * pMainMovieInstance, VisBaseEntity_cl *pPreviewEntity, const char * szTextureName, const char * szMoviePathAndName, int iSizeX, int iSizeY, float fFovH, float fFovV) : m_pMainMovieInstance(pMainMovieInstance), m_sTextureName(szTextureName), m_sMoviePathAndName(szMoviePathAndName) { VASSERT_MSG(pMainMovieInstance!=NULL, "The main movie is required for VScalefromModelPreview!"); VASSERT_MSG(pPreviewEntity!=NULL, "Specify an entity for the VScalefromModelPreview!"); VASSERT_MSG(szTextureName!=NULL, "Specify a texture for the VScalefromModelPreview!"); //Scaleform::StringBuffer buffer2; //Scaleform::Memory::pGlobalHeap->MemReport(buffer2, Scaleform::MemoryHeap::MemReportFull); //Vision::Error.Warning("\n-----------------\n1st report:\n\n%s\n-----------------\n", buffer2.ToCStr()); VString sTargetName; sTargetName.Format("ScaleformModelPreviewComponent:%p", pPreviewEntity); m_spModelPreview = new VModelPreviewComponent(sTargetName.AsChar()); m_spModelPreview->CreateEmptyLightGrid(); m_spModelPreview->SetPreviewEntity(pPreviewEntity); #ifdef _VR_DX11 //this switch is required for Scaleform DX11, because it cannot handle typeless textures so far! bool bTypedRenderTargetsActive = Vision::Renderer.GetUseTypedRenderTargets()!=0; if(!bTypedRenderTargetsActive) Vision::Renderer.SetUseTypedRenderTargets(true); #endif #ifdef HK_DEBUG_SLOW bool bSuccess = #endif m_spModelPreview->InitComponent(iSizeX, iSizeY, fFovH, fFovV); #ifdef HK_DEBUG_SLOW VASSERT_MSG(bSuccess, "Failed to initialize internal model preview component!"); #endif #ifdef _VR_DX11 if(!bTypedRenderTargetsActive) Vision::Renderer.SetUseTypedRenderTargets(false); #endif Reassign(); //Scaleform::StringBuffer buffer; //Scaleform::Memory::pGlobalHeap->MemReport(buffer, Scaleform::MemoryHeap::MemReportFull); //Vision::Error.Warning("\n-----------------\n2nd report:\n\n%s\n-----------------\n", buffer.ToCStr()); Vision::Callbacks.OnEnterForeground += this; }
void RPG_CharacterStats::DebugPrintLastCharacterEventLogged() const { #ifdef _DEBUG if (m_recentCharacterEvents.GetSize() > 0) { VString msg; const RPG_CharacterEvent event = m_recentCharacterEvents.GetLast(); msg.Format("Event Logged: Type: %i, Time: %f, Value: %i, Message: %s\n", event.m_eventType, event.m_eventTime, event.m_eventValue, "<FIXME: NO MESSAGE>"); hkvLog::Info(msg.AsChar()); } #endif }
bool RPG_VisionEffectHelper::PlaySoundFile(VString const& sfxFilename, hkvVec3 const& position /*= hkvVec3(0.f, 0.f, 0.f)*/) { VASSERT(!sfxFilename.IsEmpty()); RPG_VisionEffectSoundParams soundParams; { soundParams.m_soundFilename = sfxFilename.AsChar(); soundParams.m_position = position; if (RPG_VisionEffectHelper::CreateSoundEffect(soundParams)) { return true; } } return false; }
void RPG_Effect::Create(RPG_EffectDefinition const& effectDefinition, VisBaseEntity_cl* parentEntity) { VASSERT(parentEntity); m_parentEntity = parentEntity; bool validBone = false; if (!effectDefinition.m_vfxBoneName.IsEmpty()) { if (m_parentEntity->GetMesh()->GetSkeleton()->GetBoneIndexByName(effectDefinition.m_vfxBoneName.AsChar()) != -1) { validBone = true; } else { // warn the user if a bad bone name has been supplied. VString msg; msg.Format("Trying to spawn an RPG_Effect on character %s, at a nonexistent bone: %s.", parentEntity->GetTypeId()->m_lpszClassName, effectDefinition.m_vfxBoneName.AsChar()); hkvLog::Warning(msg.AsChar()); } } // attach this effect object to its parent entity, either at a bone or at its root if (validBone) { // valid bone. // create a proxy to attach the particle system to the named bone if none already exists if (!m_attachment) { m_attachment = new RPG_Attachment(m_parentEntity); } VASSERT(m_attachment); // attach the proxy to the parent bone m_attachment->Attach(this, effectDefinition.m_vfxBoneName, effectDefinition.m_vfxPositionOffset, effectDefinition.m_vfxOrientationOffset); } else { // attach this effect to its owning entity generally AttachToParent(m_parentEntity); ResetLocalTransformation(); // Set this RPG_Effect's local space position and orientation to (0/0/0) } UpdateBinding(); // Recompute the world space transformation from the current local space transformation // Create the effect. Sound and visual components will attach to this effect object, which is already attached to its parent. Create(effectDefinition, GetPosition(), GetOrientation()); }
void RPG_VisionSerializer::ReadVariableList(VTypedObject *typedObj, VArchive /*const*/& ar) { int numVars; ar >> numVars; for(int i = 0; i < numVars; ++i) { VString varName; ar >> varName; int varType; ar >> varType; VisVariable_cl *const var = typedObj->GetVariable(varName); VASSERT(var && var->type == varType); if(var && var->type == varType) { switch(varType) { case VULPTYPE_REFERENCED_OBJECT: { VTypedObject *varObj; ar >> varObj; VTypedObjectReference *const typedObjectReference = (VTypedObjectReference*)((char*)typedObj + var->clsOffset); typedObjectReference->SetReferencedObject(varObj); } break; default: { VString varValue; ar >> varValue; var->SetValue(typedObj, varValue.AsChar()); } } } } }
void RPG_LevelInfo::PreloadFmodEventProject(VString const& projectFilename) { VASSERT_MSG(!projectFilename.IsEmpty(), "No FMod Event Project was specified."); FMOD::EventProject* eventProject = VFmodManager::GlobalManager().LoadEventProject(projectFilename.AsChar()); #if !(RPG_FMOD_SUPPRESS_NONNULL_ASSERTS) VVERIFY_MSG(eventProject != NULL, "Specified FMod Event Project failed to load."); #endif if(!eventProject) return; int numGroups; eventProject->getNumGroups(&numGroups); for(int index = 0; index < numGroups; ++index) { FMOD::EventGroup* eventGroup; eventProject->getGroupByIndex(index, true, &eventGroup); //eventGroup->loadEventData(FMOD_EVENT_RESOURCE_STREAMS_AND_SAMPLES, FMOD_EVENT_NONBLOCKING); eventGroup->loadEventData(FMOD_EVENT_RESOURCE_STREAMS_AND_SAMPLES, FMOD_EVENT_DEFAULT); } }
void PlayerUIDialog::ExecuteOrContinueRangedAttack(RPG_Character* characterEntity) { #ifdef _DEBUG const VString msg = "Execute or Continue Ranged Attack."; //Vision::Error.SystemMessage(msg.AsChar()); Vision::Message.Add(1, msg.AsChar()); #endif const bool inputEdge = !m_wasDown_PlayerRangedAttack; // if ranged attack input is activated now, and wasn't previously, this is a press event. RPG_DamageableEntity* attackableEntity = NULL; hkvVec3 targetPoint(0.0f, 0.0f, 0.0f); GetFirstAttackableEntityUnderCursor(attackableEntity, targetPoint, characterEntity); // TODO - intersect ray with horizontal plane at characterEntity's root node if this returns false // TODO - modify static mesh target height based on normal of interaction point if(inputEdge) { // Initial press event, or a continued press that slipped from one entity to another ExecuteRangedAttack(characterEntity, attackableEntity, targetPoint); } else { if(attackableEntity != m_lastTargetEntity || !targetPoint.isIdentical(m_lastTargetPoint)) { // updates interaction data for currently active ranged attack action ExecuteRangedAttack(characterEntity, attackableEntity, targetPoint); } // continued hold ContinueRangedAttack(characterEntity); } m_lastTargetEntity = attackableEntity; m_lastTargetPoint = targetPoint; m_wasDown_PlayerRangedAttack = true; }
bool VRSDClientLuaImplementation::GetSubSymbolsForGlobal(char* GlobalName, DynArray_cl<VRSDScriptSymbol>& SubSymbols, unsigned int& SubSymbolCount) { VASSERT(m_pLuaState); if(!m_pLuaState || !m_pActivationRecord) return false; SubSymbolCount = 0; // we can only get local symbols without a crash if we are really in a Lua code execution path if(strcmp(m_pActivationRecord->what, "Lua")) return true; ScopedBooleanToTrue disableDebugCallback(m_bDebuggerRetrievingValues); VLuaStackCleaner stackCleaner(m_pLuaState); VMemoryTempBuffer<512> copyBuffer(GlobalName); // operate on a copy string in the tokenizer VStringTokenizerInPlace Tokenizer(copyBuffer.AsChar(), '.'); lua_getfield(m_pLuaState, LUA_GLOBALSINDEX, Tokenizer.Next()); if(LookupPath(Tokenizer) != HKV_SUCCESS) return false; // now the variable should be at the top of the stack and we can get the subvariables of it // first key for the iteration lua_pushnil(m_pLuaState); while (lua_next(m_pLuaState, -2) != 0) { // after this the key is at -2 and the value at -1 // we only want string fields and numeric fields // (lua_isstring returns also true for numbers, using // tostring later on will cast the number to a string) int iKeyType = lua_type(m_pLuaState, -2); if (iKeyType==LUA_TNUMBER || iKeyType==LUA_TSTRING) { VString sKeyBuffer; //this if prevents a conversion of number on the Lua stack if(iKeyType==LUA_TNUMBER) sKeyBuffer.Format("%1.0f", lua_tonumber(m_pLuaState, -2)); else sKeyBuffer = lua_tostring(m_pLuaState, -2); const char* pSymbolName = sKeyBuffer.AsChar(); if(pSymbolName) { // table member variable if(lua_istable(m_pLuaState, -1)) { // add a symbol for the table AddSymbol(SubSymbols, SubSymbolCount, pSymbolName, "table", VRSDScriptSymbol::SYMBOL_TABLE); } // numeric member variable else if(lua_type(m_pLuaState, -1) == LUA_TNUMBER) { char buffer[32]; sprintf(buffer, "%f", lua_tonumber(m_pLuaState, -1)); AddSymbol(SubSymbols, SubSymbolCount, pSymbolName, buffer, VRSDScriptSymbol::SYMBOL_NUMBER); } // string member variable else if(lua_type(m_pLuaState, -1) == LUA_TSTRING) { AddSymbol(SubSymbols, SubSymbolCount, pSymbolName, lua_tostring(m_pLuaState, -1), VRSDScriptSymbol::SYMBOL_STRING); } // function member variable else if(lua_isfunction(m_pLuaState, -1)) { AddSymbol(SubSymbols, SubSymbolCount, pSymbolName, "function", VRSDScriptSymbol::SYMBOL_FUNCTION); } // userdata member variable else if(lua_isuserdata(m_pLuaState, -1)) { char buffer[128]; swig_type_info* type = (swig_type_info *)LUA_GetSwigType(m_pLuaState, -1); void * pUserData = lua_touserdata(m_pLuaState, -1); if(type) { vis_snprintf(buffer, 128, "userdata:0x%p [%s: 0x%p]", pUserData, type->str, ((swig_lua_userdata*)pUserData)->ptr); } else { vis_snprintf(buffer, 128, "userdata:0x%p", lua_touserdata(m_pLuaState, -1)); } AddSymbol(SubSymbols, SubSymbolCount, pSymbolName, buffer, VRSDScriptSymbol::SYMBOL_USERDATA); } else if(lua_isboolean(m_pLuaState, -1)) { int iBoolVal = lua_toboolean(m_pLuaState, -1); AddSymbol(SubSymbols, SubSymbolCount, pSymbolName, iBoolVal ? "true" : "false", VRSDScriptSymbol::SYMBOL_BOOLEAN); } else if(lua_isnil(m_pLuaState, -1)) { AddSymbol(SubSymbols, SubSymbolCount, pSymbolName, "nil", VRSDScriptSymbol::SYMBOL_CLASS); } } } lua_pop(m_pLuaState, 1); // remove the value, keep the key for the next iteration } return true; }
bool VRSDClientLuaImplementation::GetSubSymbolsForLocal(char* LocalName, DynArray_cl<VRSDScriptSymbol>& SubSymbols, unsigned int& SubSymbolCount) { VASSERT(m_pLuaState); if(!m_pLuaState || !m_pActivationRecord) return false; SubSymbolCount = 0; // we can only get local symbols without a crash if we are really in a Lua code execution path if(strcmp(m_pActivationRecord->what, "Lua")) return true; VLuaStackCleaner stackCleaner(m_pLuaState); ScopedBooleanToTrue disableDebugCallback(m_bDebuggerRetrievingValues); char* pSymbolName = NULL; int iLocalIndex = 1; VMemoryTempBuffer<512> copyBuffer(LocalName); // operate on a copy string in the tokenizer VStringTokenizerInPlace Tokenizer(copyBuffer.AsChar(), '.'); char* pCurrent = Tokenizer.Next(); while((pSymbolName = (char*)lua_getlocal(m_pLuaState, m_pActivationRecord, iLocalIndex)) != NULL) { //stack: .., localX, TOP // check if this local variable is the one we want if(!strcmp(pSymbolName, pCurrent)) { //the local is already on the stack if(LookupPath(Tokenizer) != HKV_SUCCESS) return false; // now we can iterate over the contents of the table // first key for the iteration lua_pushnil(m_pLuaState); //stack: .., localX, {field}, nil, TOP //access the last field while (lua_next(m_pLuaState, -2) != 0) //stack: .., localX, {field}, key, value TOP { // we only want string fields and numeric fields // (lua_isstring returns also true for numbers, using // tostring later on will cast the number to a string) int iKeyType = lua_type(m_pLuaState, -2); if (iKeyType==LUA_TNUMBER || iKeyType==LUA_TSTRING) { VString sKeyBuffer; //this if prevents a conversion of number on the Lua stack if(iKeyType==LUA_TNUMBER) sKeyBuffer.Format("%1.0f", lua_tonumber(m_pLuaState, -2)); else sKeyBuffer = lua_tostring(m_pLuaState, -2); if(!sKeyBuffer.IsEmpty()) { int iValueType = lua_type(m_pLuaState, -1); VString sValueBuffer; // table member variable switch (iValueType) { case LUA_TTABLE: // add a symbol for the table AddSymbol(SubSymbols, SubSymbolCount, sKeyBuffer.AsChar(), "table", VRSDScriptSymbol::SYMBOL_TABLE); break; case LUA_TNUMBER: // numeric member variable sValueBuffer.Format("%f", lua_tonumber(m_pLuaState, -1)); AddSymbol(SubSymbols, SubSymbolCount, sKeyBuffer.AsChar(), sValueBuffer.AsChar(), VRSDScriptSymbol::SYMBOL_NUMBER); break; case LUA_TSTRING: AddSymbol(SubSymbols, SubSymbolCount, sKeyBuffer.AsChar(), lua_tostring(m_pLuaState, -1), VRSDScriptSymbol::SYMBOL_STRING); break; case LUA_TFUNCTION: sValueBuffer.Format("function:0x%p", lua_tocfunction(m_pLuaState, -1)); AddSymbol(SubSymbols, SubSymbolCount, sKeyBuffer.AsChar(), sValueBuffer.AsChar(), VRSDScriptSymbol::SYMBOL_FUNCTION); break; case LUA_TBOOLEAN: AddSymbol(SubSymbols, SubSymbolCount, sKeyBuffer.AsChar(), lua_toboolean(m_pLuaState, -1) ? "true" : "false", VRSDScriptSymbol::SYMBOL_BOOLEAN); break; case LUA_TNIL: AddSymbol(SubSymbols, SubSymbolCount, sKeyBuffer.AsChar(), "nil", VRSDScriptSymbol::SYMBOL_CLASS); break; case LUA_TTHREAD: sValueBuffer.Format("thread:0x%p", lua_tothread(m_pLuaState, -1)); AddSymbol(SubSymbols, SubSymbolCount, sKeyBuffer.AsChar(), sValueBuffer.AsChar(), VRSDScriptSymbol::SYMBOL_CLASS); break; case LUA_TUSERDATA: sValueBuffer.Format("userdata:0x%p", lua_touserdata(m_pLuaState, -1)); AddSymbol(SubSymbols, SubSymbolCount, sKeyBuffer.AsChar(), sValueBuffer.AsChar(), VRSDScriptSymbol::SYMBOL_USERDATA); break; default: AddSymbol(SubSymbols, SubSymbolCount, sKeyBuffer.AsChar(), "unknown", VRSDScriptSymbol::SYMBOL_STRING); break; } } } // remove the value, keep the key for the next iteration lua_pop(m_pLuaState, 1); //stack: .., localX, {field}, key, TOP } return true; } // clean up the stack and increment the index to get the next local variable lua_pop(m_pLuaState, 1); //stack: .., TOP iLocalIndex++; } return true; }
void RPG_Attachment::Attach(VisObject3D_cl* object, const VString& boneName, const hkvVec3& positionOffset /*= hkvVec3(0.f, 0.f, 0.f)*/, const hkvVec3& orientationOffset /*= hkvVec3(0.f, 0.f, 0.f)*/) { if(!m_parent || !object) { return; } m_object = object; m_boneName = boneName; m_positionOffset = positionOffset; m_orientationOffset = orientationOffset; bool validBone = false; if(!boneName.IsEmpty()) { if(m_parent->GetMesh()->GetSkeleton()->GetBoneIndexByName(m_boneName) != -1) { validBone = true; } else { Vision::Error.Warning("RPG_Attachment::Attach - Supplied bone name doesn't exist on this skeleton: %s", boneName.AsChar()); } } if(validBone) { // attach the proxy to the parent bone if specified if (!m_proxy) { // @note: m_proxy is not deleted within this class, because the attachment parent deletes it m_proxy = new VSkeletalBoneProxyObject(); } m_proxy->AttachToEntityBone(m_parent, m_boneName.AsChar()); m_proxy->UpdateBoneBinding(); // attach the new object to the proxy m_object->AttachToParent(m_proxy); VASSERT(m_proxy->GetParent() == m_parent); VASSERT(m_object->GetParent() == m_proxy); } else { // if no bone is specified, just attach to the parent object m_object->AttachToParent(m_parent); VASSERT(m_object->GetParent() == m_parent); } m_object->ResetLocalTransformation(); m_object->SetLocalPosition(m_positionOffset); m_object->SetLocalOrientation(m_orientationOffset); }
bool RPG_Effect::CreateVisualEffect(RPG_EffectDefinition const& effectDefinition, hkvVec3 const& position /*= hkvVec3(0.f, 0.f, 0.f)*/, hkvVec3 const& orientation /*= hkvVec3(0.f, 0.f, 0.f)*/) { VString vfxFilename = effectDefinition.m_vfxFilename; if (m_debugDisplay) { VString msg; if (m_parentEntity) { msg += m_parentEntity->GetTypeId()->m_lpszClassName; msg += " --> "; } msg += "Creating Particle FX: "; msg += vfxFilename.AsChar(); hkvLog::Info(msg.AsChar()); Vision::Message.Add(1, msg.AsChar()); } VisParticleEffect_cl* particleEffect = RPG_VisionEffectHelper::CreateParticleEffect(vfxFilename, position, orientation); if (!particleEffect) { hkvLog::Warning("Create Particle Effect failed: %s", vfxFilename.AsChar()); return false; } particleEffect->AttachToParent(this); // apply position offset, relative to the RPG_Effect object's transform if (!effectDefinition.m_vfxPositionOffset.isZero()) { particleEffect->SetLocalPosition(effectDefinition.m_vfxPositionOffset); } // apply orientation offset if (!effectDefinition.m_vfxOrientationOffset.isZero()) { particleEffect->SetLocalOrientation(effectDefinition.m_vfxOrientationOffset); } // by default, emitters update their position over time. We need to call TeleportSpawnPosition() to force them to update immediately. particleEffect->TeleportSpawnPosition(); // if this is a persistent effect, add it to the character's effect list. if (particleEffect && RPG_VisionEffectHelper::IsPersistentEffect(particleEffect)) { if (GetParent()) { particleEffect->SetRemoveWhenFinished(false); // if we're storing an effect here, we want to be responsible for its removal. m_persistentParticleEffect = particleEffect; } else { // a persistent effect was created, but not attached to a parent entity. Make some noise about this and shut it down. VString msg; msg.Format("Effect: %s is a looping effect, which must be attached to an entity capable of cleaning it up.", vfxFilename.AsChar()); hkvLog::Warning(msg.AsChar()); //VASSERT_MSG(false, "Effects containing looping particle systems MUST be parented to an entity which can manage their shutdown and cleanup."); particleEffect->SetFinished(); } } DebugDisplayParticleInformation(particleEffect); return true; }
inline void VLuaWrapper::setVariable (const char* szName, const VString& sValue) const { lua_pushlstring (mp_State, sValue.AsChar (), sValue.GetSize()); lua_setfield (mp_State, (m_States.m_iOpenTables == 0) ? LUA_GLOBALSINDEX : -2, szName); }
inline void VLuaWrapper::PushParameter (const VString& sParameter) { lua_pushlstring (mp_State, sParameter.AsChar (), sParameter.GetSize()); m_States.m_iParametersPushed++; }
void RPG_Action_RangedAttack::Tick(float const deltaTime) { RPG_Action_AttackBase::Tick(deltaTime); if(m_attacking) { // RangedAttacking was set to true when the action was initiated. Is reset to false by Behavior when the attack anim finishes. vHavokBehaviorComponent *const behaviorComponent = m_characterOwner->GetBehaviorComponent(); VVERIFY_OR_RET(behaviorComponent); VASSERT(!m_behaviorTriggerVarName.IsEmpty()); if (!RPG_VisionHavokBehaviorHelper::BehaviorGetVarNamed<bool>(*behaviorComponent, m_behaviorTriggerVarName.AsChar())) { if (m_flags == 1) { if(m_updatedInteraction) { m_updatedInteraction = false; if(!m_updatedInteractionEntity && m_interactionEntity) { // Do not lose the player's intended target ValidateInteractionEntity(); if(!m_interactionEntity->Components().GetComponentOfType(V_RUNTIME_CLASS(RPG_AttackableComponent))) { m_interactionEntity = NULL; } else { if(m_interactionEntity->GetPosition().getDistanceToSquared(m_updatedInteractionPosition) > s_retargetingRadius * s_retargetingRadius) { m_interactionEntity = NULL; } } } else { m_interactionEntity = m_updatedInteractionEntity; ValidateInteractionEntity(); } m_interactionPosition = m_updatedInteractionPosition; } m_startTime = Vision::GetTimer()->GetTime(); StartAttack(); } else { // if we've gotten to the end and haven't fired the projectile, fire it now if (!m_hasFired) { VString msg; msg.Format("RPG_Action_RangedAttack never received expected %s event from Behavior.", m_behaviorFireEventName.AsChar()); Vision::Error.Warning(msg.AsChar()); //VASSERT_MSG(false, msg.AsChar()); FireAttack(); } End(); } } else { // we're currently attacking hkvVec3 const targetPosition = m_interactionEntity ? m_interactionEntity->GetPosition() : m_interactionPosition; FaceTargetPoint(targetPosition); #ifdef _DEBUG if (m_debugDisplayInfo) { Vision::Game.DrawSingleLine(m_characterOwner->GetPosition(), targetPosition, VColorRef(255, 0, 255)); } #endif } } else { StartAttack(); } }
// internal helpers: static inline int MapTrigger( VStringInputMap *pMap, const char * szTriggerName, VString & sDeviceName, int iControl, const VInputOptions & options, int iOptTriggerIndex /* = -1 */, const VRectanglef & area, float fPrio, bool bNewTouchArea, int iOptionaAxisControl = -1) { VASSERT_MSG(pMap!=NULL, "No VStringInputMap present for mapping!"); if(szTriggerName==NULL || szTriggerName[0]==0) { Vision::Error.Warning("[Lua] MapTrigger: Trigger name is empty, please specify a proper name."); return -1; } sDeviceName.ToLower(); IVInputDevice* pInputDevice = NULL; #if defined(SUPPORTS_MULTITOUCH) // Special case handling for the virtual thumb stick. if (sDeviceName == "virtualthumbstick") { pInputDevice = s_pVirtualThumbStick; } else #endif { pInputDevice = &VInputManager::GetInputDevice(sDeviceName.AsChar()); } if (pInputDevice == NULL || pInputDevice->GetModel() == INPUT_DEVICE_NONE) { Vision::Error.Warning("[Lua] MapTrigger: Could not find input device '%s' for trigger '%s'.", sDeviceName.AsChar(), szTriggerName); return -1; } //touch area handling if (sDeviceName.Search("touch") || sDeviceName.Search("back")) { IVMultiTouchInput *pTouchDevice = (IVMultiTouchInput *)pInputDevice; if(!bNewTouchArea) { VTouchArea **ppAreas = pTouchDevice->GetTouchAreas().GetPtrs(); for(int i=0;i<pTouchDevice->GetTouchAreas().GetLength();i++) { if(ppAreas[i]->GetArea() == area) { return pMap->MapTrigger(szTriggerName, ppAreas[i], iControl, options, iOptTriggerIndex); } } } //we could not find a matching area -or- do not create a new one: VTouchArea* pArea = new VTouchArea(*pTouchDevice, area, fPrio); return pMap->MapTrigger(szTriggerName, pArea, iControl, options, iOptTriggerIndex); } //mapping for non-touch devices if (iOptionaAxisControl >= 0) return pMap->MapTriggerAxis(szTriggerName, *pInputDevice, iControl, (unsigned int) iOptionaAxisControl, options, iOptTriggerIndex); else return pMap->MapTrigger(szTriggerName, *pInputDevice, iControl, options, iOptTriggerIndex); }