diff --git a/indra/newview/llchannelmanager.cpp b/indra/newview/llchannelmanager.cpp
index 4f9434030f0a7588b8ab99c64ac990dcd8359173..fafa315a59d7eea7c5ac641de48e42bc0b8d336b 100644
--- a/indra/newview/llchannelmanager.cpp
+++ b/indra/newview/llchannelmanager.cpp
@@ -243,3 +243,19 @@ void LLChannelManager::killToastsFromChannel(const LLUUID& channel_id, const LLS
 	}
 }
 
+// static
+LLNotificationsUI::LLScreenChannel* LLChannelManager::getNotificationScreenChannel()
+{
+	LLNotificationsUI::LLScreenChannel* channel = static_cast<LLNotificationsUI::LLScreenChannel*>
+	(LLNotificationsUI::LLChannelManager::getInstance()->
+										findChannelByID(LLUUID(gSavedSettings.getString("NotificationChannelUUID"))));
+
+	if (channel == NULL)
+	{
+		llwarns << "Can't find screen channel by NotificationChannelUUID" << llendl;
+		llassert(!"Can't find screen channel by NotificationChannelUUID");
+	}
+
+	return channel;
+}
+
diff --git a/indra/newview/llchannelmanager.h b/indra/newview/llchannelmanager.h
index c2be39122f4d106937b718b0f1479d9440af0108..8c725f26609ddce9927043aacc1ae74cce511d87 100644
--- a/indra/newview/llchannelmanager.h
+++ b/indra/newview/llchannelmanager.h
@@ -114,6 +114,11 @@ class LLChannelManager : public LLSingleton<LLChannelManager>
 	 */
 	void killToastsFromChannel(const LLUUID& channel_id, const LLScreenChannel::Matcher& matcher);
 
+	/**
+	 * Returns notification screen channel.
+	 */
+	static LLNotificationsUI::LLScreenChannel* getNotificationScreenChannel();
+
 private:
 
 	LLScreenChannel* createChannel(LLChannelManager::Params& p);
diff --git a/indra/newview/llimfloater.cpp b/indra/newview/llimfloater.cpp
index 19dbc564d17fa61fa1e541fb804f731eac5ea3d2..c0cc3f198594b9232ed2082b89d9910ed2c576cb 100644
--- a/indra/newview/llimfloater.cpp
+++ b/indra/newview/llimfloater.cpp
@@ -53,6 +53,7 @@
 #include "llsyswellwindow.h"
 #include "lltrans.h"
 #include "llchathistory.h"
+#include "llnotifications.h"
 #include "llviewerwindow.h"
 #include "llvoicechannel.h"
 #include "lltransientfloatermgr.h"
@@ -371,6 +372,8 @@ void LLIMFloater::onSlide()
 //static
 LLIMFloater* LLIMFloater::show(const LLUUID& session_id)
 {
+	closeHiddenIMToasts();
+
 	if (!gIMMgr->hasSession(session_id)) return NULL;
 
 	if(!isChatMultiTab())
@@ -1083,6 +1086,26 @@ void LLIMFloater::removeTypingIndicator(const LLIMInfo* im_info)
 	}
 }
 
+// static
+void LLIMFloater::closeHiddenIMToasts()
+{
+	class IMToastMatcher: public LLNotificationsUI::LLScreenChannel::Matcher
+	{
+	public:
+		bool matches(const LLNotificationPtr notification) const
+		{
+			// "notifytoast" type of notifications is reserved for IM notifications
+			return "notifytoast" == notification->getType();
+		}
+	};
+
+	LLNotificationsUI::LLScreenChannel* channel = LLNotificationsUI::LLChannelManager::getNotificationScreenChannel();
+	if (channel != NULL)
+	{
+		channel->closeHiddenToasts(IMToastMatcher());
+	}
+}
+
 // static
 bool LLIMFloater::isChatMultiTab()
 {
diff --git a/indra/newview/llimfloater.h b/indra/newview/llimfloater.h
index 763dd5655ba9c85e122651ece71327a42de9e687..f9dd8b9b85206d13628b3c5b33b7910ad1b99dd5 100644
--- a/indra/newview/llimfloater.h
+++ b/indra/newview/llimfloater.h
@@ -148,6 +148,8 @@ class LLIMFloater : public LLTransientDockableFloater
 	// Remove the "User is typing..." indicator.
 	void removeTypingIndicator(const LLIMInfo* im_info = NULL);
 
+	static void closeHiddenIMToasts();
+
 	LLPanelChatControlPanel* mControlPanel;
 	LLUUID mSessionID;
 	S32 mLastMessageIndex;
diff --git a/indra/newview/llscreenchannel.cpp b/indra/newview/llscreenchannel.cpp
index af440a36891800ec427227a44c140c0937cb7cff..de1da248c12ca34935d498469e5d29a641039481 100644
--- a/indra/newview/llscreenchannel.cpp
+++ b/indra/newview/llscreenchannel.cpp
@@ -706,6 +706,31 @@ void LLScreenChannel::hideToast(const LLUUID& notification_id)
 	}
 }
 
+void LLScreenChannel::closeHiddenToasts(const Matcher& matcher)
+{
+	// since we can't guarantee that close toast operation doesn't change mToastList
+	// we collect matched toasts that should be closed into separate list
+	std::list<ToastElem> toasts;
+	for (std::vector<ToastElem>::iterator it = mToastList.begin(); it
+			!= mToastList.end(); it++)
+	{
+		LLToast * toast = it->toast;
+		// add to list valid toast that match to provided matcher criteria
+		if (toast != NULL && !toast->isDead() && toast->getNotification() != NULL
+				&& !toast->getVisible() && matcher.matches(toast->getNotification()))
+		{
+			toasts.push_back(*it);
+		}
+	}
+
+	// close collected toasts
+	for (std::list<ToastElem>::iterator it = toasts.begin(); it
+			!= toasts.end(); it++)
+	{
+		it->toast->closeFloater();
+	}
+}
+
 //--------------------------------------------------------------------------
 void LLScreenChannel::removeToastsFromChannel()
 {
diff --git a/indra/newview/llscreenchannel.h b/indra/newview/llscreenchannel.h
index 88053d87d9dedacad96f6cb5a71c55cc4f1e0184..46c5fed7b69c7b2cac93560a57ac2a8b33171d60 100644
--- a/indra/newview/llscreenchannel.h
+++ b/indra/newview/llscreenchannel.h
@@ -173,6 +173,12 @@ class LLScreenChannel : public LLScreenChannelBase
 	void		hideToastsFromScreen();
 	// hide toast by notification id
 	void		hideToast(const LLUUID& notification_id);
+
+	/**
+	 * Closes hidden matched toasts from channel.
+	 */
+	void closeHiddenToasts(const Matcher& matcher);
+
 	// removes all toasts from a channel
 	void		removeToastsFromChannel();
 	// show all toasts in a channel