/** * @file llhudeffecttrail.cpp * @brief LLHUDEffectSpiral class implementation * * $LicenseInfo:firstyear=2002&license=viewerlgpl$ * Second Life Viewer Source Code * Copyright (C) 2010, Linden Research, Inc. * * This library is free software; you can redistribute it and/or * modify it under the terms of the GNU Lesser General Public * License as published by the Free Software Foundation; * version 2.1 of the License only. * * This library is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * Lesser General Public License for more details. * * You should have received a copy of the GNU Lesser General Public * License along with this library; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA * * Linden Research, Inc., 945 Battery Street, San Francisco, CA 94111 USA * $/LicenseInfo$ */ #include "llviewerprecompiledheaders.h" #include "llhudeffecttrail.h" #include "llviewercontrol.h" #include "message.h" #include "llagent.h" #include "llbox.h" #include "lldrawable.h" #include "llhudrender.h" #include "llviewertexturelist.h" #include "llviewerobjectlist.h" #include "llviewerpartsim.h" #include "llviewerpartsource.h" #include "llvoavatar.h" #include "llworld.h" LLHUDEffectSpiral::LLHUDEffectSpiral(const U8 type) : LLHUDEffect(type), mbInit(false) { mKillTime = 10.f; mVMag = 1.f; mVOffset = 0.f; mInitialRadius = 1.f; mFinalRadius = 1.f; mSpinRate = 10.f; mFlickerRate = 50.f; mScaleBase = 0.1f; mScaleVar = 0.f; mFadeInterp.setStartTime(0.f); mFadeInterp.setEndTime(mKillTime); mFadeInterp.setStartVal(1.f); mFadeInterp.setEndVal(1.f); } LLHUDEffectSpiral::~LLHUDEffectSpiral() { } void LLHUDEffectSpiral::markDead() { if (mPartSourcep) { mPartSourcep->setDead(); mPartSourcep = NULL; } LLHUDEffect::markDead(); } void LLHUDEffectSpiral::packData(LLMessageSystem *mesgsys) { if (!mSourceObject) { //LL_WARNS() << "Missing object in trail pack!" << LL_ENDL; } LLHUDEffect::packData(mesgsys); U8 packed_data[56]; memset(packed_data, 0, 56); if (mSourceObject) { htolememcpy(packed_data, mSourceObject->mID.mData, MVT_LLUUID, 16); } if (mTargetObject) { htolememcpy(packed_data + 16, mTargetObject->mID.mData, MVT_LLUUID, 16); } if (!mPositionGlobal.isExactlyZero()) { htolememcpy(packed_data + 32, mPositionGlobal.mdV, MVT_LLVector3d, 24); } mesgsys->addBinaryDataFast(_PREHASH_TypeData, packed_data, 56); } void LLHUDEffectSpiral::unpackData(LLMessageSystem *mesgsys, S32 blocknum) { const size_t EFFECT_SIZE = 56; U8 packed_data[EFFECT_SIZE]; LLHUDEffect::unpackData(mesgsys, blocknum); LLUUID object_id, target_object_id; size_t size = mesgsys->getSizeFast(_PREHASH_Effect, blocknum, _PREHASH_TypeData); if (size != EFFECT_SIZE) { LL_WARNS() << "Spiral effect with bad size " << size << LL_ENDL; return; } mesgsys->getBinaryDataFast(_PREHASH_Effect, _PREHASH_TypeData, packed_data, EFFECT_SIZE, blocknum, EFFECT_SIZE); htolememcpy(object_id.mData, packed_data, MVT_LLUUID, 16); htolememcpy(target_object_id.mData, packed_data + 16, MVT_LLUUID, 16); htolememcpy(mPositionGlobal.mdV, packed_data + 32, MVT_LLVector3d, 24); LLViewerObject *objp = NULL; if (object_id.isNull()) { setSourceObject(NULL); } else { LLViewerObject *objp = gObjectList.findObject(object_id); if (objp) { setSourceObject(objp); } else { // We don't have this object, kill this effect markDead(); return; } } if (target_object_id.isNull()) { setTargetObject(NULL); } else { objp = gObjectList.findObject(target_object_id); if (objp) { setTargetObject(objp); } else { // We don't have this object, kill this effect markDead(); return; } } triggerLocal(); } void LLHUDEffectSpiral::triggerLocal() { mKillTime = mTimer.getElapsedTimeF32() + mDuration; bool show_beam = gSavedSettings.getBOOL("ShowSelectionBeam"); LLColor4 color; color.setVec(mColor); if (!mPartSourcep) { if (!mTargetObject.isNull() && !mSourceObject.isNull()) { if (show_beam) { LLPointer<LLViewerPartSourceBeam> psb = new LLViewerPartSourceBeam; psb->setColor(color); psb->setSourceObject(mSourceObject); psb->setTargetObject(mTargetObject); psb->setOwnerUUID(gAgent.getID()); LLViewerPartSim::getInstance()->addPartSource(psb); mPartSourcep = psb; } } else { if (!mSourceObject.isNull() && !mPositionGlobal.isExactlyZero()) { if (show_beam) { LLPointer<LLViewerPartSourceBeam> psb = new LLViewerPartSourceBeam; psb->setSourceObject(mSourceObject); psb->setTargetObject(NULL); psb->setColor(color); psb->mLKGTargetPosGlobal = mPositionGlobal; psb->setOwnerUUID(gAgent.getID()); LLViewerPartSim::getInstance()->addPartSource(psb); mPartSourcep = psb; } } else { LLVector3 pos; if (mSourceObject) { pos = mSourceObject->getPositionAgent(); } else { pos = gAgent.getPosAgentFromGlobal(mPositionGlobal); } LLPointer<LLViewerPartSourceSpiral> pss = new LLViewerPartSourceSpiral(pos); if (!mSourceObject.isNull()) { pss->setSourceObject(mSourceObject); } pss->setColor(color); pss->setOwnerUUID(gAgent.getID()); LLViewerPartSim::getInstance()->addPartSource(pss); mPartSourcep = pss; } } } else { LLPointer<LLViewerPartSource>& ps = mPartSourcep; if (mPartSourcep->getType() == LLViewerPartSource::LL_PART_SOURCE_BEAM) { LLViewerPartSourceBeam *psb = (LLViewerPartSourceBeam *)ps.get(); psb->setSourceObject(mSourceObject); psb->setTargetObject(mTargetObject); psb->setColor(color); if (mTargetObject.isNull()) { psb->mLKGTargetPosGlobal = mPositionGlobal; } } else { LLViewerPartSourceSpiral *pss = (LLViewerPartSourceSpiral *)ps.get(); pss->setSourceObject(mSourceObject); } } mbInit = true; } void LLHUDEffectSpiral::setTargetObject(LLViewerObject *objp) { if (objp == mTargetObject) { return; } mTargetObject = objp; } void LLHUDEffectSpiral::render() { F32 time = mTimer.getElapsedTimeF32(); if ((!mSourceObject.isNull() && mSourceObject->isDead()) || (!mTargetObject.isNull() && mTargetObject->isDead()) || mKillTime < time || (!mPartSourcep.isNull() && !gSavedSettings.getBOOL("ShowSelectionBeam")) ) { markDead(); return; } } void LLHUDEffectSpiral::renderForTimer() { render(); }