From 961826c5d76fe87efd37ee84f37d54752bd9667b Mon Sep 17 00:00:00 2001
From: Rye Mutt <rye@alchemyviewer.org>
Date: Mon, 30 Mar 2020 11:20:25 -0400
Subject: [PATCH] Add a pile of the menu utilities back along with actually
 adding particle editor menu callbacks

---
 indra/newview/alviewermenu.cpp                | 105 +++++++++++++++++-
 indra/newview/llhudobject.cpp                 |  16 +++
 indra/newview/llhudobject.h                   |   4 +
 .../skins/default/xui/en/menu_viewer.xml      |  40 ++++++-
 4 files changed, 153 insertions(+), 12 deletions(-)

diff --git a/indra/newview/alviewermenu.cpp b/indra/newview/alviewermenu.cpp
index bd0c586d044..0b005a3de3c 100644
--- a/indra/newview/alviewermenu.cpp
+++ b/indra/newview/alviewermenu.cpp
@@ -21,30 +21,114 @@
 #include "alviewermenu.h"
 
 // library
+#include "llfloaterreg.h"
 #include "llview.h"
 
 // newview
 #include "alavataractions.h"
+#include "alfloaterparticleeditor.h"
+#include "llagent.h"
+#include "llhudobject.h"
 #include "llselectmgr.h"
 #include "llviewermenu.h"
 #include "llviewerobject.h"
+#include "llviewerobjectlist.h"
+#include "llviewerregion.h"
 #include "llvoavatar.h"
+#include "llvoavatarself.h"
 
 namespace
 {
-	bool avatar_copy_data(const LLSD& userdata)
+	bool enable_edit_particle_source()
+	{
+		LLObjectSelectionHandle selection = LLSelectMgr::getInstance()->getSelection();
+		for (LLObjectSelection::valid_root_iterator iter = selection->valid_root_begin();
+			iter != selection->valid_root_end(); ++iter)
+		{
+			LLSelectNode* node = *iter;
+			if (node->mPermissions->getOwner() == gAgent.getID())
+			{
+				return true;
+			}
+		}
+		return false;
+	}
+
+	void edit_particle_source()
+	{
+		LLViewerObject* objectp = LLSelectMgr::getInstance()->getSelection()->getPrimaryObject();
+		if (objectp)
+		{
+			ALFloaterParticleEditor* particleEditor = LLFloaterReg::showTypedInstance<ALFloaterParticleEditor>("particle_editor", LLSD(objectp->getID()), TAKE_FOCUS_YES);
+			if (particleEditor)
+				particleEditor->setObject(objectp);
+		}
+	}
+
+	void world_clear_effects()
+	{
+		LLHUDObject::markViewerEffectsDead();
+	}
+
+	void world_sync_animations()
+	{
+		for (S32 i = 0; i < gObjectList.getNumObjects(); ++i)
+		{
+			LLViewerObject* object = gObjectList.getObject(i);
+			if (object)
+			{
+				LLVOAvatar* avatarp = object->asAvatar();
+				if (avatarp)
+				{
+					for (const auto& playpair : avatarp->mPlayingAnimations)
+					{
+						avatarp->stopMotion(playpair.first, TRUE);
+						avatarp->startMotion(playpair.first);
+					}
+				}
+			}
+		}
+	}
+
+	void avatar_copy_data(const LLSD& userdata)
 	{
 		LLViewerObject* objectp = LLSelectMgr::getInstance()->getSelection()->getPrimaryObject();
 		if (!objectp)
-			return false;
+			return;
 
 		LLVOAvatar* avatarp = find_avatar_from_object(objectp);
 		if (avatarp)
 		{
 			ALAvatarActions::copyData(avatarp->getID(), userdata);
-			return true;
 		}
-		return false;
+	}
+
+	void avatar_undeform_self()
+	{
+		if (!isAgentAvatarValid()) 
+			return;
+
+		gAgentAvatarp->resetSkeleton(true);
+		LLMessageSystem* msg = gMessageSystem;
+		msg->newMessageFast(_PREHASH_AgentAnimation);
+		msg->nextBlockFast(_PREHASH_AgentData);
+		msg->addUUIDFast(_PREHASH_AgentID, gAgent.getID());
+		msg->addUUIDFast(_PREHASH_SessionID, gAgent.getSessionID());
+		msg->nextBlockFast(_PREHASH_AnimationList);
+		msg->addUUIDFast(_PREHASH_AnimID, LLUUID("e5afcabe-1601-934b-7e89-b0c78cac373a"));
+		msg->addBOOLFast(_PREHASH_StartAnim, TRUE);
+		msg->nextBlockFast(_PREHASH_AnimationList);
+		msg->addUUIDFast(_PREHASH_AnimID, LLUUID("d307c056-636e-dda6-4a3c-b3a43c431ca8"));
+		msg->addBOOLFast(_PREHASH_StartAnim, TRUE);
+		msg->nextBlockFast(_PREHASH_AnimationList);
+		msg->addUUIDFast(_PREHASH_AnimID, LLUUID("319b4e7a-18fc-1f9e-6411-dd10326c0c7e"));
+		msg->addBOOLFast(_PREHASH_StartAnim, TRUE);
+		msg->nextBlockFast(_PREHASH_AnimationList);
+		msg->addUUIDFast(_PREHASH_AnimID, LLUUID("f05d765d-0e01-5f9a-bfc2-fdc054757e55"));
+		msg->addBOOLFast(_PREHASH_StartAnim, TRUE);
+		msg->nextBlockFast(_PREHASH_PhysicalAvatarEventList);
+		msg->addBinaryDataFast(_PREHASH_TypeData, nullptr, 0);
+		msg->sendReliable(gAgent.getRegion()->getHost());
 	}
 }
 
