Need to test: localassetbrowser preview related floaters hgfloatertexteditor maps media textures! Currently very hacky web browser alpha masks on avatars bumpmaps Are all sky components appearing? LLViewerDynamicTexture (texture baking, browser, animated textures, anim previews, etc) Snapshot related features Customize avatar vfs floater UI textures in general Texture priority issues
3298 lines
98 KiB
C++
3298 lines
98 KiB
C++
/**
|
|
* @file llfloaterregioninfo.cpp
|
|
* @author Aaron Brashears
|
|
* @brief Implementation of the region info and controls floater and panels.
|
|
*
|
|
* $LicenseInfo:firstyear=2004&license=viewergpl$
|
|
*
|
|
* Copyright (c) 2004-2009, 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://secondlifegrid.net/programs/open_source/licensing/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://secondlifegrid.net/programs/open_source/licensing/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"
|
|
#include "llfloaterregioninfo.h"
|
|
|
|
#include <algorithm>
|
|
#include <functional>
|
|
|
|
#include "llcachename.h"
|
|
#include "lldir.h"
|
|
#include "lldispatcher.h"
|
|
#include "llglheaders.h"
|
|
#include "llregionflags.h"
|
|
#include "llstl.h"
|
|
#include "indra_constants.h"
|
|
#include "message.h"
|
|
|
|
#include "llagent.h"
|
|
#include "llalertdialog.h"
|
|
#include "llappviewer.h"
|
|
#include "llfloateravatarpicker.h"
|
|
#include "llbutton.h"
|
|
#include "llcheckboxctrl.h"
|
|
#include "llcombobox.h"
|
|
#include "llfilepicker.h"
|
|
#include "llfloaterdaycycle.h"
|
|
#include "llfloatergodtools.h" // for send_sim_wide_deletes()
|
|
#include "llfloatertopobjects.h" // added to fix SL-32336
|
|
#include "llfloatergroups.h"
|
|
#include "llfloatertelehub.h"
|
|
#include "llfloaterwindlight.h"
|
|
#include "llinventorymodel.h"
|
|
#include "lllineeditor.h"
|
|
#include "llalertdialog.h"
|
|
#include "llnamelistctrl.h"
|
|
#include "llsliderctrl.h"
|
|
#include "llspinctrl.h"
|
|
#include "lltabcontainer.h"
|
|
#include "lltextbox.h"
|
|
#include "llinventory.h"
|
|
#include "lltexturectrl.h"
|
|
#include "lltrans.h"
|
|
#include "llviewercontrol.h"
|
|
#include "lluictrlfactory.h"
|
|
#include "llviewertexturelist.h"
|
|
#include "llviewerregion.h"
|
|
#include "llviewerstats.h"
|
|
#include "llviewertexteditor.h"
|
|
#include "llviewerwindow.h"
|
|
#include "llvlcomposition.h"
|
|
|
|
// [RLVa:KB]
|
|
#include "rlvhandler.h"
|
|
// [/RLVa:KB]
|
|
|
|
#define ELAR_ENABLED 0 // Enable when server support is implemented
|
|
|
|
const S32 TERRAIN_TEXTURE_COUNT = 4;
|
|
const S32 CORNER_COUNT = 4;
|
|
|
|
///----------------------------------------------------------------------------
|
|
/// Local class declaration
|
|
///----------------------------------------------------------------------------
|
|
|
|
class LLDispatchEstateUpdateInfo : public LLDispatchHandler
|
|
{
|
|
public:
|
|
LLDispatchEstateUpdateInfo() {}
|
|
virtual ~LLDispatchEstateUpdateInfo() {}
|
|
virtual bool operator()(
|
|
const LLDispatcher* dispatcher,
|
|
const std::string& key,
|
|
const LLUUID& invoice,
|
|
const sparam_t& strings);
|
|
};
|
|
|
|
class LLDispatchSetEstateAccess : public LLDispatchHandler
|
|
{
|
|
public:
|
|
LLDispatchSetEstateAccess() {}
|
|
virtual ~LLDispatchSetEstateAccess() {}
|
|
virtual bool operator()(
|
|
const LLDispatcher* dispatcher,
|
|
const std::string& key,
|
|
const LLUUID& invoice,
|
|
const sparam_t& strings);
|
|
};
|
|
|
|
|
|
/*
|
|
void unpack_request_params(
|
|
LLMessageSystem* msg,
|
|
LLDispatcher::sparam_t& strings,
|
|
LLDispatcher::iparam_t& integers)
|
|
{
|
|
char str_buf[MAX_STRING];
|
|
S32 str_count = msg->getNumberOfBlocksFast(_PREHASH_StringData);
|
|
S32 i;
|
|
for (i = 0; i < str_count; ++i)
|
|
{
|
|
// we treat the SParam as binary data (since it might be an
|
|
// LLUUID in compressed form which may have embedded \0's,)
|
|
str_buf[0] = '\0';
|
|
S32 data_size = msg->getSizeFast(_PREHASH_StringData, i, _PREHASH_SParam);
|
|
if (data_size >= 0)
|
|
{
|
|
msg->getBinaryDataFast(_PREHASH_StringData, _PREHASH_SParam,
|
|
str_buf, data_size, i, MAX_STRING - 1);
|
|
strings.push_back(std::string(str_buf, data_size));
|
|
}
|
|
}
|
|
|
|
U32 int_buf;
|
|
S32 int_count = msg->getNumberOfBlocksFast(_PREHASH_IntegerData);
|
|
for (i = 0; i < int_count; ++i)
|
|
{
|
|
msg->getU32("IntegerData", "IParam", int_buf, i);
|
|
integers.push_back(int_buf);
|
|
}
|
|
}
|
|
*/
|
|
|
|
|
|
|
|
bool estate_dispatch_initialized = false;
|
|
|
|
|
|
///----------------------------------------------------------------------------
|
|
/// LLFloaterRegionInfo
|
|
///----------------------------------------------------------------------------
|
|
|
|
//S32 LLFloaterRegionInfo::sRequestSerial = 0;
|
|
LLUUID LLFloaterRegionInfo::sRequestInvoice;
|
|
|
|
LLFloaterRegionInfo::LLFloaterRegionInfo(const LLSD& seed)
|
|
{
|
|
LLUICtrlFactory::getInstance()->buildFloater(this, "floater_region_info.xml", NULL, FALSE);
|
|
}
|
|
|
|
BOOL LLFloaterRegionInfo::postBuild()
|
|
{
|
|
mTab = getChild<LLTabContainer>("region_panels");
|
|
|
|
// contruct the panels
|
|
LLPanelRegionInfo* panel;
|
|
panel = new LLPanelRegionGeneralInfo;
|
|
mInfoPanels.push_back(panel);
|
|
LLUICtrlFactory::getInstance()->buildPanel(panel, "panel_region_general.xml");
|
|
mTab->addTabPanel(panel, panel->getLabel(), TRUE);
|
|
|
|
panel = new LLPanelRegionDebugInfo;
|
|
mInfoPanels.push_back(panel);
|
|
LLUICtrlFactory::getInstance()->buildPanel(panel, "panel_region_debug.xml");
|
|
mTab->addTabPanel(panel, panel->getLabel(), FALSE);
|
|
|
|
panel = new LLPanelRegionTextureInfo;
|
|
mInfoPanels.push_back(panel);
|
|
LLUICtrlFactory::getInstance()->buildPanel(panel, "panel_region_texture.xml");
|
|
mTab->addTabPanel(panel, panel->getLabel(), FALSE);
|
|
|
|
panel = new LLPanelRegionTerrainInfo;
|
|
mInfoPanels.push_back(panel);
|
|
LLUICtrlFactory::getInstance()->buildPanel(panel, "panel_region_terrain.xml");
|
|
mTab->addTabPanel(panel, panel->getLabel(), FALSE);
|
|
|
|
panel = new LLPanelEstateInfo;
|
|
mInfoPanels.push_back(panel);
|
|
LLUICtrlFactory::getInstance()->buildPanel(panel, "panel_region_estate.xml");
|
|
mTab->addTabPanel(panel, panel->getLabel(), FALSE);
|
|
|
|
panel = new LLPanelEstateCovenant;
|
|
mInfoPanels.push_back(panel);
|
|
LLUICtrlFactory::getInstance()->buildPanel(panel, "panel_region_covenant.xml");
|
|
mTab->addTabPanel(panel, panel->getLabel(), FALSE);
|
|
|
|
gMessageSystem->setHandlerFunc(
|
|
"EstateOwnerMessage",
|
|
&processEstateOwnerRequest);
|
|
|
|
return TRUE;
|
|
}
|
|
|
|
LLFloaterRegionInfo::~LLFloaterRegionInfo()
|
|
{
|
|
}
|
|
|
|
void LLFloaterRegionInfo::onOpen()
|
|
{
|
|
LLRect rect = gSavedSettings.getRect("FloaterRegionInfo");
|
|
S32 left, top;
|
|
gFloaterView->getNewFloaterPosition(&left, &top);
|
|
rect.translate(left,top);
|
|
|
|
refreshFromRegion(gAgent.getRegion());
|
|
requestRegionInfo();
|
|
LLFloater::onOpen();
|
|
}
|
|
|
|
// static
|
|
void LLFloaterRegionInfo::requestRegionInfo()
|
|
{
|
|
LLTabContainer* tab = findInstance()->getChild<LLTabContainer>("region_panels");
|
|
|
|
tab->getChild<LLPanel>("General")->setCtrlsEnabled(FALSE);
|
|
tab->getChild<LLPanel>("Debug")->setCtrlsEnabled(FALSE);
|
|
tab->getChild<LLPanel>("Terrain")->setCtrlsEnabled(FALSE);
|
|
tab->getChild<LLPanel>("Estate")->setCtrlsEnabled(FALSE);
|
|
|
|
// Must allow anyone to request the RegionInfo data
|
|
// so non-owners/non-gods can see the values.
|
|
// Therefore can't use an EstateOwnerMessage JC
|
|
LLMessageSystem* msg = gMessageSystem;
|
|
msg->newMessage("RequestRegionInfo");
|
|
msg->nextBlock("AgentData");
|
|
msg->addUUID("AgentID", gAgent.getID());
|
|
msg->addUUID("SessionID", gAgent.getSessionID());
|
|
gAgent.sendReliableMessage();
|
|
}
|
|
|
|
// static
|
|
void LLFloaterRegionInfo::processEstateOwnerRequest(LLMessageSystem* msg,void**)
|
|
{
|
|
static LLDispatcher dispatch;
|
|
if(!findInstance())
|
|
{
|
|
return;
|
|
}
|
|
|
|
if (!estate_dispatch_initialized)
|
|
{
|
|
LLPanelEstateInfo::initDispatch(dispatch);
|
|
}
|
|
|
|
LLTabContainer* tab = findInstance()->getChild<LLTabContainer>("region_panels");
|
|
LLPanelEstateInfo* panel = (LLPanelEstateInfo*)tab->getChild<LLPanel>("Estate");
|
|
|
|
// unpack the message
|
|
std::string request;
|
|
LLUUID invoice;
|
|
LLDispatcher::sparam_t strings;
|
|
LLDispatcher::unpackMessage(msg, request, invoice, strings);
|
|
if(invoice != getLastInvoice())
|
|
{
|
|
llwarns << "Mismatched Estate message: " << request << llendl;
|
|
return;
|
|
}
|
|
|
|
//dispatch the message
|
|
dispatch.dispatch(request, invoice, strings);
|
|
|
|
LLViewerRegion* region = gAgent.getRegion();
|
|
panel->updateControls(region);
|
|
}
|
|
|
|
|
|
// static
|
|
void LLFloaterRegionInfo::processRegionInfo(LLMessageSystem* msg)
|
|
{
|
|
LLPanel* panel;
|
|
|
|
llinfos << "LLFloaterRegionInfo::processRegionInfo" << llendl;
|
|
if(!findInstance())
|
|
{
|
|
return;
|
|
}
|
|
|
|
LLTabContainer* tab = findInstance()->getChild<LLTabContainer>("region_panels");
|
|
|
|
LLViewerRegion* region = gAgent.getRegion();
|
|
BOOL allow_modify = gAgent.isGodlike() || (region && region->canManageEstate());
|
|
|
|
// extract message
|
|
std::string sim_name;
|
|
std::string sim_type = LLTrans::getString("land_type_unknown");
|
|
U32 region_flags;
|
|
U8 agent_limit;
|
|
F32 object_bonus_factor;
|
|
U8 sim_access;
|
|
F32 water_height;
|
|
F32 terrain_raise_limit;
|
|
F32 terrain_lower_limit;
|
|
BOOL use_estate_sun;
|
|
F32 sun_hour;
|
|
msg->getString("RegionInfo", "SimName", sim_name);
|
|
msg->getU32("RegionInfo", "RegionFlags", region_flags);
|
|
msg->getU8("RegionInfo", "MaxAgents", agent_limit);
|
|
msg->getF32("RegionInfo", "ObjectBonusFactor", object_bonus_factor);
|
|
msg->getU8("RegionInfo", "SimAccess", sim_access);
|
|
msg->getF32Fast(_PREHASH_RegionInfo, _PREHASH_WaterHeight, water_height);
|
|
msg->getF32Fast(_PREHASH_RegionInfo, _PREHASH_TerrainRaiseLimit, terrain_raise_limit);
|
|
msg->getF32Fast(_PREHASH_RegionInfo, _PREHASH_TerrainLowerLimit, terrain_lower_limit);
|
|
msg->getBOOL("RegionInfo", "UseEstateSun", use_estate_sun);
|
|
// actually the "last set" sun hour, not the current sun hour. JC
|
|
msg->getF32("RegionInfo", "SunHour", sun_hour);
|
|
// the only reasonable way to decide if we actually have any data is to
|
|
// check to see if any of these fields have nonzero sizes
|
|
if (msg->getSize("RegionInfo2", "ProductSKU") > 0 ||
|
|
msg->getSize("RegionInfo2", "ProductName") > 0)
|
|
{
|
|
msg->getString("RegionInfo2", "ProductName", sim_type);
|
|
}
|
|
|
|
// GENERAL PANEL
|
|
panel = tab->getChild<LLPanel>("General");
|
|
panel->childSetValue("region_text", LLSD(sim_name));
|
|
panel->childSetValue("region_type", LLSD(sim_type));
|
|
panel->childSetValue("version_channel_text", gLastVersionChannel);
|
|
|
|
panel->childSetValue("block_terraform_check", (region_flags & REGION_FLAGS_BLOCK_TERRAFORM) ? TRUE : FALSE );
|
|
panel->childSetValue("block_fly_check", (region_flags & REGION_FLAGS_BLOCK_FLY) ? TRUE : FALSE );
|
|
panel->childSetValue("allow_damage_check", (region_flags & REGION_FLAGS_ALLOW_DAMAGE) ? TRUE : FALSE );
|
|
panel->childSetValue("restrict_pushobject", (region_flags & REGION_FLAGS_RESTRICT_PUSHOBJECT) ? TRUE : FALSE );
|
|
panel->childSetValue("allow_land_resell_check", (region_flags & REGION_FLAGS_BLOCK_LAND_RESELL) ? FALSE : TRUE );
|
|
panel->childSetValue("allow_parcel_changes_check", (region_flags & REGION_FLAGS_ALLOW_PARCEL_CHANGES) ? TRUE : FALSE );
|
|
panel->childSetValue("block_parcel_search_check", (region_flags & REGION_FLAGS_BLOCK_PARCEL_SEARCH) ? TRUE : FALSE );
|
|
panel->childSetValue("agent_limit_spin", LLSD((F32)agent_limit) );
|
|
panel->childSetValue("object_bonus_spin", LLSD(object_bonus_factor) );
|
|
panel->childSetValue("access_combo", LLSD(sim_access) );
|
|
|
|
|
|
// detect teen grid for maturity
|
|
|
|
U32 parent_estate_id;
|
|
msg->getU32("RegionInfo", "ParentEstateID", parent_estate_id);
|
|
BOOL teen_grid = (parent_estate_id == 5); // *TODO add field to estate table and test that
|
|
panel->childSetEnabled("access_combo", gAgent.isGodlike() || (region && region->canManageEstate() && !teen_grid));
|
|
panel->setCtrlsEnabled(allow_modify);
|
|
|
|
|
|
// DEBUG PANEL
|
|
panel = tab->getChild<LLPanel>("Debug");
|
|
|
|
panel->childSetValue("region_text", LLSD(sim_name) );
|
|
panel->childSetValue("disable_scripts_check", LLSD((BOOL)(region_flags & REGION_FLAGS_SKIP_SCRIPTS)) );
|
|
panel->childSetValue("disable_collisions_check", LLSD((BOOL)(region_flags & REGION_FLAGS_SKIP_COLLISIONS)) );
|
|
panel->childSetValue("disable_physics_check", LLSD((BOOL)(region_flags & REGION_FLAGS_SKIP_PHYSICS)) );
|
|
panel->setCtrlsEnabled(allow_modify);
|
|
|
|
// TERRAIN PANEL
|
|
panel = tab->getChild<LLPanel>("Terrain");
|
|
|
|
panel->childSetValue("region_text", LLSD(sim_name));
|
|
panel->childSetValue("water_height_spin", LLSD(water_height));
|
|
panel->childSetValue("terrain_raise_spin", LLSD(terrain_raise_limit));
|
|
panel->childSetValue("terrain_lower_spin", LLSD(terrain_lower_limit));
|
|
panel->childSetValue("use_estate_sun_check", LLSD(use_estate_sun));
|
|
|
|
panel->childSetValue("fixed_sun_check", LLSD((BOOL)(region_flags & REGION_FLAGS_SUN_FIXED)));
|
|
panel->childSetEnabled("fixed_sun_check", allow_modify && !use_estate_sun);
|
|
panel->childSetValue("sun_hour_slider", LLSD(sun_hour));
|
|
panel->childSetEnabled("sun_hour_slider", allow_modify && !use_estate_sun);
|
|
panel->setCtrlsEnabled(allow_modify);
|
|
|
|
getInstance()->refreshFromRegion( gAgent.getRegion() );
|
|
}
|
|
|
|
// static
|
|
LLPanelEstateInfo* LLFloaterRegionInfo::getPanelEstate()
|
|
{
|
|
LLFloaterRegionInfo* floater = LLFloaterRegionInfo::getInstance();
|
|
if (!floater) return NULL;
|
|
LLTabContainer* tab = floater->getChild<LLTabContainer>("region_panels");
|
|
LLPanelEstateInfo* panel = (LLPanelEstateInfo*)tab->getChild<LLPanel>("Estate");
|
|
return panel;
|
|
}
|
|
|
|
// static
|
|
LLPanelEstateCovenant* LLFloaterRegionInfo::getPanelCovenant()
|
|
{
|
|
LLFloaterRegionInfo* floater = LLFloaterRegionInfo::getInstance();
|
|
if (!floater) return NULL;
|
|
LLTabContainer* tab = floater->getChild<LLTabContainer>("region_panels");
|
|
LLPanelEstateCovenant* panel = (LLPanelEstateCovenant*)tab->getChild<LLPanel>("Covenant");
|
|
return panel;
|
|
}
|
|
|
|
void LLFloaterRegionInfo::refreshFromRegion(LLViewerRegion* region)
|
|
{
|
|
// call refresh from region on all panels
|
|
std::for_each(
|
|
mInfoPanels.begin(),
|
|
mInfoPanels.end(),
|
|
llbind2nd(
|
|
#if LL_WINDOWS
|
|
std::mem_fun1(&LLPanelRegionInfo::refreshFromRegion),
|
|
#else
|
|
std::mem_fun(&LLPanelRegionInfo::refreshFromRegion),
|
|
#endif
|
|
region));
|
|
}
|
|
|
|
// public
|
|
void LLFloaterRegionInfo::refresh()
|
|
{
|
|
for(info_panels_t::iterator iter = mInfoPanels.begin();
|
|
iter != mInfoPanels.end(); ++iter)
|
|
{
|
|
(*iter)->refresh();
|
|
}
|
|
}
|
|
|
|
|
|
///----------------------------------------------------------------------------
|
|
/// Local class implementation
|
|
///----------------------------------------------------------------------------
|
|
|
|
//
|
|
// LLPanelRegionInfo
|
|
//
|
|
|
|
// static
|
|
void LLPanelRegionInfo::onBtnSet(void* user_data)
|
|
{
|
|
LLPanelRegionInfo* panel = (LLPanelRegionInfo*)user_data;
|
|
if(!panel) return;
|
|
if (panel->sendUpdate())
|
|
{
|
|
panel->disableButton("apply_btn");
|
|
}
|
|
}
|
|
|
|
//static
|
|
void LLPanelRegionInfo::onChangeChildCtrl(LLUICtrl* ctrl, void* user_data)
|
|
{
|
|
if (ctrl)
|
|
{
|
|
LLPanelRegionInfo* panel = (LLPanelRegionInfo*) ctrl->getParent();
|
|
panel->updateChild(ctrl);
|
|
}
|
|
}
|
|
|
|
// static
|
|
// Enables the "set" button if it is not already enabled
|
|
void LLPanelRegionInfo::onChangeAnything(LLUICtrl* ctrl, void* user_data)
|
|
{
|
|
LLPanelRegionInfo* panel = (LLPanelRegionInfo*)user_data;
|
|
if(panel)
|
|
{
|
|
panel->enableButton("apply_btn");
|
|
panel->refresh();
|
|
}
|
|
}
|
|
|
|
// static
|
|
// Enables set button on change to line editor
|
|
void LLPanelRegionInfo::onChangeText(LLLineEditor* caller, void* user_data)
|
|
{
|
|
// reuse the previous method
|
|
onChangeAnything(0, user_data);
|
|
}
|
|
|
|
|
|
// virtual
|
|
BOOL LLPanelRegionInfo::postBuild()
|
|
{
|
|
childSetAction("apply_btn", onBtnSet, this);
|
|
childDisable("apply_btn");
|
|
refresh();
|
|
return TRUE;
|
|
}
|
|
|
|
// virtual
|
|
void LLPanelRegionInfo::updateChild(LLUICtrl* child_ctr)
|
|
{
|
|
}
|
|
|
|
// virtual
|
|
bool LLPanelRegionInfo::refreshFromRegion(LLViewerRegion* region)
|
|
{
|
|
if (region) mHost = region->getHost();
|
|
return true;
|
|
}
|
|
|
|
void LLPanelRegionInfo::sendEstateOwnerMessage(
|
|
LLMessageSystem* msg,
|
|
const std::string& request,
|
|
const LLUUID& invoice,
|
|
const strings_t& strings)
|
|
{
|
|
llinfos << "Sending estate request '" << request << "'" << llendl;
|
|
msg->newMessage("EstateOwnerMessage");
|
|
msg->nextBlockFast(_PREHASH_AgentData);
|
|
msg->addUUIDFast(_PREHASH_AgentID, gAgent.getID());
|
|
msg->addUUIDFast(_PREHASH_SessionID, gAgent.getSessionID());
|
|
msg->addUUIDFast(_PREHASH_TransactionID, LLUUID::null); //not used
|
|
msg->nextBlock("MethodData");
|
|
msg->addString("Method", request);
|
|
msg->addUUID("Invoice", invoice);
|
|
if(strings.empty())
|
|
{
|
|
msg->nextBlock("ParamList");
|
|
msg->addString("Parameter", NULL);
|
|
}
|
|
else
|
|
{
|
|
strings_t::const_iterator it = strings.begin();
|
|
strings_t::const_iterator end = strings.end();
|
|
for(; it != end; ++it)
|
|
{
|
|
msg->nextBlock("ParamList");
|
|
msg->addString("Parameter", *it);
|
|
}
|
|
}
|
|
msg->sendReliable(mHost);
|
|
}
|
|
|
|
void LLPanelRegionInfo::enableButton(const std::string& btn_name, BOOL enable)
|
|
{
|
|
childSetEnabled(btn_name, enable);
|
|
}
|
|
|
|
void LLPanelRegionInfo::disableButton(const std::string& btn_name)
|
|
{
|
|
childDisable(btn_name);
|
|
}
|
|
|
|
void LLPanelRegionInfo::initCtrl(const std::string& name)
|
|
{
|
|
childSetCommitCallback(name, onChangeAnything, this);
|
|
}
|
|
|
|
void LLPanelRegionInfo::initHelpBtn(const std::string& name, const std::string& xml_alert)
|
|
{
|
|
childSetAction(name, onClickHelp, new std::string(xml_alert));
|
|
}
|
|
|
|
// static
|
|
void LLPanelRegionInfo::onClickHelp(void* data)
|
|
{
|
|
std::string* xml_alert = (std::string*)data;
|
|
LLNotifications::instance().add(*xml_alert);
|
|
}
|
|
|
|
/////////////////////////////////////////////////////////////////////////////
|
|
// LLPanelRegionGeneralInfo
|
|
//
|
|
bool LLPanelRegionGeneralInfo::refreshFromRegion(LLViewerRegion* region)
|
|
{
|
|
BOOL allow_modify = gAgent.isGodlike() || (region && region->canManageEstate());
|
|
setCtrlsEnabled(allow_modify);
|
|
childDisable("apply_btn");
|
|
childSetEnabled("access_text", allow_modify);
|
|
// childSetEnabled("access_combo", allow_modify);
|
|
// now set in processRegionInfo for teen grid detection
|
|
childSetEnabled("kick_btn", allow_modify);
|
|
childSetEnabled("kick_all_btn", allow_modify);
|
|
childSetEnabled("assign_btn", allow_modify);
|
|
childSetEnabled("manage_telehub_btn", allow_modify);
|
|
|
|
// Data gets filled in by processRegionInfo
|
|
|
|
return LLPanelRegionInfo::refreshFromRegion(region);
|
|
}
|
|
|
|
BOOL LLPanelRegionGeneralInfo::postBuild()
|
|
{
|
|
// Enable the "Apply" button if something is changed. JC
|
|
initCtrl("block_terraform_check");
|
|
initCtrl("block_fly_check");
|
|
initCtrl("allow_damage_check");
|
|
initCtrl("allow_land_resell_check");
|
|
initCtrl("allow_parcel_changes_check");
|
|
initCtrl("agent_limit_spin");
|
|
initCtrl("object_bonus_spin");
|
|
initCtrl("access_combo");
|
|
initCtrl("restrict_pushobject");
|
|
initCtrl("block_parcel_search_check");
|
|
|
|
initHelpBtn("terraform_help", "HelpRegionBlockTerraform");
|
|
initHelpBtn("fly_help", "HelpRegionBlockFly");
|
|
initHelpBtn("damage_help", "HelpRegionAllowDamage");
|
|
initHelpBtn("agent_limit_help", "HelpRegionAgentLimit");
|
|
initHelpBtn("object_bonus_help", "HelpRegionObjectBonus");
|
|
initHelpBtn("access_help", "HelpRegionMaturity");
|
|
initHelpBtn("restrict_pushobject_help", "HelpRegionRestrictPushObject");
|
|
initHelpBtn("land_resell_help", "HelpRegionLandResell");
|
|
initHelpBtn("parcel_changes_help", "HelpParcelChanges");
|
|
initHelpBtn("parcel_search_help", "HelpRegionSearch");
|
|
|
|
childSetAction("kick_btn", onClickKick, this);
|
|
childSetAction("kick_all_btn", onClickKickAll, this);
|
|
childSetAction("im_btn", onClickMessage, this);
|
|
childSetAction("manage_telehub_btn", onClickManageTelehub, this);
|
|
|
|
return LLPanelRegionInfo::postBuild();
|
|
}
|
|
|
|
// static
|
|
void LLPanelRegionGeneralInfo::onClickKick(void* userdata)
|
|
{
|
|
llinfos << "LLPanelRegionGeneralInfo::onClickKick" << llendl;
|
|
LLPanelRegionGeneralInfo* panelp = (LLPanelRegionGeneralInfo*)userdata;
|
|
|
|
// this depends on the grandparent view being a floater
|
|
// in order to set up floater dependency
|
|
LLFloater* parent_floater = gFloaterView->getParentFloater(panelp);
|
|
LLFloater* child_floater = LLFloaterAvatarPicker::show(onKickCommit, userdata, FALSE, TRUE);
|
|
parent_floater->addDependentFloater(child_floater);
|
|
}
|
|
|
|
// static
|
|
void LLPanelRegionGeneralInfo::onKickCommit(const std::vector<std::string>& names, const std::vector<LLUUID>& ids, void* userdata)
|
|
{
|
|
if (names.empty() || ids.empty()) return;
|
|
if(ids[0].notNull())
|
|
{
|
|
LLPanelRegionGeneralInfo* self = (LLPanelRegionGeneralInfo*)userdata;
|
|
if(!self) return;
|
|
strings_t strings;
|
|
// [0] = our agent id
|
|
// [1] = target agent id
|
|
std::string buffer;
|
|
gAgent.getID().toString(buffer);
|
|
strings.push_back(buffer);
|
|
|
|
ids[0].toString(buffer);
|
|
strings.push_back(strings_t::value_type(buffer));
|
|
|
|
LLUUID invoice(LLFloaterRegionInfo::getLastInvoice());
|
|
self->sendEstateOwnerMessage(gMessageSystem, "teleporthomeuser", invoice, strings);
|
|
}
|
|
}
|
|
|
|
// static
|
|
void LLPanelRegionGeneralInfo::onClickKickAll(void* userdata)
|
|
{
|
|
llinfos << "LLPanelRegionGeneralInfo::onClickKickAll" << llendl;
|
|
LLNotifications::instance().add("KickUsersFromRegion",
|
|
LLSD(),
|
|
LLSD(),
|
|
boost::bind(&LLPanelRegionGeneralInfo::onKickAllCommit, (LLPanelRegionGeneralInfo*)userdata, _1, _2));
|
|
}
|
|
|
|
bool LLPanelRegionGeneralInfo::onKickAllCommit(const LLSD& notification, const LLSD& response)
|
|
{
|
|
S32 option = LLNotification::getSelectedOption(notification, response);
|
|
if (option == 0)
|
|
{
|
|
strings_t strings;
|
|
// [0] = our agent id
|
|
std::string buffer;
|
|
gAgent.getID().toString(buffer);
|
|
strings.push_back(buffer);
|
|
|
|
LLUUID invoice(LLFloaterRegionInfo::getLastInvoice());
|
|
// historical message name
|
|
sendEstateOwnerMessage(gMessageSystem, "teleporthomeallusers", invoice, strings);
|
|
}
|
|
return false;
|
|
}
|
|
|
|
// static
|
|
void LLPanelRegionGeneralInfo::onClickMessage(void* userdata)
|
|
{
|
|
llinfos << "LLPanelRegionGeneralInfo::onClickMessage" << llendl;
|
|
LLNotifications::instance().add("MessageRegion",
|
|
LLSD(),
|
|
LLSD(),
|
|
boost::bind(&LLPanelRegionGeneralInfo::onMessageCommit, (LLPanelRegionGeneralInfo*)userdata, _1, _2));
|
|
}
|
|
|
|
// static
|
|
bool LLPanelRegionGeneralInfo::onMessageCommit(const LLSD& notification, const LLSD& response)
|
|
{
|
|
if(LLNotification::getSelectedOption(notification, response) != 0) return false;
|
|
|
|
std::string text = response["message"].asString();
|
|
if (text.empty()) return false;
|
|
|
|
llinfos << "Message to everyone: " << text << llendl;
|
|
strings_t strings;
|
|
// [0] grid_x, unused here
|
|
// [1] grid_y, unused here
|
|
// [2] agent_id of sender
|
|
// [3] sender name
|
|
// [4] message
|
|
strings.push_back("-1");
|
|
strings.push_back("-1");
|
|
std::string buffer;
|
|
gAgent.getID().toString(buffer);
|
|
strings.push_back(buffer);
|
|
std::string name;
|
|
gAgent.buildFullname(name);
|
|
strings.push_back(strings_t::value_type(name));
|
|
strings.push_back(strings_t::value_type(text));
|
|
LLUUID invoice(LLFloaterRegionInfo::getLastInvoice());
|
|
sendEstateOwnerMessage(gMessageSystem, "simulatormessage", invoice, strings);
|
|
return false;
|
|
}
|
|
|
|
// static
|
|
void LLPanelRegionGeneralInfo::onClickManageTelehub(void* data)
|
|
{
|
|
LLFloaterRegionInfo::getInstance()->close();
|
|
|
|
LLFloaterTelehub::show();
|
|
}
|
|
|
|
// setregioninfo
|
|
// strings[0] = 'Y' - block terraform, 'N' - not
|
|
// strings[1] = 'Y' - block fly, 'N' - not
|
|
// strings[2] = 'Y' - allow damage, 'N' - not
|
|
// strings[3] = 'Y' - allow land sale, 'N' - not
|
|
// strings[4] = agent limit
|
|
// strings[5] = object bonus
|
|
// strings[6] = sim access (0 = unknown, 13 = PG, 21 = Mature, 42 = Adult)
|
|
// strings[7] = restrict pushobject
|
|
// strings[8] = 'Y' - allow parcel subdivide, 'N' - not
|
|
// strings[9] = 'Y' - block parcel search, 'N' - allow
|
|
BOOL LLPanelRegionGeneralInfo::sendUpdate()
|
|
{
|
|
llinfos << "LLPanelRegionGeneralInfo::sendUpdate()" << llendl;
|
|
|
|
// First try using a Cap. If that fails use the old method.
|
|
LLSD body;
|
|
std::string url = gAgent.getRegion()->getCapability("DispatchRegionInfo");
|
|
if (!url.empty())
|
|
{
|
|
body["block_terraform"] = childGetValue("block_terraform_check");
|
|
body["block_fly"] = childGetValue("block_fly_check");
|
|
body["allow_damage"] = childGetValue("allow_damage_check");
|
|
body["allow_land_resell"] = childGetValue("allow_land_resell_check");
|
|
body["agent_limit"] = childGetValue("agent_limit_spin");
|
|
body["prim_bonus"] = childGetValue("object_bonus_spin");
|
|
body["sim_access"] = childGetValue("access_combo");
|
|
body["restrict_pushobject"] = childGetValue("restrict_pushobject");
|
|
body["allow_parcel_changes"] = childGetValue("allow_parcel_changes_check");
|
|
body["block_parcel_search"] = childGetValue("block_parcel_search_check");
|
|
|
|
LLHTTPClient::post(url, body, new LLHTTPClient::Responder());
|
|
}
|
|
else
|
|
{
|
|
strings_t strings;
|
|
std::string buffer;
|
|
|
|
buffer = llformat("%s", (childGetValue("block_terraform_check").asBoolean() ? "Y" : "N"));
|
|
strings.push_back(strings_t::value_type(buffer));
|
|
|
|
buffer = llformat("%s", (childGetValue("block_fly_check").asBoolean() ? "Y" : "N"));
|
|
strings.push_back(strings_t::value_type(buffer));
|
|
|
|
buffer = llformat("%s", (childGetValue("allow_damage_check").asBoolean() ? "Y" : "N"));
|
|
strings.push_back(strings_t::value_type(buffer));
|
|
|
|
buffer = llformat("%s", (childGetValue("allow_land_resell_check").asBoolean() ? "Y" : "N"));
|
|
strings.push_back(strings_t::value_type(buffer));
|
|
|
|
F32 value = (F32)childGetValue("agent_limit_spin").asReal();
|
|
buffer = llformat("%f", value);
|
|
strings.push_back(strings_t::value_type(buffer));
|
|
|
|
value = (F32)childGetValue("object_bonus_spin").asReal();
|
|
buffer = llformat("%f", value);
|
|
strings.push_back(strings_t::value_type(buffer));
|
|
|
|
buffer = llformat("%d", childGetValue("access_combo").asInteger());
|
|
strings.push_back(strings_t::value_type(buffer));
|
|
|
|
buffer = llformat("%s", (childGetValue("restrict_pushobject").asBoolean() ? "Y" : "N"));
|
|
strings.push_back(strings_t::value_type(buffer));
|
|
|
|
buffer = llformat("%s", (childGetValue("allow_parcel_changes_check").asBoolean() ? "Y" : "N"));
|
|
strings.push_back(strings_t::value_type(buffer));
|
|
|
|
LLUUID invoice(LLFloaterRegionInfo::getLastInvoice());
|
|
sendEstateOwnerMessage(gMessageSystem, "setregioninfo", invoice, strings);
|
|
}
|
|
|
|
// if we changed access levels, tell user about it
|
|
LLViewerRegion* region = gAgent.getRegion();
|
|
if (region && (childGetValue("access_combo").asInteger() != region->getSimAccess()) )
|
|
{
|
|
LLNotifications::instance().add("RegionMaturityChange");
|
|
}
|
|
|
|
return TRUE;
|
|
}
|
|
|
|
/////////////////////////////////////////////////////////////////////////////
|
|
// LLPanelRegionDebugInfo
|
|
/////////////////////////////////////////////////////////////////////////////
|
|
BOOL LLPanelRegionDebugInfo::postBuild()
|
|
{
|
|
LLPanelRegionInfo::postBuild();
|
|
initCtrl("disable_scripts_check");
|
|
initCtrl("disable_collisions_check");
|
|
initCtrl("disable_physics_check");
|
|
|
|
initHelpBtn("disable_scripts_help", "HelpRegionDisableScripts");
|
|
initHelpBtn("disable_collisions_help", "HelpRegionDisableCollisions");
|
|
initHelpBtn("disable_physics_help", "HelpRegionDisablePhysics");
|
|
initHelpBtn("top_colliders_help", "HelpRegionTopColliders");
|
|
initHelpBtn("top_scripts_help", "HelpRegionTopScripts");
|
|
initHelpBtn("restart_help", "HelpRegionRestart");
|
|
|
|
childSetAction("choose_avatar_btn", onClickChooseAvatar, this);
|
|
childSetAction("return_btn", onClickReturn, this);
|
|
childSetAction("top_colliders_btn", onClickTopColliders, this);
|
|
childSetAction("top_scripts_btn", onClickTopScripts, this);
|
|
childSetAction("restart_btn", onClickRestart, this);
|
|
childSetAction("cancel_restart_btn", onClickCancelRestart, this);
|
|
|
|
return TRUE;
|
|
}
|
|
|
|
// virtual
|
|
bool LLPanelRegionDebugInfo::refreshFromRegion(LLViewerRegion* region)
|
|
{
|
|
BOOL allow_modify = gAgent.isGodlike() || (region && region->canManageEstate());
|
|
setCtrlsEnabled(allow_modify);
|
|
childDisable("apply_btn");
|
|
childDisable("target_avatar_name");
|
|
|
|
childSetEnabled("choose_avatar_btn", allow_modify);
|
|
childSetEnabled("return_scripts", allow_modify && !mTargetAvatar.isNull());
|
|
childSetEnabled("return_other_land", allow_modify && !mTargetAvatar.isNull());
|
|
childSetEnabled("return_estate_wide", allow_modify && !mTargetAvatar.isNull());
|
|
childSetEnabled("return_btn", allow_modify && !mTargetAvatar.isNull());
|
|
childSetEnabled("top_colliders_btn", allow_modify);
|
|
childSetEnabled("top_scripts_btn", allow_modify);
|
|
childSetEnabled("restart_btn", allow_modify);
|
|
childSetEnabled("cancel_restart_btn", allow_modify);
|
|
|
|
return LLPanelRegionInfo::refreshFromRegion(region);
|
|
}
|
|
|
|
// virtual
|
|
BOOL LLPanelRegionDebugInfo::sendUpdate()
|
|
{
|
|
llinfos << "LLPanelRegionDebugInfo::sendUpdate" << llendl;
|
|
strings_t strings;
|
|
std::string buffer;
|
|
|
|
buffer = llformat("%s", (childGetValue("disable_scripts_check").asBoolean() ? "Y" : "N"));
|
|
strings.push_back(buffer);
|
|
|
|
buffer = llformat("%s", (childGetValue("disable_collisions_check").asBoolean() ? "Y" : "N"));
|
|
strings.push_back(buffer);
|
|
|
|
buffer = llformat("%s", (childGetValue("disable_physics_check").asBoolean() ? "Y" : "N"));
|
|
strings.push_back(buffer);
|
|
|
|
LLUUID invoice(LLFloaterRegionInfo::getLastInvoice());
|
|
sendEstateOwnerMessage(gMessageSystem, "setregiondebug", invoice, strings);
|
|
return TRUE;
|
|
}
|
|
|
|
void LLPanelRegionDebugInfo::onClickChooseAvatar(void* data)
|
|
{
|
|
LLFloaterAvatarPicker::show(callbackAvatarID, data, FALSE, TRUE);
|
|
}
|
|
|
|
// static
|
|
void LLPanelRegionDebugInfo::callbackAvatarID(const std::vector<std::string>& names, const std::vector<LLUUID>& ids, void* data)
|
|
{
|
|
LLPanelRegionDebugInfo* self = (LLPanelRegionDebugInfo*) data;
|
|
if (ids.empty() || names.empty()) return;
|
|
self->mTargetAvatar = ids[0];
|
|
self->childSetValue("target_avatar_name", LLSD(names[0]));
|
|
self->refreshFromRegion( gAgent.getRegion() );
|
|
}
|
|
|
|
// static
|
|
void LLPanelRegionDebugInfo::onClickReturn(void* data)
|
|
{
|
|
LLPanelRegionDebugInfo* panelp = (LLPanelRegionDebugInfo*) data;
|
|
if (panelp->mTargetAvatar.isNull()) return;
|
|
|
|
LLSD args;
|
|
args["USER_NAME"] = panelp->childGetValue("target_avatar_name").asString();
|
|
LLSD payload;
|
|
payload["avatar_id"] = panelp->mTargetAvatar;
|
|
|
|
U32 flags = SWD_ALWAYS_RETURN_OBJECTS;
|
|
|
|
if (panelp->childGetValue("return_scripts").asBoolean())
|
|
{
|
|
flags |= SWD_SCRIPTED_ONLY;
|
|
}
|
|
|
|
if (panelp->childGetValue("return_other_land").asBoolean())
|
|
{
|
|
flags |= SWD_OTHERS_LAND_ONLY;
|
|
}
|
|
payload["flags"] = int(flags);
|
|
payload["return_estate_wide"] = panelp->childGetValue("return_estate_wide").asBoolean();
|
|
LLNotifications::instance().add("EstateObjectReturn", args, payload,
|
|
boost::bind(&LLPanelRegionDebugInfo::callbackReturn, panelp, _1, _2));
|
|
}
|
|
|
|
bool LLPanelRegionDebugInfo::callbackReturn(const LLSD& notification, const LLSD& response)
|
|
{
|
|
S32 option = LLNotification::getSelectedOption(notification, response);
|
|
if (option != 0) return false;
|
|
|
|
LLUUID target_avatar = notification["payload"]["avatar_id"].asUUID();
|
|
if (!target_avatar.isNull())
|
|
{
|
|
U32 flags = notification["payload"]["flags"].asInteger();
|
|
bool return_estate_wide = notification["payload"]["return_estate_wide"];
|
|
if (return_estate_wide)
|
|
{
|
|
// send as estate message - routed by spaceserver to all regions in estate
|
|
strings_t strings;
|
|
strings.push_back(llformat("%d", flags));
|
|
strings.push_back(target_avatar.asString());
|
|
|
|
LLUUID invoice(LLFloaterRegionInfo::getLastInvoice());
|
|
|
|
sendEstateOwnerMessage(gMessageSystem, "estateobjectreturn", invoice, strings);
|
|
}
|
|
else
|
|
{
|
|
// send to this simulator only
|
|
send_sim_wide_deletes(target_avatar, flags);
|
|
}
|
|
}
|
|
return false;
|
|
}
|
|
|
|
|
|
// static
|
|
void LLPanelRegionDebugInfo::onClickTopColliders(void* data)
|
|
{
|
|
LLPanelRegionDebugInfo* self = (LLPanelRegionDebugInfo*)data;
|
|
strings_t strings;
|
|
strings.push_back("1"); // one physics step
|
|
LLUUID invoice(LLFloaterRegionInfo::getLastInvoice());
|
|
LLFloaterTopObjects::show();
|
|
LLFloaterTopObjects::clearList();
|
|
self->sendEstateOwnerMessage(gMessageSystem, "colliders", invoice, strings);
|
|
}
|
|
|
|
// static
|
|
void LLPanelRegionDebugInfo::onClickTopScripts(void* data)
|
|
{
|
|
LLPanelRegionDebugInfo* self = (LLPanelRegionDebugInfo*)data;
|
|
strings_t strings;
|
|
strings.push_back("6"); // top 5 scripts
|
|
LLUUID invoice(LLFloaterRegionInfo::getLastInvoice());
|
|
LLFloaterTopObjects::show();
|
|
LLFloaterTopObjects::clearList();
|
|
self->sendEstateOwnerMessage(gMessageSystem, "scripts", invoice, strings);
|
|
}
|
|
|
|
// static
|
|
void LLPanelRegionDebugInfo::onClickRestart(void* data)
|
|
{
|
|
LLNotifications::instance().add("ConfirmRestart", LLSD(), LLSD(),
|
|
boost::bind(&LLPanelRegionDebugInfo::callbackRestart, (LLPanelRegionDebugInfo*)data, _1, _2));
|
|
}
|
|
|
|
bool LLPanelRegionDebugInfo::callbackRestart(const LLSD& notification, const LLSD& response)
|
|
{
|
|
S32 option = LLNotification::getSelectedOption(notification, response);
|
|
if (option != 0) return false;
|
|
|
|
strings_t strings;
|
|
strings.push_back("120");
|
|
LLUUID invoice(LLFloaterRegionInfo::getLastInvoice());
|
|
sendEstateOwnerMessage(gMessageSystem, "restart", invoice, strings);
|
|
return false;
|
|
}
|
|
|
|
// static
|
|
void LLPanelRegionDebugInfo::onClickCancelRestart(void* data)
|
|
{
|
|
LLPanelRegionDebugInfo* self = (LLPanelRegionDebugInfo*)data;
|
|
strings_t strings;
|
|
strings.push_back("-1");
|
|
LLUUID invoice(LLFloaterRegionInfo::getLastInvoice());
|
|
self->sendEstateOwnerMessage(gMessageSystem, "restart", invoice, strings);
|
|
}
|
|
|
|
|
|
/////////////////////////////////////////////////////////////////////////////
|
|
// LLPanelRegionTextureInfo
|
|
//
|
|
LLPanelRegionTextureInfo::LLPanelRegionTextureInfo() : LLPanelRegionInfo()
|
|
{
|
|
// nothing.
|
|
}
|
|
|
|
bool LLPanelRegionTextureInfo::refreshFromRegion(LLViewerRegion* region)
|
|
{
|
|
BOOL allow_modify = gAgent.isGodlike() || (region && region->canManageEstate());
|
|
setCtrlsEnabled(allow_modify);
|
|
childDisable("apply_btn");
|
|
|
|
if (region)
|
|
{
|
|
childSetValue("region_text", LLSD(region->getName()));
|
|
}
|
|
else
|
|
{
|
|
childSetValue("region_text", LLSD(""));
|
|
}
|
|
|
|
if (!region) return LLPanelRegionInfo::refreshFromRegion(region);
|
|
|
|
LLVLComposition* compp = region->getComposition();
|
|
LLTextureCtrl* texture_ctrl;
|
|
std::string buffer;
|
|
for(S32 i = 0; i < TERRAIN_TEXTURE_COUNT; ++i)
|
|
{
|
|
buffer = llformat("texture_detail_%d", i);
|
|
texture_ctrl = getChild<LLTextureCtrl>(buffer);
|
|
if(texture_ctrl)
|
|
{
|
|
lldebugs << "Detail Texture " << i << ": "
|
|
<< compp->getDetailTextureID(i) << llendl;
|
|
LLUUID tmp_id(compp->getDetailTextureID(i));
|
|
texture_ctrl->setImageAssetID(tmp_id);
|
|
}
|
|
}
|
|
|
|
for(S32 i = 0; i < CORNER_COUNT; ++i)
|
|
{
|
|
buffer = llformat("height_start_spin_%d", i);
|
|
childSetValue(buffer, LLSD(compp->getStartHeight(i)));
|
|
buffer = llformat("height_range_spin_%d", i);
|
|
childSetValue(buffer, LLSD(compp->getHeightRange(i)));
|
|
}
|
|
|
|
// Call the parent for common book-keeping
|
|
return LLPanelRegionInfo::refreshFromRegion(region);
|
|
}
|
|
|
|
|
|
BOOL LLPanelRegionTextureInfo::postBuild()
|
|
{
|
|
LLPanelRegionInfo::postBuild();
|
|
std::string buffer;
|
|
for(S32 i = 0; i < TERRAIN_TEXTURE_COUNT; ++i)
|
|
{
|
|
buffer = llformat("texture_detail_%d", i);
|
|
initCtrl(buffer);
|
|
}
|
|
|
|
for(S32 i = 0; i < CORNER_COUNT; ++i)
|
|
{
|
|
buffer = llformat("height_start_spin_%d", i);
|
|
initCtrl(buffer);
|
|
buffer = llformat("height_range_spin_%d", i);
|
|
initCtrl(buffer);
|
|
}
|
|
|
|
// LLButton* btn = new LLButton("dump", LLRect(0, 20, 100, 0), "", onClickDump, this);
|
|
// btn->setFollows(FOLLOWS_TOP|FOLLOWS_LEFT);
|
|
// addChild(btn);
|
|
|
|
return LLPanelRegionInfo::postBuild();
|
|
}
|
|
|
|
BOOL LLPanelRegionTextureInfo::sendUpdate()
|
|
{
|
|
llinfos << "LLPanelRegionTextureInfo::sendUpdate()" << llendl;
|
|
|
|
// Make sure user hasn't chosen wacky textures.
|
|
if (!validateTextureSizes())
|
|
{
|
|
return FALSE;
|
|
}
|
|
|
|
LLTextureCtrl* texture_ctrl;
|
|
std::string buffer;
|
|
std::string id_str;
|
|
LLMessageSystem* msg = gMessageSystem;
|
|
strings_t strings;
|
|
|
|
LLUUID invoice(LLFloaterRegionInfo::getLastInvoice());
|
|
|
|
for(S32 i = 0; i < TERRAIN_TEXTURE_COUNT; ++i)
|
|
{
|
|
buffer = llformat("texture_detail_%d", i);
|
|
texture_ctrl = getChild<LLTextureCtrl>(buffer);
|
|
if(texture_ctrl)
|
|
{
|
|
LLUUID tmp_id(texture_ctrl->getImageAssetID());
|
|
tmp_id.toString(id_str);
|
|
buffer = llformat("%d %s", i, id_str.c_str());
|
|
strings.push_back(buffer);
|
|
}
|
|
}
|
|
sendEstateOwnerMessage(msg, "texturedetail", invoice, strings);
|
|
strings.clear();
|
|
for(S32 i = 0; i < CORNER_COUNT; ++i)
|
|
{
|
|
buffer = llformat("height_start_spin_%d", i);
|
|
std::string buffer2 = llformat("height_range_spin_%d", i);
|
|
std::string buffer3 = llformat("%d %f %f", i, (F32)childGetValue(buffer).asReal(), (F32)childGetValue(buffer2).asReal());
|
|
strings.push_back(buffer3);
|
|
}
|
|
sendEstateOwnerMessage(msg, "textureheights", invoice, strings);
|
|
strings.clear();
|
|
sendEstateOwnerMessage(msg, "texturecommit", invoice, strings);
|
|
return TRUE;
|
|
}
|
|
|
|
BOOL LLPanelRegionTextureInfo::validateTextureSizes()
|
|
{
|
|
for(S32 i = 0; i < TERRAIN_TEXTURE_COUNT; ++i)
|
|
{
|
|
std::string buffer;
|
|
buffer = llformat("texture_detail_%d", i);
|
|
LLTextureCtrl* texture_ctrl = getChild<LLTextureCtrl>(buffer);
|
|
if (!texture_ctrl) continue;
|
|
|
|
LLUUID image_asset_id = texture_ctrl->getImageAssetID();
|
|
LLViewerTexture* img = LLViewerTextureManager::getFetchedTexture(image_asset_id);
|
|
S32 components = img->getComponents();
|
|
// Must ask for highest resolution version's width. JC
|
|
S32 width = img->getFullWidth();
|
|
S32 height = img->getFullHeight();
|
|
|
|
//llinfos << "texture detail " << i << " is " << width << "x" << height << "x" << components << llendl;
|
|
|
|
if (components != 3)
|
|
{
|
|
LLSD args;
|
|
args["TEXTURE_NUM"] = i+1;
|
|
args["TEXTURE_BIT_DEPTH"] = llformat("%d",components * 8);
|
|
LLNotifications::instance().add("InvalidTerrainBitDepth", args);
|
|
return FALSE;
|
|
}
|
|
|
|
if (width > 512 || height > 512)
|
|
{
|
|
|
|
LLSD args;
|
|
args["TEXTURE_NUM"] = i+1;
|
|
args["TEXTURE_SIZE_X"] = width;
|
|
args["TEXTURE_SIZE_Y"] = height;
|
|
LLNotifications::instance().add("InvalidTerrainSize", args);
|
|
return FALSE;
|
|
|
|
}
|
|
}
|
|
|
|
return TRUE;
|
|
}
|
|
|
|
|
|
// static
|
|
void LLPanelRegionTextureInfo::onClickDump(void* data)
|
|
{
|
|
llinfos << "LLPanelRegionTextureInfo::onClickDump()" << llendl;
|
|
}
|
|
|
|
|
|
/////////////////////////////////////////////////////////////////////////////
|
|
// LLPanelRegionTerrainInfo
|
|
/////////////////////////////////////////////////////////////////////////////
|
|
BOOL LLPanelRegionTerrainInfo::postBuild()
|
|
{
|
|
LLPanelRegionInfo::postBuild();
|
|
|
|
initHelpBtn("water_height_help", "HelpRegionWaterHeight");
|
|
initHelpBtn("terrain_raise_help", "HelpRegionTerrainRaise");
|
|
initHelpBtn("terrain_lower_help", "HelpRegionTerrainLower");
|
|
initHelpBtn("upload_raw_help", "HelpRegionUploadRaw");
|
|
initHelpBtn("download_raw_help", "HelpRegionDownloadRaw");
|
|
initHelpBtn("use_estate_sun_help", "HelpRegionUseEstateSun");
|
|
initHelpBtn("fixed_sun_help", "HelpRegionFixedSun");
|
|
initHelpBtn("bake_terrain_help", "HelpRegionBakeTerrain");
|
|
|
|
initCtrl("water_height_spin");
|
|
initCtrl("terrain_raise_spin");
|
|
initCtrl("terrain_lower_spin");
|
|
|
|
initCtrl("fixed_sun_check");
|
|
childSetCommitCallback("fixed_sun_check", onChangeFixedSun, this);
|
|
childSetCommitCallback("use_estate_sun_check", onChangeUseEstateTime, this);
|
|
childSetCommitCallback("sun_hour_slider", onChangeSunHour, this);
|
|
|
|
childSetAction("download_raw_btn", onClickDownloadRaw, this);
|
|
childSetAction("upload_raw_btn", onClickUploadRaw, this);
|
|
childSetAction("bake_terrain_btn", onClickBakeTerrain, this);
|
|
|
|
return TRUE;
|
|
}
|
|
|
|
// virtual
|
|
bool LLPanelRegionTerrainInfo::refreshFromRegion(LLViewerRegion* region)
|
|
{
|
|
llinfos << "LLPanelRegionTerrainInfo::refreshFromRegion" << llendl;
|
|
|
|
BOOL owner_or_god = gAgent.isGodlike()
|
|
|| (region && (region->getOwner() == gAgent.getID()));
|
|
BOOL owner_or_god_or_manager = owner_or_god
|
|
|| (region && region->isEstateManager());
|
|
setCtrlsEnabled(owner_or_god_or_manager);
|
|
childDisable("apply_btn");
|
|
|
|
childSetEnabled("download_raw_btn", owner_or_god);
|
|
childSetEnabled("upload_raw_btn", owner_or_god);
|
|
childSetEnabled("bake_terrain_btn", owner_or_god);
|
|
|
|
return LLPanelRegionInfo::refreshFromRegion(region);
|
|
}
|
|
|
|
// virtual
|
|
BOOL LLPanelRegionTerrainInfo::sendUpdate()
|
|
{
|
|
llinfos << "LLPanelRegionTerrainInfo::sendUpdate" << llendl;
|
|
std::string buffer;
|
|
strings_t strings;
|
|
LLUUID invoice(LLFloaterRegionInfo::getLastInvoice());
|
|
|
|
buffer = llformat("%f", (F32)childGetValue("water_height_spin").asReal());
|
|
strings.push_back(buffer);
|
|
buffer = llformat("%f", (F32)childGetValue("terrain_raise_spin").asReal());
|
|
strings.push_back(buffer);
|
|
buffer = llformat("%f", (F32)childGetValue("terrain_lower_spin").asReal());
|
|
strings.push_back(buffer);
|
|
buffer = llformat("%s", (childGetValue("use_estate_sun_check").asBoolean() ? "Y" : "N"));
|
|
strings.push_back(buffer);
|
|
buffer = llformat("%s", (childGetValue("fixed_sun_check").asBoolean() ? "Y" : "N"));
|
|
strings.push_back(buffer);
|
|
buffer = llformat("%f", (F32)childGetValue("sun_hour_slider").asReal() );
|
|
strings.push_back(buffer);
|
|
|
|
// Grab estate information in case the user decided to set the
|
|
// region back to estate time. JC
|
|
LLFloaterRegionInfo* floater = LLFloaterRegionInfo::getInstance();
|
|
if (!floater) return true;
|
|
|
|
LLTabContainer* tab = floater->getChild<LLTabContainer>("region_panels");
|
|
if (!tab) return true;
|
|
|
|
LLPanelEstateInfo* panel = (LLPanelEstateInfo*)tab->getChild<LLPanel>("Estate");
|
|
if (!panel) return true;
|
|
|
|
BOOL estate_global_time = panel->getGlobalTime();
|
|
BOOL estate_fixed_sun = panel->getFixedSun();
|
|
F32 estate_sun_hour;
|
|
if (estate_global_time)
|
|
{
|
|
estate_sun_hour = 0.f;
|
|
}
|
|
else
|
|
{
|
|
estate_sun_hour = panel->getSunHour();
|
|
}
|
|
|
|
buffer = llformat("%s", (estate_global_time ? "Y" : "N") );
|
|
strings.push_back(buffer);
|
|
buffer = llformat("%s", (estate_fixed_sun ? "Y" : "N") );
|
|
strings.push_back(buffer);
|
|
buffer = llformat("%f", estate_sun_hour);
|
|
strings.push_back(buffer);
|
|
|
|
sendEstateOwnerMessage(gMessageSystem, "setregionterrain", invoice, strings);
|
|
return TRUE;
|
|
}
|
|
|
|
// static
|
|
void LLPanelRegionTerrainInfo::onChangeUseEstateTime(LLUICtrl* ctrl, void* user_data)
|
|
{
|
|
LLPanelRegionTerrainInfo* panel = (LLPanelRegionTerrainInfo*) user_data;
|
|
if (!panel) return;
|
|
BOOL use_estate_sun = panel->childGetValue("use_estate_sun_check").asBoolean();
|
|
panel->childSetEnabled("fixed_sun_check", !use_estate_sun);
|
|
panel->childSetEnabled("sun_hour_slider", !use_estate_sun);
|
|
if (use_estate_sun)
|
|
{
|
|
panel->childSetValue("fixed_sun_check", LLSD(FALSE));
|
|
panel->childSetValue("sun_hour_slider", LLSD(0.f));
|
|
}
|
|
panel->childEnable("apply_btn");
|
|
}
|
|
|
|
// static
|
|
void LLPanelRegionTerrainInfo::onChangeFixedSun(LLUICtrl* ctrl, void* user_data)
|
|
{
|
|
LLPanelRegionTerrainInfo* panel = (LLPanelRegionTerrainInfo*) user_data;
|
|
if (!panel) return;
|
|
// Just enable the apply button. We let the sun-hour slider be enabled
|
|
// for both fixed-sun and non-fixed-sun. JC
|
|
panel->childEnable("apply_btn");
|
|
}
|
|
|
|
// static
|
|
void LLPanelRegionTerrainInfo::onChangeSunHour(LLUICtrl* ctrl, void*)
|
|
{
|
|
// can't use userdata to get panel, slider uses it internally
|
|
LLPanelRegionTerrainInfo* panel = (LLPanelRegionTerrainInfo*) ctrl->getParent();
|
|
if (!panel) return;
|
|
panel->childEnable("apply_btn");
|
|
}
|
|
|
|
// static
|
|
void LLPanelRegionTerrainInfo::onClickDownloadRaw(void* data)
|
|
{
|
|
LLFilePicker& picker = LLFilePicker::instance();
|
|
if (!picker.getSaveFile(LLFilePicker::FFSAVE_RAW, "terrain.raw"))
|
|
{
|
|
llwarns << "No file" << llendl;
|
|
return;
|
|
}
|
|
std::string filepath = picker.getFirstFile();
|
|
gXferManager->expectFileForRequest(filepath);
|
|
|
|
LLPanelRegionTerrainInfo* self = (LLPanelRegionTerrainInfo*)data;
|
|
strings_t strings;
|
|
strings.push_back("download filename");
|
|
strings.push_back(filepath);
|
|
LLUUID invoice(LLFloaterRegionInfo::getLastInvoice());
|
|
self->sendEstateOwnerMessage(gMessageSystem, "terrain", invoice, strings);
|
|
}
|
|
|
|
// static
|
|
void LLPanelRegionTerrainInfo::onClickUploadRaw(void* data)
|
|
{
|
|
LLFilePicker& picker = LLFilePicker::instance();
|
|
if (!picker.getOpenFile(LLFilePicker::FFLOAD_RAW))
|
|
{
|
|
llwarns << "No file" << llendl;
|
|
return;
|
|
}
|
|
std::string filepath = picker.getFirstFile();
|
|
gXferManager->expectFileForTransfer(filepath);
|
|
|
|
LLPanelRegionTerrainInfo* self = (LLPanelRegionTerrainInfo*)data;
|
|
strings_t strings;
|
|
strings.push_back("upload filename");
|
|
strings.push_back(filepath);
|
|
LLUUID invoice(LLFloaterRegionInfo::getLastInvoice());
|
|
self->sendEstateOwnerMessage(gMessageSystem, "terrain", invoice, strings);
|
|
|
|
LLNotifications::instance().add("RawUploadStarted");
|
|
}
|
|
|
|
// static
|
|
void LLPanelRegionTerrainInfo::onClickBakeTerrain(void* data)
|
|
{
|
|
LLNotifications::instance().add(
|
|
LLNotification::Params("ConfirmBakeTerrain")
|
|
.functor(boost::bind(&LLPanelRegionTerrainInfo::callbackBakeTerrain, (LLPanelRegionTerrainInfo*)data, _1, _2)));
|
|
}
|
|
|
|
bool LLPanelRegionTerrainInfo::callbackBakeTerrain(const LLSD& notification, const LLSD& response)
|
|
{
|
|
S32 option = LLNotification::getSelectedOption(notification, response);
|
|
if (option != 0) return false;
|
|
|
|
strings_t strings;
|
|
strings.push_back("bake");
|
|
LLUUID invoice(LLFloaterRegionInfo::getLastInvoice());
|
|
sendEstateOwnerMessage(gMessageSystem, "terrain", invoice, strings);
|
|
return false;
|
|
}
|
|
|
|
/////////////////////////////////////////////////////////////////////////////
|
|
// LLPanelEstateInfo
|
|
//
|
|
|
|
LLPanelEstateInfo::LLPanelEstateInfo()
|
|
: LLPanelRegionInfo(),
|
|
mEstateID(0) // invalid
|
|
{
|
|
}
|
|
|
|
// static
|
|
void LLPanelEstateInfo::initDispatch(LLDispatcher& dispatch)
|
|
{
|
|
std::string name;
|
|
|
|
// name.assign("setowner");
|
|
// static LLDispatchSetEstateOwner set_owner;
|
|
// dispatch.addHandler(name, &set_owner);
|
|
|
|
name.assign("estateupdateinfo");
|
|
static LLDispatchEstateUpdateInfo estate_update_info;
|
|
dispatch.addHandler(name, &estate_update_info);
|
|
|
|
name.assign("setaccess");
|
|
static LLDispatchSetEstateAccess set_access;
|
|
dispatch.addHandler(name, &set_access);
|
|
|
|
estate_dispatch_initialized = true;
|
|
}
|
|
|
|
// static
|
|
// Disables the sun-hour slider and the use fixed time check if the use global time is check
|
|
void LLPanelEstateInfo::onChangeUseGlobalTime(LLUICtrl* ctrl, void* user_data)
|
|
{
|
|
LLPanelEstateInfo* panel = (LLPanelEstateInfo*) user_data;
|
|
if (panel)
|
|
{
|
|
bool enabled = !panel->childGetValue("use_global_time_check").asBoolean();
|
|
panel->childSetEnabled("sun_hour_slider", enabled);
|
|
panel->childSetEnabled("fixed_sun_check", enabled);
|
|
panel->childSetValue("fixed_sun_check", LLSD(FALSE));
|
|
panel->enableButton("apply_btn");
|
|
}
|
|
}
|
|
|
|
// Enables the sun-hour slider if the fixed-sun checkbox is set
|
|
void LLPanelEstateInfo::onChangeFixedSun(LLUICtrl* ctrl, void* user_data)
|
|
{
|
|
LLPanelEstateInfo* panel = (LLPanelEstateInfo*) user_data;
|
|
if (panel)
|
|
{
|
|
bool enabled = !panel->childGetValue("fixed_sun_check").asBoolean();
|
|
panel->childSetEnabled("use_global_time_check", enabled);
|
|
panel->childSetValue("use_global_time_check", LLSD(FALSE));
|
|
panel->enableButton("apply_btn");
|
|
}
|
|
}
|
|
|
|
|
|
|
|
|
|
//---------------------------------------------------------------------------
|
|
// Add/Remove estate access button callbacks
|
|
//---------------------------------------------------------------------------
|
|
void LLPanelEstateInfo::onClickEditSky(void* user_data)
|
|
{
|
|
LLFloaterWindLight::show();
|
|
}
|
|
|
|
void LLPanelEstateInfo::onClickEditDayCycle(void* user_data)
|
|
{
|
|
LLFloaterDayCycle::show();
|
|
}
|
|
|
|
// static
|
|
void LLPanelEstateInfo::onClickAddAllowedAgent(void* user_data)
|
|
{
|
|
LLPanelEstateInfo* self = (LLPanelEstateInfo*)user_data;
|
|
LLCtrlListInterface *list = self->childGetListInterface("allowed_avatar_name_list");
|
|
if (!list) return;
|
|
if (list->getItemCount() >= ESTATE_MAX_ACCESS_IDS)
|
|
{
|
|
//args
|
|
|
|
LLSD args;
|
|
args["MAX_AGENTS"] = llformat("%d",ESTATE_MAX_ACCESS_IDS);
|
|
LLNotifications::instance().add("MaxAllowedAgentOnRegion", args);
|
|
return;
|
|
}
|
|
accessAddCore(ESTATE_ACCESS_ALLOWED_AGENT_ADD, "EstateAllowedAgentAdd");
|
|
}
|
|
|
|
// static
|
|
void LLPanelEstateInfo::onClickRemoveAllowedAgent(void* user_data)
|
|
{
|
|
accessRemoveCore(ESTATE_ACCESS_ALLOWED_AGENT_REMOVE, "EstateAllowedAgentRemove", "allowed_avatar_name_list");
|
|
}
|
|
|
|
// static
|
|
void LLPanelEstateInfo::onClickAddAllowedGroup(void* user_data)
|
|
{
|
|
LLPanelEstateInfo* self = (LLPanelEstateInfo*)user_data;
|
|
LLCtrlListInterface *list = self->childGetListInterface("allowed_group_name_list");
|
|
if (!list) return;
|
|
if (list->getItemCount() >= ESTATE_MAX_ACCESS_IDS)
|
|
{
|
|
LLSD args;
|
|
args["MAX_GROUPS"] = llformat("%d",ESTATE_MAX_ACCESS_IDS);
|
|
LLNotifications::instance().add("MaxAllowedGroupsOnRegion", args);
|
|
return;
|
|
}
|
|
|
|
LLNotification::Params params("ChangeLindenAccess");
|
|
params.functor(boost::bind(&LLPanelEstateInfo::addAllowedGroup, self, _1, _2));
|
|
if (isLindenEstate())
|
|
{
|
|
LLNotifications::instance().add(params);
|
|
}
|
|
else
|
|
{
|
|
LLNotifications::instance().forceResponse(params, 0);
|
|
}
|
|
}
|
|
|
|
bool LLPanelEstateInfo::addAllowedGroup(const LLSD& notification, const LLSD& response)
|
|
{
|
|
S32 option = LLNotification::getSelectedOption(notification, response);
|
|
if (option != 0) return false;
|
|
|
|
LLFloater* parent_floater = gFloaterView->getParentFloater(this);
|
|
|
|
LLFloaterGroupPicker* widget;
|
|
widget = LLFloaterGroupPicker::showInstance(LLSD(gAgent.getID()));
|
|
if (widget)
|
|
{
|
|
widget->setSelectCallback(addAllowedGroup2, NULL);
|
|
if (parent_floater)
|
|
{
|
|
LLRect new_rect = gFloaterView->findNeighboringPosition(parent_floater, widget);
|
|
widget->setOrigin(new_rect.mLeft, new_rect.mBottom);
|
|
parent_floater->addDependentFloater(widget);
|
|
}
|
|
}
|
|
|
|
return false;
|
|
}
|
|
|
|
// static
|
|
void LLPanelEstateInfo::onClickRemoveAllowedGroup(void* user_data)
|
|
{
|
|
accessRemoveCore(ESTATE_ACCESS_ALLOWED_GROUP_REMOVE, "EstateAllowedGroupRemove", "allowed_group_name_list");
|
|
}
|
|
|
|
// static
|
|
void LLPanelEstateInfo::onClickAddBannedAgent(void* user_data)
|
|
{
|
|
LLPanelEstateInfo* self = (LLPanelEstateInfo*)user_data;
|
|
LLCtrlListInterface *list = self->childGetListInterface("banned_avatar_name_list");
|
|
if (!list) return;
|
|
if (list->getItemCount() >= ESTATE_MAX_ACCESS_IDS)
|
|
{
|
|
LLSD args;
|
|
args["MAX_BANNED"] = llformat("%d",ESTATE_MAX_ACCESS_IDS);
|
|
LLNotifications::instance().add("MaxBannedAgentsOnRegion", args);
|
|
return;
|
|
}
|
|
accessAddCore(ESTATE_ACCESS_BANNED_AGENT_ADD, "EstateBannedAgentAdd");
|
|
}
|
|
|
|
// static
|
|
void LLPanelEstateInfo::onClickRemoveBannedAgent(void* user_data)
|
|
{
|
|
accessRemoveCore(ESTATE_ACCESS_BANNED_AGENT_REMOVE, "EstateBannedAgentRemove", "banned_avatar_name_list");
|
|
}
|
|
|
|
// static
|
|
void LLPanelEstateInfo::onClickAddEstateManager(void* user_data)
|
|
{
|
|
LLPanelEstateInfo* self = (LLPanelEstateInfo*)user_data;
|
|
LLCtrlListInterface *list = self->childGetListInterface("estate_manager_name_list");
|
|
if (!list) return;
|
|
if (list->getItemCount() >= ESTATE_MAX_MANAGERS)
|
|
{ // Tell user they can't add more managers
|
|
LLSD args;
|
|
args["MAX_MANAGER"] = llformat("%d",ESTATE_MAX_MANAGERS);
|
|
LLNotifications::instance().add("MaxManagersOnRegion", args);
|
|
}
|
|
else
|
|
{ // Go pick managers to add
|
|
accessAddCore(ESTATE_ACCESS_MANAGER_ADD, "EstateManagerAdd");
|
|
}
|
|
}
|
|
|
|
// static
|
|
void LLPanelEstateInfo::onClickRemoveEstateManager(void* user_data)
|
|
{
|
|
accessRemoveCore(ESTATE_ACCESS_MANAGER_REMOVE, "EstateManagerRemove", "estate_manager_name_list");
|
|
}
|
|
|
|
//---------------------------------------------------------------------------
|
|
// Kick from estate methods
|
|
//---------------------------------------------------------------------------
|
|
struct LLKickFromEstateInfo
|
|
{
|
|
LLPanelEstateInfo *mEstatePanelp;
|
|
LLUUID mAgentID;
|
|
};
|
|
|
|
void LLPanelEstateInfo::onClickKickUser(void *user_data)
|
|
{
|
|
LLPanelEstateInfo* panelp = (LLPanelEstateInfo*)user_data;
|
|
|
|
// this depends on the grandparent view being a floater
|
|
// in order to set up floater dependency
|
|
LLFloater* parent_floater = gFloaterView->getParentFloater(panelp);
|
|
LLFloater* child_floater = LLFloaterAvatarPicker::show(LLPanelEstateInfo::onKickUserCommit, user_data, FALSE, TRUE);
|
|
parent_floater->addDependentFloater(child_floater);
|
|
}
|
|
|
|
void LLPanelEstateInfo::onKickUserCommit(const std::vector<std::string>& names, const std::vector<LLUUID>& ids, void* userdata)
|
|
{
|
|
if (names.empty() || ids.empty()) return;
|
|
|
|
//check to make sure there is one valid user and id
|
|
if( (ids[0].isNull()) ||
|
|
(names[0].length() == 0) )
|
|
{
|
|
return;
|
|
}
|
|
|
|
LLPanelEstateInfo* self = (LLPanelEstateInfo*)userdata;
|
|
if(!self) return;
|
|
|
|
//keep track of what user they want to kick and other misc info
|
|
LLKickFromEstateInfo *kick_info = new LLKickFromEstateInfo();
|
|
kick_info->mEstatePanelp = self;
|
|
kick_info->mAgentID = ids[0];
|
|
|
|
//Bring up a confirmation dialog
|
|
LLSD args;
|
|
args["EVIL_USER"] = names[0];
|
|
LLSD payload;
|
|
payload["agent_id"] = ids[0];
|
|
LLNotifications::instance().add("EstateKickUser", args, payload, boost::bind(&LLPanelEstateInfo::kickUserConfirm, self, _1, _2));
|
|
|
|
}
|
|
|
|
bool LLPanelEstateInfo::kickUserConfirm(const LLSD& notification, const LLSD& response)
|
|
{
|
|
S32 option = LLNotification::getSelectedOption(notification, response);
|
|
switch(option)
|
|
{
|
|
case 0:
|
|
{
|
|
//Kick User
|
|
strings_t strings;
|
|
strings.push_back(notification["payload"]["agent_id"].asString());
|
|
|
|
sendEstateOwnerMessage(gMessageSystem, "kickestate", LLFloaterRegionInfo::getLastInvoice(), strings);
|
|
break;
|
|
}
|
|
default:
|
|
break;
|
|
}
|
|
return false;
|
|
}
|
|
|
|
//---------------------------------------------------------------------------
|
|
// Core Add/Remove estate access methods
|
|
// TODO: INTERNATIONAL: don't build message text here;
|
|
// instead, create multiple translatable messages and choose
|
|
// one based on the status.
|
|
//---------------------------------------------------------------------------
|
|
std::string all_estates_text()
|
|
{
|
|
LLPanelEstateInfo* panel = LLFloaterRegionInfo::getPanelEstate();
|
|
if (!panel) return "(error)";
|
|
|
|
std::string owner = panel->getOwnerName();
|
|
|
|
LLViewerRegion* region = gAgent.getRegion();
|
|
if (gAgent.isGodlike())
|
|
{
|
|
return llformat("all estates\nowned by %s", owner.c_str());
|
|
}
|
|
else if (region && region->getOwner() == gAgent.getID())
|
|
{
|
|
return "all estates you own";
|
|
}
|
|
else if (region && region->isEstateManager())
|
|
{
|
|
return llformat("all estates that\nyou manage for %s", owner.c_str());
|
|
}
|
|
else
|
|
{
|
|
return "(error)";
|
|
}
|
|
}
|
|
|
|
// static
|
|
bool LLPanelEstateInfo::isLindenEstate()
|
|
{
|
|
LLPanelEstateInfo* panel = LLFloaterRegionInfo::getPanelEstate();
|
|
if (!panel) return false;
|
|
|
|
U32 estate_id = panel->getEstateID();
|
|
return (estate_id <= ESTATE_LAST_LINDEN);
|
|
}
|
|
|
|
typedef std::vector<LLUUID> AgentOrGroupIDsVector;
|
|
struct LLEstateAccessChangeInfo
|
|
{
|
|
LLEstateAccessChangeInfo(const LLSD& sd)
|
|
{
|
|
mDialogName = sd["dialog_name"].asString();
|
|
mOperationFlag = (U32)sd["operation"].asInteger();
|
|
LLSD::array_const_iterator end_it = sd["allowed_ids"].endArray();
|
|
for (LLSD::array_const_iterator id_it = sd["allowed_ids"].beginArray();
|
|
id_it != end_it;
|
|
++id_it)
|
|
{
|
|
mAgentOrGroupIDs.push_back(id_it->asUUID());
|
|
}
|
|
}
|
|
|
|
const LLSD asLLSD() const
|
|
{
|
|
LLSD sd;
|
|
sd["name"] = mDialogName;
|
|
sd["operation"] = (S32)mOperationFlag;
|
|
for (AgentOrGroupIDsVector::const_iterator it = mAgentOrGroupIDs.begin();
|
|
it != mAgentOrGroupIDs.end();
|
|
++it)
|
|
{
|
|
sd["allowed_ids"].append(*it);
|
|
}
|
|
return sd;
|
|
}
|
|
|
|
U32 mOperationFlag; // ESTATE_ACCESS_BANNED_AGENT_ADD, _REMOVE, etc.
|
|
std::string mDialogName;
|
|
AgentOrGroupIDsVector mAgentOrGroupIDs; // List of agent IDs to apply to this change
|
|
};
|
|
|
|
// Special case callback for groups, since it has different callback format than names
|
|
// static
|
|
void LLPanelEstateInfo::addAllowedGroup2(LLUUID id, void* user_data)
|
|
{
|
|
LLSD payload;
|
|
payload["operation"] = (S32)ESTATE_ACCESS_ALLOWED_GROUP_ADD;
|
|
payload["dialog_name"] = "EstateAllowedGroupAdd";
|
|
payload["allowed_ids"].append(id);
|
|
|
|
LLSD args;
|
|
args["ALL_ESTATES"] = all_estates_text();
|
|
|
|
LLNotification::Params params("EstateAllowedGroupAdd");
|
|
params.payload(payload)
|
|
.substitutions(args)
|
|
.functor(accessCoreConfirm);
|
|
if (isLindenEstate())
|
|
{
|
|
LLNotifications::instance().forceResponse(params, 0);
|
|
}
|
|
else
|
|
{
|
|
LLNotifications::instance().add(params);
|
|
}
|
|
}
|
|
|
|
// static
|
|
void LLPanelEstateInfo::accessAddCore(U32 operation_flag, const std::string& dialog_name)
|
|
{
|
|
LLSD payload;
|
|
payload["operation"] = (S32)operation_flag;
|
|
payload["dialog_name"] = dialog_name;
|
|
// agent id filled in after avatar picker
|
|
|
|
LLNotification::Params params("ChangeLindenAccess");
|
|
params.payload(payload)
|
|
.functor(accessAddCore2);
|
|
|
|
if (isLindenEstate())
|
|
{
|
|
LLNotifications::instance().add(params);
|
|
}
|
|
else
|
|
{
|
|
// same as clicking "OK"
|
|
LLNotifications::instance().forceResponse(params, 0);
|
|
}
|
|
}
|
|
|
|
// static
|
|
bool LLPanelEstateInfo::accessAddCore2(const LLSD& notification, const LLSD& response)
|
|
{
|
|
S32 option = LLNotification::getSelectedOption(notification, response);
|
|
if (option != 0)
|
|
{
|
|
// abort change
|
|
return false;
|
|
}
|
|
|
|
LLEstateAccessChangeInfo* change_info = new LLEstateAccessChangeInfo(notification["payload"]);
|
|
// avatar picker yes multi-select, yes close-on-select
|
|
LLFloaterAvatarPicker::show(accessAddCore3, (void*)change_info, TRUE, TRUE);
|
|
return false;
|
|
}
|
|
|
|
// static
|
|
void LLPanelEstateInfo::accessAddCore3(const std::vector<std::string>& names, const std::vector<LLUUID>& ids, void* data)
|
|
{
|
|
LLEstateAccessChangeInfo* change_info = (LLEstateAccessChangeInfo*)data;
|
|
if (!change_info) return;
|
|
if (ids.empty())
|
|
{
|
|
// User didn't select a name.
|
|
delete change_info;
|
|
change_info = NULL;
|
|
return;
|
|
}
|
|
// User did select a name.
|
|
change_info->mAgentOrGroupIDs = ids;
|
|
// Can't put estate owner on ban list
|
|
LLPanelEstateInfo* panel = LLFloaterRegionInfo::getPanelEstate();
|
|
if (!panel) return;
|
|
LLViewerRegion* region = gAgent.getRegion();
|
|
if (!region) return;
|
|
|
|
if (change_info->mOperationFlag & ESTATE_ACCESS_ALLOWED_AGENT_ADD)
|
|
{
|
|
LLCtrlListInterface *list = panel->childGetListInterface("allowed_avatar_name_list");
|
|
int currentCount = (list ? list->getItemCount() : 0);
|
|
if (ids.size() + currentCount > ESTATE_MAX_ACCESS_IDS)
|
|
{
|
|
LLSD args;
|
|
args["NUM_ADDED"] = llformat("%d",ids.size());
|
|
args["MAX_AGENTS"] = llformat("%d",ESTATE_MAX_ACCESS_IDS);
|
|
args["LIST_TYPE"] = "Allowed Residents";
|
|
args["NUM_EXCESS"] = llformat("%d",(ids.size()+currentCount)-ESTATE_MAX_ACCESS_IDS);
|
|
LLNotifications::instance().add("MaxAgentOnRegionBatch", args);
|
|
delete change_info;
|
|
return;
|
|
}
|
|
}
|
|
if (change_info->mOperationFlag & ESTATE_ACCESS_BANNED_AGENT_ADD)
|
|
{
|
|
LLCtrlListInterface *list = panel->childGetListInterface("banned_avatar_name_list");
|
|
int currentCount = (list ? list->getItemCount() : 0);
|
|
if (ids.size() + currentCount > ESTATE_MAX_ACCESS_IDS)
|
|
{
|
|
LLSD args;
|
|
args["NUM_ADDED"] = llformat("%d",ids.size());
|
|
args["MAX_AGENTS"] = llformat("%d",ESTATE_MAX_ACCESS_IDS);
|
|
args["LIST_TYPE"] = "Banned Residents";
|
|
args["NUM_EXCESS"] = llformat("%d",(ids.size()+currentCount)-ESTATE_MAX_ACCESS_IDS);
|
|
LLNotifications::instance().add("MaxAgentOnRegionBatch", args);
|
|
delete change_info;
|
|
return;
|
|
}
|
|
}
|
|
|
|
LLSD args;
|
|
args["ALL_ESTATES"] = all_estates_text();
|
|
|
|
LLNotification::Params params(change_info->mDialogName);
|
|
params.substitutions(args)
|
|
.payload(change_info->asLLSD())
|
|
.functor(accessCoreConfirm);
|
|
|
|
if (isLindenEstate())
|
|
{
|
|
// just apply to this estate
|
|
LLNotifications::instance().forceResponse(params, 0);
|
|
}
|
|
else
|
|
{
|
|
// ask if this estate or all estates with this owner
|
|
LLNotifications::instance().add(params);
|
|
}
|
|
}
|
|
|
|
// static
|
|
void LLPanelEstateInfo::accessRemoveCore(U32 operation_flag, const std::string& dialog_name, const std::string& list_ctrl_name)
|
|
{
|
|
LLPanelEstateInfo* panel = LLFloaterRegionInfo::getPanelEstate();
|
|
if (!panel) return;
|
|
LLNameListCtrl* name_list = panel->getChild<LLNameListCtrl>(list_ctrl_name);
|
|
if (!name_list) return;
|
|
|
|
std::vector<LLScrollListItem*> list_vector = name_list->getAllSelected();
|
|
if (list_vector.size() == 0)
|
|
return;
|
|
|
|
LLSD payload;
|
|
payload["operation"] = (S32)operation_flag;
|
|
payload["dialog_name"] = dialog_name;
|
|
|
|
for (std::vector<LLScrollListItem*>::const_iterator iter = list_vector.begin();
|
|
iter != list_vector.end();
|
|
iter++)
|
|
{
|
|
LLScrollListItem *item = (*iter);
|
|
payload["allowed_ids"].append(item->getUUID());
|
|
}
|
|
|
|
LLNotification::Params params("ChangeLindenAccess");
|
|
params.payload(payload)
|
|
.functor(accessRemoveCore2);
|
|
|
|
if (isLindenEstate())
|
|
{
|
|
// warn on change linden estate
|
|
LLNotifications::instance().add(params);
|
|
}
|
|
else
|
|
{
|
|
// just proceed, as if clicking OK
|
|
LLNotifications::instance().forceResponse(params, 0);
|
|
}
|
|
}
|
|
|
|
// static
|
|
bool LLPanelEstateInfo::accessRemoveCore2(const LLSD& notification, const LLSD& response)
|
|
{
|
|
S32 option = LLNotification::getSelectedOption(notification, response);
|
|
if (option != 0)
|
|
{
|
|
// abort
|
|
return false;
|
|
}
|
|
|
|
// If Linden estate, can only apply to "this" estate, not all estates
|
|
// owned by NULL.
|
|
if (isLindenEstate())
|
|
{
|
|
accessCoreConfirm(notification, response);
|
|
}
|
|
else
|
|
{
|
|
LLSD args;
|
|
args["ALL_ESTATES"] = all_estates_text();
|
|
LLNotifications::instance().add(notification["payload"]["dialog_name"],
|
|
args,
|
|
notification["payload"],
|
|
accessCoreConfirm);
|
|
}
|
|
return false;
|
|
}
|
|
|
|
// Used for both access add and remove operations, depending on the mOperationFlag
|
|
// passed in (ESTATE_ACCESS_BANNED_AGENT_ADD, ESTATE_ACCESS_ALLOWED_AGENT_REMOVE, etc.)
|
|
// static
|
|
bool LLPanelEstateInfo::accessCoreConfirm(const LLSD& notification, const LLSD& response)
|
|
{
|
|
S32 option = LLNotification::getSelectedOption(notification, response);
|
|
const U32 originalFlags = (U32)notification["payload"]["operation"].asInteger();
|
|
|
|
LLViewerRegion* region = gAgent.getRegion();
|
|
|
|
LLSD::array_const_iterator end_it = notification["payload"]["allowed_ids"].endArray();
|
|
|
|
for (LLSD::array_const_iterator iter = notification["payload"]["allowed_ids"].beginArray();
|
|
iter != end_it;
|
|
iter++)
|
|
{
|
|
U32 flags = originalFlags;
|
|
if (iter + 1 != end_it)
|
|
flags |= ESTATE_ACCESS_NO_REPLY;
|
|
|
|
const LLUUID id = iter->asUUID();
|
|
if (((U32)notification["payload"]["operation"].asInteger() & ESTATE_ACCESS_BANNED_AGENT_ADD)
|
|
&& region && (region->getOwner() == id))
|
|
{
|
|
LLNotifications::instance().add("OwnerCanNotBeDenied");
|
|
break;
|
|
}
|
|
switch(option)
|
|
{
|
|
case 0:
|
|
// This estate
|
|
sendEstateAccessDelta(flags, id);
|
|
break;
|
|
case 1:
|
|
{
|
|
// All estates, either than I own or manage for this owner.
|
|
// This will be verified on simulator. JC
|
|
if (!region) break;
|
|
if (region->getOwner() == gAgent.getID()
|
|
|| gAgent.isGodlike())
|
|
{
|
|
flags |= ESTATE_ACCESS_APPLY_TO_ALL_ESTATES;
|
|
sendEstateAccessDelta(flags, id);
|
|
}
|
|
else if (region->isEstateManager())
|
|
{
|
|
flags |= ESTATE_ACCESS_APPLY_TO_MANAGED_ESTATES;
|
|
sendEstateAccessDelta(flags, id);
|
|
}
|
|
break;
|
|
}
|
|
case 2:
|
|
default:
|
|
break;
|
|
}
|
|
}
|
|
return false;
|
|
}
|
|
|
|
// key = "estateaccessdelta"
|
|
// str(estate_id) will be added to front of list by forward_EstateOwnerRequest_to_dataserver
|
|
// str[0] = str(agent_id) requesting the change
|
|
// str[1] = str(flags) (ESTATE_ACCESS_DELTA_*)
|
|
// str[2] = str(agent_id) to add or remove
|
|
// static
|
|
void LLPanelEstateInfo::sendEstateAccessDelta(U32 flags, const LLUUID& agent_or_group_id)
|
|
{
|
|
LLMessageSystem* msg = gMessageSystem;
|
|
msg->newMessage("EstateOwnerMessage");
|
|
msg->nextBlockFast(_PREHASH_AgentData);
|
|
msg->addUUIDFast(_PREHASH_AgentID, gAgent.getID());
|
|
msg->addUUIDFast(_PREHASH_SessionID, gAgent.getSessionID());
|
|
msg->addUUIDFast(_PREHASH_TransactionID, LLUUID::null); //not used
|
|
|
|
msg->nextBlock("MethodData");
|
|
msg->addString("Method", "estateaccessdelta");
|
|
msg->addUUID("Invoice", LLFloaterRegionInfo::getLastInvoice());
|
|
|
|
std::string buf;
|
|
gAgent.getID().toString(buf);
|
|
msg->nextBlock("ParamList");
|
|
msg->addString("Parameter", buf);
|
|
|
|
buf = llformat("%u", flags);
|
|
msg->nextBlock("ParamList");
|
|
msg->addString("Parameter", buf);
|
|
|
|
agent_or_group_id.toString(buf);
|
|
msg->nextBlock("ParamList");
|
|
msg->addString("Parameter", buf);
|
|
|
|
|
|
LLPanelEstateInfo* panel = LLFloaterRegionInfo::getPanelEstate();
|
|
|
|
if (flags & (ESTATE_ACCESS_ALLOWED_AGENT_ADD | ESTATE_ACCESS_ALLOWED_AGENT_REMOVE |
|
|
ESTATE_ACCESS_BANNED_AGENT_ADD | ESTATE_ACCESS_BANNED_AGENT_REMOVE))
|
|
{
|
|
|
|
panel->clearAccessLists();
|
|
}
|
|
|
|
gAgent.sendReliableMessage();
|
|
}
|
|
|
|
void LLPanelEstateInfo::updateControls(LLViewerRegion* region)
|
|
{
|
|
BOOL god = gAgent.isGodlike();
|
|
BOOL owner = (region && (region->getOwner() == gAgent.getID()));
|
|
BOOL manager = (region && region->isEstateManager());
|
|
setCtrlsEnabled(god || owner || manager);
|
|
|
|
childDisable("apply_btn");
|
|
childSetEnabled("add_allowed_avatar_btn", god || owner || manager);
|
|
childSetEnabled("remove_allowed_avatar_btn", god || owner || manager);
|
|
childSetEnabled("add_allowed_group_btn", god || owner || manager);
|
|
childSetEnabled("remove_allowed_group_btn", god || owner || manager);
|
|
childSetEnabled("add_banned_avatar_btn", god || owner || manager);
|
|
childSetEnabled("remove_banned_avatar_btn", god || owner || manager);
|
|
childSetEnabled("message_estate_btn", god || owner || manager);
|
|
childSetEnabled("kick_user_from_estate_btn", god || owner || manager);
|
|
#if ELAR_ENABLED
|
|
childSetEnabled("abuse_email_address", god || owner || manager);
|
|
#else
|
|
childSetEnabled("abuse_email_address", false);
|
|
#endif
|
|
|
|
// estate managers can't add estate managers
|
|
childSetEnabled("add_estate_manager_btn", god || owner);
|
|
childSetEnabled("remove_estate_manager_btn", god || owner);
|
|
childSetEnabled("estate_manager_name_list", god || owner);
|
|
}
|
|
|
|
bool LLPanelEstateInfo::refreshFromRegion(LLViewerRegion* region)
|
|
{
|
|
updateControls(region);
|
|
|
|
// let the parent class handle the general data collection.
|
|
bool rv = LLPanelRegionInfo::refreshFromRegion(region);
|
|
|
|
// We want estate info. To make sure it works across region
|
|
// boundaries and multiple packets, we add a serial number to the
|
|
// integers and track against that on update.
|
|
strings_t strings;
|
|
//integers_t integers;
|
|
//LLFloaterRegionInfo::incrementSerial();
|
|
LLFloaterRegionInfo::nextInvoice();
|
|
LLUUID invoice(LLFloaterRegionInfo::getLastInvoice());
|
|
//integers.push_back(LLFloaterRegionInfo::());::getPanelEstate();
|
|
|
|
|
|
LLPanelEstateInfo* panel = LLFloaterRegionInfo::getPanelEstate();
|
|
panel->clearAccessLists();
|
|
|
|
|
|
sendEstateOwnerMessage(gMessageSystem, "getinfo", invoice, strings);
|
|
|
|
refresh();
|
|
|
|
return rv;
|
|
}
|
|
|
|
void LLPanelEstateInfo::updateChild(LLUICtrl* child_ctrl)
|
|
{
|
|
if (checkRemovalButton(child_ctrl->getName()))
|
|
{
|
|
// do nothing
|
|
}
|
|
else if (checkSunHourSlider(child_ctrl))
|
|
{
|
|
// do nothing
|
|
}
|
|
}
|
|
|
|
bool LLPanelEstateInfo::estateUpdate(LLMessageSystem* msg)
|
|
{
|
|
llinfos << "LLPanelEstateInfo::estateUpdate()" << llendl;
|
|
return false;
|
|
}
|
|
|
|
|
|
BOOL LLPanelEstateInfo::postBuild()
|
|
{
|
|
// set up the callbacks for the generic controls
|
|
initCtrl("externally_visible_check");
|
|
initCtrl("use_global_time_check");
|
|
initCtrl("fixed_sun_check");
|
|
initCtrl("allow_direct_teleport");
|
|
initCtrl("limit_payment");
|
|
initCtrl("limit_age_verified");
|
|
initCtrl("voice_chat_check");
|
|
childSetCommitCallback("abuse_email_address", onChangeAnything, this);
|
|
childSetKeystrokeCallback("abuse_email_address", onChangeText, this);
|
|
|
|
initHelpBtn("estate_manager_help", "HelpEstateEstateManager");
|
|
initHelpBtn("use_global_time_help", "HelpEstateUseGlobalTime");
|
|
initHelpBtn("fixed_sun_help", "HelpEstateFixedSun");
|
|
initHelpBtn("WLEditSkyHelp", "HelpEditSky");
|
|
initHelpBtn("WLEditDayCycleHelp", "HelpEditDayCycle");
|
|
|
|
initHelpBtn("externally_visible_help", "HelpEstateExternallyVisible");
|
|
initHelpBtn("allow_direct_teleport_help", "HelpEstateAllowDirectTeleport");
|
|
initHelpBtn("allow_resident_help", "HelpEstateAllowResident");
|
|
initHelpBtn("allow_group_help", "HelpEstateAllowGroup");
|
|
initHelpBtn("ban_resident_help", "HelpEstateBanResident");
|
|
initHelpBtn("abuse_email_address_help", "HelpEstateAbuseEmailAddress");
|
|
initHelpBtn("voice_chat_help", "HelpEstateVoiceChat");
|
|
|
|
// set up the use global time checkbox
|
|
childSetCommitCallback("use_global_time_check", onChangeUseGlobalTime, this);
|
|
childSetCommitCallback("fixed_sun_check", onChangeFixedSun, this);
|
|
childSetCommitCallback("sun_hour_slider", onChangeChildCtrl, this);
|
|
|
|
childSetCommitCallback("allowed_avatar_name_list", onChangeChildCtrl, this);
|
|
LLNameListCtrl *avatar_name_list = getChild<LLNameListCtrl>("allowed_avatar_name_list");
|
|
if (avatar_name_list)
|
|
{
|
|
avatar_name_list->setCommitOnSelectionChange(TRUE);
|
|
avatar_name_list->setMaxItemCount(ESTATE_MAX_ACCESS_IDS);
|
|
}
|
|
|
|
childSetAction("add_allowed_avatar_btn", onClickAddAllowedAgent, this);
|
|
childSetAction("remove_allowed_avatar_btn", onClickRemoveAllowedAgent, this);
|
|
|
|
childSetCommitCallback("allowed_group_name_list", onChangeChildCtrl, this);
|
|
LLNameListCtrl* group_name_list = getChild<LLNameListCtrl>("allowed_group_name_list");
|
|
if (group_name_list)
|
|
{
|
|
group_name_list->setCommitOnSelectionChange(TRUE);
|
|
group_name_list->setMaxItemCount(ESTATE_MAX_ACCESS_IDS);
|
|
}
|
|
|
|
childSetAction("add_allowed_group_btn", onClickAddAllowedGroup, this);
|
|
childSetAction("remove_allowed_group_btn", onClickRemoveAllowedGroup, this);
|
|
|
|
childSetCommitCallback("banned_avatar_name_list", onChangeChildCtrl, this);
|
|
LLNameListCtrl* banned_name_list = getChild<LLNameListCtrl>("banned_avatar_name_list");
|
|
if (banned_name_list)
|
|
{
|
|
banned_name_list->setCommitOnSelectionChange(TRUE);
|
|
banned_name_list->setMaxItemCount(ESTATE_MAX_ACCESS_IDS);
|
|
}
|
|
|
|
childSetAction("add_banned_avatar_btn", onClickAddBannedAgent, this);
|
|
childSetAction("remove_banned_avatar_btn", onClickRemoveBannedAgent, this);
|
|
|
|
childSetCommitCallback("estate_manager_name_list", onChangeChildCtrl, this);
|
|
LLNameListCtrl* manager_name_list = getChild<LLNameListCtrl>("estate_manager_name_list");
|
|
if (manager_name_list)
|
|
{
|
|
manager_name_list->setCommitOnSelectionChange(TRUE);
|
|
manager_name_list->setMaxItemCount(ESTATE_MAX_MANAGERS * 4); // Allow extras for dupe issue
|
|
}
|
|
|
|
childSetAction("add_estate_manager_btn", onClickAddEstateManager, this);
|
|
childSetAction("remove_estate_manager_btn", onClickRemoveEstateManager, this);
|
|
childSetAction("message_estate_btn", onClickMessageEstate, this);
|
|
childSetAction("kick_user_from_estate_btn", onClickKickUser, this);
|
|
|
|
childSetAction("WLEditSky", onClickEditSky, this);
|
|
childSetAction("WLEditDayCycle", onClickEditDayCycle, this);
|
|
|
|
return LLPanelRegionInfo::postBuild();
|
|
}
|
|
|
|
void LLPanelEstateInfo::refresh()
|
|
{
|
|
bool public_access = childGetValue("externally_visible_check").asBoolean();
|
|
childSetEnabled("Only Allow", public_access);
|
|
childSetEnabled("limit_payment", public_access);
|
|
childSetEnabled("limit_age_verified", public_access);
|
|
// if this is set to false, then the limit fields are meaningless and should be turned off
|
|
if (public_access == false)
|
|
{
|
|
childSetValue("limit_payment", false);
|
|
childSetValue("limit_age_verified", false);
|
|
}
|
|
}
|
|
|
|
BOOL LLPanelEstateInfo::sendUpdate()
|
|
{
|
|
llinfos << "LLPanelEsateInfo::sendUpdate()" << llendl;
|
|
|
|
LLNotification::Params params("ChangeLindenEstate");
|
|
params.functor(boost::bind(&LLPanelEstateInfo::callbackChangeLindenEstate, this, _1, _2));
|
|
|
|
if (getEstateID() <= ESTATE_LAST_LINDEN)
|
|
{
|
|
// trying to change reserved estate, warn
|
|
LLNotifications::instance().add(params);
|
|
}
|
|
else
|
|
{
|
|
// for normal estates, just make the change
|
|
LLNotifications::instance().forceResponse(params, 0);
|
|
}
|
|
return TRUE;
|
|
}
|
|
|
|
bool LLPanelEstateInfo::callbackChangeLindenEstate(const LLSD& notification, const LLSD& response)
|
|
{
|
|
S32 option = LLNotification::getSelectedOption(notification, response);
|
|
switch(option)
|
|
{
|
|
case 0:
|
|
// send the update
|
|
if (!commitEstateInfoCaps())
|
|
{
|
|
// the caps method failed, try the old way
|
|
LLFloaterRegionInfo::nextInvoice();
|
|
commitEstateInfoDataserver();
|
|
}
|
|
// we don't want to do this because we'll get it automatically from the sim
|
|
// after the spaceserver processes it
|
|
// else
|
|
// {
|
|
// // caps method does not automatically send this info
|
|
// LLFloaterRegionInfo::requestRegionInfo();
|
|
// }
|
|
break;
|
|
case 1:
|
|
default:
|
|
// do nothing
|
|
break;
|
|
}
|
|
return false;
|
|
}
|
|
|
|
|
|
/*
|
|
// Request = "getowner"
|
|
// SParam[0] = "" (empty string)
|
|
// IParam[0] = serial
|
|
void LLPanelEstateInfo::getEstateOwner()
|
|
{
|
|
// TODO -- disable the panel
|
|
// and call this function whenever we cross a region boundary
|
|
// re-enable when owner matches, and get new estate info
|
|
LLMessageSystem* msg = gMessageSystem;
|
|
msg->newMessageFast(_PREHASH_EstateOwnerRequest);
|
|
msg->nextBlockFast(_PREHASH_AgentData);
|
|
msg->addUUIDFast(_PREHASH_AgentID, gAgent.getID());
|
|
|
|
msg->nextBlockFast(_PREHASH_RequestData);
|
|
msg->addStringFast(_PREHASH_Request, "getowner");
|
|
|
|
// we send an empty string so that the variable block is not empty
|
|
msg->nextBlockFast(_PREHASH_StringData);
|
|
msg->addStringFast(_PREHASH_SParam, "");
|
|
|
|
msg->nextBlockFast(_PREHASH_IntegerData);
|
|
msg->addS32Fast(_PREHASH_IParam, LLFloaterRegionInfo::getSerial());
|
|
|
|
gAgent.sendMessage();
|
|
}
|
|
*/
|
|
|
|
class LLEstateChangeInfoResponder : public LLHTTPClient::Responder
|
|
{
|
|
public:
|
|
LLEstateChangeInfoResponder(void* userdata) : mpPanel((LLPanelEstateInfo*)userdata) {};
|
|
|
|
// if we get a normal response, handle it here
|
|
virtual void result(const LLSD& content)
|
|
{
|
|
// refresh the panel from the database
|
|
mpPanel->refresh();
|
|
}
|
|
|
|
// if we get an error response
|
|
virtual void error(U32 status, const std::string& reason)
|
|
{
|
|
llinfos << "LLEstateChangeInfoResponder::error "
|
|
<< status << ": " << reason << llendl;
|
|
}
|
|
private:
|
|
LLPanelEstateInfo* mpPanel;
|
|
};
|
|
|
|
// tries to send estate info using a cap; returns true if it succeeded
|
|
bool LLPanelEstateInfo::commitEstateInfoCaps()
|
|
{
|
|
std::string url = gAgent.getRegion()->getCapability("EstateChangeInfo");
|
|
|
|
if (url.empty())
|
|
{
|
|
// whoops, couldn't find the cap, so bail out
|
|
return false;
|
|
}
|
|
|
|
LLSD body;
|
|
body["estate_name"] = getEstateName();
|
|
|
|
body["is_externally_visible"] = childGetValue("externally_visible_check").asBoolean();
|
|
body["allow_direct_teleport"] = childGetValue("allow_direct_teleport").asBoolean();
|
|
body["is_sun_fixed" ] = childGetValue("fixed_sun_check").asBoolean();
|
|
body["deny_anonymous" ] = childGetValue("limit_payment").asBoolean();
|
|
body["deny_age_unverified" ] = childGetValue("limit_age_verified").asBoolean();
|
|
body["allow_voice_chat" ] = childGetValue("voice_chat_check").asBoolean();
|
|
body["invoice" ] = LLFloaterRegionInfo::getLastInvoice();
|
|
|
|
// block fly is in estate database but not in estate UI, so we're not supporting it
|
|
//body["block_fly" ] = childGetValue("").asBoolean();
|
|
|
|
F32 sun_hour = getSunHour();
|
|
if (childGetValue("use_global_time_check").asBoolean())
|
|
{
|
|
sun_hour = 0.f; // 0 = global time
|
|
}
|
|
body["sun_hour"] = sun_hour;
|
|
|
|
body["owner_abuse_email"] = childGetValue("abuse_email_address").asString();
|
|
|
|
// we use a responder so that we can re-get the data after committing to the database
|
|
LLHTTPClient::post(url, body, new LLEstateChangeInfoResponder((void*)this));
|
|
return true;
|
|
}
|
|
|
|
/* This is the old way of doing things, is deprecated, and should be
|
|
deleted when the dataserver model can be removed */
|
|
// key = "estatechangeinfo"
|
|
// strings[0] = str(estate_id) (added by simulator before relay - not here)
|
|
// strings[1] = estate_name
|
|
// strings[2] = str(estate_flags)
|
|
// strings[3] = str((S32)(sun_hour * 1024.f))
|
|
void LLPanelEstateInfo::commitEstateInfoDataserver()
|
|
{
|
|
LLMessageSystem* msg = gMessageSystem;
|
|
msg->newMessage("EstateOwnerMessage");
|
|
msg->nextBlockFast(_PREHASH_AgentData);
|
|
msg->addUUIDFast(_PREHASH_AgentID, gAgent.getID());
|
|
msg->addUUIDFast(_PREHASH_SessionID, gAgent.getSessionID());
|
|
msg->addUUIDFast(_PREHASH_TransactionID, LLUUID::null); //not used
|
|
|
|
msg->nextBlock("MethodData");
|
|
msg->addString("Method", "estatechangeinfo");
|
|
msg->addUUID("Invoice", LLFloaterRegionInfo::getLastInvoice());
|
|
|
|
msg->nextBlock("ParamList");
|
|
msg->addString("Parameter", getEstateName());
|
|
|
|
std::string buffer;
|
|
buffer = llformat("%u", computeEstateFlags());
|
|
msg->nextBlock("ParamList");
|
|
msg->addString("Parameter", buffer);
|
|
|
|
F32 sun_hour = getSunHour();
|
|
if (childGetValue("use_global_time_check").asBoolean())
|
|
{
|
|
sun_hour = 0.f; // 0 = global time
|
|
}
|
|
|
|
buffer = llformat("%d", (S32)(sun_hour*1024.0f));
|
|
msg->nextBlock("ParamList");
|
|
msg->addString("Parameter", buffer);
|
|
|
|
gAgent.sendMessage();
|
|
}
|
|
|
|
void LLPanelEstateInfo::setEstateFlags(U32 flags)
|
|
{
|
|
childSetValue("externally_visible_check", LLSD(flags & REGION_FLAGS_EXTERNALLY_VISIBLE ? TRUE : FALSE) );
|
|
childSetValue("fixed_sun_check", LLSD(flags & REGION_FLAGS_SUN_FIXED ? TRUE : FALSE) );
|
|
childSetValue(
|
|
"voice_chat_check",
|
|
LLSD(flags & REGION_FLAGS_ALLOW_VOICE ? TRUE : FALSE));
|
|
childSetValue("allow_direct_teleport", LLSD(flags & REGION_FLAGS_ALLOW_DIRECT_TELEPORT ? TRUE : FALSE) );
|
|
childSetValue("limit_payment", LLSD(flags & REGION_FLAGS_DENY_ANONYMOUS ? TRUE : FALSE) );
|
|
childSetValue("limit_age_verified", LLSD(flags & REGION_FLAGS_DENY_AGEUNVERIFIED ? TRUE : FALSE) );
|
|
|
|
refresh();
|
|
}
|
|
|
|
U32 LLPanelEstateInfo::computeEstateFlags()
|
|
{
|
|
U32 flags = 0;
|
|
|
|
if (childGetValue("externally_visible_check").asBoolean())
|
|
{
|
|
flags |= REGION_FLAGS_EXTERNALLY_VISIBLE;
|
|
}
|
|
|
|
if ( childGetValue("voice_chat_check").asBoolean() )
|
|
{
|
|
flags |= REGION_FLAGS_ALLOW_VOICE;
|
|
}
|
|
|
|
if (childGetValue("allow_direct_teleport").asBoolean())
|
|
{
|
|
flags |= REGION_FLAGS_ALLOW_DIRECT_TELEPORT;
|
|
}
|
|
|
|
if (childGetValue("fixed_sun_check").asBoolean())
|
|
{
|
|
flags |= REGION_FLAGS_SUN_FIXED;
|
|
}
|
|
|
|
if (childGetValue("limit_payment").asBoolean())
|
|
{
|
|
flags |= REGION_FLAGS_DENY_ANONYMOUS;
|
|
}
|
|
|
|
if (childGetValue("limit_age_verified").asBoolean())
|
|
{
|
|
flags |= REGION_FLAGS_DENY_AGEUNVERIFIED;
|
|
}
|
|
|
|
|
|
return flags;
|
|
}
|
|
|
|
BOOL LLPanelEstateInfo::getGlobalTime()
|
|
{
|
|
return childGetValue("use_global_time_check").asBoolean();
|
|
}
|
|
|
|
void LLPanelEstateInfo::setGlobalTime(bool b)
|
|
{
|
|
childSetValue("use_global_time_check", LLSD(b));
|
|
childSetEnabled("fixed_sun_check", LLSD(!b));
|
|
childSetEnabled("sun_hour_slider", LLSD(!b));
|
|
if (b)
|
|
{
|
|
childSetValue("sun_hour_slider", LLSD(0.f));
|
|
}
|
|
}
|
|
|
|
|
|
BOOL LLPanelEstateInfo::getFixedSun()
|
|
{
|
|
return childGetValue("fixed_sun_check").asBoolean();
|
|
}
|
|
|
|
void LLPanelEstateInfo::setSunHour(F32 sun_hour)
|
|
{
|
|
if(sun_hour < 6.0f)
|
|
{
|
|
sun_hour = 24.0f + sun_hour;
|
|
}
|
|
childSetValue("sun_hour_slider", LLSD(sun_hour));
|
|
}
|
|
|
|
F32 LLPanelEstateInfo::getSunHour()
|
|
{
|
|
if (childIsEnabled("sun_hour_slider"))
|
|
{
|
|
return (F32)childGetValue("sun_hour_slider").asReal();
|
|
}
|
|
return 0.f;
|
|
}
|
|
|
|
const std::string LLPanelEstateInfo::getEstateName() const
|
|
{
|
|
return childGetValue("estate_name").asString();
|
|
}
|
|
|
|
void LLPanelEstateInfo::setEstateName(const std::string& name)
|
|
{
|
|
childSetValue("estate_name", LLSD(name));
|
|
}
|
|
|
|
const std::string LLPanelEstateInfo::getOwnerName() const
|
|
{
|
|
return childGetValue("estate_owner").asString();
|
|
}
|
|
|
|
void LLPanelEstateInfo::setOwnerName(const std::string& name)
|
|
{
|
|
childSetValue("estate_owner", LLSD(name));
|
|
}
|
|
|
|
const std::string LLPanelEstateInfo::getAbuseEmailAddress() const
|
|
{
|
|
return childGetValue("abuse_email_address").asString();
|
|
}
|
|
|
|
void LLPanelEstateInfo::setAbuseEmailAddress(const std::string& address)
|
|
{
|
|
childSetValue("abuse_email_address", LLSD(address));
|
|
}
|
|
|
|
void LLPanelEstateInfo::setAccessAllowedEnabled(bool enable_agent,
|
|
bool enable_group,
|
|
bool enable_ban)
|
|
{
|
|
childSetEnabled("allow_resident_label", enable_agent);
|
|
childSetEnabled("allowed_avatar_name_list", enable_agent);
|
|
childSetVisible("allowed_avatar_name_list", enable_agent);
|
|
childSetEnabled("add_allowed_avatar_btn", enable_agent);
|
|
childSetEnabled("remove_allowed_avatar_btn", enable_agent);
|
|
|
|
// Groups
|
|
childSetEnabled("allow_group_label", enable_group);
|
|
childSetEnabled("allowed_group_name_list", enable_group);
|
|
childSetVisible("allowed_group_name_list", enable_group);
|
|
childSetEnabled("add_allowed_group_btn", enable_group);
|
|
childSetEnabled("remove_allowed_group_btn", enable_group);
|
|
|
|
// Ban
|
|
childSetEnabled("ban_resident_label", enable_ban);
|
|
childSetEnabled("banned_avatar_name_list", enable_ban);
|
|
childSetVisible("banned_avatar_name_list", enable_ban);
|
|
childSetEnabled("add_banned_avatar_btn", enable_ban);
|
|
childSetEnabled("remove_banned_avatar_btn", enable_ban);
|
|
|
|
// Update removal buttons if needed
|
|
if (enable_agent)
|
|
{
|
|
checkRemovalButton("allowed_avatar_name_list");
|
|
}
|
|
|
|
if (enable_group)
|
|
{
|
|
checkRemovalButton("allowed_group_name_list");
|
|
}
|
|
|
|
if (enable_ban)
|
|
{
|
|
checkRemovalButton("banned_avatar_name_list");
|
|
}
|
|
}
|
|
|
|
// static
|
|
void LLPanelEstateInfo::callbackCacheName(
|
|
const LLUUID& id,
|
|
const std::string& first,
|
|
const std::string& last,
|
|
BOOL is_group,
|
|
void*)
|
|
{
|
|
LLPanelEstateInfo* self = LLFloaterRegionInfo::getPanelEstate();
|
|
if (!self) return;
|
|
|
|
std::string name;
|
|
|
|
if (id.isNull())
|
|
{
|
|
name = "(none)";
|
|
}
|
|
else
|
|
{
|
|
name = first + " " + last;
|
|
}
|
|
|
|
self->setOwnerName(name);
|
|
}
|
|
|
|
void LLPanelEstateInfo::clearAccessLists()
|
|
{
|
|
LLNameListCtrl* name_list = getChild<LLNameListCtrl>("allowed_avatar_name_list");
|
|
if (name_list)
|
|
{
|
|
name_list->deleteAllItems();
|
|
}
|
|
|
|
name_list = getChild<LLNameListCtrl>("banned_avatar_name_list");
|
|
if (name_list)
|
|
{
|
|
name_list->deleteAllItems();
|
|
}
|
|
}
|
|
|
|
// enables/disables the "remove" button for the various allow/ban lists
|
|
BOOL LLPanelEstateInfo::checkRemovalButton(std::string name)
|
|
{
|
|
std::string btn_name = "";
|
|
if (name == "allowed_avatar_name_list")
|
|
{
|
|
btn_name = "remove_allowed_avatar_btn";
|
|
}
|
|
else if (name == "allowed_group_name_list")
|
|
{
|
|
btn_name = "remove_allowed_group_btn";
|
|
}
|
|
else if (name == "banned_avatar_name_list")
|
|
{
|
|
btn_name = "remove_banned_avatar_btn";
|
|
}
|
|
else if (name == "estate_manager_name_list")
|
|
{
|
|
//ONLY OWNER CAN ADD /DELET ESTATE MANAGER
|
|
LLViewerRegion* region = gAgent.getRegion();
|
|
if (region && (region->getOwner() == gAgent.getID()))
|
|
{
|
|
btn_name = "remove_estate_manager_btn";
|
|
}
|
|
}
|
|
|
|
// enable the remove button if something is selected
|
|
LLNameListCtrl* name_list = getChild<LLNameListCtrl>(name);
|
|
childSetEnabled(btn_name, name_list && name_list->getFirstSelected() ? TRUE : FALSE);
|
|
|
|
return (btn_name != "");
|
|
}
|
|
|
|
BOOL LLPanelEstateInfo::checkSunHourSlider(LLUICtrl* child_ctrl)
|
|
{
|
|
BOOL found_child_ctrl = FALSE;
|
|
if (child_ctrl->getName() == "sun_hour_slider")
|
|
{
|
|
enableButton("apply_btn");
|
|
found_child_ctrl = TRUE;
|
|
}
|
|
return found_child_ctrl;
|
|
}
|
|
|
|
// static
|
|
void LLPanelEstateInfo::onClickMessageEstate(void* userdata)
|
|
{
|
|
llinfos << "LLPanelEstateInfo::onClickMessageEstate" << llendl;
|
|
LLNotifications::instance().add("MessageEstate", LLSD(), LLSD(), boost::bind(&LLPanelEstateInfo::onMessageCommit, (LLPanelEstateInfo*)userdata, _1, _2));
|
|
}
|
|
|
|
bool LLPanelEstateInfo::onMessageCommit(const LLSD& notification, const LLSD& response)
|
|
{
|
|
S32 option = LLNotification::getSelectedOption(notification, response);
|
|
std::string text = response["message"].asString();
|
|
if(option != 0) return false;
|
|
if(text.empty()) return false;
|
|
llinfos << "Message to everyone: " << text << llendl;
|
|
strings_t strings;
|
|
//integers_t integers;
|
|
std::string name;
|
|
gAgent.buildFullname(name);
|
|
strings.push_back(strings_t::value_type(name));
|
|
strings.push_back(strings_t::value_type(text));
|
|
LLUUID invoice(LLFloaterRegionInfo::getLastInvoice());
|
|
sendEstateOwnerMessage(gMessageSystem, "instantmessage", invoice, strings);
|
|
return false;
|
|
}
|
|
|
|
LLPanelEstateCovenant::LLPanelEstateCovenant()
|
|
: mCovenantID(LLUUID::null)
|
|
{
|
|
}
|
|
|
|
// virtual
|
|
bool LLPanelEstateCovenant::refreshFromRegion(LLViewerRegion* region)
|
|
{
|
|
LLTextBox* region_name = getChild<LLTextBox>("region_name_text");
|
|
if (region_name)
|
|
{
|
|
region_name->setText(region->getName());
|
|
}
|
|
|
|
LLTextBox* resellable_clause = getChild<LLTextBox>("resellable_clause");
|
|
if (resellable_clause)
|
|
{
|
|
if (region->getRegionFlags() & REGION_FLAGS_BLOCK_LAND_RESELL)
|
|
{
|
|
resellable_clause->setText(getString("can_not_resell"));
|
|
}
|
|
else
|
|
{
|
|
resellable_clause->setText(getString("can_resell"));
|
|
}
|
|
}
|
|
|
|
LLTextBox* changeable_clause = getChild<LLTextBox>("changeable_clause");
|
|
if (changeable_clause)
|
|
{
|
|
if (region->getRegionFlags() & REGION_FLAGS_ALLOW_PARCEL_CHANGES)
|
|
{
|
|
changeable_clause->setText(getString("can_change"));
|
|
}
|
|
else
|
|
{
|
|
changeable_clause->setText(getString("can_not_change"));
|
|
}
|
|
}
|
|
|
|
LLTextBox* region_maturity = getChild<LLTextBox>("region_maturity_text");
|
|
if (region_maturity)
|
|
{
|
|
region_maturity->setText(region->getSimAccessString());
|
|
}
|
|
|
|
LLTextBox* region_landtype = getChild<LLTextBox>("region_landtype_text");
|
|
if (region_landtype)
|
|
{
|
|
region_landtype->setText(region->getSimProductName());
|
|
}
|
|
|
|
|
|
// let the parent class handle the general data collection.
|
|
bool rv = LLPanelRegionInfo::refreshFromRegion(region);
|
|
LLMessageSystem *msg = gMessageSystem;
|
|
msg->newMessage("EstateCovenantRequest");
|
|
msg->nextBlockFast(_PREHASH_AgentData);
|
|
msg->addUUIDFast(_PREHASH_AgentID, gAgent.getID());
|
|
msg->addUUIDFast(_PREHASH_SessionID,gAgent.getSessionID());
|
|
msg->sendReliable(region->getHost());
|
|
return rv;
|
|
}
|
|
|
|
// virtual
|
|
bool LLPanelEstateCovenant::estateUpdate(LLMessageSystem* msg)
|
|
{
|
|
llinfos << "LLPanelEstateCovenant::estateUpdate()" << llendl;
|
|
return true;
|
|
}
|
|
|
|
// virtual
|
|
BOOL LLPanelEstateCovenant::postBuild()
|
|
{
|
|
initHelpBtn("covenant_help", "HelpEstateCovenant");
|
|
mEstateNameText = getChild<LLTextBox>("estate_name_text");
|
|
mEstateOwnerText = getChild<LLTextBox>("estate_owner_text");
|
|
mLastModifiedText = getChild<LLTextBox>("covenant_timestamp_text");
|
|
mEditor = getChild<LLViewerTextEditor>("covenant_editor");
|
|
if (mEditor) mEditor->setHandleEditKeysDirectly(TRUE);
|
|
LLButton* reset_button = getChild<LLButton>("reset_covenant");
|
|
reset_button->setEnabled(gAgent.canManageEstate());
|
|
reset_button->setClickedCallback(LLPanelEstateCovenant::resetCovenantID, NULL);
|
|
|
|
return LLPanelRegionInfo::postBuild();
|
|
}
|
|
|
|
// virtual
|
|
void LLPanelEstateCovenant::updateChild(LLUICtrl* child_ctrl)
|
|
{
|
|
}
|
|
|
|
// virtual
|
|
BOOL LLPanelEstateCovenant::handleDragAndDrop(S32 x, S32 y, MASK mask, BOOL drop,
|
|
EDragAndDropType cargo_type,
|
|
void* cargo_data,
|
|
EAcceptance* accept,
|
|
std::string& tooltip_msg)
|
|
{
|
|
LLInventoryItem* item = (LLInventoryItem*)cargo_data;
|
|
|
|
if (!gAgent.canManageEstate())
|
|
{
|
|
*accept = ACCEPT_NO;
|
|
return TRUE;
|
|
}
|
|
|
|
switch(cargo_type)
|
|
{
|
|
case DAD_NOTECARD:
|
|
*accept = ACCEPT_YES_COPY_SINGLE;
|
|
if (item && drop)
|
|
{
|
|
LLSD payload;
|
|
payload["item_id"] = item->getUUID();
|
|
LLNotifications::instance().add("EstateChangeCovenant", LLSD(), payload,
|
|
LLPanelEstateCovenant::confirmChangeCovenantCallback);
|
|
}
|
|
break;
|
|
default:
|
|
*accept = ACCEPT_NO;
|
|
break;
|
|
}
|
|
|
|
return TRUE;
|
|
}
|
|
|
|
// static
|
|
bool LLPanelEstateCovenant::confirmChangeCovenantCallback(const LLSD& notification, const LLSD& response)
|
|
{
|
|
S32 option = LLNotification::getSelectedOption(notification, response);
|
|
LLInventoryItem* item = gInventory.getItem(notification["payload"]["item_id"].asUUID());
|
|
LLPanelEstateCovenant* self = LLFloaterRegionInfo::getPanelCovenant();
|
|
|
|
if (!item || !self) return false;
|
|
|
|
switch(option)
|
|
{
|
|
case 0:
|
|
self->loadInvItem(item);
|
|
break;
|
|
default:
|
|
break;
|
|
}
|
|
return false;
|
|
}
|
|
|
|
// static
|
|
void LLPanelEstateCovenant::resetCovenantID(void* userdata)
|
|
{
|
|
LLNotifications::instance().add("EstateChangeCovenant", LLSD(), LLSD(), confirmResetCovenantCallback);
|
|
}
|
|
|
|
// static
|
|
bool LLPanelEstateCovenant::confirmResetCovenantCallback(const LLSD& notification, const LLSD& response)
|
|
{
|
|
LLPanelEstateCovenant* self = LLFloaterRegionInfo::getPanelCovenant();
|
|
if (!self) return false;
|
|
|
|
S32 option = LLNotification::getSelectedOption(notification, response);
|
|
switch(option)
|
|
{
|
|
case 0:
|
|
self->loadInvItem(NULL);
|
|
break;
|
|
default:
|
|
break;
|
|
}
|
|
return false;
|
|
}
|
|
|
|
void LLPanelEstateCovenant::loadInvItem(LLInventoryItem *itemp)
|
|
{
|
|
const BOOL high_priority = TRUE;
|
|
if (itemp)
|
|
{
|
|
gAssetStorage->getInvItemAsset(gAgent.getRegionHost(),
|
|
gAgent.getID(),
|
|
gAgent.getSessionID(),
|
|
itemp->getPermissions().getOwner(),
|
|
LLUUID::null,
|
|
itemp->getUUID(),
|
|
itemp->getAssetUUID(),
|
|
itemp->getType(),
|
|
onLoadComplete,
|
|
(void*)this,
|
|
high_priority);
|
|
mAssetStatus = ASSET_LOADING;
|
|
}
|
|
else
|
|
{
|
|
mAssetStatus = ASSET_LOADED;
|
|
setCovenantTextEditor("There is no Covenant provided for this Estate.");
|
|
sendChangeCovenantID(LLUUID::null);
|
|
}
|
|
}
|
|
|
|
// static
|
|
void LLPanelEstateCovenant::onLoadComplete(LLVFS *vfs,
|
|
const LLUUID& asset_uuid,
|
|
LLAssetType::EType type,
|
|
void* user_data, S32 status, LLExtStat ext_status)
|
|
{
|
|
llinfos << "LLPanelEstateCovenant::onLoadComplete()" << llendl;
|
|
LLPanelEstateCovenant* panelp = (LLPanelEstateCovenant*)user_data;
|
|
if( panelp )
|
|
{
|
|
if(0 == status)
|
|
{
|
|
LLVFile file(vfs, asset_uuid, type, LLVFile::READ);
|
|
|
|
S32 file_length = file.getSize();
|
|
|
|
char* buffer = new char[file_length+1];
|
|
if (buffer == NULL)
|
|
{
|
|
llerrs << "Memory Allocation Failed" << llendl;
|
|
return;
|
|
}
|
|
|
|
file.read((U8*)buffer, file_length); /* Flawfinder: ignore */
|
|
// put a EOS at the end
|
|
buffer[file_length] = 0;
|
|
|
|
if( (file_length > 19) && !strncmp( buffer, "Linden text version", 19 ) )
|
|
{
|
|
if( !panelp->mEditor->importBuffer( buffer, file_length+1 ) )
|
|
{
|
|
llwarns << "Problem importing estate covenant." << llendl;
|
|
LLNotifications::instance().add("ProblemImportingEstateCovenant");
|
|
}
|
|
else
|
|
{
|
|
panelp->sendChangeCovenantID(asset_uuid);
|
|
}
|
|
}
|
|
else
|
|
{
|
|
// Version 0 (just text, doesn't include version number)
|
|
panelp->sendChangeCovenantID(asset_uuid);
|
|
}
|
|
delete[] buffer;
|
|
}
|
|
else
|
|
{
|
|
LLViewerStats::getInstance()->incStat( LLViewerStats::ST_DOWNLOAD_FAILED );
|
|
|
|
if( LL_ERR_ASSET_REQUEST_NOT_IN_DATABASE == status ||
|
|
LL_ERR_FILE_EMPTY == status)
|
|
{
|
|
LLNotifications::instance().add("MissingNotecardAssetID");
|
|
}
|
|
else if (LL_ERR_INSUFFICIENT_PERMISSIONS == status)
|
|
{
|
|
LLNotifications::instance().add("NotAllowedToViewNotecard");
|
|
}
|
|
else
|
|
{
|
|
LLNotifications::instance().add("UnableToLoadNotecardAsset");
|
|
}
|
|
|
|
llwarns << "Problem loading notecard: " << status << llendl;
|
|
}
|
|
panelp->mAssetStatus = ASSET_LOADED;
|
|
panelp->setCovenantID(asset_uuid);
|
|
}
|
|
}
|
|
|
|
// key = "estatechangecovenantid"
|
|
// strings[0] = str(estate_id) (added by simulator before relay - not here)
|
|
// strings[1] = str(covenant_id)
|
|
void LLPanelEstateCovenant::sendChangeCovenantID(const LLUUID &asset_id)
|
|
{
|
|
if (asset_id != getCovenantID())
|
|
{
|
|
setCovenantID(asset_id);
|
|
|
|
LLMessageSystem* msg = gMessageSystem;
|
|
msg->newMessage("EstateOwnerMessage");
|
|
msg->nextBlockFast(_PREHASH_AgentData);
|
|
msg->addUUIDFast(_PREHASH_AgentID, gAgent.getID());
|
|
msg->addUUIDFast(_PREHASH_SessionID, gAgent.getSessionID());
|
|
msg->addUUIDFast(_PREHASH_TransactionID, LLUUID::null); //not used
|
|
|
|
msg->nextBlock("MethodData");
|
|
msg->addString("Method", "estatechangecovenantid");
|
|
msg->addUUID("Invoice", LLFloaterRegionInfo::getLastInvoice());
|
|
|
|
msg->nextBlock("ParamList");
|
|
msg->addString("Parameter", getCovenantID().asString());
|
|
gAgent.sendReliableMessage();
|
|
}
|
|
}
|
|
|
|
// virtual
|
|
BOOL LLPanelEstateCovenant::sendUpdate()
|
|
{
|
|
return TRUE;
|
|
}
|
|
|
|
const std::string& LLPanelEstateCovenant::getEstateName() const
|
|
{
|
|
return mEstateNameText->getText();
|
|
}
|
|
|
|
void LLPanelEstateCovenant::setEstateName(const std::string& name)
|
|
{
|
|
mEstateNameText->setText(name);
|
|
}
|
|
|
|
// static
|
|
void LLPanelEstateCovenant::updateCovenantText(const std::string& string, const LLUUID& asset_id)
|
|
{
|
|
LLPanelEstateCovenant* panelp = LLFloaterRegionInfo::getPanelCovenant();
|
|
if( panelp )
|
|
{
|
|
panelp->mEditor->setText(string);
|
|
panelp->setCovenantID(asset_id);
|
|
}
|
|
}
|
|
|
|
// static
|
|
void LLPanelEstateCovenant::updateEstateName(const std::string& name)
|
|
{
|
|
LLPanelEstateCovenant* panelp = LLFloaterRegionInfo::getPanelCovenant();
|
|
if( panelp )
|
|
{
|
|
panelp->mEstateNameText->setText(name);
|
|
}
|
|
}
|
|
|
|
// static
|
|
void LLPanelEstateCovenant::updateLastModified(const std::string& text)
|
|
{
|
|
LLPanelEstateCovenant* panelp = LLFloaterRegionInfo::getPanelCovenant();
|
|
if( panelp )
|
|
{
|
|
panelp->mLastModifiedText->setText(text);
|
|
}
|
|
}
|
|
|
|
// static
|
|
void LLPanelEstateCovenant::updateEstateOwnerName(const std::string& name)
|
|
{
|
|
LLPanelEstateCovenant* panelp = LLFloaterRegionInfo::getPanelCovenant();
|
|
if( panelp )
|
|
{
|
|
panelp->mEstateOwnerText->setText(name);
|
|
}
|
|
}
|
|
|
|
const std::string& LLPanelEstateCovenant::getOwnerName() const
|
|
{
|
|
return mEstateOwnerText->getText();
|
|
}
|
|
|
|
void LLPanelEstateCovenant::setOwnerName(const std::string& name)
|
|
{
|
|
mEstateOwnerText->setText(name);
|
|
}
|
|
|
|
void LLPanelEstateCovenant::setCovenantTextEditor(const std::string& text)
|
|
{
|
|
mEditor->setText(text);
|
|
}
|
|
|
|
// key = "estateupdateinfo"
|
|
// strings[0] = estate name
|
|
// strings[1] = str(owner_id)
|
|
// strings[2] = str(estate_id)
|
|
// strings[3] = str(estate_flags)
|
|
// strings[4] = str((S32)(sun_hour * 1024))
|
|
// strings[5] = str(parent_estate_id)
|
|
// strings[6] = str(covenant_id)
|
|
// strings[7] = str(covenant_timestamp)
|
|
// strings[8] = str(send_to_agent_only)
|
|
// strings[9] = str(abuse_email_addr)
|
|
bool LLDispatchEstateUpdateInfo::operator()(
|
|
const LLDispatcher* dispatcher,
|
|
const std::string& key,
|
|
const LLUUID& invoice,
|
|
const sparam_t& strings)
|
|
{
|
|
LLPanelEstateInfo* panel = LLFloaterRegionInfo::getPanelEstate();
|
|
if (!panel) return true;
|
|
|
|
// NOTE: LLDispatcher extracts strings with an extra \0 at the
|
|
// end. If we pass the std::string direct to the UI/renderer
|
|
// it draws with a weird character at the end of the string.
|
|
std::string estate_name = strings[0].c_str(); // preserve c_str() call!
|
|
panel->setEstateName(estate_name);
|
|
|
|
#if ELAR_ENABLED
|
|
if (strings.size() > 9)
|
|
{
|
|
std::string abuse_email = strings[9].c_str(); // preserve c_str() call!
|
|
panel->setAbuseEmailAddress(abuse_email);
|
|
}
|
|
else
|
|
#endif
|
|
{
|
|
panel->setAbuseEmailAddress(panel->getString("email_unsupported"));
|
|
}
|
|
|
|
LLViewerRegion* regionp = gAgent.getRegion();
|
|
|
|
LLUUID owner_id(strings[1]);
|
|
regionp->setOwner(owner_id);
|
|
// Update estate owner name in UI
|
|
const BOOL is_group = FALSE;
|
|
gCacheName->get(owner_id, is_group, LLPanelEstateInfo::callbackCacheName);
|
|
|
|
U32 estate_id = strtoul(strings[2].c_str(), NULL, 10);
|
|
panel->setEstateID(estate_id);
|
|
|
|
U32 flags = strtoul(strings[3].c_str(), NULL, 10);
|
|
panel->setEstateFlags(flags);
|
|
|
|
F32 sun_hour = ((F32)(strtod(strings[4].c_str(), NULL)))/1024.0f;
|
|
if(sun_hour == 0 && (flags & REGION_FLAGS_SUN_FIXED ? FALSE : TRUE))
|
|
{
|
|
panel->setGlobalTime(TRUE);
|
|
}
|
|
else
|
|
{
|
|
panel->setGlobalTime(FALSE);
|
|
panel->setSunHour(sun_hour);
|
|
}
|
|
|
|
bool visible_from_mainland = (bool)(flags & REGION_FLAGS_EXTERNALLY_VISIBLE);
|
|
bool god = gAgent.isGodlike();
|
|
bool linden_estate = (estate_id <= ESTATE_LAST_LINDEN);
|
|
|
|
// If visible from mainland, disable the access allowed
|
|
// UI, as anyone can teleport there.
|
|
// However, gods need to be able to edit the access list for
|
|
// linden estates, regardless of visibility, to allow object
|
|
// and L$ transfers.
|
|
bool enable_agent = (!visible_from_mainland || (god && linden_estate));
|
|
bool enable_group = enable_agent;
|
|
bool enable_ban = !linden_estate;
|
|
panel->setAccessAllowedEnabled(enable_agent, enable_group, enable_ban);
|
|
|
|
return true;
|
|
}
|
|
|
|
|
|
// key = "setaccess"
|
|
// strings[0] = str(estate_id)
|
|
// strings[1] = str(packed_access_lists)
|
|
// strings[2] = str(num allowed agent ids)
|
|
// strings[3] = str(num allowed group ids)
|
|
// strings[4] = str(num banned agent ids)
|
|
// strings[5] = str(num estate manager agent ids)
|
|
// strings[6] = bin(uuid)
|
|
// strings[7] = bin(uuid)
|
|
// strings[8] = bin(uuid)
|
|
// ...
|
|
bool LLDispatchSetEstateAccess::operator()(
|
|
const LLDispatcher* dispatcher,
|
|
const std::string& key,
|
|
const LLUUID& invoice,
|
|
const sparam_t& strings)
|
|
{
|
|
LLPanelEstateInfo* panel = LLFloaterRegionInfo::getPanelEstate();
|
|
if (!panel) return true;
|
|
|
|
S32 index = 1; // skip estate_id
|
|
U32 access_flags = strtoul(strings[index++].c_str(), NULL,10);
|
|
S32 num_allowed_agents = strtol(strings[index++].c_str(), NULL, 10);
|
|
S32 num_allowed_groups = strtol(strings[index++].c_str(), NULL, 10);
|
|
S32 num_banned_agents = strtol(strings[index++].c_str(), NULL, 10);
|
|
S32 num_estate_managers = strtol(strings[index++].c_str(), NULL, 10);
|
|
|
|
// sanity ckecks
|
|
if (num_allowed_agents > 0
|
|
&& !(access_flags & ESTATE_ACCESS_ALLOWED_AGENTS))
|
|
{
|
|
llwarns << "non-zero count for allowed agents, but no corresponding flag" << llendl;
|
|
}
|
|
if (num_allowed_groups > 0
|
|
&& !(access_flags & ESTATE_ACCESS_ALLOWED_GROUPS))
|
|
{
|
|
llwarns << "non-zero count for allowed groups, but no corresponding flag" << llendl;
|
|
}
|
|
if (num_banned_agents > 0
|
|
&& !(access_flags & ESTATE_ACCESS_BANNED_AGENTS))
|
|
{
|
|
llwarns << "non-zero count for banned agents, but no corresponding flag" << llendl;
|
|
}
|
|
if (num_estate_managers > 0
|
|
&& !(access_flags & ESTATE_ACCESS_MANAGERS))
|
|
{
|
|
llwarns << "non-zero count for managers, but no corresponding flag" << llendl;
|
|
}
|
|
|
|
// grab the UUID's out of the string fields
|
|
if (access_flags & ESTATE_ACCESS_ALLOWED_AGENTS)
|
|
{
|
|
LLNameListCtrl* allowed_agent_name_list;
|
|
allowed_agent_name_list = panel->getChild<LLNameListCtrl>("allowed_avatar_name_list");
|
|
|
|
int totalAllowedAgents = num_allowed_agents;
|
|
|
|
if (allowed_agent_name_list)
|
|
{
|
|
totalAllowedAgents += allowed_agent_name_list->getItemCount();
|
|
}
|
|
|
|
std::string msg = llformat("Allowed residents: (%d, max %d)",
|
|
totalAllowedAgents,
|
|
ESTATE_MAX_ACCESS_IDS);
|
|
panel->childSetValue("allow_resident_label", LLSD(msg));
|
|
|
|
if (allowed_agent_name_list)
|
|
{
|
|
//allowed_agent_name_list->deleteAllItems();
|
|
for (S32 i = 0; i < num_allowed_agents && i < ESTATE_MAX_ACCESS_IDS; i++)
|
|
{
|
|
LLUUID id;
|
|
memcpy(id.mData, strings[index++].data(), UUID_BYTES); /* Flawfinder: ignore */
|
|
allowed_agent_name_list->addNameItem(id);
|
|
}
|
|
panel->childSetEnabled("remove_allowed_avatar_btn", allowed_agent_name_list->getFirstSelected() ? TRUE : FALSE);
|
|
allowed_agent_name_list->sortByColumnIndex(0, TRUE);
|
|
}
|
|
}
|
|
|
|
if (access_flags & ESTATE_ACCESS_ALLOWED_GROUPS)
|
|
{
|
|
LLNameListCtrl* allowed_group_name_list;
|
|
allowed_group_name_list = panel->getChild<LLNameListCtrl>("allowed_group_name_list");
|
|
|
|
std::string msg = llformat("Allowed groups: (%d, max %d)",
|
|
num_allowed_groups,
|
|
(S32) ESTATE_MAX_GROUP_IDS);
|
|
panel->childSetValue("allow_group_label", LLSD(msg));
|
|
|
|
if (allowed_group_name_list)
|
|
{
|
|
allowed_group_name_list->deleteAllItems();
|
|
for (S32 i = 0; i < num_allowed_groups && i < ESTATE_MAX_GROUP_IDS; i++)
|
|
{
|
|
LLUUID id;
|
|
memcpy(id.mData, strings[index++].data(), UUID_BYTES); /* Flawfinder: ignore */
|
|
allowed_group_name_list->addGroupNameItem(id);
|
|
}
|
|
panel->childSetEnabled("remove_allowed_group_btn", allowed_group_name_list->getFirstSelected() ? TRUE : FALSE);
|
|
allowed_group_name_list->sortByColumnIndex(0, TRUE);
|
|
}
|
|
}
|
|
|
|
if (access_flags & ESTATE_ACCESS_BANNED_AGENTS)
|
|
{
|
|
LLNameListCtrl* banned_agent_name_list;
|
|
banned_agent_name_list = panel->getChild<LLNameListCtrl>("banned_avatar_name_list");
|
|
|
|
int totalBannedAgents = num_banned_agents;
|
|
|
|
if (banned_agent_name_list)
|
|
{
|
|
totalBannedAgents += banned_agent_name_list->getItemCount();
|
|
}
|
|
|
|
|
|
std::string msg = llformat("Banned residents: (%d, max %d)",
|
|
totalBannedAgents,
|
|
ESTATE_MAX_ACCESS_IDS);
|
|
panel->childSetValue("ban_resident_label", LLSD(msg));
|
|
|
|
if (banned_agent_name_list)
|
|
{
|
|
//banned_agent_name_list->deleteAllItems();
|
|
for (S32 i = 0; i < num_banned_agents && i < ESTATE_MAX_ACCESS_IDS; i++)
|
|
{
|
|
LLUUID id;
|
|
memcpy(id.mData, strings[index++].data(), UUID_BYTES); /* Flawfinder: ignore */
|
|
banned_agent_name_list->addNameItem(id);
|
|
}
|
|
panel->childSetEnabled("remove_banned_avatar_btn", banned_agent_name_list->getFirstSelected() ? TRUE : FALSE);
|
|
banned_agent_name_list->sortByColumnIndex(0, TRUE);
|
|
}
|
|
}
|
|
|
|
if (access_flags & ESTATE_ACCESS_MANAGERS)
|
|
{
|
|
std::string msg = llformat("Estate Managers: (%d, max %d)",
|
|
num_estate_managers,
|
|
ESTATE_MAX_MANAGERS);
|
|
panel->childSetValue("estate_manager_label", LLSD(msg));
|
|
|
|
LLNameListCtrl* estate_manager_name_list =
|
|
panel->getChild<LLNameListCtrl>("estate_manager_name_list");
|
|
if (estate_manager_name_list)
|
|
{
|
|
estate_manager_name_list->deleteAllItems(); // Clear existing entries
|
|
|
|
// There should be only ESTATE_MAX_MANAGERS people in the list, but if the database gets more (SL-46107) don't
|
|
// truncate the list unless it's really big. Go ahead and show the extras so the user doesn't get confused,
|
|
// and they can still remove them.
|
|
for (S32 i = 0; i < num_estate_managers && i < (ESTATE_MAX_MANAGERS * 4); i++)
|
|
{
|
|
LLUUID id;
|
|
memcpy(id.mData, strings[index++].data(), UUID_BYTES); /* Flawfinder: ignore */
|
|
estate_manager_name_list->addNameItem(id);
|
|
}
|
|
panel->childSetEnabled("remove_estate_manager_btn", estate_manager_name_list->getFirstSelected() ? TRUE : FALSE);
|
|
estate_manager_name_list->sortByColumnIndex(0, TRUE);
|
|
}
|
|
}
|
|
|
|
return true;
|
|
}
|
|
|
|
// [RLVa:KB] - Checked: 2009-07-04 (RLVa-1.0.0a)
|
|
void LLFloaterRegionInfo::open()
|
|
{
|
|
// We'll allow access to the estate tools for estate managers (and for the sim owner)
|
|
if (gRlvHandler.hasBehaviour(RLV_BHVR_SHOWLOC))
|
|
{
|
|
LLViewerRegion* pRegion = gAgent.getRegion();
|
|
if (!pRegion)
|
|
return;
|
|
|
|
// Should be able to call LLRegion::canManageEstate() but then we can fake god like
|
|
if ( (!pRegion->isEstateManager()) && (pRegion->getOwner() != gAgent.getID()) )
|
|
return;
|
|
}
|
|
|
|
LLFloater::open();
|
|
}
|
|
// [/RLVa:KB]
|