diff options
| -rw-r--r-- | indra/newview/CMakeLists.txt | 86 | ||||
| -rw-r--r-- | indra/newview/llpanelprimmediacontrols.cpp | 1095 | ||||
| -rw-r--r-- | indra/newview/llpanelprimmediacontrols.h | 148 | ||||
| -rw-r--r-- | indra/newview/llviewermediafocus.cpp | 2 | ||||
| -rw-r--r-- | indra/newview/skins/default/xui/en/panel_prim_media_controls.xml | 594 | 
5 files changed, 1881 insertions, 44 deletions
| diff --git a/indra/newview/CMakeLists.txt b/indra/newview/CMakeLists.txt index 5210ff66ed..a7681e4a1d 100644 --- a/indra/newview/CMakeLists.txt +++ b/indra/newview/CMakeLists.txt @@ -63,13 +63,13 @@ include_directories(      )  set(viewer_SOURCE_FILES -    llaccordionctrltab.cpp      llaccordionctrl.cpp +    llaccordionctrltab.cpp      llagent.cpp -    llagentlistener.cpp      llagentaccess.cpp      llagentdata.cpp      llagentlanguage.cpp +    llagentlistener.cpp      llagentpicksinfo.cpp      llagentpilot.cpp      llagentui.cpp @@ -78,8 +78,8 @@ set(viewer_SOURCE_FILES      llappearancemgr.cpp      llappviewer.cpp      llappviewerlistener.cpp -    llassetuploadresponders.cpp      llassetuploadqueue.cpp +    llassetuploadresponders.cpp      llaudiosourcevo.cpp      llavataractions.cpp      llavatariconctrl.cpp @@ -95,8 +95,8 @@ set(viewer_SOURCE_FILES      llcaphttpsender.cpp      llchannelmanager.cpp      llchatbar.cpp -    llchatitemscontainerctrl.cpp      llchathistory.cpp +    llchatitemscontainerctrl.cpp      llchatmsgbox.cpp      llchiclet.cpp      llclassifiedinfo.cpp @@ -116,10 +116,10 @@ set(viewer_SOURCE_FILES      lldirpicker.cpp      lldndbutton.cpp      lldrawable.cpp +    lldrawpool.cpp      lldrawpoolalpha.cpp      lldrawpoolavatar.cpp      lldrawpoolbump.cpp -    lldrawpool.cpp      lldrawpoolground.cpp      lldrawpoolsimple.cpp      lldrawpoolsky.cpp @@ -151,8 +151,8 @@ set(viewer_SOURCE_FILES      llfloaterbuildoptions.cpp      llfloaterbulkpermission.cpp      llfloaterbump.cpp -    llfloaterbuycontents.cpp      llfloaterbuy.cpp +    llfloaterbuycontents.cpp      llfloaterbuycurrency.cpp      llfloaterbuyland.cpp      llfloatercall.cpp @@ -163,8 +163,8 @@ set(viewer_SOURCE_FILES      llfloatercustomize.cpp      llfloaterdaycycle.cpp      llfloaterenvsettings.cpp -    llfloaterfriends.cpp      llfloaterfonttest.cpp +    llfloaterfriends.cpp      llfloatergesture.cpp      llfloatergodtools.cpp      llfloatergroupinvite.cpp @@ -172,8 +172,6 @@ set(viewer_SOURCE_FILES      llfloaterhandler.cpp      llfloaterhardwaresettings.cpp      llfloaterhelpbrowser.cpp -    llfloatermediabrowser.cpp -    llfloatermediasettings.cpp      llfloaterhud.cpp      llfloaterimagepreview.cpp      llfloaterinspect.cpp @@ -183,6 +181,8 @@ set(viewer_SOURCE_FILES      llfloaterland.cpp      llfloaterlandholdings.cpp      llfloatermap.cpp +    llfloatermediabrowser.cpp +    llfloatermediasettings.cpp      llfloatermemleak.cpp      llfloaternamedesc.cpp      llfloaternotificationsconsole.cpp @@ -227,8 +227,8 @@ set(viewer_SOURCE_FILES      llgroupmgr.cpp      llgroupnotify.cpp      llhomelocationresponder.cpp -    llhudeffectbeam.cpp      llhudeffect.cpp +    llhudeffectbeam.cpp      llhudeffectlookat.cpp      llhudeffectpointat.cpp      llhudeffecttrail.cpp @@ -238,11 +238,11 @@ set(viewer_SOURCE_FILES      llhudrender.cpp      llhudtext.cpp      llhudview.cpp +    llimcontrolpanel.cpp      llimfloater.cpp      llimhandler.cpp      llimpanel.cpp      llimview.cpp -    llimcontrolpanel.cpp      llinspect.cpp      llinspectavatar.cpp      llinspectgroup.cpp @@ -260,7 +260,6 @@ set(viewer_SOURCE_FILES      lllocaltextureobject.cpp      lllocationhistory.cpp      lllocationinputctrl.cpp -    llurllineeditorctrl.cpp      lllogchat.cpp      llloginhandler.cpp      lllogininstance.cpp @@ -312,8 +311,8 @@ set(viewer_SOURCE_FILES      llpanelgrouplandmoney.cpp      llpanelgroupnotices.cpp      llpanelgrouproles.cpp -    llpanelinventory.cpp      llpanelimcontrolpanel.cpp +    llpanelinventory.cpp      llpanelland.cpp      llpanellandaudio.cpp      llpanellandmarks.cpp @@ -322,11 +321,10 @@ set(viewer_SOURCE_FILES      llpanellookinfo.cpp      llpanellooks.cpp      llpanelmedia.cpp -    llpanelmediahud.cpp -    llpanelmeprofile.cpp      llpanelmediasettingsgeneral.cpp -    llpanelmediasettingssecurity.cpp      llpanelmediasettingspermissions.cpp +    llpanelmediasettingssecurity.cpp +    llpanelmeprofile.cpp      llpanelobject.cpp      llpanelpeople.cpp      llpanelpeoplemenus.cpp @@ -335,11 +333,12 @@ set(viewer_SOURCE_FILES      llpanelpicks.cpp      llpanelplace.cpp      llpanelplaceinfo.cpp -    llpanelshower.cpp      llpanelplaces.cpp      llpanelplacestab.cpp +    llpanelprimmediacontrols.cpp      llpanelprofile.cpp      llpanelprofileview.cpp +    llpanelshower.cpp      llpanelteleporthistory.cpp      llpanelvolume.cpp      llparcelselection.cpp @@ -348,8 +347,8 @@ set(viewer_SOURCE_FILES      llplacesinventorybridge.cpp      llpolymesh.cpp      llpolymorph.cpp -    llpreviewanim.cpp      llpreview.cpp +    llpreviewanim.cpp      llpreviewgesture.cpp      llpreviewnotecard.cpp      llpreviewscript.cpp @@ -398,10 +397,10 @@ set(viewer_SOURCE_FILES      lltoastimpanel.cpp      lltoastnotifypanel.cpp      lltoastpanel.cpp +    lltool.cpp      lltoolbar.cpp      lltoolbrush.cpp      lltoolcomp.cpp -    lltool.cpp      lltooldraganddrop.cpp      lltoolface.cpp      lltoolfocus.cpp @@ -425,6 +424,7 @@ set(viewer_SOURCE_FILES      llurl.cpp      llurldispatcher.cpp      llurlhistory.cpp +    llurllineeditorctrl.cpp      llurlsimstring.cpp      llurlwhitelist.cpp      llvectorperfoptions.cpp @@ -441,18 +441,18 @@ set(viewer_SOURCE_FILES      llviewerhelp.cpp      llviewerhelputil.cpp      llviewerinventory.cpp -    llviewerjointattachment.cpp      llviewerjoint.cpp +    llviewerjointattachment.cpp      llviewerjointmesh.cpp -    llviewerjointmesh_sse2.cpp      llviewerjointmesh_sse.cpp +    llviewerjointmesh_sse2.cpp      llviewerjointmesh_vec.cpp      llviewerjoystick.cpp      llviewerkeyboard.cpp      llviewerlayer.cpp      llviewermedia.cpp -    llviewermediafocus.cpp      llviewermedia_streamingaudio.cpp +    llviewermediafocus.cpp      llviewermenu.cpp      llviewermenufile.cpp      llviewermessage.cpp @@ -487,9 +487,9 @@ set(viewer_SOURCE_FILES      llvoground.cpp      llvoicechannel.cpp      llvoiceclient.cpp +    llvoicecontrolpanel.cpp      llvoiceremotectrl.cpp      llvoicevisualizer.cpp -    llvoicecontrolpanel.cpp      llvoinventorylistener.cpp      llvopartgroup.cpp      llvosky.cpp @@ -540,25 +540,25 @@ endif (LINUX)  set(viewer_HEADER_FILES      CMakeLists.txt      ViewerInstall.cmake -    llaccordionctrltab.h      llaccordionctrl.h +    llaccordionctrltab.h      llagent.h -    llagentlistener.h      llagentaccess.h      llagentdata.h      llagentlanguage.h +    llagentlistener.h      llagentpicksinfo.h      llagentpilot.h      llagentui.h      llagentwearables.h      llanimstatelabels.h      llappearance.h +    llappearancemgr.h      llappviewer.h      llappviewerlistener.h -    llassetuploadresponders.h      llassetuploadqueue.h +    llassetuploadresponders.h      llaudiosourcevo.h -    llappearancemgr.h      llavataractions.h      llavatariconctrl.h      llavatarlist.h @@ -574,8 +574,8 @@ set(viewer_HEADER_FILES      llcaphttpsender.h      llchannelmanager.h      llchatbar.h -    llchatitemscontainerctrl.h      llchathistory.h +    llchatitemscontainerctrl.h      llchatmsgbox.h      llchiclet.h      llclassifiedinfo.h @@ -652,8 +652,6 @@ set(viewer_HEADER_FILES      llfloaterhandler.h      llfloaterhardwaresettings.h      llfloaterhelpbrowser.h -    llfloatermediabrowser.h -    llfloatermediasettings.h      llfloaterhud.h      llfloaterimagepreview.h      llfloaterinspect.h @@ -663,16 +661,18 @@ set(viewer_HEADER_FILES      llfloaterland.h      llfloaterlandholdings.h      llfloatermap.h +    llfloatermediabrowser.h +    llfloatermediasettings.h      llfloatermemleak.h      llfloaternamedesc.h      llfloaternotificationsconsole.h      llfloateropenobject.h      llfloaterparcel.h      llfloaterpay.h +    llfloaterperms.h      llfloaterpostcard.h      llfloaterpostprocess.h      llfloaterpreference.h -    llfloaterperms.h      llfloaterproperties.h      llfloaterregioninfo.h      llfloaterreporter.h @@ -718,12 +718,12 @@ set(viewer_HEADER_FILES      llhudrender.h      llhudtext.h      llhudview.h +    llimcontrolpanel.h      llimfloater.h      llimpanel.h      llimview.h -    llimcontrolpanel.h -    llinspectavatar.h      llinspect.h +    llinspectavatar.h      llinspectgroup.h      llinspectobject.h      llinventorybridge.h @@ -740,7 +740,6 @@ set(viewer_HEADER_FILES      lllocaltextureobject.h      lllocationhistory.h      lllocationinputctrl.h -    llurllineeditorctrl.h      lllogchat.h      llloginhandler.h      lllogininstance.h @@ -749,6 +748,7 @@ set(viewer_HEADER_FILES      llmanipscale.h      llmaniptranslate.h      llmapresponders.h +    llmediactrl.h      llmediadataclient.h      llmediaremotectrl.h      llmemoryview.h @@ -788,8 +788,8 @@ set(viewer_HEADER_FILES      llpanelgrouplandmoney.h      llpanelgroupnotices.h      llpanelgrouproles.h -    llpanelinventory.h      llpanelimcontrolpanel.h +    llpanelinventory.h      llpanelland.h      llpanellandaudio.h      llpanellandmarks.h @@ -798,11 +798,10 @@ set(viewer_HEADER_FILES      llpanellookinfo.h      llpanellooks.h      llpanelmedia.h -    llpanelmediahud.h -    llpanelmeprofile.h      llpanelmediasettingsgeneral.h -    llpanelmediasettingssecurity.h      llpanelmediasettingspermissions.h +    llpanelmediasettingssecurity.h +    llpanelmeprofile.h      llpanelobject.h      llpanelpeople.h      llpanelpeoplemenus.h @@ -811,11 +810,12 @@ set(viewer_HEADER_FILES      llpanelpicks.h      llpanelplace.h      llpanelplaceinfo.h -    llpanelshower.h      llpanelplaces.h      llpanelplacestab.h +    llpanelprimmediacontrols.h      llpanelprofile.h      llpanelprofileview.h +    llpanelshower.h      llpanelteleporthistory.h      llpanelvolume.h      llparcelselection.h @@ -838,9 +838,9 @@ set(viewer_HEADER_FILES      llremoteparcelrequest.h      llresourcedata.h      llrootview.h +    llsavedsettingsglue.h      llscreenchannel.h      llscrollingpanelparam.h -    llsavedsettingsglue.h      llsearchcombobox.h      llsearchhistory.h      llselectmgr.h @@ -905,6 +905,7 @@ set(viewer_HEADER_FILES      llurl.h      llurldispatcher.h      llurlhistory.h +    llurllineeditorctrl.h      llurlsimstring.h      llurlwhitelist.h      llvectorperfoptions.h @@ -928,8 +929,8 @@ set(viewer_HEADER_FILES      llviewerkeyboard.h      llviewerlayer.h      llviewermedia.h -    llviewermediaobserver.h      llviewermediafocus.h +    llviewermediaobserver.h      llviewermenu.h      llviewermenufile.h      llviewermessage.h @@ -965,9 +966,9 @@ set(viewer_HEADER_FILES      llvoground.h      llvoicechannel.h      llvoiceclient.h +    llvoicecontrolpanel.h      llvoiceremotectrl.h      llvoicevisualizer.h -    llvoicecontrolpanel.h      llvoinventorylistener.h      llvopartgroup.h      llvosky.h @@ -985,7 +986,6 @@ set(viewer_HEADER_FILES      llwearabledictionary.h      llwearablelist.h      llweb.h -    llmediactrl.h      llwind.h      llwindebug.h      llwlanimator.h diff --git a/indra/newview/llpanelprimmediacontrols.cpp b/indra/newview/llpanelprimmediacontrols.cpp new file mode 100644 index 0000000000..8a202dabef --- /dev/null +++ b/indra/newview/llpanelprimmediacontrols.cpp @@ -0,0 +1,1095 @@ +/**  + * @file llpanelmediahud.cpp + * @brief media controls popup panel + * + * $LicenseInfo:firstyear=2003&license=viewergpl$ + *  + * Copyright (c) 2003-2007, Linden Research, Inc. + *  + * Second Life Viewer Source Code + * The source code in this file ("Source Code") is provided by Linden Lab + * to you under the terms of the GNU General Public License, version 2.0 + * ("GPL"), unless you have obtained a separate licensing agreement + * ("Other License"), formally executed by you and Linden Lab.  Terms of + * the GPL can be found in doc/GPL-license.txt in this distribution, or + * online at http://secondlife.com/developers/opensource/gplv2 + *  + * There are special exceptions to the terms and conditions of the GPL as + * it is applied to this Source Code. View the full text of the exception + * in the file doc/FLOSS-exception.txt in this software distribution, or + * online at http://secondlife.com/developers/opensource/flossexception + *  + * By copying, modifying or distributing this software, you acknowledge + * that you have read and understood your obligations described above, + * and agree to abide by those obligations. + *  + * ALL LINDEN LAB SOURCE CODE IS PROVIDED "AS IS." LINDEN LAB MAKES NO + * WARRANTIES, EXPRESS, IMPLIED OR OTHERWISE, REGARDING ITS ACCURACY, + * COMPLETENESS OR PERFORMANCE. + * $/LicenseInfo$ + */ + +#include "llviewerprecompiledheaders.h" + +//LLPanelMediaControls +#include "llagent.h" +#include "llparcel.h" +#include "llpanel.h" +#include "llselectmgr.h" +#include "llmediaentry.h" +#include "llrender.h" +#include "lldrawable.h" +#include "llviewerwindow.h" +#include "lluictrlfactory.h" +#include "llbutton.h" +#include "llface.h" +#include "llcombobox.h" +#include "llslider.h" +#include "llhudview.h" +#include "lliconctrl.h" +#include "lltoolpie.h" +#include "llviewercamera.h" +#include "llviewerobjectlist.h" +#include "llpanelprimmediacontrols.h" +#include "llpluginclassmedia.h" +#include "llprogressbar.h" +#include "llviewercontrol.h" +#include "llviewerparcelmgr.h" +#include "llviewermedia.h" +#include "llviewermediafocus.h" +#include "llvovolume.h" +#include "llweb.h" +#include "llwindow.h" + +glh::matrix4f glh_get_current_modelview(); +glh::matrix4f glh_get_current_projection(); + +const F32 ZOOM_NEAR_PADDING		= 1.0f; +const F32 ZOOM_MEDIUM_PADDING	= 1.15f; +const F32 ZOOM_FAR_PADDING		= 1.5f; + +// Warning: make sure these two match! +const LLPanelMediaControls::EZoomLevel LLPanelMediaControls::kZoomLevels[] = { ZOOM_NONE, ZOOM_MEDIUM }; +const int LLPanelMediaControls::kNumZoomLevels = 2; + +// +// LLPanelMediaControls +// + +LLPanelMediaControls::LLPanelMediaControls() :  +	mAlpha(1.f), +	mCurrentURL(""), +	mPreviousURL(""), +	mPauseFadeout(false), +	mUpdateSlider(true), +	mClearFaceOnFade(false), +	mCurrentRate(0.0), +	mMovieDuration(0.0), +	mUpdatePercent(0) +{ +	mCommitCallbackRegistrar.add("MediaCtrl.Close",		boost::bind(&LLPanelMediaControls::onClickClose, this)); +	mCommitCallbackRegistrar.add("MediaCtrl.Back",		boost::bind(&LLPanelMediaControls::onClickBack, this)); +	mCommitCallbackRegistrar.add("MediaCtrl.Forward",	boost::bind(&LLPanelMediaControls::onClickForward, this)); +	mCommitCallbackRegistrar.add("MediaCtrl.Home",		boost::bind(&LLPanelMediaControls::onClickHome, this)); +	mCommitCallbackRegistrar.add("MediaCtrl.Stop",		boost::bind(&LLPanelMediaControls::onClickStop, this)); +	mCommitCallbackRegistrar.add("MediaCtrl.Reload",	boost::bind(&LLPanelMediaControls::onClickReload, this)); +	mCommitCallbackRegistrar.add("MediaCtrl.Play",		boost::bind(&LLPanelMediaControls::onClickPlay, this)); +	mCommitCallbackRegistrar.add("MediaCtrl.Pause",		boost::bind(&LLPanelMediaControls::onClickPause, this)); +	mCommitCallbackRegistrar.add("MediaCtrl.Open",		boost::bind(&LLPanelMediaControls::onClickOpen, this)); +	mCommitCallbackRegistrar.add("MediaCtrl.Zoom",		boost::bind(&LLPanelMediaControls::onClickZoom, this)); +	mCommitCallbackRegistrar.add("MediaCtrl.CommitURL",	boost::bind(&LLPanelMediaControls::onCommitURL, this)); +	mCommitCallbackRegistrar.add("MediaCtrl.JumpProgress",		boost::bind(&LLPanelMediaControls::onCommitSlider, this)); +	mCommitCallbackRegistrar.add("MediaCtrl.CommitVolumeUp",	boost::bind(&LLPanelMediaControls::onCommitVolumeUp, this)); +	mCommitCallbackRegistrar.add("MediaCtrl.CommitVolumeDown",	boost::bind(&LLPanelMediaControls::onCommitVolumeDown, this)); +	mCommitCallbackRegistrar.add("MediaCtrl.ToggleMute",		boost::bind(&LLPanelMediaControls::onToggleMute, this)); +	 +	LLUICtrlFactory::getInstance()->buildPanel(this, "panel_media_hud.xml"); +	mInactivityTimer.reset(); +	mFadeTimer.stop(); +	mCurrentZoom = ZOOM_NONE; +	mScrollState = SCROLL_NONE; + +	mPanelHandle.bind(this); +} +LLPanelMediaControls::~LLPanelMediaControls() +{ +} + +BOOL LLPanelMediaControls::postBuild() +{ +	LLButton* scroll_up_ctrl = getChild<LLButton>("scrollup"); +	scroll_up_ctrl->setClickedCallback(onScrollUp, this); +	scroll_up_ctrl->setHeldDownCallback(onScrollUpHeld, this); +	scroll_up_ctrl->setMouseUpCallback(onScrollStop, this); +	LLButton* scroll_left_ctrl = getChild<LLButton>("scrollleft"); +	scroll_left_ctrl->setClickedCallback(onScrollLeft, this); +	scroll_left_ctrl->setHeldDownCallback(onScrollLeftHeld, this); +	scroll_left_ctrl->setMouseUpCallback(onScrollStop, this); +	LLButton* scroll_right_ctrl = getChild<LLButton>("scrollright"); +	scroll_right_ctrl->setClickedCallback(onScrollRight, this); +	scroll_right_ctrl->setHeldDownCallback(onScrollLeftHeld, this); +	scroll_right_ctrl->setMouseUpCallback(onScrollStop, this); +	LLButton* scroll_down_ctrl = getChild<LLButton>("scrolldown"); +	scroll_down_ctrl->setClickedCallback(onScrollDown, this); +	scroll_down_ctrl->setHeldDownCallback(onScrollDownHeld, this); +	scroll_down_ctrl->setMouseUpCallback(onScrollStop, this); +	 +	LLUICtrl* media_address	= getChild<LLUICtrl>("media_address"); +	media_address->setFocusReceivedCallback(boost::bind(&LLPanelMediaControls::onInputURL, _1, this )); +	mInactiveTimeout = gSavedSettings.getF32("MediaControlTimeout"); +	mControlFadeTime = gSavedSettings.getF32("MediaControlFadeTime"); + +	mCurrentZoom = ZOOM_NONE; +	// clicks on HUD buttons do not remove keyboard focus from media +	setIsChrome(TRUE); +	return TRUE; +} + +void LLPanelMediaControls::setMediaFace(LLPointer<LLViewerObject> objectp, S32 face, viewer_media_t media_impl, LLVector3 pick_normal) +{ +	if (media_impl.notNull() && objectp.notNull()) +	{ +		mTargetImplID = media_impl->getMediaTextureID(); +		mTargetObjectID = objectp->getID(); +		mTargetObjectFace = face; +		mTargetObjectNormal = pick_normal; +		mClearFaceOnFade = false; +	} +	else +	{ +		// This happens on a timer now. +//		mTargetImplID = LLUUID::null; +//		mTargetObjectID = LLUUID::null; +//		mTargetObjectFace = 0; +		mClearFaceOnFade = true; +	} + +	updateShape(); +} + +void LLPanelMediaControls::focusOnTarget() +{ +	// Sets the media focus to the current target of the LLPanelMediaControls. +	// This is how we transition from hover to focus when the user clicks on a control. +	LLViewerMediaImpl* media_impl = getTargetMediaImpl(); +	if(media_impl) +	{ +		if(!media_impl->hasFocus()) +		{	 +			// The current target doesn't have media focus -- focus on it. +			LLViewerObject* objectp = getTargetObject(); +			LLViewerMediaFocus::getInstance()->setFocusFace(objectp, mTargetObjectFace, media_impl, mTargetObjectNormal); +		} +	}	 +} + +LLViewerMediaImpl* LLPanelMediaControls::getTargetMediaImpl() +{ +	return LLViewerMedia::getMediaImplFromTextureID(mTargetImplID); +} + +LLViewerObject* LLPanelMediaControls::getTargetObject() +{ +	return gObjectList.findObject(mTargetObjectID); +} + +LLPluginClassMedia* LLPanelMediaControls::getTargetMediaPlugin() +{ +	LLViewerMediaImpl* impl = getTargetMediaImpl(); +	if(impl && impl->hasMedia()) +	{ +		return impl->getMediaPlugin(); +	} +	 +	return NULL; +} + +void LLPanelMediaControls::updateShape() +{ +	const S32 MIN_HUD_WIDTH=400; +	const S32 MIN_HUD_HEIGHT=120; + +	LLViewerMediaImpl* media_impl = getTargetMediaImpl(); +	LLViewerObject* objectp = getTargetObject(); +	 +	if(!media_impl) +	{ +		setVisible(FALSE); +		return; +	} + +	LLPluginClassMedia* media_plugin = NULL; +	if(media_impl->hasMedia()) +	{ +		media_plugin = media_impl->getMediaPlugin(); +	} +	 +	LLParcel *parcel = LLViewerParcelMgr::getInstance()->getAgentParcel(); + +	bool can_navigate = parcel->getMediaAllowNavigate(); +	bool enabled = false; +	bool has_focus = media_impl->hasFocus(); +	setVisible(enabled); + +	if (objectp) +	{ +		bool mini_controls = false; +		LLMediaEntry *media_data = objectp->getTE(mTargetObjectFace)->getMediaData(); +		if (media_data && NULL != dynamic_cast<LLVOVolume*>(objectp)) +		{ +			// Don't show the media HUD if we do not have permissions +			enabled = dynamic_cast<LLVOVolume*>(objectp)->hasMediaPermission(media_data, LLVOVolume::MEDIA_PERM_CONTROL); +			mini_controls = (LLMediaEntry::MINI == media_data->getControls()); +		} +		 +		// +		// Set the state of the buttons +		// +		LLUICtrl* back_ctrl					= getChild<LLUICtrl>("back"); +		LLUICtrl* fwd_ctrl					= getChild<LLUICtrl>("fwd"); +		LLUICtrl* reload_ctrl				= getChild<LLUICtrl>("reload"); +		LLUICtrl* play_ctrl					= getChild<LLUICtrl>("play"); +		LLUICtrl* pause_ctrl				= getChild<LLUICtrl>("pause"); +		LLUICtrl* stop_ctrl					= getChild<LLUICtrl>("stop"); +		LLUICtrl* media_stop_ctrl			= getChild<LLUICtrl>("media_stop"); +		LLUICtrl* home_ctrl					= getChild<LLUICtrl>("home"); +		LLUICtrl* close_ctrl				= getChild<LLUICtrl>("close"); +		LLUICtrl* open_ctrl					= getChild<LLUICtrl>("new_window"); +        LLUICtrl* zoom_ctrl					= getChild<LLUICtrl>("zoom_frame"); +		LLPanel* media_loading_panel		= getChild<LLPanel>("media_progress_indicator"); +		LLUICtrl* media_address_ctrl		= getChild<LLUICtrl>("media_address"); +		LLUICtrl* media_play_slider_ctrl	= getChild<LLUICtrl>("media_play_position"); +		LLUICtrl* volume_ctrl				= getChild<LLUICtrl>("media_volume"); +		LLButton* volume_btn				= getChild<LLButton>("media_volume_button"); +		LLUICtrl* volume_up_ctrl			= getChild<LLUICtrl>("volume_up"); +		LLUICtrl* volume_down_ctrl			= getChild<LLUICtrl>("volume_down"); +		LLIconCtrl* whitelist_icon			= getChild<LLIconCtrl>("media_whitelist_flag"); +		LLIconCtrl* secure_lock_icon		= getChild<LLIconCtrl>("media_secure_lock_flag"); +		 +		LLUICtrl* media_panel_scroll		= getChild<LLUICtrl>("media_panel_scroll"); +		LLUICtrl* scroll_up_ctrl			= getChild<LLUICtrl>("scrollup"); +		LLUICtrl* scroll_left_ctrl			= getChild<LLUICtrl>("scrollleft"); +		LLUICtrl* scroll_right_ctrl			= getChild<LLUICtrl>("scrollright"); +		LLUICtrl* scroll_down_ctrl			= getChild<LLUICtrl>("scrolldown");		 +				 +		// XXX RSP: TODO: FIXME: clean this up so that it is clearer what mode we are in, +		// and that only the proper controls get made visible/enabled according to that mode.  +		back_ctrl->setVisible(has_focus); +		fwd_ctrl->setVisible(has_focus); +		reload_ctrl->setVisible(has_focus); +		stop_ctrl->setVisible(false); +		home_ctrl->setVisible(has_focus); +		close_ctrl->setVisible(has_focus); +		open_ctrl->setVisible(true); +		media_address_ctrl->setVisible(has_focus && !mini_controls); +		media_play_slider_ctrl->setVisible(has_focus && !mini_controls); +		volume_ctrl->setVisible(false); +		volume_up_ctrl->setVisible(false); +		volume_down_ctrl->setVisible(false); +		 +		whitelist_icon->setVisible(!mini_controls && (media_data)?media_data->getWhiteListEnable():false); +		// Disable zoom if HUD +		zoom_ctrl->setEnabled(!objectp->isHUDAttachment()); +		secure_lock_icon->setVisible(false); +		mCurrentURL = media_impl->getMediaURL(); +		 +		back_ctrl->setEnabled((media_impl != NULL) && media_impl->canNavigateBack() && can_navigate); +		fwd_ctrl->setEnabled((media_impl != NULL) && media_impl->canNavigateForward() && can_navigate); +		stop_ctrl->setEnabled(has_focus && can_navigate); +		home_ctrl->setEnabled(has_focus && can_navigate); +		LLPluginClassMediaOwner::EMediaStatus result = ((media_impl != NULL) && media_impl->hasMedia()) ? media_plugin->getStatus() : LLPluginClassMediaOwner::MEDIA_NONE; + +		if(media_plugin && media_plugin->pluginSupportsMediaTime()) +		{ +			reload_ctrl->setEnabled(FALSE); +			reload_ctrl->setVisible(FALSE); +			media_stop_ctrl->setVisible(has_focus); +			home_ctrl->setVisible(FALSE); +			back_ctrl->setEnabled(has_focus); +			fwd_ctrl->setEnabled(has_focus); +			media_address_ctrl->setVisible(false); +			media_address_ctrl->setEnabled(false); +			media_play_slider_ctrl->setVisible(!mini_controls); +			media_play_slider_ctrl->setEnabled(!mini_controls); +				 +			volume_ctrl->setVisible(has_focus); +			volume_up_ctrl->setVisible(has_focus); +			volume_down_ctrl->setVisible(has_focus); +			volume_ctrl->setEnabled(has_focus); + +			whitelist_icon->setVisible(false); +			secure_lock_icon->setVisible(false); +			scroll_up_ctrl->setVisible(false); +			scroll_left_ctrl->setVisible(false); +			scroll_right_ctrl->setVisible(false); +			scroll_down_ctrl->setVisible(false); +			media_panel_scroll->setVisible(false); +				 +			F32 volume = media_impl->getVolume(); +			// movie's url changed +			if(mCurrentURL!=mPreviousURL) +			{ +				mMovieDuration = media_plugin->getDuration(); +				mPreviousURL = mCurrentURL; +			} +				 +			if(mMovieDuration == 0)  +			{ +				mMovieDuration = media_plugin->getDuration(); +				media_play_slider_ctrl->setValue(0); +				media_play_slider_ctrl->setEnabled(false); +			} +			// TODO: What if it's not fully loaded +					 +			if(mUpdateSlider && mMovieDuration!= 0) +			{ +				F64 current_time =  media_plugin->getCurrentTime(); +				F32 percent = current_time / mMovieDuration; +				media_play_slider_ctrl->setValue(percent); +				media_play_slider_ctrl->setEnabled(true); +			} +				 +			// video vloume +			if(volume <= 0.0) +			{ +				volume_up_ctrl->setEnabled(TRUE); +				volume_down_ctrl->setEnabled(FALSE); +				media_impl->setVolume(0.0); +				volume_btn->setToggleState(true); +			} +			else if (volume >= 1.0) +			{ +				volume_up_ctrl->setEnabled(FALSE); +				volume_down_ctrl->setEnabled(TRUE); +				media_impl->setVolume(1.0); +				volume_btn->setToggleState(false); +			} +			else +			{ +				volume_up_ctrl->setEnabled(TRUE); +				volume_down_ctrl->setEnabled(TRUE); +			} +				 +			switch(result) +			{ +				case LLPluginClassMediaOwner::MEDIA_PLAYING: +					play_ctrl->setEnabled(FALSE); +					play_ctrl->setVisible(FALSE); +					pause_ctrl->setEnabled(TRUE); +					pause_ctrl->setVisible(has_focus); +					media_stop_ctrl->setEnabled(TRUE); +					 +					break; +				case LLPluginClassMediaOwner::MEDIA_PAUSED: +				default: +					pause_ctrl->setEnabled(FALSE); +					pause_ctrl->setVisible(FALSE); +					play_ctrl->setEnabled(TRUE); +					play_ctrl->setVisible(has_focus); +					media_stop_ctrl->setEnabled(FALSE); +					break; +			} +		} +		else   // web based +		{ +			if(media_plugin) +			{ +				mCurrentURL = media_plugin->getLocation(); +			} +			else +			{ +				mCurrentURL.clear(); +			} +				 +			play_ctrl->setVisible(FALSE); +			pause_ctrl->setVisible(FALSE); +			media_stop_ctrl->setVisible(FALSE); +			media_address_ctrl->setVisible(has_focus && !mini_controls); +			media_address_ctrl->setEnabled(has_focus && !mini_controls); +			media_play_slider_ctrl->setVisible(FALSE); +			media_play_slider_ctrl->setEnabled(FALSE); +				 +			volume_ctrl->setVisible(FALSE); +			volume_up_ctrl->setVisible(FALSE); +			volume_down_ctrl->setVisible(FALSE); +			volume_ctrl->setEnabled(FALSE); +			volume_up_ctrl->setEnabled(FALSE); +			volume_down_ctrl->setEnabled(FALSE); +				 +			scroll_up_ctrl->setVisible(has_focus); +			scroll_left_ctrl->setVisible(has_focus); +			scroll_right_ctrl->setVisible(has_focus); +			scroll_down_ctrl->setVisible(has_focus); +			media_panel_scroll->setVisible(has_focus); +			// TODO: get the secure lock bool from media plug in +			std::string prefix =  std::string("https://"); +			std::string test_prefix = mCurrentURL.substr(0, prefix.length()); +			LLStringUtil::toLower(test_prefix); +			if(test_prefix == prefix) +			{ +				secure_lock_icon->setVisible(has_focus); +			} +				 +			if(mCurrentURL!=mPreviousURL) +			{ +				setCurrentURL(); +				mPreviousURL = mCurrentURL; +			} + +			if(result == LLPluginClassMediaOwner::MEDIA_LOADING) +			{ +				reload_ctrl->setEnabled(FALSE); +				reload_ctrl->setVisible(FALSE); +				stop_ctrl->setEnabled(TRUE); +				stop_ctrl->setVisible(has_focus); +			} +			else +			{ +				reload_ctrl->setEnabled(TRUE); +				reload_ctrl->setVisible(has_focus); +				stop_ctrl->setEnabled(FALSE); +				stop_ctrl->setVisible(FALSE); +			} +		} + +		 +		if(media_plugin) +		{ +			// +			// Handle progress bar +			// +			mUpdatePercent = media_plugin->getProgressPercent(); +			if(mUpdatePercent<100.0f) +			{ +				media_loading_panel->setVisible(true); +				getChild<LLProgressBar>("media_progress_bar")->setPercent(mUpdatePercent); +				gFocusMgr.setTopCtrl(media_loading_panel); +			} +			else +			{ +				media_loading_panel->setVisible(false); +				gFocusMgr.setTopCtrl(NULL); +			} +		} + +		if(media_plugin) +		{ +			// +			// Handle Scrolling +			// +			switch (mScrollState)  +			{ +			case SCROLL_UP: +				media_plugin->scrollEvent(0, -1, MASK_NONE); +				break; +			case SCROLL_DOWN: +				media_plugin->scrollEvent(0, 1, MASK_NONE); +				break; +			case SCROLL_LEFT: +				media_impl->handleKeyHere(KEY_LEFT, MASK_NONE); +				break; +			case SCROLL_RIGHT: +				media_impl->handleKeyHere(KEY_RIGHT, MASK_NONE); +				break; +			case SCROLL_NONE: +			default: +				break; +			} +		} +		 +		setVisible(enabled); + +		// +		// Calculate position and shape of the controls +		// +		glh::matrix4f mat = glh_get_current_projection()*glh_get_current_modelview(); +		std::vector<LLVector3>::iterator vert_it; +		std::vector<LLVector3>::iterator vert_end; +		std::vector<LLVector3> vect_face; + +		LLVolume* volume = objectp->getVolume(); + +		if (volume) +		{ +			const LLVolumeFace& vf = volume->getVolumeFace(mTargetObjectFace); + +			const LLVector3* ext = vf.mExtents; + +			LLVector3 center = (ext[0]+ext[1])*0.5f; +			LLVector3 size = (ext[1]-ext[0])*0.5f; +			LLVector3 vert[] = +			{ +				center + size.scaledVec(LLVector3(1,1,1)), +				center + size.scaledVec(LLVector3(-1,1,1)), +				center + size.scaledVec(LLVector3(1,-1,1)), +				center + size.scaledVec(LLVector3(-1,-1,1)), +				center + size.scaledVec(LLVector3(1,1,-1)), +				center + size.scaledVec(LLVector3(-1,1,-1)), +				center + size.scaledVec(LLVector3(1,-1,-1)), +				center + size.scaledVec(LLVector3(-1,-1,-1)), +			}; + +			LLVOVolume* vo = (LLVOVolume*) objectp; + +			for (U32 i = 0; i < 8; i++) +			{ +				vect_face.push_back(vo->volumePositionToAgent(vert[i]));	 +			} +		} +		vert_it = vect_face.begin(); +		vert_end = vect_face.end(); + +		LLVector3 min = LLVector3(1,1,1); +		LLVector3 max = LLVector3(-1,-1,-1); +		for(; vert_it != vert_end; ++vert_it) +		{ +			// project silhouette vertices into screen space +			glh::vec3f screen_vert = glh::vec3f(vert_it->mV);  +			mat.mult_matrix_vec(screen_vert); + +			// add to screenspace bounding box +			update_min_max(min, max, LLVector3(screen_vert.v)); +		} + +        LLCoordGL screen_min; +		screen_min.mX = llround((F32)gViewerWindow->getWorldViewWidth() * (min.mV[VX] + 1.f) * 0.5f); +		screen_min.mY = llround((F32)gViewerWindow->getWorldViewHeight() * (min.mV[VY] + 1.f) * 0.5f); + +		LLCoordGL screen_max; +		screen_max.mX = llround((F32)gViewerWindow->getWorldViewWidth() * (max.mV[VX] + 1.f) * 0.5f); +		screen_max.mY = llround((F32)gViewerWindow->getWorldViewHeight() * (max.mV[VY] + 1.f) * 0.5f); + +		// grow panel so that screenspace bounding box fits inside "media_region" element of HUD +		LLRect media_hud_rect; +		getParent()->screenRectToLocal(LLRect(screen_min.mX, screen_max.mY, screen_max.mX, screen_min.mY), &media_hud_rect); +		LLView* media_region = getChild<LLView>("media_region"); +		media_hud_rect.mLeft -= media_region->getRect().mLeft; +		media_hud_rect.mBottom -= media_region->getRect().mBottom; +		media_hud_rect.mTop += getRect().getHeight() - media_region->getRect().mTop; +		media_hud_rect.mRight += getRect().getWidth() - media_region->getRect().mRight; + +		LLRect old_hud_rect = media_hud_rect; +		// keep all parts of HUD on-screen +		media_hud_rect.intersectWith(getParent()->getLocalRect()); + +		// clamp to minimum size, keeping centered +		media_hud_rect.setCenterAndSize(media_hud_rect.getCenterX(), media_hud_rect.getCenterY(), +			llmax(MIN_HUD_WIDTH, media_hud_rect.getWidth()), llmax(MIN_HUD_HEIGHT, media_hud_rect.getHeight())); + +		setShape(media_hud_rect, true); + +		// Test mouse position to see if the cursor is stationary +		LLCoordWindow cursor_pos_window; +		getWindow()->getCursorPosition(&cursor_pos_window); + +		// If last pos is not equal to current pos, the mouse has moved +		// We need to reset the timer, and make sure the panel is visible +		if(cursor_pos_window.mX != mLastCursorPos.mX || +			cursor_pos_window.mY != mLastCursorPos.mY || +			mScrollState != SCROLL_NONE) +		{ +			mInactivityTimer.start(); +			mLastCursorPos = cursor_pos_window; +		} +		 +		if(isMouseOver()) +		{ +			// Never fade the controls if the mouse is over them. +			mFadeTimer.stop(); +		} +		else if(!mClearFaceOnFade && (mInactivityTimer.getElapsedTimeF32() < mInactiveTimeout)) +		{ +			// Mouse is over the object, but has not been stationary for long enough to fade the UI +			mFadeTimer.stop(); +		} +		else if(! mFadeTimer.getStarted() ) +		{ +			// we need to start fading the UI (and we have not already started) +			mFadeTimer.reset(); +			mFadeTimer.start(); +		} +		else +		{ +			// I don't think this is correct anymore.  This is done in draw() after the fade has completed. +//			setVisible(FALSE); +		} +	} +} + +/*virtual*/ +void LLPanelMediaControls::draw() +{ +	F32 alpha = 1.f; +	if(mFadeTimer.getStarted()) +	{ +		F32 time = mFadeTimer.getElapsedTimeF32(); +		alpha = llmax(lerp(1.0, 0.0, time / mControlFadeTime), 0.0f); + +		if(mFadeTimer.getElapsedTimeF32() >= mControlFadeTime) +		{ +			setVisible(FALSE); +			if(mClearFaceOnFade) +			{ +				mClearFaceOnFade = false; +				mTargetImplID = LLUUID::null; +				mTargetObjectID = LLUUID::null; +				mTargetObjectFace = 0; +			} +		} +	} +	 +	{ +		LLViewDrawContext context(alpha); +		LLPanel::draw(); +	} +} + +BOOL LLPanelMediaControls::handleScrollWheel(S32 x, S32 y, S32 clicks) +{ +	mInactivityTimer.start(); +	return LLViewerMediaFocus::getInstance()->handleScrollWheel(x, y, clicks); +} + +BOOL LLPanelMediaControls::handleMouseDown(S32 x, S32 y, MASK mask) +{ +	mInactivityTimer.start(); +	return LLPanel::handleMouseDown(x, y, mask); +} + +BOOL LLPanelMediaControls::handleMouseUp(S32 x, S32 y, MASK mask) +{ +	mInactivityTimer.start(); +	return LLPanel::handleMouseUp(x, y, mask); +} + +BOOL LLPanelMediaControls::handleKeyHere( KEY key, MASK mask ) +{ +	mInactivityTimer.start(); +	return LLPanel::handleKeyHere(key, mask); +} + +bool LLPanelMediaControls::isMouseOver() +{ +	bool result = false; +	 +	if( getVisible() ) +	{ +		LLCoordWindow cursor_pos_window; +		LLCoordScreen cursor_pos_screen; +		LLCoordGL cursor_pos_gl; +		S32 x, y; +		getWindow()->getCursorPosition(&cursor_pos_window); +		getWindow()->convertCoords(cursor_pos_window, &cursor_pos_gl); +		 +		LLPanel* controls_panel = NULL; +		controls_panel = getChild<LLPanel>("media_hover_controls"); +		if(controls_panel && !controls_panel->getVisible()) +		{ +			// The hover controls aren't visible -- use the focused controls instead. +			controls_panel = getChild<LLPanel>("media_focused_controls"); +		} +		 +		if(controls_panel && controls_panel->getVisible()) +		{ +			controls_panel->screenPointToLocal(cursor_pos_gl.mX, cursor_pos_gl.mY, &x, &y); + +			LLView *hit_child = controls_panel->childFromPoint(x, y); +			if(hit_child) +			{ +				// This was useful for debugging both coordinate translation and view hieararchy problems... +//				llinfos << "mouse coords: " << x << ", " << y << " hit child " << hit_child->getName() << llendl; +				result = true; +			} +		} +	} + +	return result; +} + + +void LLPanelMediaControls::onClickClose() +{ +	close(); +} + +void LLPanelMediaControls::close() +{ +	LLViewerMediaFocus::getInstance()->clearFocus(); +	resetZoomLevel(); +	setVisible(FALSE); +} + + +void LLPanelMediaControls::onClickBack() +{ +	focusOnTarget(); + +	LLViewerMediaImpl* impl =getTargetMediaImpl(); +	 +	if (impl) +	{ +		impl->navigateBack(); +	} +} + +void LLPanelMediaControls::onClickForward() +{ +	focusOnTarget(); + +	LLViewerMediaImpl* impl = getTargetMediaImpl(); +	 +	if (impl) +	{ +		impl->navigateForward(); +	} +} + +void LLPanelMediaControls::onClickHome() +{ +	focusOnTarget(); + +	LLViewerMediaImpl* impl = getTargetMediaImpl(); + +	if(impl) +	{ +		impl->navigateHome(); +	} +} + +void LLPanelMediaControls::onClickOpen() +{ +	LLViewerMediaImpl* impl =getTargetMediaImpl(); +	if(impl) +	{ +		if(impl->getMediaPlugin()) +		{	 +			if(impl->getMediaPlugin()->getLocation().empty()) +			{ +				LLWeb::loadURL(impl->getMediaURL()); +			} +			else +			{ +				LLWeb::loadURL( impl->getMediaPlugin()->getLocation()); +			} +		} +	}	 +} + +void LLPanelMediaControls::onClickReload() +{ +	focusOnTarget(); + +	//LLViewerMedia::navigateHome(); +	LLViewerMediaImpl* impl = getTargetMediaImpl(); + +	if(impl) +	{ +		impl->navigateReload(); +	} +} + +void LLPanelMediaControls::onClickPlay() +{ +	focusOnTarget(); + +	LLViewerMediaImpl* impl = getTargetMediaImpl(); + +	if(impl) +	{ +		impl->play(); +	} +} + +void LLPanelMediaControls::onClickPause() +{ +	focusOnTarget(); + +	LLViewerMediaImpl* impl = getTargetMediaImpl(); + +	if(impl) +	{ +		impl->pause(); +	} +} + +void LLPanelMediaControls::onClickStop() +{ +	focusOnTarget(); + +	LLViewerMediaImpl* impl = getTargetMediaImpl(); + +	if(impl) +	{ +		impl->stop(); +	} +} + +void LLPanelMediaControls::onClickZoom() +{ +	focusOnTarget(); + +	nextZoomLevel(); +} +void LLPanelMediaControls::nextZoomLevel() +{ +	int index = 0; +	while (index < kNumZoomLevels) +	{ +		if (kZoomLevels[index] == mCurrentZoom)  +		{ +			index++; +			break; +		} +		index++; +	} +	mCurrentZoom = kZoomLevels[index % kNumZoomLevels]; +	updateZoom(); +} + +void LLPanelMediaControls::resetZoomLevel() +{ +	if(mCurrentZoom != ZOOM_NONE) +	{ +		mCurrentZoom = ZOOM_NONE; +		updateZoom(); +	} +} + +void LLPanelMediaControls::updateZoom() +{ +	F32 zoom_padding = 0.0f; +	switch (mCurrentZoom) +	{ +	case ZOOM_NONE: +		{ +			gAgent.setFocusOnAvatar(TRUE, ANIMATE); +			break; +		} +	case ZOOM_FAR: +		{ +			zoom_padding = ZOOM_FAR_PADDING; +			break; +		} +	case ZOOM_MEDIUM: +		{ +			zoom_padding = ZOOM_MEDIUM_PADDING; +			break; +		} +	case ZOOM_NEAR: +		{ +			zoom_padding = ZOOM_NEAR_PADDING; +			break; +		} +	default: +		{ +			gAgent.setFocusOnAvatar(TRUE, ANIMATE); +			break; +		} +	} + +	if (zoom_padding > 0.0f)		 +		LLViewerMediaFocus::setCameraZoom(getTargetObject(), mTargetObjectNormal, zoom_padding); +} +void LLPanelMediaControls::onScrollUp(void* user_data) +{ +	LLPanelMediaControls* this_panel = static_cast<LLPanelMediaControls*> (user_data); +	this_panel->focusOnTarget(); + +	LLPluginClassMedia* plugin = this_panel->getTargetMediaPlugin(); +	 +	if(plugin) +	{ +		plugin->scrollEvent(0, -1, MASK_NONE); +	} +} +void LLPanelMediaControls::onScrollUpHeld(void* user_data) +{ +	LLPanelMediaControls* this_panel = static_cast<LLPanelMediaControls*> (user_data); +	this_panel->mScrollState = SCROLL_UP; +} +void LLPanelMediaControls::onScrollRight(void* user_data) +{ +	LLPanelMediaControls* this_panel = static_cast<LLPanelMediaControls*> (user_data); +	this_panel->focusOnTarget(); + +	LLViewerMediaImpl* impl = this_panel->getTargetMediaImpl(); + +	if(impl) +	{ +		impl->handleKeyHere(KEY_RIGHT, MASK_NONE); +	} +} +void LLPanelMediaControls::onScrollRightHeld(void* user_data) +{ +	LLPanelMediaControls* this_panel = static_cast<LLPanelMediaControls*> (user_data); +	this_panel->mScrollState = SCROLL_RIGHT; +} + +void LLPanelMediaControls::onScrollLeft(void* user_data) +{ +	LLPanelMediaControls* this_panel = static_cast<LLPanelMediaControls*> (user_data); +	this_panel->focusOnTarget(); + +	LLViewerMediaImpl* impl = this_panel->getTargetMediaImpl(); + +	if(impl) +	{ +		impl->handleKeyHere(KEY_LEFT, MASK_NONE); +	} +} +void LLPanelMediaControls::onScrollLeftHeld(void* user_data) +{ +	LLPanelMediaControls* this_panel = static_cast<LLPanelMediaControls*> (user_data); +	this_panel->mScrollState = SCROLL_LEFT; +} + +void LLPanelMediaControls::onScrollDown(void* user_data) +{ +	LLPanelMediaControls* this_panel = static_cast<LLPanelMediaControls*> (user_data); +	this_panel->focusOnTarget(); + +	LLPluginClassMedia* plugin = this_panel->getTargetMediaPlugin(); +	 +	if(plugin) +	{ +		plugin->scrollEvent(0, 1, MASK_NONE); +	} +} +void LLPanelMediaControls::onScrollDownHeld(void* user_data) +{ +	LLPanelMediaControls* this_panel = static_cast<LLPanelMediaControls*> (user_data); +	this_panel->mScrollState = SCROLL_DOWN; +} + +void LLPanelMediaControls::onScrollStop(void* user_data) +{ +	LLPanelMediaControls* this_panel = static_cast<LLPanelMediaControls*> (user_data); +	this_panel->mScrollState = SCROLL_NONE; +} + +void LLPanelMediaControls::onCommitURL() +{ +	focusOnTarget(); + +	LLUICtrl *media_address_ctrl = getChild<LLUICtrl>("media_address_url"); +	std::string url = media_address_ctrl->getValue().asString(); +	if(getTargetMediaImpl() && !url.empty()) +	{ +		getTargetMediaImpl()->navigateTo( url, "", true); + +		// Make sure keyboard focus is set to the media focus object. +		gFocusMgr.setKeyboardFocus(LLViewerMediaFocus::getInstance()); +			 +	} +	mPauseFadeout = false; +	mFadeTimer.start(); +} + + +void LLPanelMediaControls::onInputURL(LLFocusableElement* caller, void *userdata) +{ + +	LLPanelMediaControls* this_panel = static_cast<LLPanelMediaControls*> (userdata); +	this_panel->focusOnTarget(); + +	this_panel->mPauseFadeout = true; +	this_panel->mFadeTimer.stop(); +	this_panel->mFadeTimer.reset(); +	 +} + +void LLPanelMediaControls::setCurrentURL() +{	 +	LLComboBox* media_address_combo	= getChild<LLComboBox>("media_address_combo"); +	// redirects will navigate momentarily to about:blank, don't add to history +	if (media_address_combo && mCurrentURL != "about:blank") +	{ +		media_address_combo->remove(mCurrentURL); +		media_address_combo->add(mCurrentURL, ADD_SORTED); +		media_address_combo->selectByValue(mCurrentURL); +	} +} + +void LLPanelMediaControls::onCommitSlider() +{ +	focusOnTarget(); + +	LLSlider* media_play_slider_ctrl	= getChild<LLSlider>("media_play_slider"); +	LLViewerMediaImpl* media_impl = getTargetMediaImpl(); +	if (media_impl)  +	{ +		// get slider value +		F64 slider_value = media_play_slider_ctrl->getValue().asReal(); +		if(slider_value <= 0.0) +		{	 +			media_impl->stop(); +		} +		else  +		{ +			media_impl->seek(slider_value*mMovieDuration); +			//mUpdateSlider= false; +		} +	} +}		 + +void LLPanelMediaControls::onCommitVolumeUp() +{ +	focusOnTarget(); + +	LLViewerMediaImpl* media_impl = getTargetMediaImpl(); +	if (media_impl)  +	{ +		F32 volume = media_impl->getVolume(); +		 +		volume += 0.1f; +		if(volume >= 1.0f) +		{ +			volume = 1.0f; +		} +		 +		media_impl->setVolume(volume); +		getChild<LLButton>("media_volume")->setToggleState(false); +	} +}		 + +void LLPanelMediaControls::onCommitVolumeDown() +{ +	focusOnTarget(); + +	LLViewerMediaImpl* media_impl = getTargetMediaImpl(); +	if (media_impl)  +	{ +		F32 volume = media_impl->getVolume(); +		 +		volume -= 0.1f; +		if(volume <= 0.0f) +		{ +			volume = 0.0f; +		} + +		media_impl->setVolume(volume); +		getChild<LLButton>("media_volume")->setToggleState(false); +	} +}		 + + +void LLPanelMediaControls::onToggleMute() +{ +	focusOnTarget(); + +	LLViewerMediaImpl* media_impl = getTargetMediaImpl(); +	if (media_impl)  +	{ +		F32 volume = media_impl->getVolume(); +		 +		if(volume > 0.0) +		{ +			media_impl->setVolume(0.0); +		} +		else  +		{ +			media_impl->setVolume(0.5); +		} +	} +} + diff --git a/indra/newview/llpanelprimmediacontrols.h b/indra/newview/llpanelprimmediacontrols.h new file mode 100644 index 0000000000..b605c08a55 --- /dev/null +++ b/indra/newview/llpanelprimmediacontrols.h @@ -0,0 +1,148 @@ +/**  + * @file llpanelmediahud.h + * @brief Pop-up media controls panel + * + * $LicenseInfo:firstyear=2003&license=viewergpl$ + *  + * Copyright (c) 2003-2007, Linden Research, Inc. + *  + * Second Life Viewer Source Code + * The source code in this file ("Source Code") is provided by Linden Lab + * to you under the terms of the GNU General Public License, version 2.0 + * ("GPL"), unless you have obtained a separate licensing agreement + * ("Other License"), formally executed by you and Linden Lab.  Terms of + * the GPL can be found in doc/GPL-license.txt in this distribution, or + * online at http://secondlife.com/developers/opensource/gplv2 + *  + * There are special exceptions to the terms and conditions of the GPL as + * it is applied to this Source Code. View the full text of the exception + * in the file doc/FLOSS-exception.txt in this software distribution, or + * online at http://secondlife.com/developers/opensource/flossexception + *  + * By copying, modifying or distributing this software, you acknowledge + * that you have read and understood your obligations described above, + * and agree to abide by those obligations. + *  + * ALL LINDEN LAB SOURCE CODE IS PROVIDED "AS IS." LINDEN LAB MAKES NO + * WARRANTIES, EXPRESS, IMPLIED OR OTHERWISE, REGARDING ITS ACCURACY, + * COMPLETENESS OR PERFORMANCE. + * $/LicenseInfo$ + */ + +#ifndef LL_PANELMEDIAHUD_H +#define LL_PANELMEDIAHUD_H + +#include "llpanel.h" +#include "llviewermedia.h" + +class LLCoordWindow; +class LLViewerMediaImpl; + +class LLPanelMediaControls : public LLPanel +{ +public: +	LLPanelMediaControls(); +	virtual ~LLPanelMediaControls(); +	/*virtual*/ BOOL postBuild(); +	virtual void draw(); +	virtual BOOL handleScrollWheel(S32 x, S32 y, S32 clicks); + +	virtual BOOL handleMouseDown(S32 x, S32 y, MASK mask); +	virtual BOOL handleMouseUp(S32 x, S32 y, MASK mask); +	virtual BOOL handleKeyHere(KEY key, MASK mask); +	 +	void updateShape(); +	bool isMouseOver(); +	void nextZoomLevel(); +	void resetZoomLevel(); +	void close(); + +	LLHandle<LLPanelMediaControls>	getHandle() const { return mPanelHandle; } +	void setMediaFace(LLPointer<LLViewerObject> objectp, S32 face, viewer_media_t media_impl, LLVector3 pick_normal = LLVector3::zero); + + +	enum EZoomLevel +	{ +		ZOOM_NONE = 0, +		ZOOM_FAR, +		ZOOM_MEDIUM, +		ZOOM_NEAR +	}; +	static const EZoomLevel kZoomLevels[]; +	static const int kNumZoomLevels; +	 +	enum EScrollDir +	{ +		SCROLL_UP = 0, +		SCROLL_DOWN, +		SCROLL_LEFT, +		SCROLL_RIGHT, +		SCROLL_NONE +	}; + +private: +	void onClickClose(); +	void onClickBack(); +	void onClickForward(); +	void onClickHome(); +	void onClickOpen(); +	void onClickReload(); +	void onClickPlay(); +	void onClickPause(); +	void onClickStop(); +	void onClickZoom(); +	void onCommitURL(); +	 +	void updateZoom(); +	void setCurrentURL(); +	void onCommitSlider(); +	 +	void onCommitVolumeUp(); +	void onCommitVolumeDown(); +	void onToggleMute(); +	 +	static void onScrollUp(void* user_data); +	static void onScrollUpHeld(void* user_data); +	static void onScrollLeft(void* user_data); +	static void onScrollLeftHeld(void* user_data); +	static void onScrollRight(void* user_data); +	static void onScrollRightHeld(void* user_data); +	static void onScrollDown(void* user_data); +	static void onScrollDownHeld(void* user_data); +	static void onScrollStop(void* user_data); +	 +	static void onInputURL(LLFocusableElement* caller, void *userdata); +	static bool hasControlsPermission(LLViewerObject *obj, const LLMediaEntry *media_entry); +	 +	void focusOnTarget(); +	 +	LLViewerMediaImpl* getTargetMediaImpl(); +	LLViewerObject* getTargetObject(); +	LLPluginClassMedia* getTargetMediaPlugin(); +	bool mPauseFadeout; +	bool mUpdateSlider; +	bool mClearFaceOnFade; + +	LLMatrix4 mLastCameraMat; +	EZoomLevel mCurrentZoom; +	EScrollDir mScrollState; +	LLCoordWindow mLastCursorPos; +	LLFrameTimer mInactivityTimer; +	LLFrameTimer mFadeTimer; +	F32 mInactiveTimeout; +	F32 mControlFadeTime; +	LLRootHandle<LLPanelMediaControls> mPanelHandle; +	F32 mAlpha; +	std::string mCurrentURL; +	std::string mPreviousURL; +	F64 mCurrentRate; +	F64 mMovieDuration; +	int mUpdatePercent; + +	LLUUID mTargetObjectID; +	S32 mTargetObjectFace; +	LLUUID mTargetImplID; +	LLVector3 mTargetObjectNormal; +}; + +#endif // LL_PANELMEDIAHUD_H diff --git a/indra/newview/llviewermediafocus.cpp b/indra/newview/llviewermediafocus.cpp index 174dcb3410..cb5637a5bc 100644 --- a/indra/newview/llviewermediafocus.cpp +++ b/indra/newview/llviewermediafocus.cpp @@ -35,7 +35,7 @@  //LLViewerMediaFocus  #include "llviewerobjectlist.h" -#include "llpanelmediahud.h" +#include "llpanelprimmediacontrols.h"  #include "llpluginclassmedia.h"  #include "llagent.h"  #include "lltoolpie.h" diff --git a/indra/newview/skins/default/xui/en/panel_prim_media_controls.xml b/indra/newview/skins/default/xui/en/panel_prim_media_controls.xml new file mode 100644 index 0000000000..b21fbc1795 --- /dev/null +++ b/indra/newview/skins/default/xui/en/panel_prim_media_controls.xml @@ -0,0 +1,594 @@ +<?xml version="1.0" encoding="utf-8" standalone="yes" ?> +<panel +	follows="left|right|top|bottom" +	name="MediaControls" +	bg_alpha_color="1 1 1 0" +	height="160" +	layout="topleft" +	mouse_opaque="false" +	width="800"> +  <panel +	  name="media_region" +	  bottom="125" +	  follows="left|right|top|bottom" +	  layout="topleft" +	  left="20" +	  mouse_opaque="false" +	  right="-20" +	  top="20" /> +  <layout_stack +	  follows="left|right|bottom" +	  height="32" +	  layout="topleft" +	  animate="false" +	  left="0" +	  orientation="horizontal" +	  top="96"> +	<!-- outer layout_panels center the inner one --> +	<layout_panel +		width="0" +		layout="topleft" +		user_resize="false" /> +	<panel +		name="media_progress_indicator" +		height="22" +		layout="topleft" +		left="0" +		top="0" +		auto_resize="false" +		user_resize="false" +		min_width="100" +		width="200"> +	  <progress_bar +		  name="media_progress_bar" +		  color_bar="1 1 1 0.96" +		  follows="left|right|top" +		  height="16" +		  layout="topleft" +		  left="0" +		  tool_tip="Media is Loading"/> +	</panel> +	<layout_panel +		width="0" +		layout="topleft" +		user_resize="false" /> +  </layout_stack> +  <layout_stack +	  name="media_controls" +	  follows="left|right" +	  animate="false" +	  height="32" +	  layout="topleft" +	  left="0" +	  orientation="horizontal" +	  top="128"> +	<!-- outer layout_panels center the inner one --> +	<layout_panel +		width="0" +		layout="topleft" +		user_resize="false" /> +	<layout_panel +		name="back" +		auto_resize="false" +		user_resize="false" +		layout="topleft" +		min_width="22" +		width="22" +		top="4"> +	  <button +		  auto_resize="false" +		  height="22" +		  image_selected="media_btn_back.png" +		  image_unselected="media_btn_back.png" +		  layout="topleft" +		  tool_tip="Step back" +		  picture_style="true" +		  width="22" +		  top_delta="4"> +		<button.commit_callback +			function="MediaCtrl.Back" /> +	  </button> +	</layout_panel> +	<layout_panel +		name="fwd" +		auto_resize="false" +		user_resize="false" +		layout="topleft" +		top="10" +		min_width="17" +		width="17"> +	  <button +		  height="22" +		  image_selected="media_btn_forward.png" +		  image_unselected="media_btn_forward.png" +		  layout="topleft" +		  tool_tip="Step forward" +		  picture_style="true" +		  top_delta="0" +		  min_width="17" +		  width="17"> +		<button.commit_callback +			function="MediaCtrl.Forward" /> +	  </button> +	</layout_panel> +<!-- +	<panel +		height="22" +		layout="topleft" +		auto_resize="false" +		min_width="3" +		width="3"> +	  <icon +		  height="22" +		  image_name="media_panel_divider.png" +		  layout="topleft" +		  top="0" +		  min_width="3" +		  width="3" /> +	</panel> +--> +	<layout_panel +		name="home" +		auto_resize="false" +		user_resize="false" +		layout="topleft" +		top="-2" +		min_width="22" +		width="22"> +	  <button +		  height="22" +		  image_selected="media_btn_home.png" +		  image_unselected="media_btn_home.png" +		  layout="topleft" +		  tool_tip="Home page" +		  picture_style="true" +		  min_width="22" +		  width="22"> +		<button.commit_callback +			function="MediaCtrl.Home" /> +	  </button> +	</layout_panel> +	<layout_panel +		name="media_stop" +		auto_resize="false" +		user_resize="false" +		layout="topleft" +		top="2" +		min_width="22" +		width="22"> +	  <button +		  height="22" +		  image_selected="button_anim_stop.tga" +		  image_unselected="button_anim_stop.tga" +		  layout="topleft" +		  tool_tip="Stop media" +		  picture_style="true" +		  min_width="22" +		  width="22"> +		<button.commit_callback +			function="MediaCtrl.Stop" /> +	  </button> +	</layout_panel> +<!-- +	<panel +		height="22" +		layout="topleft" +		auto_resize="false" +		min_width="3" +		width="3"> +	  <icon +		  height="22" +		  image_name="media_panel_divider.png" +		  layout="topleft" +		  top="0" +		  min_width="3" +		  width="3" /> +	</panel> +--> +	<layout_panel +		name="reload" +		auto_resize="false" +		user_resize="false" +		layout="topleft" +		top="6" +		min_width="22" +		width="22"> +	  <button +		  height="22" +		  image_selected="media_btn_reload.png" +		  image_unselected="media_btn_reload.png" +		  layout="topleft" +		  tool_tip="Reload" +		  picture_style="true" +		  min_width="22" +		  width="22"> +		<button.commit_callback +			function="MediaCtrl.Reload" /> +	  </button> +	</layout_panel> +	<layout_panel +		name="stop" +		auto_resize="false" +		user_resize="false" +		layout="topleft" +		top="10" +		min_width="22" +		width="22"> +	  <button +		  height="22" +		  image_selected="media_btn_stoploading.png" +		  image_unselected="media_btn_stoploading.png" +		  layout="topleft" +		  picture_style="true" +		  tool_tip = "Stop loading" +		  min_width="22" +		  width="22"> +		<button.commit_callback +			function="MediaCtrl.Stop" /> +	  </button> +	</layout_panel> +	<layout_panel +		name="play" +		auto_resize="false" +		user_resize="false" +		layout="topleft" +		top="14" +		min_width="22" +		width="22"> +	  <button +		  height="22" +		  image_selected="button_anim_play.tga" +		  image_unselected="button_anim_play.tga" +		  layout="topleft" +		  tool_tip = "Play media" +		  picture_style="true" +		  min_width="22" +		  width="22"> +		<button.commit_callback +			function="MediaCtrl.Play" /> +	  </button> +	</layout_panel> +	<layout_panel +		name="pause" +		auto_resize="false" +		user_resize="false" +		layout="topleft" +		top="18" +		min_width="22" +		width="22"> +	  <button +		  height="22" +		  image_selected="button_anim_pause.tga" +		  image_unselected="button_anim_pause.tga" +		  layout="topleft" +		  tool_tip = "Pause media" +		  picture_style="true"> +		<button.commit_callback +			function="MediaCtrl.Pause" /> +	  </button> +	</layout_panel> +	<!-- media URL entry  --> +	<layout_panel +		name="media_address" +		auto_resize="true" +		user_resize="false" +		height="22" +		follows="left|right|bottom" +		layout="topleft" +		width="190" +		min_width="90"> +	  <!-- +		  RE-ENABLE THIS WHEN WE HAVE A HISTORY DROP-DOWN AGAIN + +<combo_box +name="media_address_url" +allow_text_entry="true" +height="22" +layout="topleft" +max_chars="1024" +tool_tip = "Media URL" +<combo_box.commit_callback +function="MediaCtrl.CommitURL" /> +</combo_box> +	  --> +	  <line_editor  +		  name="media_address_url" +		  follows="left|right"  +		  height="22" +		  top="0" +		  tool_tip="Media URL" +		  text_pad_right="16">  +		<line_editor.commit_callback +			function="MediaCtrl.CommitURL"/> +	  </line_editor> +	  <layout_stack +		  animate="false" +		  follows="right" +		  width="32" +		  min_width="32" +		  height="16" +		  top="3" +		  orientation="horizontal" +		  left_pad="-38"> +		<icon +			name="media_whitelist_flag" +			follows="top|right" +			height="16" +			image_name="smicon_warn.tga" +			layout="topleft" +			tool_tip="White List enabled" +			min_width="16" +			width="16" /> +		<icon +			name="media_secure_lock_flag" +			height="16" +			image_name="inv_item_eyes.tga" +			layout="topleft" +			tool_tip="Secured Browsing" +			min_width="16" +			width="16" /> +	  </layout_stack> +	</layout_panel> +	<layout_panel +		name="media_play_position" +		auto_resize="true" +		user_resize="false" +		follows="left|right|top|bottom" +		layout="topleft" +		min_width="100" +		width="200"> +	  <slider_bar +		  name="media_play_slider" +		  follows="left|right|top" +		  height="22" +		  increment="0.05" +		  initial_value="0.5" +		  layout="topleft" +		  tool_tip="Movie play progress" +		  min_width="100" +		  width="200"> +		<slider_bar.commit_callback +			function="MediaCtrl.JumpProgress" /> +	  </slider_bar> +	</layout_panel> +	<layout_panel +		name="media_volume" +		auto_resize="false" +		user_resize="false" +		layout="topleft" +		height="24" +		min_width="24" +		width="24"> +	  <button +		  name="media_volume_button" +		  height="22" +		  image_selected="icn_speaker-muted_dark.tga" +		  image_unselected="icn_speaker_dark.tga" +		  is_toggle="true" +		  layout="topleft" +		  scale_image="false"  +		  picture_style="true" +		  tool_tip="Mute This Media" +		  top_delta="22" +		  min_width="24" +		  width="24" > +		<button.commit_callback +			function="MediaCtrl.ToggleMute" /> +	  </button> +	</layout_panel> +	<layout_panel +		name="volume_up" +		auto_resize="false" +		user_resize="false" +		layout="topleft" +		min_width="20" +		height="14" +		width="20"> +	  <button +		  top="-3" +		  height="14" +		  image_selected="media_btn_scrollup.png" +		  image_unselected="media_btn_scrollup.png" +		  layout="topleft" +		  tool_tip="Volume up" +		  picture_style="true" +		  scale_image="true" +		  min_width="20" +		  width="20" > +		<button.commit_callback +			function="MediaCtrl.CommitVolumeUp" /> +	  </button> +	</layout_panel> +	<layout_panel +		name="volume_down" +		auto_resize="false" +		user_resize="false" +		layout="topleft" +		min_width="20" +		height="14" +		width="20"> +	  <button +		  top="-5" +		  height="14" +		  image_selected="media_btn_scrolldown.png" +		  image_unselected="media_btn_scrolldown.png" +		  layout="topleft" +		  tool_tip="Volume down" +		  picture_style="true" +		  scale_image="true" +		  min_width="20" +		  width="20"> +		<button.commit_callback +			function="MediaCtrl.CommitVolumeDown" /> +	  </button> +	</layout_panel> +	<!-- Scroll pad --> +	<layout_panel +		name="media_panel_scroll" +		auto_resize="false" +		user_resize="false" +		height="32" +		follows="left|right|top|bottom" +		layout="topleft" +		min_width="32" +		width="32"> +	  <icon +		  height="32" +		  image_name="media_panel_scrollbg.png" +		  layout="topleft" +		  top="0" +		  min_width="32" +		  width="32" /> +	  <button +		  name="scrollup" +		  height="8" +		  image_selected="media_btn_scrollup.png" +		  image_unselected="media_btn_scrollup.png" +		  layout="topleft" +		  tool_tip="Scroll up" +		  picture_style="true" +		  scale_image="false" +		  left="12" +		  top_delta="4" +		  min_width="8" +		  width="8" /> +	  <button +		  name="scrollleft" +		  height="8" +		  image_selected="media_btn_scrollleft.png" +		  image_unselected="media_btn_scrollleft.png" +		  layout="topleft" +		  left="3" +		  tool_tip="Scroll left" +		  picture_style="true" +		  scale_image="false" +		  top="12" +		  min_width="8" +		  width="8" /> +	  <button +		  name="scrollright" +		  height="8" +		  image_selected="media_btn_scrollright.png" +		  image_unselected="media_btn_scrollright.png" +		  layout="topleft" +		  left_pad="9" +		  tool_tip="Scroll right" +		  picture_style="true" +		  scale_image="false" +		  top_delta="0" +		  min_width="8" +		  width="8" /> +	  <button +		  name="scrolldown" +		  height="8" +		  image_selected="media_btn_scrolldown.png" +		  image_unselected="media_btn_scrolldown.png" +		  layout="topleft" +		  left="12" +		  tool_tip="Scroll down" +		  picture_style="true" +		  scale_image="false" +		  top="20" +		  min_width="8" +		  width="8" /> +	</layout_panel> +	<layout_panel +		name="zoom_frame" +		auto_resize="false" +		user_resize="false" +		layout="topleft" +		height="28" +		min_width="22" +		width="22"> +	  <button +		  height="22" +		  image_selected="media_btn_optimalzoom.png" +		  image_unselected="media_btn_optimalzoom.png" +		  layout="topleft" +		  tool_tip="Zoom" +		  picture_style="true" +		  min_width="22" +		  width="22"> +		<button.commit_callback +			function="MediaCtrl.Zoom" /> +	  </button> +	</layout_panel> +<!-- +	<panel +		height="22" +		layout="topleft" +		auto_resize="false" +		min_width="3" +		width="3"> +	  <icon +		  height="22" +		  image_name="media_panel_divider.png" +		  layout="topleft" +		  top="0" +		  min_width="3" +		  width="3" /> +	</panel> +--> +	<layout_panel +		name="new_window" +		auto_resize="false" +		user_resize="false" +		layout="topleft" +		min_width="22" +		width="22"> +	  <button +		  height="22" +		  image_selected="media_btn_newwindow.png" +		  image_unselected="media_btn_newwindow.png" +		  layout="topleft" +		  tool_tip = "Open URL in browser" +		  picture_style="true" +		  top_delta="-3" +		  min_width="24" +		  width="24" > +		<button.commit_callback +			function="MediaCtrl.Open" /> +	  </button> +	</layout_panel> +<!-- +	<panel +		height="22" +		layout="topleft" +		auto_resize="false" +		min_width="3" +		width="3"> +	  <icon +		  height="22" +		  image_name="media_panel_divider.png" +		  layout="topleft" +		  top="0" +		  min_width="3" +		  width="3" /> +	</panel> +--> +	<layout_panel +		name="close" +		auto_resize="false" +		user_resize="false" +		layout="topleft" +		min_width="21" +		width="21" > +	  <button +		  height="22" +		  image_selected="media_btn_done.png" +		  image_unselected="media_btn_done.png" +		  layout="topleft" +		  tool_tip ="Close media control" +		  picture_style="true" +		  top_delta="-4" +		  width="21" > +		<button.commit_callback +			function="MediaCtrl.Close" /> +	  </button> +	</layout_panel> +	<layout_panel +		width="0" +		layout="topleft" +		user_resize="false" /> +  </layout_stack> +</panel> | 