@@ -52,7 +136,16 @@ namespace
 
 void ALViewerMenu::initialize_menus()
 {
-	//LLUICtrl::EnableCallbackRegistry::Registrar& enable = LLUICtrl::EnableCallbackRegistry::currentRegistrar();
+	LLUICtrl::EnableCallbackRegistry::Registrar& enable = LLUICtrl::EnableCallbackRegistry::currentRegistrar();
+	enable.add("Object.EnableEditParticles", [](LLUICtrl* ctrl, const LLSD& param) { return enable_edit_particle_source(); });
+
 	LLUICtrl::CommitCallbackRegistry::Registrar& commit = LLUICtrl::CommitCallbackRegistry::currentRegistrar();
-	commit.add("Avatar.CopyData", [](LLUICtrl* ctrl, const LLSD& param) { avatar_copy_data(param); });
+	commit.add("Avatar.CopyData",		[](LLUICtrl* ctrl, const LLSD& param) { avatar_copy_data(param); });
+
+	commit.add("Object.EditParticles",	[](LLUICtrl* ctrl, const LLSD& param) { edit_particle_source(); });
+
+	commit.add("Tools.UndeformSelf", [](LLUICtrl* ctrl, const LLSD& param) { avatar_undeform_self(); });
+
+	commit.add("World.ClearEffects",	[](LLUICtrl* ctrl, const LLSD& param) { world_clear_effects(); });
+	commit.add("World.SyncAnimations",	[](LLUICtrl* ctrl, const LLSD& param) { world_sync_animations(); });
 }
diff --git a/indra/newview/llhudobject.cpp b/indra/newview/llhudobject.cpp
index 45fa09e1a1c..7e18da88a7b 100644
--- a/indra/newview/llhudobject.cpp
+++ b/indra/newview/llhudobject.cpp
@@ -321,3 +321,19 @@ void LLHUDObject::sortObjects()
 {
 	sHUDObjects.sort(hud_object_further_away());	
 }
+
+// static
+void LLHUDObject::markViewerEffectsDead()
+{
+	for (LLPointer<LLHUDObject> hud_objp : sHUDObjects)
+	{
+		U8 type = hud_objp->getType();
+		if (hud_objp->isVisible() && (type & LL_HUD_EFFECT_LOOKAT ||
+			type & LL_HUD_EFFECT_POINTAT || type & LL_HUD_EFFECT_POINT ||
+			type & LL_HUD_EFFECT_BEAM || type & LL_HUD_EFFECT_SPIRAL))
+		{
+			hud_objp->markDead();
+		}
+	}
+}
+
diff --git a/indra/newview/llhudobject.h b/indra/newview/llhudobject.h
index 2f7a98c86cf..67490e2e099 100644
--- a/indra/newview/llhudobject.h
+++ b/indra/newview/llhudobject.h
@@ -76,6 +76,10 @@ class LLHUDObject : public LLRefCount
 
 	static void cleanupHUDObjects();
 
+	// Used to clean up the dirty viewer effect spam that can occur.
+	// This includes: LOOKAT, POINTAT, SPIRAL, POINT, EDIT, BEAM, SPHERE
+	static void markViewerEffectsDead();
+
 	enum
 	{
 		LL_HUD_TEXT,
diff --git a/indra/newview/skins/default/xui/en/menu_viewer.xml b/indra/newview/skins/default/xui/en/menu_viewer.xml
index d8d94ffaf00..11f9fec5ff7 100644
--- a/indra/newview/skins/default/xui/en/menu_viewer.xml
+++ b/indra/newview/skins/default/xui/en/menu_viewer.xml
@@ -147,12 +147,6 @@
           <menu_item_check.on_click
            function="World.AlwaysRun" />
         </menu_item_check>
-        <menu_item_call
-         label="Stop Animating Me"
-         name="Stop Animating My Avatar">
-          <menu_item_call.on_click
-           function="Tools.StopAllAnimations" />
-        </menu_item_call>
         <menu_item_check
          label="Walk / run / fly..."
          name="WalkRunFly">
@@ -165,6 +159,32 @@
         </menu_item_check>
       </menu>
 
+      <menu
+       create_jump_keys="true"
+       label="Health"
+       name="Health"
+       tear_off="true">
+        <menu_item_call
+         label="Stop Animating Me"
+         name="Stop Animating My Avatar"
+         shortcut="alt|shift|A">
+          <menu_item_call.on_click
+           function="Tools.StopAllAnimations" />
+        </menu_item_call>
+        <menu_item_call
+         label="Undeform Me"
+         name="Undeform Me">
+          <menu_item_call.on_click
+           function="Tools.UndeformSelf" />
+        </menu_item_call>
+        <menu_item_call
+         label="Clear Viewer Effects"
+         name="Clear Viewer Effects">
+          <menu_item_call.on_click
+           function="World.ClearEffects" />
+        </menu_item_call>
+      </menu>
+
       <menu
        create_jump_keys="true"
        label="Status"
@@ -417,6 +437,14 @@
      label="World"
      name="World"
      tear_off="true">
+        <menu_item_call
+         label="Resync Animations"
+         name="Resync Animations"
+         shortcut="control|S">
+          <menu_item_call.on_click
+           function="World.SyncAnimations" />
+        </menu_item_call>
+        <menu_item_separator/>
         <menu_item_call
          label="Landmark This Place"
          name="Create Landmark Here">
-- 
GitLab