// static
std::string LLScriptFloaterManager::getObjectName(const LLUUID& notification_id)
{
	using namespace LLNotificationsUI;
	LLNotificationPtr notification = LLNotifications::getInstance()->find(notification_id);
	if(!notification)
	{
		llwarns << "Invalid notification" << llendl;
		return LLStringUtil::null;
	}

	std::string text;

	switch(LLScriptFloaterManager::getObjectType(notification_id))
	{
	case LLScriptFloaterManager::OBJ_SCRIPT:
		text = notification->getSubstitutions()["TITLE"].asString();
		break;
	case LLScriptFloaterManager::OBJ_LOAD_URL:
		text = notification->getSubstitutions()["OBJECTNAME"].asString();
		break;
	case LLScriptFloaterManager::OBJ_GIVE_INVENTORY:
		text = notification->getSubstitutions()["OBJECTFROMNAME"].asString();
		break;
	default:
		text = LLTrans::getString("object");
		break;
	}

	return text;
}
예제 #2
0
bool GrowlManager::onLLNotification(const LLSD& notice)
{
	if(notice["sigtype"].asString() != "add")
		return false;
	static BOOL* enabled = rebind_llcontrol<BOOL>("PhoenixEnableGrowl", &gSavedSettings, true);
	if(!*enabled)
		return false;
	if(!shouldNotify())
		return false;
	LLNotificationPtr notification = LLNotifications::instance().find(notice["id"].asUUID());
	std::string name = notification->getName();
	LLSD substitutions = notification->getSubstitutions();
	if(LLStartUp::getStartupState() < STATE_STARTED)
	{
		LL_WARNS("GrowlLLNotification") << "GrowlManager discarded a notification (" << name << ") - too early." << LL_ENDL;
		return false;
	}
	if(gGrowlManager->mNotifications.find(name) != gGrowlManager->mNotifications.end())
	{
		GrowlNotification* growl_notification = &gGrowlManager->mNotifications[name];
		std::string body = "";
		std::string title = "";
		if(growl_notification->useDefaultTextForTitle)
			title = notification->getMessage();
		else if(growl_notification->growlTitle != "")
			title = LLNotification::format(growl_notification->growlTitle, substitutions);
		if(growl_notification->useDefaultTextForBody)
			body = notification->getMessage();
		else if(growl_notification->growlBody != "")
			body = LLNotification::format(growl_notification->growlBody, substitutions);
		LL_INFOS("GrowlLLNotification") << "Notice: " << title << ": " << body << LL_ENDL;
		gGrowlManager->notify(title, body, growl_notification->growlName);
	}
	return false;
}
bool LLNotification::isEquivalentTo(LLNotificationPtr that) const
{
	if (this->mTemplatep->mName != that->mTemplatep->mName) 
	{
		return false; // must have the same template name or forget it
	}
	if (this->mTemplatep->mUnique)
	{
		const LLSD& these_substitutions = this->getSubstitutions();
		const LLSD& those_substitutions = that->getSubstitutions();
		const LLSD& this_payload = this->getPayload();
		const LLSD& that_payload = that->getPayload();

		// highlander bit sez there can only be one of these
		for (std::vector<std::string>::const_iterator it = mTemplatep->mUniqueContext.begin(), end_it = mTemplatep->mUniqueContext.end();
			it != end_it;
			++it)
		{
			// if templates differ in either substitution strings or payload with the given field name
			// then they are considered inequivalent
			// use of get() avoids converting the LLSD value to a map as the [] operator would
			if (these_substitutions.get(*it).asString() != those_substitutions.get(*it).asString()
				|| this_payload.get(*it).asString() != that_payload.get(*it).asString())
			{
				return false;
			}
		}
		return true;
	}

	return false; 
}
예제 #4
0
//static
bool KVGrowlManager::onLLNotification(const LLSD& notice)
{
	if(notice["sigtype"].asString() != "add")
		return false;
	if(!shouldNotify())
		return false;
	LLNotificationPtr notification = LLNotifications::instance().find(notice["id"].asUUID());
	std::string name = notification->getName();
	LLSD substitutions = notification->getSubstitutions();
	if(LLStartUp::getStartupState() < STATE_STARTED)
	{
		LL_WARNS("GrowlLLNotification") << "GrowlManager discarded a notification (" << name << ") - too early." << LL_ENDL;
		return false;
	}
	if(gGrowlManager->mNotifications.find(name) != gGrowlManager->mNotifications.end())
	{
		KVGrowlNotification* growl_notification = &gGrowlManager->mNotifications[name];
		std::string body = "";
		std::string title = "";
		if(growl_notification->useDefaultTextForTitle)
			title = notification->getMessage();
		else if(growl_notification->growlTitle != "")
			title = growl_notification->growlTitle;
			LLStringUtil::format(title, substitutions);
		if(growl_notification->useDefaultTextForBody)
			body = notification->getMessage();
		else if(growl_notification->growlBody != "")
			body = growl_notification->growlBody;
			LLStringUtil::format(body, substitutions);
		gGrowlManager->notify(title, body, growl_notification->growlName);
	}
	return false;
}
예제 #5
0
//--------------------------------------------------------------------------
bool LLIMHandler::processNotification(const LLSD& notify)
{
	if(!mChannel)
	{
		return false;
	}

	LLNotificationPtr notification = LLNotifications::instance().find(notify["id"].asUUID());

	if(!notification)
		return false;

	// arrange a channel on a screen
	if(!mChannel->getVisible())
	{
		initChannel();
	}

	if(notify["sigtype"].asString() == "add" || notify["sigtype"].asString() == "change")
	{
		LLSD substitutions = notification->getSubstitutions();

		// According to comments in LLIMMgr::addMessage(), if we get message
		// from ourselves, the sender id is set to null. This fixes EXT-875.
		LLUUID avatar_id = substitutions["FROM_ID"].asUUID();
		if (avatar_id.isNull())
			avatar_id = gAgentID;

		LLToastIMPanel::Params im_p;
		im_p.notification = notification;
		im_p.avatar_id = avatar_id;
		im_p.from = substitutions["FROM"].asString();
		im_p.time = substitutions["TIME"].asString();
		im_p.message = substitutions["MESSAGE"].asString();
		im_p.session_id = substitutions["SESSION_ID"].asUUID();

		LLToastIMPanel* im_box = new LLToastIMPanel(im_p);

		LLToast::Params p;
		p.notif_id = notification->getID();
		p.session_id = im_p.session_id;
		p.notification = notification;
		p.panel = im_box;
		p.can_be_stored = false;
		p.on_delete_toast = boost::bind(&LLIMHandler::onDeleteToast, this, _1);
		LLScreenChannel* channel = dynamic_cast<LLScreenChannel*>(mChannel);
		if(channel)
			channel->addToast(p);

		// send a signal to the counter manager;
		mNewNotificationSignal();
	}
	else if (notify["sigtype"].asString() == "delete")
	{
		mChannel->killToastByNotificationID(notification->getID());
	}
	return false;
}
예제 #6
0
bool GrowlManager::onLLNotification(const LLSD& notice)
{
	if (notice["sigtype"].asString() != "add")
	{
		return false;
	}

	LLNotificationPtr notification = LLNotifications::instance().find(notice["id"].asUUID());
	std::string name = notification->getName();
	LLSD substitutions = notification->getSubstitutions();
	if (gGrowlManager->mNotifications.find(name) != gGrowlManager->mNotifications.end())
	{
		GrowlNotification* growl_notification = &gGrowlManager->mNotifications[name];
		std::string body = "";
		std::string title = "";
		if (growl_notification->useDefaultTextForTitle)
		{
			title = notification->getMessage();
		}
		else if (!growl_notification->growlTitle.empty())
		{
			title = growl_notification->growlTitle;
			LLStringUtil::format(title, substitutions);
		}
		if (growl_notification->useDefaultTextForBody)
		{
			body = notification->getMessage();
		}
		else if (!growl_notification->growlBody.empty())
		{
			body = growl_notification->growlBody;
			LLStringUtil::format(body, substitutions);
		}
		//TM:FS no need to log whats sent to growl
		//LL_INFOS("GrowlLLNotification") << "Notice: " << title << ": " << body << LL_ENDL;
		if (name == "ObjectGiveItem" || name == "OwnObjectGiveItem" || name == "ObjectGiveItemUnknownUser" || name == "UserGiveItem" || name == "SystemMessageTip")
		{
			LLUrlMatch urlMatch;
			LLWString newLine = utf8str_to_wstring(body);
			LLWString workLine = utf8str_to_wstring(body);
			while (LLUrlRegistry::instance().findUrl(workLine, urlMatch) && !urlMatch.getUrl().empty())
			{
				LLWStringUtil::replaceString(newLine, utf8str_to_wstring(urlMatch.getUrl()), utf8str_to_wstring(urlMatch.getLabel()));

				// Remove the URL from the work line so we don't end in a loop in case of regular URLs!
				// findUrl will always return the very first URL in a string
				workLine = workLine.erase(0, urlMatch.getEnd() + 1);
			}
			body = wstring_to_utf8str(newLine);
		}
		gGrowlManager->notify(title, body, growl_notification->growlName);
	}
	return false;
}
// static
std::string LLHandlerUtil::getSubstitutionName(const LLNotificationPtr& notification)
{
	std::string res = notification->getSubstitutions().has("NAME")
		? notification->getSubstitutions()["NAME"]
		: notification->getSubstitutions()["[NAME]"];
	if (res.empty())
	{
		LLUUID from_id = notification->getPayload()["FROM_ID"];

		//*TODO all keys everywhere should be made of the same case, there is a mix of keys in lower and upper cases
		if (from_id.isNull()) 
		{
			from_id = notification->getPayload()["from_id"];
		}
		if(!gCacheName->getFullName(from_id, res))
		{
			res = "";
		}
	}
	return res;
}
예제 #8
0
//static
void GrowlManager::onScriptDialog(const LLSD& data)
{
	LLNotificationPtr notification = LLNotifications::instance().find(data["notification_id"].asUUID());
	std::string name = notification->getName();
	LLSD payload = notification->getPayload();
	LLSD substitutions = notification->getSubstitutions();

	//LL_INFOS("GrowlLLNotification") << "Script dialog: name=" << name << " - payload=" << payload << " subs=" << substitutions << LL_ENDL;
	if (gGrowlManager->mNotifications.find(name) != gGrowlManager->mNotifications.end())
	{
		GrowlNotification* growl_notification = &gGrowlManager->mNotifications[name];

		std::string body = "";
		std::string title = "";
		if (growl_notification->useDefaultTextForTitle)
		{
			title = notification->getMessage();
		}
		else if (!growl_notification->growlTitle.empty())
		{
			title = growl_notification->growlTitle;
			LLStringUtil::format(title, substitutions);
		}

		if (growl_notification->useDefaultTextForBody)
		{
			body = notification->getMessage();
		}
		else if (!growl_notification->growlBody.empty())
		{
			body = growl_notification->growlBody;
			LLStringUtil::format(body, substitutions);
		}

		gGrowlManager->notify(title, body, growl_notification->growlName);
	}
}
void LLPanelMsgs::buildLists() //void LLFloaterPreference::buildPopupLists() in v3
{
	LLScrollListCtrl& disabled_popups =
		getChildRef<LLScrollListCtrl>("disabled_popups");
	LLScrollListCtrl& enabled_popups =
		getChildRef<LLScrollListCtrl>("enabled_popups");
	
	disabled_popups.deleteAllItems();
	enabled_popups.deleteAllItems();

	for (LLNotifications::TemplateMap::const_iterator iter = LLNotifications::instance().templatesBegin();
		iter != LLNotifications::instance().templatesEnd();
		++iter)
	{
		LLNotificationTemplatePtr templatep = iter->second;
		LLNotificationFormPtr formp = templatep->mForm;

		LLNotificationForm::EIgnoreType ignore = formp->getIgnoreType();
		if (ignore == LLNotificationForm::IGNORE_NO)
				continue;

		LLSD params;
		params["name"] = (*iter).first;
		LLNotificationPtr notification = LLNotificationPtr(new LLNotification(params));

		LLSD row;
		std::string ignore_msg = formp->getIgnoreMessage();
		LLStringUtil::format(ignore_msg,notification->getSubstitutions());
		row["columns"][0]["value"] = ignore_msg;
		row["columns"][0]["font"] = "SANSSERIF_SMALL";
		row["columns"][0]["width"] = 300;

		LLScrollListItem* item = NULL;

		bool show_popup = !formp->getIgnored();
		if (!show_popup)
		{
			if (ignore == LLNotificationForm::IGNORE_WITH_LAST_RESPONSE)
			{
				LLSD last_response = LLUI::sConfigGroup->getLLSD("Default" + templatep->mName);
				if (!last_response.isUndefined())
				{
					for (LLSD::map_const_iterator it = last_response.beginMap();
						it != last_response.endMap();
						++it)
					{
						if (it->second.asBoolean())
						{
							row["columns"][1]["value"] = formp->getElement(it->first)["ignore"].asString();
							break;
						}
					}
				}
				row["columns"][1]["font"] = "SANSSERIF_SMALL";
				row["columns"][1]["width"] = 160;
			}
			item = disabled_popups.addElement(row,
							   ADD_SORTED);
		}
		else
		{
			item = enabled_popups.addElement(row,
							  ADD_SORTED);
		}

		if (item)
		{
			item->setUserdata((void*)&iter->first);
		}
	}
}
//--------------------------------------------------------------------------
bool LLTipHandler::processNotification(const LLSD& notify)
{
	if(mChannel.isDead())
	{
		return false;
	}

	LLNotificationPtr notification = LLNotifications::instance().find(notify["id"].asUUID());

	if(!notification)
		return false;	

	// arrange a channel on a screen
	if(!mChannel.get()->getVisible())
	{
		initChannel();
	}

	if(notify["sigtype"].asString() == "add" || notify["sigtype"].asString() == "change")
	{
		// archive message in nearby chat
		if (LLHandlerUtil::canLogToNearbyChat(notification))
		{
			LLHandlerUtil::logToNearbyChat(notification, CHAT_SOURCE_SYSTEM);

			// don't show toast if Nearby Chat is opened
			LLFloaterNearbyChat* nearby_chat = LLFloaterNearbyChat::getInstance();
			// <FS:Zi> Remove floating chat bar
			// LLNearbyChatBar* nearby_chat_bar = LLNearbyChatBar::getInstance();
			// if (!nearby_chat_bar->isMinimized() && nearby_chat_bar->getVisible() && nearby_chat->getVisible())
			if (nearby_chat->getVisible())
			// </FS:Zi>
			{
				return false;
			}
		}

		std::string session_name = notification->getPayload()["SESSION_NAME"];
		const std::string name = notification->getSubstitutions()["NAME"];
		const LLUUID agent_id = notification->getSubstitutions()["AGENT-ID"];
		
		if (session_name.empty())
		{
			session_name = name;
		}
		LLUUID from_id = notification->getPayload()["from_id"];
		if (LLHandlerUtil::canLogToIM(notification))
		{
//			LLHandlerUtil::logToIM(IM_NOTHING_SPECIAL, session_name, name,
//					notification->getMessage(), from_id, from_id);
// [SL:KB] - Patch: Chat-Logs | Checked: 2010-11-18 (Catznip-2.4.0c) | Added: Catznip-2.4.0c
			LLHandlerUtil::logToIMP2P(notification, false);
// [/SL:KB]
		}

		if (LLHandlerUtil::canSpawnIMSession(notification))
		{
			LLHandlerUtil::spawnIMSession(name, from_id);
		}

		// don't spawn toast for inventory accepted/declined offers if respective IM window is open (EXT-5909)
		if (!LLHandlerUtil::canSpawnToast(notification))
		{
			return false;
		}

		// [FIRE-3522 : SJ] Only show Online/Offline toast when ChatOnlineNotification is enabled or the Friend is one you want to have on/offline notices from
		if (!gSavedSettings.getBOOL("ChatOnlineNotification") && ("FriendOffline" == notification->getName() || "FriendOnline" == notification->getName()))
		{
			// [FIRE-3522 : SJ] Only show Online/Offline toast for groups which have enabled "Show notice for this set" and in the settingpage of CS is checked that the messages need to be in Toasts
			if (!(gSavedSettings.getBOOL("FSContactSetsNotificationToast") && LGGContactSets::getInstance()->notifyForFriend(agent_id)))
			{
				return false;
			}
		}

		LLToastPanel* notify_box = LLToastPanel::buidPanelFromNotification(notification);

		LLToast::Params p;
		p.notif_id = notification->getID();
		p.notification = notification;
		p.lifetime_secs = gSavedSettings.getS32("NotificationTipToastLifeTime");
		p.panel = notify_box;
		p.is_tip = true;
		p.can_be_stored = false;
		
		removeExclusiveNotifications(notification);

		LLScreenChannel* channel = dynamic_cast<LLScreenChannel*>(mChannel.get());
		if(channel)
			channel->addToast(p);
	}
	else if (notify["sigtype"].asString() == "delete")
	{
		mChannel.get()->killToastByNotificationID(notification->getID());
	}
	return false;
}
예제 #11
0
LLToastAlertPanel::LLToastAlertPanel( LLNotificationPtr notification, bool modal)
	  : LLToastPanel(notification),
		mDefaultOption( 0 ),
		mCheck(NULL),
		mCaution(notification->getPriority() >= NOTIFICATION_PRIORITY_HIGH),
		mLabel(notification->getName()),
		mLineEditor(NULL)
{
	const LLFontGL* font = LLFontGL::getFontSansSerif();
	const S32 LINE_HEIGHT = llfloor(font->getLineHeight() + 0.99f);
	const S32 EDITOR_HEIGHT = 20;

	LLNotificationFormPtr form = mNotification->getForm();
	std::string edit_text_name;
	std::string edit_text_contents;
	S32 edit_text_max_chars = 0;
	bool is_password = false;

	LLToastPanel::setBackgroundVisible(FALSE);
	LLToastPanel::setBackgroundOpaque(TRUE);


	typedef std::vector<std::pair<std::string, std::string> > options_t;
	options_t supplied_options;

	// for now, get LLSD to iterator over form elements
	LLSD form_sd = form->asLLSD();

	S32 option_index = 0;
	for (LLSD::array_const_iterator it = form_sd.beginArray(); it != form_sd.endArray(); ++it)
	{
		std::string type = (*it)["type"].asString();
		if (type == "button")
		{
			if((*it)["default"])
			{
				mDefaultOption = option_index;
			}

			supplied_options.push_back(std::make_pair((*it)["name"].asString(), (*it)["text"].asString()));

			ButtonData data;
			if (option_index == mNotification->getURLOption())
			{
				data.mURL = mNotification->getURL();
				data.mURLExternal = mNotification->getURLOpenExternally();
			}

			mButtonData.push_back(data);
			option_index++;
		}
		else if (type == "text")
		{
			edit_text_contents = (*it)["value"].asString();
			edit_text_name = (*it)["name"].asString();
			edit_text_max_chars = (*it)["max_length_chars"].asInteger();
		}
		else if (type == "password")
		{
			edit_text_contents = (*it)["value"].asString();
			edit_text_name = (*it)["name"].asString();
			is_password = true;
		}
	}

	// Buttons
	options_t options;
	if (supplied_options.empty())
	{
		options.push_back(std::make_pair(std::string("close"), LLNotifications::instance().getGlobalString("implicitclosebutton")));

		// add data for ok button.
		ButtonData ok_button;
		mButtonData.push_back(ok_button);
		mDefaultOption = 0;
	}
	else
	{
		options = supplied_options;
	}

	S32 num_options = options.size();

	// Calc total width of buttons
	S32 button_width = 0;
	S32 sp = font->getWidth(std::string("OO"));
	for( S32 i = 0; i < num_options; i++ )
	{
		S32 w = S32(font->getWidth( options[i].second ) + 0.99f) + sp + 2 * LLBUTTON_H_PAD;
		button_width = llmax( w, button_width );
	}
	S32 btn_total_width = button_width;
	if( num_options > 1 )
	{
		btn_total_width = (num_options * button_width) + ((num_options - 1) * BTN_HPAD);
	}

	// Message: create text box using raw string, as text has been structure deliberately
	// Use size of created text box to generate dialog box size
	std::string msg = mNotification->getMessage();
	llwarns << "Alert: " << msg << llendl;
	LLTextBox::Params params;
	params.name("Alert message");
	params.font(font);
	params.tab_stop(false);
	params.wrap(true);
	params.follows.flags(FOLLOWS_LEFT | FOLLOWS_TOP);
	params.allow_scroll(true);

	LLTextBox * msg_box = LLUICtrlFactory::create<LLTextBox> (params);
	// Compute max allowable height for the dialog text, so we can allocate
	// space before wrapping the text to fit.
	S32 max_allowed_msg_height = 
			gFloaterView->getRect().getHeight()
			- LINE_HEIGHT			// title bar
			- 3*VPAD - BTN_HEIGHT;
	// reshape to calculate real text width and height
	msg_box->reshape( MAX_ALLOWED_MSG_WIDTH, max_allowed_msg_height );
	msg_box->setValue(msg);

	S32 pixel_width = msg_box->getTextPixelWidth();
	S32 pixel_height = msg_box->getTextPixelHeight();

	// We should use some space to prevent set textbox's scroller visible when it is unnecessary.
	msg_box->reshape( llmin(MAX_ALLOWED_MSG_WIDTH,pixel_width + 2 * msg_box->getHPad() + HPAD),
		llmin(max_allowed_msg_height,pixel_height + 2 * msg_box->getVPad())  ) ;

	const LLRect& text_rect = msg_box->getRect();
	S32 dialog_width = llmax( btn_total_width, text_rect.getWidth() ) + 2 * HPAD;
	S32 dialog_height = text_rect.getHeight() + 3 * VPAD + BTN_HEIGHT;

	if (hasTitleBar())
	{
		dialog_height += LINE_HEIGHT; // room for title bar
	}

	// it's ok for the edit text body to be empty, but we want the name to exist if we're going to draw it
	if (!edit_text_name.empty())
	{
		dialog_height += EDITOR_HEIGHT + VPAD;
		dialog_width = llmax(dialog_width, (S32)(font->getWidth( edit_text_contents ) + 0.99f));
	}

	if (mCaution)
	{
		// Make room for the caution icon.
		dialog_width += 32 + HPAD;
	}

	LLToastPanel::reshape( dialog_width, dialog_height, FALSE );

	S32 msg_y = LLToastPanel::getRect().getHeight() - VPAD;
	S32 msg_x = HPAD;
	if (hasTitleBar())
	{
		msg_y -= LINE_HEIGHT; // room for title
	}

	static LLUIColor alert_caution_text_color = LLUIColorTable::instance().getColor("AlertCautionTextColor");
	if (mCaution)
	{
		LLIconCtrl* icon = LLUICtrlFactory::getInstance()->createFromFile<LLIconCtrl>("alert_icon.xml", this, LLPanel::child_registry_t::instance());
		if(icon)
		{
			icon->setRect(LLRect(msg_x, msg_y, msg_x+32, msg_y-32));
			LLToastPanel::addChild(icon);
		}
		
		msg_x += 32 + HPAD;
		msg_box->setColor( alert_caution_text_color );
	}

	LLRect rect;
	rect.setLeftTopAndSize( msg_x, msg_y, text_rect.getWidth(), text_rect.getHeight() );
	msg_box->setRect( rect );
	LLToastPanel::addChild(msg_box);

	// (Optional) Edit Box	
	if (!edit_text_name.empty())
	{
		S32 y = VPAD + BTN_HEIGHT + VPAD/2;
		mLineEditor = LLUICtrlFactory::getInstance()->createFromFile<LLLineEditor>("alert_line_editor.xml", this, LLPanel::child_registry_t::instance());
	
		if (mLineEditor)
		{
			LLRect leditor_rect = LLRect( HPAD, y+EDITOR_HEIGHT, dialog_width-HPAD, y);
			mLineEditor->setName(edit_text_name);
			mLineEditor->reshape(leditor_rect.getWidth(), leditor_rect.getHeight());
			mLineEditor->setRect(leditor_rect);
			mLineEditor->setMaxTextChars(edit_text_max_chars);
			mLineEditor->setText(edit_text_contents);

			// decrease limit of line editor of teleport offer dialog to avoid truncation of
			// location URL in invitation message, see EXT-6891
			if ("OfferTeleport" == mNotification->getName())
			{
				mLineEditor->setMaxTextLength(gSavedSettings.getS32(
						"teleport_offer_invitation_max_length"));
			}
			else
			{
				mLineEditor->setMaxTextLength(STD_STRING_STR_LEN - 1);
			}

			LLToastPanel::addChild(mLineEditor);

			mLineEditor->setDrawAsterixes(is_password);

			setEditTextArgs(notification->getSubstitutions());

			mLineEditor->setFollowsLeft();
			mLineEditor->setFollowsRight();

			// find form text input field
			LLSD form_text;
			for (LLSD::array_const_iterator it = form_sd.beginArray(); it != form_sd.endArray(); ++it)
			{
				std::string type = (*it)["type"].asString();
				if (type == "text")
				{
					form_text = (*it);
				}
			}

			// if form text input field has width attribute
			if (form_text.has("width"))
			{
				// adjust floater width to fit line editor
				S32 editor_width = form_text["width"];
				LLRect editor_rect =  mLineEditor->getRect();
				U32 width_delta = editor_width  - editor_rect.getWidth();
				LLRect toast_rect = getRect();
				reshape(toast_rect.getWidth() +  width_delta, toast_rect.getHeight());
			}
		}
	}

	// Buttons
	S32 button_left = (LLToastPanel::getRect().getWidth() - btn_total_width) / 2;

	for( S32 i = 0; i < num_options; i++ )
	{
		LLRect button_rect;

		LLButton* btn = LLUICtrlFactory::getInstance()->createFromFile<LLButton>("alert_button.xml", this, LLPanel::child_registry_t::instance());
		if(btn)
		{
			btn->setName(options[i].first);
			btn->setRect(button_rect.setOriginAndSize( button_left, VPAD, button_width, BTN_HEIGHT ));
			btn->setLabel(options[i].second);
			btn->setFont(font);

			btn->setClickedCallback(boost::bind(&LLToastAlertPanel::onButtonPressed, this, _2, i));

			mButtonData[i].mButton = btn;

			LLToastPanel::addChild(btn);

			if( i == mDefaultOption )
			{
				btn->setFocus(TRUE);
			}
		}
		button_left += button_width + BTN_HPAD;
	}

	std::string ignore_label;

	if (form->getIgnoreType() == LLNotificationForm::IGNORE_WITH_DEFAULT_RESPONSE)
	{
		setCheckBox(LLNotifications::instance().getGlobalString("skipnexttime"), ignore_label);
	}
	else if (form->getIgnoreType() == LLNotificationForm::IGNORE_WITH_LAST_RESPONSE)
	{
		setCheckBox(LLNotifications::instance().getGlobalString("alwayschoose"), ignore_label);
	}

	// *TODO: check necessity of this code
	//gFloaterView->adjustToFitScreen(this, FALSE);
	if (mLineEditor)
	{
		mLineEditor->selectAll();
	}
	if(mDefaultOption >= 0)
	{
		// delay before enabling default button
		mDefaultBtnTimer.start();
		mDefaultBtnTimer.setTimerExpirySec(DEFAULT_BUTTON_DELAY);
	}

	LLTransientFloaterMgr::instance().addControlView(
			LLTransientFloaterMgr::GLOBAL, this);
}
예제 #12
0
LLAlertDialog::LLAlertDialog( LLNotificationPtr notification, bool modal)
	:	LLModalDialog( notification->getLabel(), 100, 100, modal ),  // dummy size.  Will reshape below.
		LLInstanceTracker<LLAlertDialog, LLUUID>(notification->getID()),
		mDefaultButton( NULL ),
		mCheck(NULL),
		mCaution(notification->getPriority() >= NOTIFICATION_PRIORITY_HIGH),
		mLabel(notification->getName()),
		mLineEditor(NULL),
		mNote(notification)
{
	const LLFontGL* font = LLResMgr::getInstance()->getRes( FONT_NAME );
	const S32 LINE_HEIGHT = llfloor(font->getLineHeight() + 0.99f);
	const S32 EDITOR_HEIGHT = 20;

	LLNotificationFormPtr form = mNote->getForm();
	std::string edit_text_name;
	std::string edit_text_contents;
	bool is_password = false;

	setBackgroundVisible(TRUE);
	setBackgroundOpaque(TRUE);

	typedef std::list<ButtonData> options_t;
	options_t options;

	// for now, get LLSD to iterator over form elements
	LLSD form_sd = form->asLLSD();

	for (LLSD::array_const_iterator it = form_sd.beginArray(); it != form_sd.endArray(); ++it)
	{
		std::string type = (*it)["type"].asString();
		if (type == "button")
		{
			options.push_back(ButtonData());
			ButtonData& button_data = options.back();
			button_data.mName = (*it)["name"].asString();
			button_data.mText = (*it)["text"].asString();
			button_data.mDefault = (*it)["default"].asBoolean();
			if(options.size()-1 == mNote->getURLOption())
				button_data.mUrl = mNote->getURL();
		}
		else if (type == "text")
		{
			edit_text_contents = (*it)["value"].asString();
			edit_text_name = (*it)["name"].asString();
		}
		else if (type == "password")
		{
			edit_text_contents = (*it)["value"].asString();
			edit_text_name = (*it)["name"].asString();
			is_password = true;
		}
	}
	// Buttons
	if (options.empty())
	{
		options.push_back(ButtonData());
		ButtonData& button_data = options.back();
		button_data.mName = "close";
		button_data.mText = "Close";
		button_data.mDefault = true;
	}

	S32 num_options = options.size();

	// Calc total width of buttons
	S32 button_width = 0;
	S32 sp = font->getWidth(std::string("OO"));
	for( options_t::iterator it = options.begin(); it != options.end(); it++ )
	{
		S32 w = S32(font->getWidth( it->mText ) + 0.99f) + sp + 2 * LLBUTTON_H_PAD;
		button_width = llmax( w, button_width );
	}
	S32 btn_total_width = button_width;
	if( num_options > 1 )
	{
		btn_total_width = (num_options * button_width) + ((num_options - 1) * BTN_HPAD);
	}

	// Message: create text box using raw string, as text has been structure deliberately
	// Use size of created text box to generate dialog box size
	std::string msg = mNote->getMessage();
	llwarns << "Alert: " << msg << llendl;
	LLTextBox* msg_box = new LLTextBox( std::string("Alert message"), msg, (F32)MAX_ALLOWED_MSG_WIDTH, font );

	const LLRect& text_rect = msg_box->getRect();
	S32 dialog_width = llmax( btn_total_width, text_rect.getWidth() ) + 2 * HPAD;
	S32 dialog_height = text_rect.getHeight() + 3 * VPAD + BTN_HEIGHT;

	if (hasTitleBar())
	{
		dialog_height += LINE_HEIGHT; // room for title bar
	}

	// it's ok for the edit text body to be empty, but we want the name to exist if we're going to draw it
	if (!edit_text_name.empty())
	{
		dialog_height += EDITOR_HEIGHT + VPAD;
		dialog_width = llmax(dialog_width, (S32)(font->getWidth( edit_text_contents ) + 0.99f));
	}

	if (mCaution)
	{
		// Make room for the caution icon.
		dialog_width += 32 + HPAD;
	}

	reshape( dialog_width, dialog_height, FALSE );

	S32 msg_y = getRect().getHeight() - VPAD;
	S32 msg_x = HPAD;
	if (hasTitleBar())
	{
		msg_y -= LINE_HEIGHT; // room for title
	}

	if (mCaution)
	{
		LLIconCtrl* icon = new LLIconCtrl(std::string("icon"), LLRect(msg_x, msg_y, msg_x+32, msg_y-32), std::string("notify_caution_icon.tga"));
		icon->setMouseOpaque(FALSE);
		addChild(icon);
		msg_x += 32 + HPAD;
		msg_box->setColor( LLUI::sColorsGroup->getColor( "AlertCautionTextColor" ) );
	}
	else
	{
		msg_box->setColor( LLUI::sColorsGroup->getColor( "AlertTextColor" ) );
	}

	LLRect rect;
	rect.setLeftTopAndSize( msg_x, msg_y, text_rect.getWidth(), text_rect.getHeight() );
	msg_box->setRect( rect );
	addChild(msg_box);

	// Buttons	
	S32 button_left = (getRect().getWidth() - btn_total_width) / 2;

	for( options_t::iterator it = options.begin(); it != options.end(); it++ )
	{
		LLRect button_rect;
		button_rect.setOriginAndSize( button_left, VPAD, button_width, BTN_HEIGHT );

		ButtonData& button_data = *it;

		LLButton* btn = new LLButton(
			button_data.mName, button_rect,
			"","", "", 
			NULL,
			font,
			button_data.mText, 
			button_data.mText);

		btn->setClickedCallback(boost::bind(&LLAlertDialog::onButtonPressed, this, _1, button_data.mUrl));

		addChild(btn);

		if(!mDefaultButton || button_data.mDefault)
		{
			mDefaultButton = btn;
		}

		button_left += button_width + BTN_HPAD;
	}

	llassert(mDefaultButton); //'options' map should never be empty, thus mDefaultButton should always get set in the above loop.
	mDefaultButton->setFocus(TRUE);


	// (Optional) Edit Box	
	if (!edit_text_name.empty())
	{
		S32 y = VPAD + BTN_HEIGHT + VPAD/2;
		mLineEditor = new LLLineEditor(edit_text_name,
			LLRect( HPAD, y+EDITOR_HEIGHT, dialog_width-HPAD, y),
			edit_text_contents,
			LLFontGL::getFontSansSerif(),
			STD_STRING_STR_LEN);

		// make sure all edit keys get handled properly (DEV-22396)
		mLineEditor->setHandleEditKeysDirectly(TRUE);

		addChild(mLineEditor);
	}
	
	if (mLineEditor)
	{
		mLineEditor->setDrawAsterixes(is_password);

		setEditTextArgs(notification->getSubstitutions());
	}

	std::string ignore_label;

	if (form->getIgnoreType() == LLNotificationForm::IGNORE_WITH_DEFAULT_RESPONSE)
	{
		setCheckBox(LLNotificationTemplates::instance().getGlobalString("skipnexttime"), ignore_label);
	}
	else if (form->getIgnoreType() == LLNotificationForm::IGNORE_WITH_LAST_RESPONSE)
	{
		setCheckBox(LLNotificationTemplates::instance().getGlobalString("alwayschoose"), ignore_label);
	}
}
//--------------------------------------------------------------------------
bool LLTipHandler::processNotification(const LLSD& notify)
{
	if(!mChannel)
	{
		return false;
	}

	LLNotificationPtr notification = LLNotifications::instance().find(notify["id"].asUUID());

	if(!notification)
		return false;	

	// arrange a channel on a screen
	if(!mChannel->getVisible())
	{
		initChannel();
	}

	if(notify["sigtype"].asString() == "add" || notify["sigtype"].asString() == "change")
	{
		// archive message in nearby chat
		if (LLHandlerUtil::canLogToNearbyChat(notification))
		{
			LLHandlerUtil::logToNearbyChat(notification, CHAT_SOURCE_SYSTEM);

			// don't show toast if Nearby Chat is opened
			LLNearbyChat* nearby_chat = LLFloaterReg::getTypedInstance<
					LLNearbyChat>("nearby_chat", LLSD());
			if (nearby_chat->getVisible())
			{
				return false;
			}
		}

		std::string session_name = notification->getPayload()["SESSION_NAME"];
		const std::string name = notification->getSubstitutions()["NAME"];
		if (session_name.empty())
		{
			session_name = name;
		}
		LLUUID from_id = notification->getPayload()["from_id"];
		if (LLHandlerUtil::canLogToIM(notification))
		{
//			LLHandlerUtil::logToIM(IM_NOTHING_SPECIAL, session_name, name,
//					notification->getMessage(), from_id, from_id);
// [SL:KB] - Patch: Chat-Logs | Checked: 2010-11-18 (Catznip-2.4.0c) | Added: Catznip-2.4.0c
			LLHandlerUtil::logToIMP2P(notification, false);
// [/SL:KB]
		}

		if (LLHandlerUtil::canSpawnIMSession(notification))
		{
			LLHandlerUtil::spawnIMSession(name, from_id);
		}

		// don't spawn toast for inventory accepted/declined offers if respective IM window is open (EXT-5909)
		if (!LLHandlerUtil::canSpawnToast(notification))
		{
			return false;
		}

		LLToastPanel* notify_box = LLToastPanel::buidPanelFromNotification(notification);

		LLToast::Params p;
		p.notif_id = notification->getID();
		p.notification = notification;
		p.lifetime_secs = gSavedSettings.getS32("NotificationTipToastLifeTime");
		p.panel = notify_box;
		p.is_tip = true;
		p.can_be_stored = false;
		
		removeExclusiveNotifications(notification);

		LLScreenChannel* channel = dynamic_cast<LLScreenChannel*>(mChannel);
		if(channel)
			channel->addToast(p);
	}
	else if (notify["sigtype"].asString() == "delete")
	{
		mChannel->killToastByNotificationID(notification->getID());
	}
	return false;
}
//--------------------------------------------------------------------------
bool LLTipHandler::processNotification(const LLSD& notify)
{
	if(!mChannel)
	{
		return false;
	}

	LLNotificationPtr notification = LLNotifications::instance().find(notify["id"].asUUID());

	if(!notification)
		return false;	

	// arrange a channel on a screen
	if(!mChannel->getVisible())
	{
		initChannel();
	}

	if(notify["sigtype"].asString() == "add" || notify["sigtype"].asString() == "change")
	{
		// archive message in nearby chat
		if (LLHandlerUtil::canLogToNearbyChat(notification))
		{
			LLHandlerUtil::logToNearbyChat(notification, CHAT_SOURCE_SYSTEM);

			// don't show toast if Nearby Chat is opened
			LLNearbyChat* nearby_chat = LLFloaterReg::getTypedInstance<
					LLNearbyChat>("nearby_chat", LLSD());
			if (nearby_chat->getVisible())
			{
				return true;
			}
		}

		const std::string name = notification->getSubstitutions()["NAME"];
		LLUUID from_id = notification->getPayload()["from_id"];
		if (LLHandlerUtil::canLogToIM(notification))
		{
			LLHandlerUtil::logToIM(IM_NOTHING_SPECIAL, name, name,
					notification->getMessage(), from_id, from_id);
		}

		if (LLHandlerUtil::canSpawnIMSession(notification))
		{
			LLHandlerUtil::spawnIMSession(name, from_id);
		}

		// don't spawn toast for inventory accepted/declined offers if respective IM window is open (EXT-5909)
		if (!LLHandlerUtil::canSpawnToast(notification))
		{
			return true;
		}

		LLToastPanel* notify_box = NULL;
		if("FriendOffline" == notification->getName() || "FriendOnline" == notification->getName())
		{
			LLOnlineStatusToast::Params p;
			p.notification = notification;
			p.message = notification->getMessage();
			p.avatar_id = notification->getPayload()["FROM_ID"];
			notify_box = new LLOnlineStatusToast(p);
		}
		else
		{
			notify_box = new LLToastNotifyPanel(notification);
		}

		LLToast::Params p;
		p.notif_id = notification->getID();
		p.notification = notification;
		p.lifetime_secs = gSavedSettings.getS32("NotificationTipToastLifeTime");
		p.panel = notify_box;
		p.is_tip = true;
		p.can_be_stored = false;
		
		removeExclusiveNotifications(notification);

		LLScreenChannel* channel = dynamic_cast<LLScreenChannel*>(mChannel);
		if(channel)
			channel->addToast(p);
	}
	else if (notify["sigtype"].asString() == "delete")
	{
		mChannel->killToastByNotificationID(notification->getID());
	}
	return true;
}
예제 #15
0
//--------------------------------------------------------------------------
bool LLIMHandler::processNotification(const LLSD& notify)
{
	if(mChannel.isDead())
	{
		return false;
	}

	LLNotificationPtr notification = LLNotifications::instance().find(notify["id"].asUUID());

	if(!notification)
		return false;

	static LLCachedControl<bool> fsUseNearbyChatConsole(gSavedSettings, "FSUseNearbyChatConsole");
	if (FSLogImToChatConsole && fsUseNearbyChatConsole)
	{
		if(notify["sigtype"].asString() == "add" || notify["sigtype"].asString() == "change")
		{
			LLSD substitutions = notification->getSubstitutions();

			// FS:LO FIRE-5230 - Chat Console Improvement: Replacing the "IM" in front of group chat messages with the actual group name
			std::string group;
			LLIMModel::LLIMSession* session = LLIMModel::getInstance()->findIMSession(substitutions["SESSION_ID"]);
			if(session)
			{
				S32 groupNameLength = gSavedSettings.getS32("FSShowGroupNameLength");
				if(groupNameLength != 0 && session->isGroupSessionType())
				{
					group = session->mName.substr(0,groupNameLength);
				}
			}
			// FS:LO FIRE-5230 - Chat Console Improvement: Replacing the "IM" in front of group chat messages with the actual group name

			// Filter notifications with empty ID and empty message
			if (substitutions["FROM_ID"].asString() == "" && substitutions["MESSAGE"].asString() == "") return false;

			// Ansarial, replace long lock of local DN handling with the following call
			//LLAvatarNameCache::get(LLUUID(substitutions["FROM_ID"].asString()), boost::bind(&LLIMHandler::onAvatarNameLookup, this, _1, _2, substitutions["MESSAGE"].asString()));
			LLAvatarNameCache::get(LLUUID(substitutions["FROM_ID"].asString()), boost::bind(&LLIMHandler::onAvatarNameLookup, this, _1, _2, substitutions["MESSAGE"].asString(),group)); // FS:LO FIRE-5230 - Chat Console Improvement: Replacing the "IM" in front of group chat messages with the actual group name
		}
	}
	else
	{
		// arrange a channel on a screen
		if(!mChannel.get()->getVisible())
		{
			initChannel();
		}

		if(notify["sigtype"].asString() == "add" || notify["sigtype"].asString() == "change")
		{
			LLSD substitutions = notification->getSubstitutions();

			// According to comments in LLIMMgr::addMessage(), if we get message
			// from ourselves, the sender id is set to null. This fixes EXT-875.
			LLUUID avatar_id = substitutions["FROM_ID"].asUUID();
			if (avatar_id.isNull())
				avatar_id = gAgentID;

			LLToastIMPanel::Params im_p;
			im_p.notification = notification;
			im_p.avatar_id = avatar_id;
			im_p.from = substitutions["FROM"].asString();
			im_p.time = substitutions["TIME"].asString();
			im_p.message = substitutions["MESSAGE"].asString();
			im_p.session_id = substitutions["SESSION_ID"].asUUID();

			LLToastIMPanel* im_box = new LLToastIMPanel(im_p);

			LLToast::Params p;
			p.notif_id = notification->getID();
			p.session_id = im_p.session_id;
			p.notification = notification;
			p.panel = im_box;
			p.can_be_stored = false;
			p.on_delete_toast = boost::bind(&LLIMHandler::onDeleteToast, this, _1);
			LLScreenChannel* channel = dynamic_cast<LLScreenChannel*>(mChannel.get());
			if(channel)
				channel->addToast(p);

			// send a signal to the counter manager;
			mNewNotificationSignal();
		}
		else if (notify["sigtype"].asString() == "delete")
		{
			mChannel.get()->killToastByNotificationID(notification->getID());
		}
	}
	return false;
}