diff --git a/indra/newview/llvoavatar.cpp b/indra/newview/llvoavatar.cpp
index 7b43632fc0a6f401a128b2faba92b22ef632b76b..221f771bc1f935e8d78c94ff5b22b1401386f43e 100644
--- a/indra/newview/llvoavatar.cpp
+++ b/indra/newview/llvoavatar.cpp
@@ -3088,7 +3088,7 @@ void LLVOAvatar::idleUpdateNameTag(const LLVector3& root_pos_last)
 	bool fRlvShowAvTag = true, fRlvShowAvName = true;
 	if (RlvActions::isRlvEnabled())
 	{
-		fRlvShowAvTag = RlvActions::canShowName(RlvActions::SNC_NAMETAG, getID());
+		fRlvShowAvTag = RlvActions::canShowNameTag(this);
 		fRlvShowAvName = (fRlvShowAvTag) && (RlvActions::canShowName(RlvActions::SNC_DEFAULT, getID()));
 	}
 // [/RLVa:KB]
diff --git a/indra/newview/rlvactions.cpp b/indra/newview/rlvactions.cpp
index 44def7256c187f18b5b47152c3836b5e95f28f16..0a2c8b5b587c1b5ef40d8b7f6501ea1d066b1e14 100644
--- a/indra/newview/rlvactions.cpp
+++ b/indra/newview/rlvactions.cpp
@@ -220,9 +220,6 @@ bool RlvActions::canShowName(EShowNamesContext eContext, const LLUUID& idAgent)
 	{
 		switch (eContext)
 		{
-			// Show/hide avatar nametag
-			case SNC_NAMETAG:
-				return (gRlvHandler.isException(RLV_BHVR_SHOWNAMETAGS, idAgent)) || (gAgentID == idAgent);
 			// Show/hide avatar name
 			case SNC_DEFAULT:
 			case SNC_TELEPORTOFFER:
@@ -233,6 +230,19 @@ bool RlvActions::canShowName(EShowNamesContext eContext, const LLUUID& idAgent)
 	return false;
 }
 
+bool RlvActions::canShowNameTag(const LLVOAvatar* pAvatar)
+{
+	// An avatar's name tag can be shown if:
+	//   - not restricted from seeing avatars' name tags
+	//   - OR the avatar is a @shownametags exception
+	//   - OR the avatar is within the distance that nametags can be shown
+	if ( (!gRlvHandler.hasBehaviour(RLV_BHVR_SHOWNAMETAGS)) || (gRlvHandler.isException(RLV_BHVR_SHOWNAMETAGS, pAvatar->getID())) || (gAgentID == pAvatar->getID()) )
+		return true;
+
+	const F32 nShowNameTagsDist = RlvBehaviourDictionary::instance().getModifier(RLV_MODIFIER_SHOWNAMETAGSDIST)->getValue<F32>();
+	return (nShowNameTagsDist != 0.f) && (dist_vec_squared(pAvatar->getPositionGlobal(), gAgent.getPositionGlobal()) < nShowNameTagsDist * nShowNameTagsDist);
+}
+
 bool RlvActions::canShowNearbyAgents()
 {
 	return !gRlvHandler.hasBehaviour(RLV_BHVR_SHOWNEARBY);
diff --git a/indra/newview/rlvactions.h b/indra/newview/rlvactions.h
index 6571023ca71f9e03e47924a83bc7b80763130a62..499b53b6a5a125e9afbd342b394a56ad2c3db8f2 100644
--- a/indra/newview/rlvactions.h
+++ b/indra/newview/rlvactions.h
@@ -123,8 +123,9 @@ class RlvActions
 	 * (This is used to hide an avatar name in one case but not a near-identical case - such as teleporting a friend vs a nearby agent -
 	 *  in a way that limits the amount of code that needs to be changed to carry context from one function to another)
 	 */
-	enum EShowNamesContext { SNC_DEFAULT = 0, SNC_NAMETAG, SNC_TELEPORTOFFER, SNC_TELEPORTREQUEST, SNC_COUNT };
+	enum EShowNamesContext { SNC_DEFAULT = 0, SNC_TELEPORTOFFER, SNC_TELEPORTREQUEST, SNC_COUNT };
 	static bool canShowName(EShowNamesContext eContext, const LLUUID& idAgent = LLUUID::null);
+	static bool canShowNameTag(const LLVOAvatar* pAvatar);
 	static void setShowName(EShowNamesContext eContext, bool fCanShowName) { if ( (eContext < SNC_COUNT) && (isRlvEnabled()) ) { s_BlockNamesContexts[eContext] = !fCanShowName; } }
 
 	/*
diff --git a/indra/newview/rlvdefines.h b/indra/newview/rlvdefines.h
index 3d7d77ae408b32831a87b9f6fd980eb901e6e520..13631811d23152a3e95c0ab9fd1392bee968f213 100644
--- a/indra/newview/rlvdefines.h
+++ b/indra/newview/rlvdefines.h
@@ -274,6 +274,7 @@ enum ERlvBehaviourModifier
 	RLV_MODIFIER_SETCAM_FOVMIN,			// Minimum value for the camera's field of view (angle in radians)
 	RLV_MODIFIER_SETCAM_FOVMAX,			// Maximum value for the camera's field of view (angle in radians)
 	RLV_MODIFIER_SETCAM_TEXTURE,		// Specifies the UUID of the texture used to texture the world view
+	RLV_MODIFIER_SHOWNAMETAGSDIST,		// Distance at which name tags will still be shown
 	RLV_MODIFIER_SITTPDIST,
 	RLV_MODIFIER_TPLOCALDIST,
 
diff --git a/indra/newview/rlvhandler.cpp b/indra/newview/rlvhandler.cpp
index 441d5034c2b9ba66ed93537a555f19eded281753..5ba4839812fcbbe30e16e88de90fea19b3f062b2 100644
--- a/indra/newview/rlvhandler.cpp
+++ b/indra/newview/rlvhandler.cpp
@@ -2564,28 +2564,31 @@ ERlvCmdRet RlvBehaviourHandler<RLV_BHVR_SHOWNAMES>::onCommand(const RlvCommand&
 	return eRet;
 }
 
-// Handles: @shownametags[:<uuid>]=n|y toggles
-template<> template<>
-void RlvBehaviourToggleHandler<RLV_BHVR_SHOWNAMETAGS>::onCommandToggle(ERlvBehaviour eBhvr, bool fHasBhvr)
+// Handles: @shownametags[:<distance>] value changes
+template<>
+void RlvBehaviourModifierHandler<RLV_MODIFIER_SHOWNAMETAGSDIST>::onValueChange() const
 {
 	if (LLApp::isExiting())
 		return;	// Nothing to do if the viewer is shutting down
 
-	// Update the shownames context
-	RlvActions::setShowName(RlvActions::SNC_NAMETAG, !fHasBhvr);
-
 	// Refresh all name tags
 	LLVOAvatar::invalidateNameTags();
 }
 
-// Handles: @shownametags[:<uuid>]=n|y
+// Handles: @shownametags[:<distance|uuid>]=n|y
 template<> template<>
 ERlvCmdRet RlvBehaviourHandler<RLV_BHVR_SHOWNAMETAGS>::onCommand(const RlvCommand& rlvCmd, bool& fRefCount)
 {
-	ERlvCmdRet eRet = RlvBehaviourGenericHandler<RLV_OPTION_NONE_OR_EXCEPTION>::onCommand(rlvCmd, fRefCount);
-	if ( (RLV_RET_SUCCESS == eRet) && (rlvCmd.hasOption()) )
-		LLVOAvatar::invalidateNameTag(RlvCommandOptionHelper::parseOption<LLUUID>(rlvCmd.getOption()));
-	return eRet;
+	LLUUID idOption;
+	if ( (rlvCmd.hasOption()) && (RlvCommandOptionHelper::parseOption(rlvCmd.getOption(), idOption)) )
+	{
+		ERlvCmdRet eRet = RlvBehaviourGenericHandler<RLV_OPTION_EXCEPTION>::onCommand(rlvCmd, fRefCount);
+		if (RLV_RET_SUCCESS == eRet)
+			LLVOAvatar::invalidateNameTag(idOption);
+		fRefCount = false;
+		return eRet;
+	}
+	return RlvBehaviourGenericHandler<RLV_OPTION_NONE_OR_MODIFIER>::onCommand(rlvCmd, fRefCount);
 }
 
 // Handles: @shownearby=n|y toggles
diff --git a/indra/newview/rlvhelper.cpp b/indra/newview/rlvhelper.cpp
index 0b73a6faae0b211fe6f51a37b87cbf779ed6d249..dcef3f982747736ef4cce49dd447d32fce16f9c1 100644
--- a/indra/newview/rlvhelper.cpp
+++ b/indra/newview/rlvhelper.cpp
@@ -146,7 +146,8 @@ RlvBehaviourDictionary::RlvBehaviourDictionary()
 	addEntry(new RlvBehaviourGenericProcessor<RLV_OPTION_NONE>("showloc", RLV_BHVR_SHOWLOC));
 	addEntry(new RlvBehaviourGenericProcessor<RLV_OPTION_NONE>("showminimap", RLV_BHVR_SHOWMINIMAP));
 	addEntry(new RlvBehaviourToggleProcessor<RLV_BHVR_SHOWNAMES>("shownames", RlvBehaviourInfo::BHVR_STRICT));
-	addEntry(new RlvBehaviourToggleProcessor<RLV_BHVR_SHOWNAMETAGS>("shownametags", RlvBehaviourInfo::BHVR_STRICT ));
+	addEntry(new RlvBehaviourProcessor<RLV_BHVR_SHOWNAMETAGS>("shownametags", RlvBehaviourInfo::BHVR_STRICT));
+	addModifier(RLV_BHVR_SHOWNAMETAGS, RLV_MODIFIER_SHOWNAMETAGSDIST, new RlvBehaviourModifierHandler<RLV_MODIFIER_SHOWNAMETAGSDIST>("Name Tags - Visible Distance", 0.0f, true, new RlvBehaviourModifierCompMin));
 	addEntry(new RlvBehaviourGenericToggleProcessor<RLV_BHVR_SHOWNEARBY, RLV_OPTION_NONE>("shownearby", RlvBehaviourInfo::BHVR_EXPERIMENTAL));
 	addEntry(new RlvBehaviourGenericToggleProcessor<RLV_BHVR_SHOWSELF, RLV_OPTION_NONE, RlvBehaviourShowSelfToggleHandler>("showself", RlvBehaviourInfo::BHVR_EXPERIMENTAL));
 	addEntry(new RlvBehaviourGenericToggleProcessor<RLV_BHVR_SHOWSELFHEAD, RLV_OPTION_NONE, RlvBehaviourShowSelfToggleHandler>("showselfhead", RlvBehaviourInfo::BHVR_EXPERIMENTAL));