llfloaterland.cpp
上传用户:king477883
上传日期:2021-03-01
资源大小:9553k
文件大小:86k
源码类别:

游戏引擎

开发平台:

C++ Builder

  1. /** 
  2.  * @file llfloaterland.cpp
  3.  * @brief "About Land" floater, allowing display and editing of land parcel properties.
  4.  *
  5.  * $LicenseInfo:firstyear=2002&license=viewergpl$
  6.  * 
  7.  * Copyright (c) 2002-2010, Linden Research, Inc.
  8.  * 
  9.  * Second Life Viewer Source Code
  10.  * The source code in this file ("Source Code") is provided by Linden Lab
  11.  * to you under the terms of the GNU General Public License, version 2.0
  12.  * ("GPL"), unless you have obtained a separate licensing agreement
  13.  * ("Other License"), formally executed by you and Linden Lab.  Terms of
  14.  * the GPL can be found in doc/GPL-license.txt in this distribution, or
  15.  * online at http://secondlifegrid.net/programs/open_source/licensing/gplv2
  16.  * 
  17.  * There are special exceptions to the terms and conditions of the GPL as
  18.  * it is applied to this Source Code. View the full text of the exception
  19.  * in the file doc/FLOSS-exception.txt in this software distribution, or
  20.  * online at
  21.  * http://secondlifegrid.net/programs/open_source/licensing/flossexception
  22.  * 
  23.  * By copying, modifying or distributing this software, you acknowledge
  24.  * that you have read and understood your obligations described above,
  25.  * and agree to abide by those obligations.
  26.  * 
  27.  * ALL LINDEN LAB SOURCE CODE IS PROVIDED "AS IS." LINDEN LAB MAKES NO
  28.  * WARRANTIES, EXPRESS, IMPLIED OR OTHERWISE, REGARDING ITS ACCURACY,
  29.  * COMPLETENESS OR PERFORMANCE.
  30.  * $/LicenseInfo$
  31.  */
  32. #include "llviewerprecompiledheaders.h"
  33. #include <sstream>
  34. #include <time.h>
  35. #include "llfloaterland.h"
  36. #include "llcachename.h"
  37. #include "llfocusmgr.h"
  38. #include "llnotificationsutil.h"
  39. #include "llparcel.h"
  40. #include "message.h"
  41. #include "lluserauth.h"
  42. #include "llagent.h"
  43. #include "llbutton.h"
  44. #include "llcheckboxctrl.h"
  45. #include "llcombobox.h"
  46. #include "llfloaterreg.h"
  47. #include "llfloateravatarpicker.h"
  48. #include "llfloaterauction.h"
  49. #include "llfloatergroups.h"
  50. #include "llfloaterscriptlimits.h"
  51. #include "llavataractions.h"
  52. #include "lllineeditor.h"
  53. #include "llnamelistctrl.h"
  54. #include "llpanellandaudio.h"
  55. #include "llpanellandmedia.h"
  56. #include "llradiogroup.h"
  57. #include "llscrolllistctrl.h"
  58. #include "llscrolllistitem.h"
  59. #include "llscrolllistcell.h"
  60. #include "llselectmgr.h"
  61. #include "llslurl.h"
  62. #include "llspinctrl.h"
  63. #include "lltabcontainer.h"
  64. #include "lltextbox.h"
  65. #include "lltexturectrl.h"
  66. #include "lluiconstants.h"
  67. #include "lluictrlfactory.h"
  68. #include "llviewertexturelist.h" // LLUIImageList
  69. #include "llviewermessage.h"
  70. #include "llviewerparcelmgr.h"
  71. #include "llviewerregion.h"
  72. #include "llviewerstats.h"
  73. #include "llviewertexteditor.h"
  74. #include "llviewerwindow.h"
  75. #include "llviewercontrol.h"
  76. #include "roles_constants.h"
  77. #include "lltrans.h"
  78. #include "llgroupactions.h"
  79. static std::string OWNER_ONLINE  = "0";
  80. static std::string OWNER_OFFLINE = "1";
  81. static std::string OWNER_GROUP  = "2";
  82. // constants used in callbacks below - syntactic sugar.
  83. static const BOOL BUY_GROUP_LAND = TRUE;
  84. static const BOOL BUY_PERSONAL_LAND = FALSE;
  85. // Statics
  86. LLParcelSelectionObserver* LLFloaterLand::sObserver = NULL;
  87. S32 LLFloaterLand::sLastTab = 0;
  88. // Local classes
  89. class LLParcelSelectionObserver : public LLParcelObserver
  90. {
  91. public:
  92. virtual void changed() { LLFloaterLand::refreshAll(); }
  93. };
  94. //---------------------------------------------------------------------------
  95. // LLFloaterLand
  96. //---------------------------------------------------------------------------
  97. void send_parcel_select_objects(S32 parcel_local_id, U32 return_type,
  98. uuid_list_t* return_ids = NULL)
  99. {
  100. LLMessageSystem *msg = gMessageSystem;
  101. LLViewerRegion* region = LLViewerParcelMgr::getInstance()->getSelectionRegion();
  102. if (!region) return;
  103. // Since new highlight will be coming in, drop any highlights
  104. // that exist right now.
  105. LLSelectMgr::getInstance()->unhighlightAll();
  106. msg->newMessageFast(_PREHASH_ParcelSelectObjects);
  107. msg->nextBlockFast(_PREHASH_AgentData);
  108. msg->addUUIDFast(_PREHASH_AgentID, gAgent.getID());
  109. msg->addUUIDFast(_PREHASH_SessionID,gAgent.getSessionID());
  110. msg->nextBlockFast(_PREHASH_ParcelData);
  111. msg->addS32Fast(_PREHASH_LocalID, parcel_local_id);
  112. msg->addU32Fast(_PREHASH_ReturnType, return_type);
  113. // Throw all return ids into the packet.
  114. // TODO: Check for too many ids.
  115. if (return_ids)
  116. {
  117. uuid_list_t::iterator end = return_ids->end();
  118. for (uuid_list_t::iterator it = return_ids->begin();
  119.  it != end;
  120.  ++it)
  121. {
  122. msg->nextBlockFast(_PREHASH_ReturnIDs);
  123. msg->addUUIDFast(_PREHASH_ReturnID, (*it));
  124. }
  125. }
  126. else
  127. {
  128. // Put in a null key so that the message is complete.
  129. msg->nextBlockFast(_PREHASH_ReturnIDs);
  130. msg->addUUIDFast(_PREHASH_ReturnID, LLUUID::null);
  131. }
  132. msg->sendReliable(region->getHost());
  133. }
  134. LLParcel* LLFloaterLand::getCurrentSelectedParcel()
  135. {
  136. return mParcel->getParcel();
  137. };
  138. //static
  139. LLPanelLandObjects* LLFloaterLand::getCurrentPanelLandObjects()
  140. {
  141. LLFloaterLand* land_instance = LLFloaterReg::getTypedInstance<LLFloaterLand>("about_land");
  142. if(land_instance)
  143. {
  144. return land_instance->mPanelObjects;
  145. }
  146. else
  147. {
  148. return NULL;
  149. }
  150. }
  151. //static
  152. LLPanelLandCovenant* LLFloaterLand::getCurrentPanelLandCovenant()
  153. {
  154. LLFloaterLand* land_instance = LLFloaterReg::getTypedInstance<LLFloaterLand>("about_land");
  155. if(land_instance)
  156. {
  157. return land_instance->mPanelCovenant;
  158. }
  159. else
  160. {
  161. return NULL;
  162. }
  163. }
  164. // static
  165. void LLFloaterLand::refreshAll()
  166. {
  167. LLFloaterLand* land_instance = LLFloaterReg::getTypedInstance<LLFloaterLand>("about_land");
  168. if(land_instance)
  169. {
  170. land_instance->refresh();
  171. }
  172. }
  173. void LLFloaterLand::onOpen(const LLSD& key)
  174. {
  175. // moved from triggering show instance in llviwermenu.cpp
  176. if (LLViewerParcelMgr::getInstance()->selectionEmpty())
  177. {
  178. LLViewerParcelMgr::getInstance()->selectParcelAt(gAgent.getPositionGlobal());
  179. }
  180. // Done automatically when the selected parcel's properties arrive
  181. // (and hence we have the local id).
  182. // LLViewerParcelMgr::getInstance()->sendParcelAccessListRequest(AL_ACCESS | AL_BAN | AL_RENTER);
  183. mParcel = LLViewerParcelMgr::getInstance()->getFloatingParcelSelection();
  184. // Refresh even if not over a region so we don't get an
  185. // uninitialized dialog. The dialog is 0-region aware.
  186. refresh();
  187. }
  188. void LLFloaterLand::onVisibilityChange(const LLSD& visible)
  189. {
  190. if (!visible.asBoolean())
  191. {
  192. // Might have been showing owned objects
  193. LLSelectMgr::getInstance()->unhighlightAll();
  194. // Save which panel we had open
  195. sLastTab = mTabLand->getCurrentPanelIndex();
  196. }
  197. }
  198. LLFloaterLand::LLFloaterLand(const LLSD& seed)
  199. : LLFloater(seed)
  200. {
  201. mFactoryMap["land_general_panel"] = LLCallbackMap(createPanelLandGeneral, this);
  202. mFactoryMap["land_covenant_panel"] = LLCallbackMap(createPanelLandCovenant, this);
  203. mFactoryMap["land_objects_panel"] = LLCallbackMap(createPanelLandObjects, this);
  204. mFactoryMap["land_options_panel"] = LLCallbackMap(createPanelLandOptions, this);
  205. mFactoryMap["land_audio_panel"] = LLCallbackMap(createPanelLandAudio, this);
  206. mFactoryMap["land_media_panel"] = LLCallbackMap(createPanelLandMedia, this);
  207. mFactoryMap["land_access_panel"] = LLCallbackMap(createPanelLandAccess, this);
  208. //LLUICtrlFactory::getInstance()->buildFloater(this, "floater_about_land.xml", false);
  209. sObserver = new LLParcelSelectionObserver();
  210. LLViewerParcelMgr::getInstance()->addObserver( sObserver );
  211. }
  212. BOOL LLFloaterLand::postBuild()
  213. {
  214. setVisibleCallback(boost::bind(&LLFloaterLand::onVisibilityChange, this, _2));
  215. LLTabContainer* tab = getChild<LLTabContainer>("landtab");
  216. mTabLand = (LLTabContainer*) tab;
  217. if (tab)
  218. {
  219. tab->selectTab(sLastTab);
  220. }
  221. return TRUE;
  222. }
  223. // virtual
  224. LLFloaterLand::~LLFloaterLand()
  225. {
  226. LLViewerParcelMgr::getInstance()->removeObserver( sObserver );
  227. delete sObserver;
  228. sObserver = NULL;
  229. }
  230. // public
  231. void LLFloaterLand::refresh()
  232. {
  233. mPanelGeneral->refresh();
  234. mPanelObjects->refresh();
  235. mPanelOptions->refresh();
  236. mPanelAudio->refresh();
  237. mPanelMedia->refresh();
  238. mPanelAccess->refresh();
  239. mPanelCovenant->refresh();
  240. }
  241. void* LLFloaterLand::createPanelLandGeneral(void* data)
  242. {
  243. LLFloaterLand* self = (LLFloaterLand*)data;
  244. self->mPanelGeneral = new LLPanelLandGeneral(self->mParcel);
  245. return self->mPanelGeneral;
  246. }
  247. // static
  248. void* LLFloaterLand::createPanelLandCovenant(void* data)
  249. {
  250. LLFloaterLand* self = (LLFloaterLand*)data;
  251. self->mPanelCovenant = new LLPanelLandCovenant(self->mParcel);
  252. return self->mPanelCovenant;
  253. }
  254. // static
  255. void* LLFloaterLand::createPanelLandObjects(void* data)
  256. {
  257. LLFloaterLand* self = (LLFloaterLand*)data;
  258. self->mPanelObjects = new LLPanelLandObjects(self->mParcel);
  259. return self->mPanelObjects;
  260. }
  261. // static
  262. void* LLFloaterLand::createPanelLandOptions(void* data)
  263. {
  264. LLFloaterLand* self = (LLFloaterLand*)data;
  265. self->mPanelOptions = new LLPanelLandOptions(self->mParcel);
  266. return self->mPanelOptions;
  267. }
  268. // static
  269. void* LLFloaterLand::createPanelLandAudio(void* data)
  270. {
  271. LLFloaterLand* self = (LLFloaterLand*)data;
  272. self->mPanelAudio = new LLPanelLandAudio(self->mParcel);
  273. return self->mPanelAudio;
  274. }
  275. // static
  276. void* LLFloaterLand::createPanelLandMedia(void* data)
  277. {
  278. LLFloaterLand* self = (LLFloaterLand*)data;
  279. self->mPanelMedia = new LLPanelLandMedia(self->mParcel);
  280. return self->mPanelMedia;
  281. }
  282. // static
  283. void* LLFloaterLand::createPanelLandAccess(void* data)
  284. {
  285. LLFloaterLand* self = (LLFloaterLand*)data;
  286. self->mPanelAccess = new LLPanelLandAccess(self->mParcel);
  287. return self->mPanelAccess;
  288. }
  289. //---------------------------------------------------------------------------
  290. // LLPanelLandGeneral
  291. //---------------------------------------------------------------------------
  292. LLPanelLandGeneral::LLPanelLandGeneral(LLParcelSelectionHandle& parcel)
  293. : LLPanel(),
  294. mUncheckedSell(FALSE),
  295. mParcel(parcel)
  296. {
  297. }
  298. BOOL LLPanelLandGeneral::postBuild()
  299. {
  300. mEditName = getChild<LLLineEditor>("Name");
  301. mEditName->setCommitCallback(onCommitAny, this);
  302. childSetPrevalidate("Name", LLTextValidate::validateASCIIPrintableNoPipe);
  303. mEditDesc = getChild<LLTextEditor>("Description");
  304. mEditDesc->setCommitOnFocusLost(TRUE);
  305. mEditDesc->setCommitCallback(onCommitAny, this);
  306. // No prevalidate function - historically the prevalidate function was broken,
  307. // allowing residents to put in characters like U+2661 WHITE HEART SUIT, so
  308. // preserve that ability.
  309. mTextSalePending = getChild<LLTextBox>("SalePending");
  310. mTextOwnerLabel = getChild<LLTextBox>("Owner:");
  311. mTextOwner = getChild<LLTextBox>("OwnerText");
  312. mContentRating = getChild<LLTextBox>("ContentRatingText");
  313. mLandType = getChild<LLTextBox>("LandTypeText");
  314. mBtnProfile = getChild<LLButton>("Profile...");
  315. mBtnProfile->setClickedCallback(onClickProfile, this);
  316. mTextGroupLabel = getChild<LLTextBox>("Group:");
  317. mTextGroup = getChild<LLTextBox>("GroupText");
  318. mBtnSetGroup = getChild<LLButton>("Set...");
  319. mBtnSetGroup->setCommitCallback(boost::bind(&LLPanelLandGeneral::onClickSetGroup, this));
  320. mCheckDeedToGroup = getChild<LLCheckBoxCtrl>( "check deed");
  321. childSetCommitCallback("check deed", onCommitAny, this);
  322. mBtnDeedToGroup = getChild<LLButton>("Deed...");
  323. mBtnDeedToGroup->setClickedCallback(onClickDeed, this);
  324. mCheckContributeWithDeed = getChild<LLCheckBoxCtrl>( "check contrib");
  325. childSetCommitCallback("check contrib", onCommitAny, this);
  326. mSaleInfoNotForSale = getChild<LLTextBox>("Not for sale.");
  327. mSaleInfoForSale1 = getChild<LLTextBox>("For Sale: Price L$[PRICE].");
  328. mBtnSellLand = getChild<LLButton>("Sell Land...");
  329. mBtnSellLand->setClickedCallback(onClickSellLand, this);
  330. mSaleInfoForSale2 = getChild<LLTextBox>("For sale to");
  331. mSaleInfoForSaleObjects = getChild<LLTextBox>("Sell with landowners objects in parcel.");
  332. mSaleInfoForSaleNoObjects = getChild<LLTextBox>("Selling with no objects in parcel.");
  333. mBtnStopSellLand = getChild<LLButton>("Cancel Land Sale");
  334. mBtnStopSellLand->setClickedCallback(onClickStopSellLand, this);
  335. mTextClaimDateLabel = getChild<LLTextBox>("Claimed:");
  336. mTextClaimDate = getChild<LLTextBox>("DateClaimText");
  337. mTextPriceLabel = getChild<LLTextBox>("PriceLabel");
  338. mTextPrice = getChild<LLTextBox>("PriceText");
  339. mTextDwell = getChild<LLTextBox>("DwellText");
  340. mBtnBuyLand = getChild<LLButton>("Buy Land...");
  341. mBtnBuyLand->setClickedCallback(onClickBuyLand, (void*)&BUY_PERSONAL_LAND);
  342. // note: on region change this will not be re checked, should not matter on Agni as
  343. // 99% of the time all regions will return the same caps. In case of an erroneous setting
  344. // to enabled the floater will just throw an error when trying to get it's cap
  345. std::string url = gAgent.getRegion()->getCapability("LandResources");
  346. if (!url.empty())
  347. {
  348. mBtnScriptLimits = getChild<LLButton>("Scripts...");
  349. if(mBtnScriptLimits)
  350. {
  351. mBtnScriptLimits->setClickedCallback(onClickScriptLimits, this);
  352. }
  353. }
  354. else
  355. {
  356. mBtnScriptLimits = getChild<LLButton>("Scripts...");
  357. if(mBtnScriptLimits)
  358. {
  359. mBtnScriptLimits->setVisible(false);
  360. }
  361. }
  362. mBtnBuyGroupLand = getChild<LLButton>("Buy For Group...");
  363. mBtnBuyGroupLand->setClickedCallback(onClickBuyLand, (void*)&BUY_GROUP_LAND);
  364. mBtnBuyPass = getChild<LLButton>("Buy Pass...");
  365. mBtnBuyPass->setClickedCallback(onClickBuyPass, this);
  366. mBtnReleaseLand = getChild<LLButton>("Abandon Land...");
  367. mBtnReleaseLand->setClickedCallback(onClickRelease, NULL);
  368. mBtnReclaimLand = getChild<LLButton>("Reclaim Land...");
  369. mBtnReclaimLand->setClickedCallback(onClickReclaim, NULL);
  370. mBtnStartAuction = getChild<LLButton>("Linden Sale...");
  371. mBtnStartAuction->setClickedCallback(onClickStartAuction, this);
  372. return TRUE;
  373. }
  374. // virtual
  375. LLPanelLandGeneral::~LLPanelLandGeneral()
  376. { }
  377. // public
  378. void LLPanelLandGeneral::refresh()
  379. {
  380. mBtnStartAuction->setVisible(gAgent.isGodlike());
  381. LLParcel *parcel = mParcel->getParcel();
  382. bool region_owner = false;
  383. LLViewerRegion* regionp = LLViewerParcelMgr::getInstance()->getSelectionRegion();
  384. if(regionp && (regionp->getOwner() == gAgent.getID()))
  385. {
  386. region_owner = true;
  387. mBtnReleaseLand->setVisible(FALSE);
  388. mBtnReclaimLand->setVisible(TRUE);
  389. }
  390. else
  391. {
  392. mBtnReleaseLand->setVisible(TRUE);
  393. mBtnReclaimLand->setVisible(FALSE);
  394. }
  395. if (!parcel)
  396. {
  397. // nothing selected, disable panel
  398. mEditName->setEnabled(FALSE);
  399. mEditName->setText(LLStringUtil::null);
  400. mEditDesc->setEnabled(FALSE);
  401. mEditDesc->setText(getString("no_selection_text"));
  402. mTextSalePending->setText(LLStringUtil::null);
  403. mTextSalePending->setEnabled(FALSE);
  404. mBtnDeedToGroup->setEnabled(FALSE);
  405. mBtnSetGroup->setEnabled(FALSE);
  406. mBtnStartAuction->setEnabled(FALSE);
  407. mCheckDeedToGroup ->set(FALSE);
  408. mCheckDeedToGroup ->setEnabled(FALSE);
  409. mCheckContributeWithDeed->set(FALSE);
  410. mCheckContributeWithDeed->setEnabled(FALSE);
  411. mTextOwner->setText(LLStringUtil::null);
  412. mContentRating->setText(LLStringUtil::null);
  413. mLandType->setText(LLStringUtil::null);
  414. mBtnProfile->setLabel(getString("profile_text"));
  415. mBtnProfile->setEnabled(FALSE);
  416. mTextClaimDate->setText(LLStringUtil::null);
  417. mTextGroup->setText(LLStringUtil::null);
  418. mTextPrice->setText(LLStringUtil::null);
  419. mSaleInfoForSale1->setVisible(FALSE);
  420. mSaleInfoForSale2->setVisible(FALSE);
  421. mSaleInfoForSaleObjects->setVisible(FALSE);
  422. mSaleInfoForSaleNoObjects->setVisible(FALSE);
  423. mSaleInfoNotForSale->setVisible(FALSE);
  424. mBtnSellLand->setVisible(FALSE);
  425. mBtnStopSellLand->setVisible(FALSE);
  426. mTextPriceLabel->setText(LLStringUtil::null);
  427. mTextDwell->setText(LLStringUtil::null);
  428. mBtnBuyLand->setEnabled(FALSE);
  429. mBtnScriptLimits->setEnabled(FALSE);
  430. mBtnBuyGroupLand->setEnabled(FALSE);
  431. mBtnReleaseLand->setEnabled(FALSE);
  432. mBtnReclaimLand->setEnabled(FALSE);
  433. mBtnBuyPass->setEnabled(FALSE);
  434. }
  435. else
  436. {
  437. // something selected, hooray!
  438. BOOL is_leased = (LLParcel::OS_LEASED == parcel->getOwnershipStatus());
  439. BOOL region_xfer = FALSE;
  440. if(regionp
  441.    && !(regionp->getRegionFlags() & REGION_FLAGS_BLOCK_LAND_RESELL))
  442. {
  443. region_xfer = TRUE;
  444. }
  445. if (regionp)
  446. {
  447. mContentRating->setText(regionp->getSimAccessString());
  448. mLandType->setText(regionp->getSimProductName());
  449. }
  450. // estate owner/manager cannot edit other parts of the parcel
  451. BOOL estate_manager_sellable = !parcel->getAuctionID()
  452. && gAgent.canManageEstate()
  453. // estate manager/owner can only sell parcels owned by estate owner
  454. && regionp
  455. && (parcel->getOwnerID() == regionp->getOwner());
  456. BOOL owner_sellable = region_xfer && !parcel->getAuctionID()
  457. && LLViewerParcelMgr::isParcelModifiableByAgent(
  458. parcel, GP_LAND_SET_SALE_INFO);
  459. BOOL can_be_sold = owner_sellable || estate_manager_sellable;
  460. const LLUUID &owner_id = parcel->getOwnerID();
  461. BOOL is_public = parcel->isPublic();
  462. // Is it owned?
  463. if (is_public)
  464. {
  465. mTextSalePending->setText(LLStringUtil::null);
  466. mTextSalePending->setEnabled(FALSE);
  467. mTextOwner->setText(getString("public_text"));
  468. mTextOwner->setEnabled(FALSE);
  469. mBtnProfile->setEnabled(FALSE);
  470. mTextClaimDate->setText(LLStringUtil::null);
  471. mTextClaimDate->setEnabled(FALSE);
  472. mTextGroup->setText(getString("none_text"));
  473. mTextGroup->setEnabled(FALSE);
  474. mBtnStartAuction->setEnabled(FALSE);
  475. }
  476. else
  477. {
  478. if(!is_leased && (owner_id == gAgent.getID()))
  479. {
  480. mTextSalePending->setText(getString("need_tier_to_modify"));
  481. mTextSalePending->setEnabled(TRUE);
  482. }
  483. else if(parcel->getAuctionID())
  484. {
  485. mTextSalePending->setText(getString("auction_id_text"));
  486. mTextSalePending->setTextArg("[ID]", llformat("%u", parcel->getAuctionID()));
  487. mTextSalePending->setEnabled(TRUE);
  488. }
  489. else
  490. {
  491. // not the owner, or it is leased
  492. mTextSalePending->setText(LLStringUtil::null);
  493. mTextSalePending->setEnabled(FALSE);
  494. }
  495. //refreshNames();
  496. mTextOwner->setEnabled(TRUE);
  497. // We support both group and personal profiles
  498. mBtnProfile->setEnabled(TRUE);
  499. if (parcel->getGroupID().isNull())
  500. {
  501. // Not group owned, so "Profile"
  502. mBtnProfile->setLabel(getString("profile_text"));
  503. mTextGroup->setText(getString("none_text"));
  504. mTextGroup->setEnabled(FALSE);
  505. }
  506. else
  507. {
  508. // Group owned, so "Info"
  509. mBtnProfile->setLabel(getString("info_text"));
  510. //mTextGroup->setText("HIPPOS!");//parcel->getGroupName());
  511. mTextGroup->setEnabled(TRUE);
  512. }
  513. // Display claim date
  514. // *TODO:Localize (Time format may need Translating)
  515. time_t claim_date = parcel->getClaimDate();
  516. mTextClaimDate->setText(formatted_time(claim_date));
  517. mTextClaimDate->setEnabled(is_leased);
  518. BOOL enable_auction = (gAgent.getGodLevel() >= GOD_LIAISON)
  519.   && (owner_id == GOVERNOR_LINDEN_ID)
  520.   && (parcel->getAuctionID() == 0);
  521. mBtnStartAuction->setEnabled(enable_auction);
  522. }
  523. // Display options
  524. BOOL can_edit_identity = LLViewerParcelMgr::isParcelModifiableByAgent(parcel, GP_LAND_CHANGE_IDENTITY);
  525. mEditName->setEnabled(can_edit_identity);
  526. mEditDesc->setEnabled(can_edit_identity);
  527. BOOL can_edit_agent_only = LLViewerParcelMgr::isParcelModifiableByAgent(parcel, GP_NO_POWERS);
  528. mBtnSetGroup->setEnabled(can_edit_agent_only && !parcel->getIsGroupOwned());
  529. const LLUUID& group_id = parcel->getGroupID();
  530. // Can only allow deeding if you own it and it's got a group.
  531. BOOL enable_deed = (owner_id == gAgent.getID()
  532. && group_id.notNull()
  533. && gAgent.isInGroup(group_id));
  534. // You don't need special powers to allow your object to
  535. // be deeded to the group.
  536. mCheckDeedToGroup->setEnabled(enable_deed);
  537. mCheckDeedToGroup->set( parcel->getAllowDeedToGroup() );
  538. mCheckContributeWithDeed->setEnabled(enable_deed && parcel->getAllowDeedToGroup());
  539. mCheckContributeWithDeed->set(parcel->getContributeWithDeed());
  540. // Actually doing the deeding requires you to have GP_LAND_DEED
  541. // powers in the group.
  542. BOOL can_deed = gAgent.hasPowerInGroup(group_id, GP_LAND_DEED);
  543. mBtnDeedToGroup->setEnabled(   parcel->getAllowDeedToGroup()
  544. && group_id.notNull()
  545. && can_deed
  546. && !parcel->getIsGroupOwned()
  547. );
  548. mEditName->setText( parcel->getName() );
  549. mEditDesc->setText( parcel->getDesc() );
  550. BOOL for_sale = parcel->getForSale();
  551. mBtnSellLand->setVisible(FALSE);
  552. mBtnStopSellLand->setVisible(FALSE);
  553. // show pricing information
  554. S32 area;
  555. S32 claim_price;
  556. S32 rent_price;
  557. F32 dwell;
  558. LLViewerParcelMgr::getInstance()->getDisplayInfo(&area,
  559.  &claim_price,
  560.  &rent_price,
  561.  &for_sale,
  562.  &dwell);
  563. // Area
  564. LLUIString price = getString("area_size_text");
  565. price.setArg("[AREA]", llformat("%d",area));    
  566. mTextPriceLabel->setText(getString("area_text"));
  567. mTextPrice->setText(price.getString());
  568. mTextDwell->setText(llformat("%.0f", dwell));
  569. if (for_sale)
  570. {
  571. mSaleInfoForSale1->setVisible(TRUE);
  572. mSaleInfoForSale2->setVisible(TRUE);
  573. if (parcel->getSellWithObjects())
  574. {
  575. mSaleInfoForSaleObjects->setVisible(TRUE);
  576. mSaleInfoForSaleNoObjects->setVisible(FALSE);
  577. }
  578. else
  579. {
  580. mSaleInfoForSaleObjects->setVisible(FALSE);
  581. mSaleInfoForSaleNoObjects->setVisible(TRUE);
  582. }
  583. mSaleInfoNotForSale->setVisible(FALSE);
  584. F32 cost_per_sqm = 0.0f;
  585. if (area > 0)
  586. {
  587. cost_per_sqm = (F32)parcel->getSalePrice() / (F32)area;
  588. }
  589. mSaleInfoForSale1->setTextArg("[PRICE]", llformat("%d", parcel->getSalePrice()));
  590. mSaleInfoForSale1->setTextArg("[PRICE_PER_SQM]", llformat("%.1f", cost_per_sqm));
  591. if (can_be_sold)
  592. {
  593. mBtnStopSellLand->setVisible(TRUE);
  594. }
  595. }
  596. else
  597. {
  598. mSaleInfoForSale1->setVisible(FALSE);
  599. mSaleInfoForSale2->setVisible(FALSE);
  600. mSaleInfoForSaleObjects->setVisible(FALSE);
  601. mSaleInfoForSaleNoObjects->setVisible(FALSE);
  602. mSaleInfoNotForSale->setVisible(TRUE);
  603. if (can_be_sold)
  604. {
  605. mBtnSellLand->setVisible(TRUE);
  606. }
  607. }
  608. refreshNames();
  609. mBtnBuyLand->setEnabled(
  610. LLViewerParcelMgr::getInstance()->canAgentBuyParcel(parcel, false));
  611. mBtnScriptLimits->setEnabled(true);
  612. // LLViewerParcelMgr::getInstance()->canAgentBuyParcel(parcel, false));
  613. mBtnBuyGroupLand->setEnabled(
  614. LLViewerParcelMgr::getInstance()->canAgentBuyParcel(parcel, true));
  615. if(region_owner)
  616. {
  617. mBtnReclaimLand->setEnabled(
  618. !is_public && (parcel->getOwnerID() != gAgent.getID()));
  619. }
  620. else
  621. {
  622. BOOL is_owner_release = LLViewerParcelMgr::isParcelOwnedByAgent(parcel, GP_LAND_RELEASE);
  623. BOOL is_manager_release = (gAgent.canManageEstate() && 
  624. regionp && 
  625. (parcel->getOwnerID() != regionp->getOwner()));
  626. BOOL can_release = is_owner_release || is_manager_release;
  627. mBtnReleaseLand->setEnabled( can_release );
  628. }
  629. BOOL use_pass = parcel->getParcelFlag(PF_USE_PASS_LIST) && !LLViewerParcelMgr::getInstance()->isCollisionBanned();;
  630. mBtnBuyPass->setEnabled(use_pass);
  631. }
  632. }
  633. // public
  634. void LLPanelLandGeneral::refreshNames()
  635. {
  636. LLParcel *parcel = mParcel->getParcel();
  637. if (!parcel)
  638. {
  639. mTextOwner->setText(LLStringUtil::null);
  640. mTextGroup->setText(LLStringUtil::null);
  641. return;
  642. }
  643. std::string owner;
  644. if (parcel->getIsGroupOwned())
  645. {
  646. owner = getString("group_owned_text");
  647. }
  648. else
  649. {
  650. // Figure out the owner's name
  651. owner = LLSLURL::buildCommand("agent", parcel->getOwnerID(), "inspect");
  652. }
  653. if(LLParcel::OS_LEASE_PENDING == parcel->getOwnershipStatus())
  654. {
  655. owner += getString("sale_pending_text");
  656. }
  657. mTextOwner->setText(owner);
  658. std::string group;
  659. if (!parcel->getGroupID().isNull())
  660. {
  661. group = LLSLURL::buildCommand("group", parcel->getGroupID(), "inspect");
  662. }
  663. mTextGroup->setText(group);
  664. const LLUUID& auth_buyer_id = parcel->getAuthorizedBuyerID();
  665. if(auth_buyer_id.notNull())
  666. {
  667. std::string name;
  668. name = LLSLURL::buildCommand("agent", auth_buyer_id, "inspect");
  669. mSaleInfoForSale2->setTextArg("[BUYER]", name);
  670. }
  671. else
  672. {
  673. mSaleInfoForSale2->setTextArg("[BUYER]", getString("anyone"));
  674. }
  675. }
  676. // virtual
  677. void LLPanelLandGeneral::draw()
  678. {
  679. LLPanel::draw();
  680. }
  681. void LLPanelLandGeneral::onClickSetGroup()
  682. {
  683. LLFloater* parent_floater = gFloaterView->getParentFloater(this);
  684. LLFloaterGroupPicker* fg =  LLFloaterReg::showTypedInstance<LLFloaterGroupPicker>("group_picker", LLSD(gAgent.getID()));
  685. if (fg)
  686. {
  687. fg->setSelectGroupCallback( boost::bind(&LLPanelLandGeneral::setGroup, this, _1 ));
  688. if (parent_floater)
  689. {
  690. LLRect new_rect = gFloaterView->findNeighboringPosition(parent_floater, fg);
  691. fg->setOrigin(new_rect.mLeft, new_rect.mBottom);
  692. parent_floater->addDependentFloater(fg);
  693. }
  694. }
  695. }
  696. // static
  697. void LLPanelLandGeneral::onClickProfile(void* data)
  698. {
  699. LLPanelLandGeneral* panelp = (LLPanelLandGeneral*)data;
  700. LLParcel* parcel = panelp->mParcel->getParcel();
  701. if (!parcel) return;
  702. if (parcel->getIsGroupOwned())
  703. {
  704. const LLUUID& group_id = parcel->getGroupID();
  705. LLGroupActions::show(group_id);
  706. }
  707. else
  708. {
  709. const LLUUID& avatar_id = parcel->getOwnerID();
  710. LLAvatarActions::showProfile(avatar_id);
  711. }
  712. }
  713. // public
  714. void LLPanelLandGeneral::setGroup(const LLUUID& group_id)
  715. {
  716. LLParcel* parcel = mParcel->getParcel();
  717. if (!parcel) return;
  718. // Set parcel properties and send message
  719. parcel->setGroupID(group_id);
  720. //parcel->setGroupName(group_name);
  721. //mTextGroup->setText(group_name);
  722. // Send update
  723. LLViewerParcelMgr::getInstance()->sendParcelPropertiesUpdate(parcel);
  724. // Update UI
  725. refresh();
  726. }
  727. // static
  728. void LLPanelLandGeneral::onClickBuyLand(void* data)
  729. {
  730. BOOL* for_group = (BOOL*)data;
  731. LLViewerParcelMgr::getInstance()->startBuyLand(*for_group);
  732. }
  733. // static
  734. void LLPanelLandGeneral::onClickScriptLimits(void* data)
  735. {
  736. LLPanelLandGeneral* panelp = (LLPanelLandGeneral*)data;
  737. LLParcel* parcel = panelp->mParcel->getParcel();
  738. if(parcel != NULL)
  739. {
  740. LLFloaterReg::showInstance("script_limits");
  741. }
  742. }
  743. BOOL LLPanelLandGeneral::enableDeedToGroup(void* data)
  744. {
  745. LLPanelLandGeneral* panelp = (LLPanelLandGeneral*)data;
  746. LLParcel* parcel = panelp->mParcel->getParcel();
  747. return (parcel != NULL) && (parcel->getParcelFlag(PF_ALLOW_DEED_TO_GROUP));
  748. }
  749. // static
  750. void LLPanelLandGeneral::onClickDeed(void*)
  751. {
  752. //LLParcel* parcel = mParcel->getParcel();
  753. //if (parcel)
  754. //{
  755. LLViewerParcelMgr::getInstance()->startDeedLandToGroup();
  756. //}
  757. }
  758. // static
  759. void LLPanelLandGeneral::onClickRelease(void*)
  760. {
  761. LLViewerParcelMgr::getInstance()->startReleaseLand();
  762. }
  763. // static
  764. void LLPanelLandGeneral::onClickReclaim(void*)
  765. {
  766. lldebugs << "LLPanelLandGeneral::onClickReclaim()" << llendl;
  767. LLViewerParcelMgr::getInstance()->reclaimParcel();
  768. }
  769. // static
  770. BOOL LLPanelLandGeneral::enableBuyPass(void* data)
  771. {
  772. LLPanelLandGeneral* panelp = (LLPanelLandGeneral*)data;
  773. LLParcel* parcel = panelp != NULL ? panelp->mParcel->getParcel() : LLViewerParcelMgr::getInstance()->getParcelSelection()->getParcel();
  774. return (parcel != NULL) && (parcel->getParcelFlag(PF_USE_PASS_LIST) && !LLViewerParcelMgr::getInstance()->isCollisionBanned());
  775. }
  776. // static
  777. void LLPanelLandGeneral::onClickBuyPass(void* data)
  778. {
  779. LLPanelLandGeneral* panelp = (LLPanelLandGeneral*)data;
  780. LLParcel* parcel = panelp != NULL ? panelp->mParcel->getParcel() : LLViewerParcelMgr::getInstance()->getParcelSelection()->getParcel();
  781. if (!parcel) return;
  782. S32 pass_price = parcel->getPassPrice();
  783. std::string parcel_name = parcel->getName();
  784. F32 pass_hours = parcel->getPassHours();
  785. std::string cost, time;
  786. cost = llformat("%d", pass_price);
  787. time = llformat("%.2f", pass_hours);
  788. LLSD args;
  789. args["COST"] = cost;
  790. args["PARCEL_NAME"] = parcel_name;
  791. args["TIME"] = time;
  792. LLNotificationsUtil::add("LandBuyPass", args, LLSD(), cbBuyPass);
  793. }
  794. // static
  795. void LLPanelLandGeneral::onClickStartAuction(void* data)
  796. {
  797. LLPanelLandGeneral* panelp = (LLPanelLandGeneral*)data;
  798. LLParcel* parcelp = panelp->mParcel->getParcel();
  799. if(parcelp)
  800. {
  801. if(parcelp->getForSale())
  802. {
  803. LLNotificationsUtil::add("CannotStartAuctionAlreadyForSale");
  804. }
  805. else
  806. {
  807. //LLFloaterAuction::showInstance();
  808. LLFloaterReg::showInstance("auction");
  809. }
  810. }
  811. }
  812. // static
  813. bool LLPanelLandGeneral::cbBuyPass(const LLSD& notification, const LLSD& response)
  814. {
  815. S32 option = LLNotificationsUtil::getSelectedOption(notification, response);
  816. if (0 == option)
  817. {
  818. // User clicked OK
  819. LLViewerParcelMgr::getInstance()->buyPass();
  820. }
  821. return false;
  822. }
  823. // static
  824. void LLPanelLandGeneral::onCommitAny(LLUICtrl *ctrl, void *userdata)
  825. {
  826. LLPanelLandGeneral *panelp = (LLPanelLandGeneral *)userdata;
  827. LLParcel* parcel = panelp->mParcel->getParcel();
  828. if (!parcel)
  829. {
  830. return;
  831. }
  832. // Extract data from UI
  833. std::string name = panelp->mEditName->getText();
  834. std::string desc = panelp->mEditDesc->getText();
  835. // Valid data from UI
  836. // Stuff data into selected parcel
  837. parcel->setName(name);
  838. parcel->setDesc(desc);
  839. BOOL allow_deed_to_group= panelp->mCheckDeedToGroup->get();
  840. BOOL contribute_with_deed = panelp->mCheckContributeWithDeed->get();
  841. parcel->setParcelFlag(PF_ALLOW_DEED_TO_GROUP, allow_deed_to_group);
  842. parcel->setContributeWithDeed(contribute_with_deed);
  843. // Send update to server
  844. LLViewerParcelMgr::getInstance()->sendParcelPropertiesUpdate( parcel );
  845. // Might have changed properties, so let's redraw!
  846. panelp->refresh();
  847. }
  848. // static
  849. void LLPanelLandGeneral::onClickSellLand(void* data)
  850. {
  851. LLViewerParcelMgr::getInstance()->startSellLand();
  852. }
  853. // static
  854. void LLPanelLandGeneral::onClickStopSellLand(void* data)
  855. {
  856. LLPanelLandGeneral* panelp = (LLPanelLandGeneral*)data;
  857. LLParcel* parcel = panelp->mParcel->getParcel();
  858. parcel->setParcelFlag(PF_FOR_SALE, FALSE);
  859. parcel->setSalePrice(0);
  860. parcel->setAuthorizedBuyerID(LLUUID::null);
  861. LLViewerParcelMgr::getInstance()->sendParcelPropertiesUpdate(parcel);
  862. }
  863. //---------------------------------------------------------------------------
  864. // LLPanelLandObjects
  865. //---------------------------------------------------------------------------
  866. LLPanelLandObjects::LLPanelLandObjects(LLParcelSelectionHandle& parcel)
  867. : LLPanel(),
  868. mParcel(parcel),
  869. mParcelObjectBonus(NULL),
  870. mSWTotalObjects(NULL),
  871. mObjectContribution(NULL),
  872. mTotalObjects(NULL),
  873. mOwnerObjects(NULL),
  874. mBtnShowOwnerObjects(NULL),
  875. mBtnReturnOwnerObjects(NULL),
  876. mGroupObjects(NULL),
  877. mBtnShowGroupObjects(NULL),
  878. mBtnReturnGroupObjects(NULL),
  879. mOtherObjects(NULL),
  880. mBtnShowOtherObjects(NULL),
  881. mBtnReturnOtherObjects(NULL),
  882. mSelectedObjects(NULL),
  883. mCleanOtherObjectsTime(NULL),
  884. mOtherTime(0),
  885. mBtnRefresh(NULL),
  886. mBtnReturnOwnerList(NULL),
  887. mOwnerList(NULL),
  888. mFirstReply(TRUE),
  889. mSelectedCount(0),
  890. mSelectedIsGroup(FALSE)
  891. {
  892. }
  893. BOOL LLPanelLandObjects::postBuild()
  894. {
  895. mFirstReply = TRUE;
  896. mParcelObjectBonus = getChild<LLTextBox>("parcel_object_bonus");
  897. mSWTotalObjects = getChild<LLTextBox>("objects_available");
  898. mObjectContribution = getChild<LLTextBox>("object_contrib_text");
  899. mTotalObjects = getChild<LLTextBox>("total_objects_text");
  900. mOwnerObjects = getChild<LLTextBox>("owner_objects_text");
  901. mBtnShowOwnerObjects = getChild<LLButton>("ShowOwner");
  902. mBtnShowOwnerObjects->setClickedCallback(onClickShowOwnerObjects, this);
  903. mBtnReturnOwnerObjects = getChild<LLButton>("ReturnOwner...");
  904. mBtnReturnOwnerObjects->setClickedCallback(onClickReturnOwnerObjects, this);
  905. mGroupObjects = getChild<LLTextBox>("group_objects_text");
  906. mBtnShowGroupObjects = getChild<LLButton>("ShowGroup");
  907. mBtnShowGroupObjects->setClickedCallback(onClickShowGroupObjects, this);
  908. mBtnReturnGroupObjects = getChild<LLButton>("ReturnGroup...");
  909. mBtnReturnGroupObjects->setClickedCallback(onClickReturnGroupObjects, this);
  910. mOtherObjects = getChild<LLTextBox>("other_objects_text");
  911. mBtnShowOtherObjects = getChild<LLButton>("ShowOther");
  912. mBtnShowOtherObjects->setClickedCallback(onClickShowOtherObjects, this);
  913. mBtnReturnOtherObjects = getChild<LLButton>("ReturnOther...");
  914. mBtnReturnOtherObjects->setClickedCallback(onClickReturnOtherObjects, this);
  915. mSelectedObjects = getChild<LLTextBox>("selected_objects_text");
  916. mCleanOtherObjectsTime = getChild<LLLineEditor>("clean other time");
  917. mCleanOtherObjectsTime->setFocusLostCallback(boost::bind(onLostFocus, _1, this));
  918. mCleanOtherObjectsTime->setCommitCallback(onCommitClean, this);
  919. childSetPrevalidate("clean other time", LLTextValidate::validateNonNegativeS32);
  920. mBtnRefresh = getChild<LLButton>("Refresh List");
  921. mBtnRefresh->setClickedCallback(onClickRefresh, this);
  922. mBtnReturnOwnerList = getChild<LLButton>("Return objects...");
  923. mBtnReturnOwnerList->setClickedCallback(onClickReturnOwnerList, this);
  924. mIconAvatarOnline = LLUIImageList::getInstance()->getUIImage("icon_avatar_online.tga", 0);
  925. mIconAvatarOffline = LLUIImageList::getInstance()->getUIImage("icon_avatar_offline.tga", 0);
  926. mIconGroup = LLUIImageList::getInstance()->getUIImage("icon_group.tga", 0);
  927. mOwnerList = getChild<LLNameListCtrl>("owner list");
  928. mOwnerList->sortByColumnIndex(3, FALSE);
  929. childSetCommitCallback("owner list", onCommitList, this);
  930. mOwnerList->setDoubleClickCallback(onDoubleClickOwner, this);
  931. mOwnerList->setContextMenu(LLScrollListCtrl::MENU_AVATAR);
  932. return TRUE;
  933. }
  934. // virtual
  935. LLPanelLandObjects::~LLPanelLandObjects()
  936. { }
  937. // static
  938. void LLPanelLandObjects::onDoubleClickOwner(void *userdata)
  939. {
  940. LLPanelLandObjects *self = (LLPanelLandObjects *)userdata;
  941. LLScrollListItem* item = self->mOwnerList->getFirstSelected();
  942. if (item)
  943. {
  944. LLUUID owner_id = item->getUUID();
  945. // Look up the selected name, for future dialog box use.
  946. const LLScrollListCell* cell;
  947. cell = item->getColumn(1);
  948. if (!cell)
  949. {
  950. return;
  951. }
  952. // Is this a group?
  953. BOOL is_group = cell->getValue().asString() == OWNER_GROUP;
  954. if (is_group)
  955. {
  956. LLGroupActions::show(owner_id);
  957. }
  958. else
  959. {
  960. LLAvatarActions::showProfile(owner_id);
  961. }
  962. }
  963. }
  964. // public
  965. void LLPanelLandObjects::refresh()
  966. {
  967. LLParcel *parcel = mParcel->getParcel();
  968. mBtnShowOwnerObjects->setEnabled(FALSE);
  969. mBtnShowGroupObjects->setEnabled(FALSE);
  970. mBtnShowOtherObjects->setEnabled(FALSE);
  971. mBtnReturnOwnerObjects->setEnabled(FALSE);
  972. mBtnReturnGroupObjects->setEnabled(FALSE);
  973. mBtnReturnOtherObjects->setEnabled(FALSE);
  974. mCleanOtherObjectsTime->setEnabled(FALSE);
  975. mBtnRefresh-> setEnabled(FALSE);
  976. mBtnReturnOwnerList-> setEnabled(FALSE);
  977. mSelectedOwners.clear();
  978. mOwnerList->deleteAllItems();
  979. mOwnerList->setEnabled(FALSE);
  980. if (!parcel)
  981. {
  982. mSWTotalObjects->setTextArg("[COUNT]", llformat("%d", 0));
  983. mSWTotalObjects->setTextArg("[TOTAL]", llformat("%d", 0));
  984. mSWTotalObjects->setTextArg("[AVAILABLE]", llformat("%d", 0));
  985. mObjectContribution->setTextArg("[COUNT]", llformat("%d", 0));
  986. mTotalObjects->setTextArg("[COUNT]", llformat("%d", 0));
  987. mOwnerObjects->setTextArg("[COUNT]", llformat("%d", 0));
  988. mGroupObjects->setTextArg("[COUNT]", llformat("%d", 0));
  989. mOtherObjects->setTextArg("[COUNT]", llformat("%d", 0));
  990. mSelectedObjects->setTextArg("[COUNT]", llformat("%d", 0));
  991. }
  992. else
  993. {
  994. S32 sw_max = parcel->getSimWideMaxPrimCapacity();
  995. S32 sw_total = parcel->getSimWidePrimCount();
  996. S32 max = llround(parcel->getMaxPrimCapacity() * parcel->getParcelPrimBonus());
  997. S32 total = parcel->getPrimCount();
  998. S32 owned = parcel->getOwnerPrimCount();
  999. S32 group = parcel->getGroupPrimCount();
  1000. S32 other = parcel->getOtherPrimCount();
  1001. S32 selected = parcel->getSelectedPrimCount();
  1002. F32 parcel_object_bonus = parcel->getParcelPrimBonus();
  1003. mOtherTime = parcel->getCleanOtherTime();
  1004. // Can't have more than region max tasks, regardless of parcel
  1005. // object bonus factor.
  1006. LLViewerRegion* region = LLViewerParcelMgr::getInstance()->getSelectionRegion();
  1007. if (region)
  1008. {
  1009. S32 max_tasks_per_region = (S32)region->getMaxTasks();
  1010. sw_max = llmin(sw_max, max_tasks_per_region);
  1011. max = llmin(max, max_tasks_per_region);
  1012. }
  1013. if (parcel_object_bonus != 1.0f)
  1014. {
  1015. mParcelObjectBonus->setVisible(TRUE);
  1016. mParcelObjectBonus->setTextArg("[BONUS]", llformat("%.2f", parcel_object_bonus));
  1017. }
  1018. else
  1019. {
  1020. mParcelObjectBonus->setVisible(FALSE);
  1021. }
  1022. if (sw_total > sw_max)
  1023. {
  1024. mSWTotalObjects->setText(getString("objects_deleted_text"));
  1025. mSWTotalObjects->setTextArg("[DELETED]", llformat("%d", sw_total - sw_max));
  1026. }
  1027. else
  1028. {
  1029. mSWTotalObjects->setText(getString("objects_available_text"));
  1030. mSWTotalObjects->setTextArg("[AVAILABLE]", llformat("%d", sw_max - sw_total));
  1031. }
  1032. mSWTotalObjects->setTextArg("[COUNT]", llformat("%d", sw_total));
  1033. mSWTotalObjects->setTextArg("[MAX]", llformat("%d", sw_max));
  1034. mObjectContribution->setTextArg("[COUNT]", llformat("%d", max));
  1035. mTotalObjects->setTextArg("[COUNT]", llformat("%d", total));
  1036. mOwnerObjects->setTextArg("[COUNT]", llformat("%d", owned));
  1037. mGroupObjects->setTextArg("[COUNT]", llformat("%d", group));
  1038. mOtherObjects->setTextArg("[COUNT]", llformat("%d", other));
  1039. mSelectedObjects->setTextArg("[COUNT]", llformat("%d", selected));
  1040. mCleanOtherObjectsTime->setText(llformat("%d", mOtherTime));
  1041. BOOL can_return_owned = LLViewerParcelMgr::isParcelModifiableByAgent(parcel, GP_LAND_RETURN_GROUP_OWNED);
  1042. BOOL can_return_group_set = LLViewerParcelMgr::isParcelModifiableByAgent(parcel, GP_LAND_RETURN_GROUP_SET);
  1043. BOOL can_return_other = LLViewerParcelMgr::isParcelModifiableByAgent(parcel, GP_LAND_RETURN_NON_GROUP);
  1044. if (can_return_owned || can_return_group_set || can_return_other)
  1045. {
  1046. if (owned && can_return_owned)
  1047. {
  1048. mBtnShowOwnerObjects->setEnabled(TRUE);
  1049. mBtnReturnOwnerObjects->setEnabled(TRUE);
  1050. }
  1051. if (group && can_return_group_set)
  1052. {
  1053. mBtnShowGroupObjects->setEnabled(TRUE);
  1054. mBtnReturnGroupObjects->setEnabled(TRUE);
  1055. }
  1056. if (other && can_return_other)
  1057. {
  1058. mBtnShowOtherObjects->setEnabled(TRUE);
  1059. mBtnReturnOtherObjects->setEnabled(TRUE);
  1060. }
  1061. mCleanOtherObjectsTime->setEnabled(TRUE);
  1062. mBtnRefresh->setEnabled(TRUE);
  1063. }
  1064. }
  1065. }
  1066. // virtual
  1067. void LLPanelLandObjects::draw()
  1068. {
  1069. LLPanel::draw();
  1070. }
  1071. void send_other_clean_time_message(S32 parcel_local_id, S32 other_clean_time)
  1072. {
  1073. LLMessageSystem *msg = gMessageSystem;
  1074. LLViewerRegion* region = LLViewerParcelMgr::getInstance()->getSelectionRegion();
  1075. if (!region) return;
  1076. msg->newMessageFast(_PREHASH_ParcelSetOtherCleanTime);
  1077. msg->nextBlockFast(_PREHASH_AgentData);
  1078. msg->addUUIDFast(_PREHASH_AgentID, gAgent.getID());
  1079. msg->addUUIDFast(_PREHASH_SessionID,gAgent.getSessionID());
  1080. msg->nextBlockFast(_PREHASH_ParcelData);
  1081. msg->addS32Fast(_PREHASH_LocalID, parcel_local_id);
  1082. msg->addS32Fast(_PREHASH_OtherCleanTime, other_clean_time);
  1083. msg->sendReliable(region->getHost());
  1084. }
  1085. void send_return_objects_message(S32 parcel_local_id, S32 return_type, 
  1086.  uuid_list_t* owner_ids = NULL)
  1087. {
  1088. LLMessageSystem *msg = gMessageSystem;
  1089. LLViewerRegion* region = LLViewerParcelMgr::getInstance()->getSelectionRegion();
  1090. if (!region) return;
  1091. msg->newMessageFast(_PREHASH_ParcelReturnObjects);
  1092. msg->nextBlockFast(_PREHASH_AgentData);
  1093. msg->addUUIDFast(_PREHASH_AgentID, gAgent.getID());
  1094. msg->addUUIDFast(_PREHASH_SessionID,gAgent.getSessionID());
  1095. msg->nextBlockFast(_PREHASH_ParcelData);
  1096. msg->addS32Fast(_PREHASH_LocalID, parcel_local_id);
  1097. msg->addU32Fast(_PREHASH_ReturnType, (U32) return_type);
  1098. // Dummy task id, not used
  1099. msg->nextBlock("TaskIDs");
  1100. msg->addUUID("TaskID", LLUUID::null);
  1101. // Throw all return ids into the packet.
  1102. // TODO: Check for too many ids.
  1103. if (owner_ids)
  1104. {
  1105. uuid_list_t::iterator end = owner_ids->end();
  1106. for (uuid_list_t::iterator it = owner_ids->begin();
  1107.  it != end;
  1108.  ++it)
  1109. {
  1110. msg->nextBlockFast(_PREHASH_OwnerIDs);
  1111. msg->addUUIDFast(_PREHASH_OwnerID, (*it));
  1112. }
  1113. }
  1114. else
  1115. {
  1116. msg->nextBlockFast(_PREHASH_OwnerIDs);
  1117. msg->addUUIDFast(_PREHASH_OwnerID, LLUUID::null);
  1118. }
  1119. msg->sendReliable(region->getHost());
  1120. }
  1121. bool LLPanelLandObjects::callbackReturnOwnerObjects(const LLSD& notification, const LLSD& response)
  1122. {
  1123. S32 option = LLNotificationsUtil::getSelectedOption(notification, response);
  1124. LLParcel *parcel = mParcel->getParcel();
  1125. if (0 == option)
  1126. {
  1127. if (parcel)
  1128. {
  1129. LLUUID owner_id = parcel->getOwnerID();
  1130. LLSD args;
  1131. if (owner_id == gAgentID)
  1132. {
  1133. LLNotificationsUtil::add("OwnedObjectsReturned");
  1134. }
  1135. else
  1136. {
  1137. std::string first, last;
  1138. gCacheName->getName(owner_id, first, last);
  1139. args["FIRST"] = first;
  1140. args["LAST"] = last;
  1141. LLNotificationsUtil::add("OtherObjectsReturned", args);
  1142. }
  1143. send_return_objects_message(parcel->getLocalID(), RT_OWNER);
  1144. }
  1145. }
  1146. LLSelectMgr::getInstance()->unhighlightAll();
  1147. LLViewerParcelMgr::getInstance()->sendParcelPropertiesUpdate( parcel );
  1148. refresh();
  1149. return false;
  1150. }
  1151. bool LLPanelLandObjects::callbackReturnGroupObjects(const LLSD& notification, const LLSD& response)
  1152. {
  1153. S32 option = LLNotificationsUtil::getSelectedOption(notification, response);
  1154. LLParcel *parcel = mParcel->getParcel();
  1155. if (0 == option)
  1156. {
  1157. if (parcel)
  1158. {
  1159. std::string group_name;
  1160. gCacheName->getGroupName(parcel->getGroupID(), group_name);
  1161. LLSD args;
  1162. args["GROUPNAME"] = group_name;
  1163. LLNotificationsUtil::add("GroupObjectsReturned", args);
  1164. send_return_objects_message(parcel->getLocalID(), RT_GROUP);
  1165. }
  1166. }
  1167. LLSelectMgr::getInstance()->unhighlightAll();
  1168. LLViewerParcelMgr::getInstance()->sendParcelPropertiesUpdate( parcel );
  1169. refresh();
  1170. return false;
  1171. }
  1172. bool LLPanelLandObjects::callbackReturnOtherObjects(const LLSD& notification, const LLSD& response)
  1173. {
  1174. S32 option = LLNotificationsUtil::getSelectedOption(notification, response);
  1175. LLParcel *parcel = mParcel->getParcel();
  1176. if (0 == option)
  1177. {
  1178. if (parcel)
  1179. {
  1180. LLNotificationsUtil::add("UnOwnedObjectsReturned");
  1181. send_return_objects_message(parcel->getLocalID(), RT_OTHER);
  1182. }
  1183. }
  1184. LLSelectMgr::getInstance()->unhighlightAll();
  1185. LLViewerParcelMgr::getInstance()->sendParcelPropertiesUpdate( parcel );
  1186. refresh();
  1187. return false;
  1188. }
  1189. bool LLPanelLandObjects::callbackReturnOwnerList(const LLSD& notification, const LLSD& response)
  1190. {
  1191. S32 option = LLNotificationsUtil::getSelectedOption(notification, response);
  1192. LLParcel *parcel = mParcel->getParcel();
  1193. if (0 == option)
  1194. {
  1195. if (parcel)
  1196. {
  1197. // Make sure we have something selected.
  1198. uuid_list_t::iterator selected = mSelectedOwners.begin();
  1199. if (selected != mSelectedOwners.end())
  1200. {
  1201. LLSD args;
  1202. if (mSelectedIsGroup)
  1203. {
  1204. args["GROUPNAME"] = mSelectedName;
  1205. LLNotificationsUtil::add("GroupObjectsReturned", args);
  1206. }
  1207. else
  1208. {
  1209. args["NAME"] = mSelectedName;
  1210. LLNotificationsUtil::add("OtherObjectsReturned2", args);
  1211. }
  1212. send_return_objects_message(parcel->getLocalID(), RT_LIST, &(mSelectedOwners));
  1213. }
  1214. }
  1215. }
  1216. LLSelectMgr::getInstance()->unhighlightAll();
  1217. LLViewerParcelMgr::getInstance()->sendParcelPropertiesUpdate( parcel );
  1218. refresh();
  1219. return false;
  1220. }
  1221. // static
  1222. void LLPanelLandObjects::onClickReturnOwnerList(void* userdata)
  1223. {
  1224. LLPanelLandObjects *self = (LLPanelLandObjects *)userdata;
  1225. LLParcel* parcelp = self->mParcel->getParcel();
  1226. if (!parcelp) return;
  1227. // Make sure we have something selected.
  1228. if (self->mSelectedOwners.empty())
  1229. {
  1230. return;
  1231. }
  1232. //uuid_list_t::iterator selected_itr = self->mSelectedOwners.begin();
  1233. //if (selected_itr == self->mSelectedOwners.end()) return;
  1234. send_parcel_select_objects(parcelp->getLocalID(), RT_LIST, &(self->mSelectedOwners));
  1235. LLSD args;
  1236. args["NAME"] = self->mSelectedName;
  1237. args["N"] = llformat("%d",self->mSelectedCount);
  1238. if (self->mSelectedIsGroup)
  1239. {
  1240. LLNotificationsUtil::add("ReturnObjectsDeededToGroup", args, LLSD(), boost::bind(&LLPanelLandObjects::callbackReturnOwnerList, self, _1, _2));
  1241. }
  1242. else 
  1243. {
  1244. LLNotificationsUtil::add("ReturnObjectsOwnedByUser", args, LLSD(), boost::bind(&LLPanelLandObjects::callbackReturnOwnerList, self, _1, _2));
  1245. }
  1246. }
  1247. // static
  1248. void LLPanelLandObjects::onClickRefresh(void* userdata)
  1249. {
  1250. LLPanelLandObjects *self = (LLPanelLandObjects*)userdata;
  1251. LLMessageSystem *msg = gMessageSystem;
  1252. LLParcel* parcel = self->mParcel->getParcel();
  1253. if (!parcel) return;
  1254. LLViewerRegion* region = LLViewerParcelMgr::getInstance()->getSelectionRegion();
  1255. if (!region) return;
  1256. // ready the list for results
  1257. self->mOwnerList->deleteAllItems();
  1258. self->mOwnerList->setCommentText(LLTrans::getString("Searching"));
  1259. self->mOwnerList->setEnabled(FALSE);
  1260. self->mFirstReply = TRUE;
  1261. // send the message
  1262. msg->newMessageFast(_PREHASH_ParcelObjectOwnersRequest);
  1263. msg->nextBlockFast(_PREHASH_AgentData);
  1264. msg->addUUIDFast(_PREHASH_AgentID, gAgent.getID());
  1265. msg->addUUIDFast(_PREHASH_SessionID, gAgent.getSessionID());
  1266. msg->nextBlockFast(_PREHASH_ParcelData);
  1267. msg->addS32Fast(_PREHASH_LocalID, parcel->getLocalID());
  1268. msg->sendReliable(region->getHost());
  1269. }
  1270. // static
  1271. void LLPanelLandObjects::processParcelObjectOwnersReply(LLMessageSystem *msg, void **)
  1272. {
  1273. LLPanelLandObjects* self = LLFloaterLand::getCurrentPanelLandObjects();
  1274. if (!self)
  1275. {
  1276. llwarns << "Received message for nonexistent LLPanelLandObject"
  1277. << llendl;
  1278. return;
  1279. }
  1280. const LLFontGL* FONT = LLFontGL::getFontSansSerif();
  1281. // Extract all of the owners.
  1282. S32 rows = msg->getNumberOfBlocksFast(_PREHASH_Data);
  1283. //uuid_list_t return_ids;
  1284. LLUUID owner_id;
  1285. BOOL is_group_owned;
  1286. S32 object_count;
  1287. U32 most_recent_time = 0;
  1288. BOOL is_online;
  1289. std::string object_count_str;
  1290. //BOOL b_need_refresh = FALSE;
  1291. // If we were waiting for the first reply, clear the "Searching..." text.
  1292. if (self->mFirstReply)
  1293. {
  1294. self->mOwnerList->deleteAllItems();
  1295. self->mFirstReply = FALSE;
  1296. }
  1297. for(S32 i = 0; i < rows; ++i)
  1298. {
  1299. msg->getUUIDFast(_PREHASH_Data, _PREHASH_OwnerID, owner_id, i);
  1300. msg->getBOOLFast(_PREHASH_Data, _PREHASH_IsGroupOwned, is_group_owned, i);
  1301. msg->getS32Fast (_PREHASH_Data, _PREHASH_Count, object_count, i);
  1302. msg->getBOOLFast(_PREHASH_Data, _PREHASH_OnlineStatus, is_online, i);
  1303. if(msg->has("DataExtended"))
  1304. {
  1305. msg->getU32("DataExtended", "TimeStamp", most_recent_time, i);
  1306. }
  1307. if (owner_id.isNull())
  1308. {
  1309. continue;
  1310. }
  1311. LLNameListCtrl::NameItem item_params;
  1312. item_params.value = owner_id;
  1313. item_params.target = is_group_owned ? LLNameListCtrl::GROUP : LLNameListCtrl::INDIVIDUAL;
  1314. if (is_group_owned)
  1315. {
  1316. item_params.columns.add().type("icon").value(self->mIconGroup->getName()).column("type");
  1317. item_params.columns.add().value(OWNER_GROUP).font(FONT).column("online_status");
  1318. }
  1319. else if (is_online)
  1320. {
  1321. item_params.columns.add().type("icon").value(self->mIconAvatarOnline->getName()).column("type");
  1322. item_params.columns.add().value(OWNER_ONLINE).font(FONT).column("online_status");
  1323. }
  1324. else  // offline
  1325. {
  1326. item_params.columns.add().type("icon").value(self->mIconAvatarOffline->getName()).column("type");
  1327. item_params.columns.add().value(OWNER_OFFLINE).font(FONT).column("online_status");
  1328. }
  1329. // Placeholder for name.
  1330. std::string name;
  1331. gCacheName->getFullName(owner_id, name);
  1332. item_params.columns.add().value(name).font(FONT).column("name");
  1333. object_count_str = llformat("%d", object_count);
  1334. item_params.columns.add().value(object_count_str).font(FONT).column("count");
  1335. item_params.columns.add().value(LLDate((time_t)most_recent_time)).font(FONT).column("mostrecent").type("date");
  1336. self->mOwnerList->addRow(item_params);
  1337. lldebugs << "object owner " << owner_id << " (" << (is_group_owned ? "group" : "agent")
  1338. << ") owns " << object_count << " objects." << llendl;
  1339. }
  1340. // check for no results
  1341. if (0 == self->mOwnerList->getItemCount())
  1342. {
  1343. self->mOwnerList->setCommentText(LLTrans::getString("NoneFound"));
  1344. }
  1345. else
  1346. {
  1347. self->mOwnerList->setEnabled(TRUE);
  1348. }
  1349. }
  1350. // static
  1351. void LLPanelLandObjects::onCommitList(LLUICtrl* ctrl, void* data)
  1352. {
  1353. LLPanelLandObjects* self = (LLPanelLandObjects*)data;
  1354. if (FALSE == self->mOwnerList->getCanSelect())
  1355. {
  1356. return;
  1357. }
  1358. LLScrollListItem *item = self->mOwnerList->getFirstSelected();
  1359. if (item)
  1360. {
  1361. // Look up the selected name, for future dialog box use.
  1362. const LLScrollListCell* cell;
  1363. cell = item->getColumn(1);
  1364. if (!cell)
  1365. {
  1366. return;
  1367. }
  1368. // Is this a group?
  1369. self->mSelectedIsGroup = cell->getValue().asString() == OWNER_GROUP;
  1370. cell = item->getColumn(2);
  1371. self->mSelectedName = cell->getValue().asString();
  1372. cell = item->getColumn(3);
  1373. self->mSelectedCount = atoi(cell->getValue().asString().c_str());
  1374. // Set the selection, and enable the return button.
  1375. self->mSelectedOwners.clear();
  1376. self->mSelectedOwners.insert(item->getUUID());
  1377. self->mBtnReturnOwnerList->setEnabled(TRUE);
  1378. // Highlight this user's objects
  1379. clickShowCore(self, RT_LIST, &(self->mSelectedOwners));
  1380. }
  1381. }
  1382. // static
  1383. void LLPanelLandObjects::clickShowCore(LLPanelLandObjects* self, S32 return_type, uuid_list_t* list)
  1384. {
  1385. LLParcel* parcel = self->mParcel->getParcel();
  1386. if (!parcel) return;
  1387. send_parcel_select_objects(parcel->getLocalID(), return_type, list);
  1388. }
  1389. // static
  1390. void LLPanelLandObjects::onClickShowOwnerObjects(void* userdata)
  1391. {
  1392. clickShowCore((LLPanelLandObjects*)userdata, RT_OWNER);
  1393. }
  1394. // static
  1395. void LLPanelLandObjects::onClickShowGroupObjects(void* userdata)
  1396. {
  1397. clickShowCore((LLPanelLandObjects*)userdata, (RT_GROUP));
  1398. }
  1399. // static
  1400. void LLPanelLandObjects::onClickShowOtherObjects(void* userdata)
  1401. {
  1402. clickShowCore((LLPanelLandObjects*)userdata, RT_OTHER);
  1403. }
  1404. // static
  1405. void LLPanelLandObjects::onClickReturnOwnerObjects(void* userdata)
  1406. {
  1407. S32 owned = 0;
  1408. LLPanelLandObjects* panelp = (LLPanelLandObjects*)userdata;
  1409. LLParcel* parcel = panelp->mParcel->getParcel();
  1410. if (!parcel) return;
  1411. owned = parcel->getOwnerPrimCount();
  1412. send_parcel_select_objects(parcel->getLocalID(), RT_OWNER);
  1413. LLUUID owner_id = parcel->getOwnerID();
  1414. LLSD args;
  1415. args["N"] = llformat("%d",owned);
  1416. if (owner_id == gAgent.getID())
  1417. {
  1418. LLNotificationsUtil::add("ReturnObjectsOwnedBySelf", args, LLSD(), boost::bind(&LLPanelLandObjects::callbackReturnOwnerObjects, panelp, _1, _2));
  1419. }
  1420. else
  1421. {
  1422. std::string name;
  1423. gCacheName->getFullName(owner_id, name);
  1424. args["NAME"] = name;
  1425. LLNotificationsUtil::add("ReturnObjectsOwnedByUser", args, LLSD(), boost::bind(&LLPanelLandObjects::callbackReturnOwnerObjects, panelp, _1, _2));
  1426. }
  1427. }
  1428. // static
  1429. void LLPanelLandObjects::onClickReturnGroupObjects(void* userdata)
  1430. {
  1431. LLPanelLandObjects* panelp = (LLPanelLandObjects*)userdata;
  1432. LLParcel* parcel = panelp->mParcel->getParcel();
  1433. if (!parcel) return;
  1434. send_parcel_select_objects(parcel->getLocalID(), RT_GROUP);
  1435. std::string group_name;
  1436. gCacheName->getGroupName(parcel->getGroupID(), group_name);
  1437. LLSD args;
  1438. args["NAME"] = group_name;
  1439. args["N"] = llformat("%d", parcel->getGroupPrimCount());
  1440. // create and show confirmation textbox
  1441. LLNotificationsUtil::add("ReturnObjectsDeededToGroup", args, LLSD(), boost::bind(&LLPanelLandObjects::callbackReturnGroupObjects, panelp, _1, _2));
  1442. }
  1443. // static
  1444. void LLPanelLandObjects::onClickReturnOtherObjects(void* userdata)
  1445. {
  1446. S32 other = 0;
  1447. LLPanelLandObjects* panelp = (LLPanelLandObjects*)userdata;
  1448. LLParcel* parcel = panelp->mParcel->getParcel();
  1449. if (!parcel) return;
  1450. other = parcel->getOtherPrimCount();
  1451. send_parcel_select_objects(parcel->getLocalID(), RT_OTHER);
  1452. LLSD args;
  1453. args["N"] = llformat("%d", other);
  1454. if (parcel->getIsGroupOwned())
  1455. {
  1456. std::string group_name;
  1457. gCacheName->getGroupName(parcel->getGroupID(), group_name);
  1458. args["NAME"] = group_name;
  1459. LLNotificationsUtil::add("ReturnObjectsNotOwnedByGroup", args, LLSD(), boost::bind(&LLPanelLandObjects::callbackReturnOtherObjects, panelp, _1, _2));
  1460. }
  1461. else
  1462. {
  1463. LLUUID owner_id = parcel->getOwnerID();
  1464. if (owner_id == gAgent.getID())
  1465. {
  1466. LLNotificationsUtil::add("ReturnObjectsNotOwnedBySelf", args, LLSD(), boost::bind(&LLPanelLandObjects::callbackReturnOtherObjects, panelp, _1, _2));
  1467. }
  1468. else
  1469. {
  1470. std::string name;
  1471. gCacheName->getFullName(owner_id, name);
  1472. args["NAME"] = name;
  1473. LLNotificationsUtil::add("ReturnObjectsNotOwnedByUser", args, LLSD(), boost::bind(&LLPanelLandObjects::callbackReturnOtherObjects, panelp, _1, _2));
  1474. }
  1475. }
  1476. }
  1477. // static
  1478. void LLPanelLandObjects::onLostFocus(LLFocusableElement* caller, void* user_data)
  1479. {
  1480. onCommitClean((LLUICtrl*)caller, user_data);
  1481. }
  1482. // static
  1483. void LLPanelLandObjects::onCommitClean(LLUICtrl *caller, void* user_data)
  1484. {
  1485. LLPanelLandObjects *lop = (LLPanelLandObjects *)user_data;
  1486. LLParcel* parcel = lop->mParcel->getParcel();
  1487. if (parcel)
  1488. {
  1489. lop->mOtherTime = atoi(lop->mCleanOtherObjectsTime->getText().c_str());
  1490. parcel->setCleanOtherTime(lop->mOtherTime);
  1491. send_other_clean_time_message(parcel->getLocalID(), lop->mOtherTime);
  1492. }
  1493. }
  1494. //---------------------------------------------------------------------------
  1495. // LLPanelLandOptions
  1496. //---------------------------------------------------------------------------
  1497. LLPanelLandOptions::LLPanelLandOptions(LLParcelSelectionHandle& parcel)
  1498. : LLPanel(),
  1499. mCheckEditObjects(NULL),
  1500. mCheckEditGroupObjects(NULL),
  1501. mCheckAllObjectEntry(NULL),
  1502. mCheckGroupObjectEntry(NULL),
  1503. mCheckEditLand(NULL),
  1504. mCheckSafe(NULL),
  1505. mCheckFly(NULL),
  1506. mCheckGroupScripts(NULL),
  1507. mCheckOtherScripts(NULL),
  1508. mCheckShowDirectory(NULL),
  1509. mCategoryCombo(NULL),
  1510. mLandingTypeCombo(NULL),
  1511. mSnapshotCtrl(NULL),
  1512. mLocationText(NULL),
  1513. mSetBtn(NULL),
  1514. mClearBtn(NULL),
  1515. mMatureCtrl(NULL),
  1516. mPushRestrictionCtrl(NULL),
  1517. mParcel(parcel)
  1518. {
  1519. }
  1520. BOOL LLPanelLandOptions::postBuild()
  1521. {
  1522. mCheckEditObjects = getChild<LLCheckBoxCtrl>( "edit objects check");
  1523. childSetCommitCallback("edit objects check", onCommitAny, this);
  1524. mCheckEditGroupObjects = getChild<LLCheckBoxCtrl>( "edit group objects check");
  1525. childSetCommitCallback("edit group objects check", onCommitAny, this);
  1526. mCheckAllObjectEntry = getChild<LLCheckBoxCtrl>( "all object entry check");
  1527. childSetCommitCallback("all object entry check", onCommitAny, this);
  1528. mCheckGroupObjectEntry = getChild<LLCheckBoxCtrl>( "group object entry check");
  1529. childSetCommitCallback("group object entry check", onCommitAny, this);
  1530. mCheckEditLand = getChild<LLCheckBoxCtrl>( "edit land check");
  1531. childSetCommitCallback("edit land check", onCommitAny, this);
  1532. mCheckGroupScripts = getChild<LLCheckBoxCtrl>( "check group scripts");
  1533. childSetCommitCallback("check group scripts", onCommitAny, this);
  1534. mCheckFly = getChild<LLCheckBoxCtrl>( "check fly");
  1535. childSetCommitCallback("check fly", onCommitAny, this);
  1536. mCheckOtherScripts = getChild<LLCheckBoxCtrl>( "check other scripts");
  1537. childSetCommitCallback("check other scripts", onCommitAny, this);
  1538. mCheckSafe = getChild<LLCheckBoxCtrl>( "check safe");
  1539. childSetCommitCallback("check safe", onCommitAny, this);
  1540. mPushRestrictionCtrl = getChild<LLCheckBoxCtrl>( "PushRestrictCheck");
  1541. childSetCommitCallback("PushRestrictCheck", onCommitAny, this);
  1542. mCheckShowDirectory = getChild<LLCheckBoxCtrl>( "ShowDirectoryCheck");
  1543. childSetCommitCallback("ShowDirectoryCheck", onCommitAny, this);
  1544. if (gAgent.getAgentAccess().isInTransition())
  1545. {
  1546. // during the AO transition, this combo has an Adult item.
  1547. // Post-transition, it goes away. We can remove this conditional
  1548. // after the transition and just use the "else" clause.
  1549. mCategoryCombo = getChild<LLComboBox>( "land category with adult");
  1550. childSetCommitCallback("land category with adult", onCommitAny, this);
  1551. }
  1552. else
  1553. {
  1554. // this is the code that should be preserved post-transition
  1555. // you could also change the XML to set visibility and enabled true.
  1556. mCategoryCombo = getChild<LLComboBox>( "land category");
  1557. childSetCommitCallback("land category", onCommitAny, this);
  1558. }
  1559. mCategoryCombo->setVisible(true);
  1560. mCategoryCombo->setEnabled(true);
  1561. mMatureCtrl = getChild<LLCheckBoxCtrl>( "MatureCheck");
  1562. childSetCommitCallback("MatureCheck", onCommitAny, this);
  1563. if (gAgent.wantsPGOnly())
  1564. {
  1565. // Disable these buttons if they are PG (Teen) users
  1566. mMatureCtrl->setVisible(FALSE);
  1567. mMatureCtrl->setEnabled(FALSE);
  1568. }
  1569. mSnapshotCtrl = getChild<LLTextureCtrl>("snapshot_ctrl");
  1570. if (mSnapshotCtrl)
  1571. {
  1572. mSnapshotCtrl->setCommitCallback( onCommitAny, this );
  1573. mSnapshotCtrl->setAllowNoTexture ( TRUE );
  1574. mSnapshotCtrl->setImmediateFilterPermMask(PERM_COPY | PERM_TRANSFER);
  1575. mSnapshotCtrl->setNonImmediateFilterPermMask(PERM_COPY | PERM_TRANSFER);
  1576. }
  1577. else
  1578. {
  1579. llwarns << "LLUICtrlFactory::getTexturePickerByName() returned NULL for 'snapshot_ctrl'" << llendl;
  1580. }
  1581. mLocationText = getChild<LLTextBox>("landing_point");
  1582. mSetBtn = getChild<LLButton>("Set");
  1583. mSetBtn->setClickedCallback(onClickSet, this);
  1584. mClearBtn = getChild<LLButton>("Clear");
  1585. mClearBtn->setClickedCallback(onClickClear, this);
  1586. mLandingTypeCombo = getChild<LLComboBox>( "landing type");
  1587. childSetCommitCallback("landing type", onCommitAny, this);
  1588. getChild<LLTextureCtrl>("snapshot_ctrl")->setFallbackImageName("default_land_picture.j2c");
  1589. return TRUE;
  1590. }
  1591. // virtual
  1592. LLPanelLandOptions::~LLPanelLandOptions()
  1593. { }
  1594. // virtual
  1595. void LLPanelLandOptions::refresh()
  1596. {
  1597. refreshSearch();
  1598. LLParcel *parcel = mParcel->getParcel();
  1599. if (!parcel)
  1600. {
  1601. mCheckEditObjects ->set(FALSE);
  1602. mCheckEditObjects ->setEnabled(FALSE);
  1603. mCheckEditGroupObjects ->set(FALSE);
  1604. mCheckEditGroupObjects ->setEnabled(FALSE);
  1605. mCheckAllObjectEntry ->set(FALSE);
  1606. mCheckAllObjectEntry ->setEnabled(FALSE);
  1607. mCheckGroupObjectEntry ->set(FALSE);
  1608. mCheckGroupObjectEntry ->setEnabled(FALSE);
  1609. mCheckEditLand ->set(FALSE);
  1610. mCheckEditLand ->setEnabled(FALSE);
  1611. mCheckSafe ->set(FALSE);
  1612. mCheckSafe ->setEnabled(FALSE);
  1613. mCheckFly ->set(FALSE);
  1614. mCheckFly ->setEnabled(FALSE);
  1615. mCheckGroupScripts ->set(FALSE);
  1616. mCheckGroupScripts ->setEnabled(FALSE);
  1617. mCheckOtherScripts ->set(FALSE);
  1618. mCheckOtherScripts ->setEnabled(FALSE);
  1619. mPushRestrictionCtrl->set(FALSE);
  1620. mPushRestrictionCtrl->setEnabled(FALSE);
  1621. mLandingTypeCombo->setCurrentByIndex(0);
  1622. mLandingTypeCombo->setEnabled(FALSE);
  1623. mSnapshotCtrl->setImageAssetID(LLUUID::null);
  1624. mSnapshotCtrl->setEnabled(FALSE);
  1625. mLocationText->setTextArg("[LANDING]", getString("landing_point_none"));
  1626. mSetBtn->setEnabled(FALSE);
  1627. mClearBtn->setEnabled(FALSE);
  1628. mMatureCtrl->setEnabled(FALSE);
  1629. }
  1630. else
  1631. {
  1632. // something selected, hooray!
  1633. // Display options
  1634. BOOL can_change_options = LLViewerParcelMgr::isParcelModifiableByAgent(parcel, GP_LAND_OPTIONS);
  1635. mCheckEditObjects ->set( parcel->getAllowModify() );
  1636. mCheckEditObjects ->setEnabled( can_change_options );
  1637. mCheckEditGroupObjects ->set( parcel->getAllowGroupModify() ||  parcel->getAllowModify());
  1638. mCheckEditGroupObjects ->setEnabled( can_change_options && !parcel->getAllowModify() ); // If others edit is enabled, then this is explicitly enabled.
  1639. mCheckAllObjectEntry ->set( parcel->getAllowAllObjectEntry() );
  1640. mCheckAllObjectEntry ->setEnabled( can_change_options );
  1641. mCheckGroupObjectEntry ->set( parcel->getAllowGroupObjectEntry() ||  parcel->getAllowAllObjectEntry());
  1642. mCheckGroupObjectEntry ->setEnabled( can_change_options && !parcel->getAllowAllObjectEntry() );
  1643. BOOL can_change_terraform = LLViewerParcelMgr::isParcelModifiableByAgent(parcel, GP_LAND_EDIT);
  1644. mCheckEditLand ->set( parcel->getAllowTerraform() );
  1645. mCheckEditLand ->setEnabled( can_change_terraform );
  1646. mCheckSafe ->set( !parcel->getAllowDamage() );
  1647. mCheckSafe ->setEnabled( can_change_options );
  1648. mCheckFly ->set( parcel->getAllowFly() );
  1649. mCheckFly ->setEnabled( can_change_options );
  1650. mCheckGroupScripts ->set( parcel->getAllowGroupScripts() || parcel->getAllowOtherScripts());
  1651. mCheckGroupScripts ->setEnabled( can_change_options && !parcel->getAllowOtherScripts());
  1652. mCheckOtherScripts ->set( parcel->getAllowOtherScripts() );
  1653. mCheckOtherScripts ->setEnabled( can_change_options );
  1654. mPushRestrictionCtrl->set( parcel->getRestrictPushObject() );
  1655. if(parcel->getRegionPushOverride())
  1656. {
  1657. mPushRestrictionCtrl->setLabel(getString("push_restrict_region_text"));
  1658. mPushRestrictionCtrl->setEnabled(false);
  1659. mPushRestrictionCtrl->set(TRUE);
  1660. }
  1661. else
  1662. {
  1663. mPushRestrictionCtrl->setLabel(getString("push_restrict_text"));
  1664. mPushRestrictionCtrl->setEnabled(can_change_options);
  1665. }
  1666. BOOL can_change_landing_point = LLViewerParcelMgr::isParcelModifiableByAgent(parcel, 
  1667. GP_LAND_SET_LANDING_POINT);
  1668. mLandingTypeCombo->setCurrentByIndex((S32)parcel->getLandingType());
  1669. mLandingTypeCombo->setEnabled( can_change_landing_point );
  1670. bool can_change_identity =
  1671. LLViewerParcelMgr::isParcelModifiableByAgent(
  1672. parcel, GP_LAND_CHANGE_IDENTITY);
  1673. mSnapshotCtrl->setImageAssetID(parcel->getSnapshotID());
  1674. mSnapshotCtrl->setEnabled( can_change_identity );
  1675. LLVector3 pos = parcel->getUserLocation();
  1676. if (pos.isExactlyZero())
  1677. {
  1678. mLocationText->setTextArg("[LANDING]", getString("landing_point_none"));
  1679. }
  1680. else
  1681. {
  1682. mLocationText->setTextArg("[LANDING]",llformat("%d, %d, %d",
  1683.    llround(pos.mV[VX]),
  1684.    llround(pos.mV[VY]),
  1685.    llround(pos.mV[VZ])));
  1686. }
  1687. mSetBtn->setEnabled( can_change_landing_point );
  1688. mClearBtn->setEnabled( can_change_landing_point );
  1689. if (gAgent.wantsPGOnly())
  1690. {
  1691. // Disable these buttons if they are PG (Teen) users
  1692. mMatureCtrl->setVisible(FALSE);
  1693. mMatureCtrl->setEnabled(FALSE);
  1694. }
  1695. else
  1696. {
  1697. // not teen so fill in the data for the maturity control
  1698. mMatureCtrl->setVisible(TRUE);
  1699. mMatureCtrl->setLabel(getString("mature_check_mature"));
  1700. mMatureCtrl->setToolTip(getString("mature_check_mature_tooltip"));
  1701. // they can see the checkbox, but its disposition depends on the 
  1702. // state of the region
  1703. LLViewerRegion* regionp = LLViewerParcelMgr::getInstance()->getSelectionRegion();
  1704. if (regionp)
  1705. {
  1706. if (regionp->getSimAccess() == SIM_ACCESS_PG)
  1707. {
  1708. mMatureCtrl->setEnabled(FALSE);
  1709. mMatureCtrl->set(FALSE);
  1710. }
  1711. else if (regionp->getSimAccess() == SIM_ACCESS_MATURE)
  1712. {
  1713. mMatureCtrl->setEnabled(can_change_identity);
  1714. mMatureCtrl->set(parcel->getMaturePublish());
  1715. }
  1716. else if (regionp->getSimAccess() == SIM_ACCESS_ADULT)
  1717. {
  1718. mMatureCtrl->setEnabled(FALSE);
  1719. mMatureCtrl->set(TRUE);
  1720. mMatureCtrl->setLabel(getString("mature_check_adult"));
  1721. mMatureCtrl->setToolTip(getString("mature_check_adult_tooltip"));
  1722. }
  1723. }
  1724. }
  1725. }
  1726. }
  1727. // virtual
  1728. void LLPanelLandOptions::draw()
  1729. {
  1730. refreshSearch(); // Is this necessary?  JC
  1731. LLPanel::draw();
  1732. }
  1733. // private
  1734. void LLPanelLandOptions::refreshSearch()
  1735. {
  1736. LLParcel *parcel = mParcel->getParcel();
  1737. if (!parcel)
  1738. {
  1739. mCheckShowDirectory->set(FALSE);
  1740. mCheckShowDirectory->setEnabled(FALSE);
  1741. // *TODO:Translate
  1742. const std::string& none_string = LLParcel::getCategoryUIString(LLParcel::C_NONE);
  1743. mCategoryCombo->setSimple(none_string);
  1744. mCategoryCombo->setEnabled(FALSE);
  1745. return;
  1746. }
  1747. LLViewerRegion* region =
  1748. LLViewerParcelMgr::getInstance()->getSelectionRegion();
  1749. bool can_change =
  1750. LLViewerParcelMgr::isParcelModifiableByAgent(
  1751. parcel, GP_LAND_CHANGE_IDENTITY)
  1752. && region
  1753. && !(region->getRegionFlags() & REGION_FLAGS_BLOCK_PARCEL_SEARCH);
  1754. // There is a bug with this panel whereby the Show Directory bit can be 
  1755. // slammed off by the Region based on an override.  Since this data is cached
  1756. // locally the change will not reflect in the panel, which could cause confusion
  1757. // A workaround for this is to flip the bit off in the locally cached version
  1758. // when we detect a mismatch case.
  1759. if(!can_change && parcel->getParcelFlag(PF_SHOW_DIRECTORY))
  1760. {
  1761. parcel->setParcelFlag(PF_SHOW_DIRECTORY, FALSE);
  1762. }
  1763. BOOL show_directory = parcel->getParcelFlag(PF_SHOW_DIRECTORY);
  1764. mCheckShowDirectory ->set(show_directory);
  1765. // Set by string in case the order in UI doesn't match the order by index.
  1766. // *TODO:Translate
  1767. LLParcel::ECategory cat = parcel->getCategory();
  1768. const std::string& category_string = LLParcel::getCategoryUIString(cat);
  1769. mCategoryCombo->setSimple(category_string);
  1770. std::string tooltip;
  1771. bool enable_show_directory = false;
  1772. // Parcels <= 128 square meters cannot be listed in search, in an
  1773. // effort to reduce search spam from small parcels.  See also
  1774. // the search crawler "grid-crawl.py" in secondlife.com/doc/app/search/ JC
  1775. const S32 MIN_PARCEL_AREA_FOR_SEARCH = 128;
  1776. bool large_enough = parcel->getArea() > MIN_PARCEL_AREA_FOR_SEARCH;
  1777. if (large_enough)
  1778. {
  1779. if (can_change)
  1780. {
  1781. tooltip = getString("search_enabled_tooltip");
  1782. enable_show_directory = true;
  1783. }
  1784. else
  1785. {
  1786. tooltip = getString("search_disabled_permissions_tooltip");
  1787. enable_show_directory = false;
  1788. }
  1789. }
  1790. else
  1791. {
  1792. // not large enough to include in search
  1793. if (can_change)
  1794. {
  1795. if (show_directory)
  1796. {
  1797. // parcels that are too small, but are still in search for
  1798. // legacy reasons, need to have the check box enabled so
  1799. // the owner can delist the parcel. JC
  1800. tooltip = getString("search_enabled_tooltip");
  1801. enable_show_directory = true;
  1802. }
  1803. else
  1804. {
  1805. tooltip = getString("search_disabled_small_tooltip");
  1806. enable_show_directory = false;
  1807. }
  1808. }
  1809. else
  1810. {
  1811. // both too small and don't have permission, so just
  1812. // show the permissions as the reason (which is probably
  1813. // the more common case) JC
  1814. tooltip = getString("search_disabled_permissions_tooltip");
  1815. enable_show_directory = false;
  1816. }
  1817. }
  1818. mCheckShowDirectory->setToolTip(tooltip);
  1819. mCategoryCombo->setToolTip(tooltip);
  1820. mCheckShowDirectory->setEnabled(enable_show_directory);
  1821. mCategoryCombo->setEnabled(enable_show_directory);
  1822. }
  1823. // static
  1824. void LLPanelLandOptions::onCommitAny(LLUICtrl *ctrl, void *userdata)
  1825. {
  1826. LLPanelLandOptions *self = (LLPanelLandOptions *)userdata;
  1827. LLParcel* parcel = self->mParcel->getParcel();
  1828. if (!parcel)
  1829. {
  1830. return;
  1831. }
  1832. // Extract data from UI
  1833. BOOL create_objects = self->mCheckEditObjects->get();
  1834. BOOL create_group_objects = self->mCheckEditGroupObjects->get() || self->mCheckEditObjects->get();
  1835. BOOL all_object_entry = self->mCheckAllObjectEntry->get();
  1836. BOOL group_object_entry = self->mCheckGroupObjectEntry->get() || self->mCheckAllObjectEntry->get();
  1837. BOOL allow_terraform = self->mCheckEditLand->get();
  1838. BOOL allow_damage = !self->mCheckSafe->get();
  1839. BOOL allow_fly = self->mCheckFly->get();
  1840. BOOL allow_landmark = TRUE; // cannot restrict landmark creation
  1841. BOOL allow_group_scripts = self->mCheckGroupScripts->get() || self->mCheckOtherScripts->get();
  1842. BOOL allow_other_scripts = self->mCheckOtherScripts->get();
  1843. BOOL allow_publish = FALSE;
  1844. BOOL mature_publish = self->mMatureCtrl->get();
  1845. BOOL push_restriction = self->mPushRestrictionCtrl->get();
  1846. BOOL show_directory = self->mCheckShowDirectory->get();
  1847. // we have to get the index from a lookup, not from the position in the dropdown!
  1848. S32  category_index = LLParcel::getCategoryFromString(self->mCategoryCombo->getSelectedValue());
  1849. S32  landing_type_index = self->mLandingTypeCombo->getCurrentIndex();
  1850. LLUUID snapshot_id = self->mSnapshotCtrl->getImageAssetID();
  1851. LLViewerRegion* region;
  1852. region = LLViewerParcelMgr::getInstance()->getSelectionRegion();
  1853. if (!allow_other_scripts && region && region->getAllowDamage())
  1854. {
  1855. LLNotificationsUtil::add("UnableToDisableOutsideScripts");
  1856. return;
  1857. }
  1858. // Push data into current parcel
  1859. parcel->setParcelFlag(PF_CREATE_OBJECTS, create_objects);
  1860. parcel->setParcelFlag(PF_CREATE_GROUP_OBJECTS, create_group_objects);
  1861. parcel->setParcelFlag(PF_ALLOW_ALL_OBJECT_ENTRY, all_object_entry);
  1862. parcel->setParcelFlag(PF_ALLOW_GROUP_OBJECT_ENTRY, group_object_entry);
  1863. parcel->setParcelFlag(PF_ALLOW_TERRAFORM, allow_terraform);
  1864. parcel->setParcelFlag(PF_ALLOW_DAMAGE, allow_damage);
  1865. parcel->setParcelFlag(PF_ALLOW_FLY, allow_fly);
  1866. parcel->setParcelFlag(PF_ALLOW_LANDMARK, allow_landmark);
  1867. parcel->setParcelFlag(PF_ALLOW_GROUP_SCRIPTS, allow_group_scripts);
  1868. parcel->setParcelFlag(PF_ALLOW_OTHER_SCRIPTS, allow_other_scripts);
  1869. parcel->setParcelFlag(PF_SHOW_DIRECTORY, show_directory);
  1870. parcel->setParcelFlag(PF_ALLOW_PUBLISH, allow_publish);
  1871. parcel->setParcelFlag(PF_MATURE_PUBLISH, mature_publish);
  1872. parcel->setParcelFlag(PF_RESTRICT_PUSHOBJECT, push_restriction);
  1873. parcel->setCategory((LLParcel::ECategory)category_index);
  1874. parcel->setLandingType((LLParcel::ELandingType)landing_type_index);
  1875. parcel->setSnapshotID(snapshot_id);
  1876. // Send current parcel data upstream to server
  1877. LLViewerParcelMgr::getInstance()->sendParcelPropertiesUpdate( parcel );
  1878. // Might have changed properties, so let's redraw!
  1879. self->refresh();
  1880. }
  1881. // static
  1882. void LLPanelLandOptions::onClickSet(void* userdata)
  1883. {
  1884. LLPanelLandOptions* self = (LLPanelLandOptions*)userdata;
  1885. LLParcel* selected_parcel = self->mParcel->getParcel();
  1886. if (!selected_parcel) return;
  1887. LLParcel* agent_parcel = LLViewerParcelMgr::getInstance()->getAgentParcel();
  1888. if (!agent_parcel) return;
  1889. if (agent_parcel->getLocalID() != selected_parcel->getLocalID())
  1890. {
  1891. LLNotificationsUtil::add("MustBeInParcel");
  1892. return;
  1893. }
  1894. LLVector3 pos_region = gAgent.getPositionAgent();
  1895. selected_parcel->setUserLocation(pos_region);
  1896. selected_parcel->setUserLookAt(gAgent.getFrameAgent().getAtAxis());
  1897. LLViewerParcelMgr::getInstance()->sendParcelPropertiesUpdate(selected_parcel);
  1898. self->refresh();
  1899. }
  1900. void LLPanelLandOptions::onClickClear(void* userdata)
  1901. {
  1902. LLPanelLandOptions* self = (LLPanelLandOptions*)userdata;
  1903. LLParcel* selected_parcel = self->mParcel->getParcel();
  1904. if (!selected_parcel) return;
  1905. // yes, this magic number of 0,0,0 means that it is clear
  1906. LLVector3 zero_vec(0.f, 0.f, 0.f);
  1907. selected_parcel->setUserLocation(zero_vec);
  1908. selected_parcel->setUserLookAt(zero_vec);
  1909. LLViewerParcelMgr::getInstance()->sendParcelPropertiesUpdate(selected_parcel);
  1910. self->refresh();
  1911. }
  1912. //---------------------------------------------------------------------------
  1913. // LLPanelLandAccess
  1914. //---------------------------------------------------------------------------
  1915. LLPanelLandAccess::LLPanelLandAccess(LLParcelSelectionHandle& parcel)
  1916. : LLPanel(),
  1917.   mParcel(parcel)
  1918. {
  1919. }
  1920. BOOL LLPanelLandAccess::postBuild()
  1921. {
  1922. childSetCommitCallback("public_access", onCommitPublicAccess, this);
  1923. childSetCommitCallback("limit_payment", onCommitAny, this);
  1924. childSetCommitCallback("limit_age_verified", onCommitAny, this);
  1925. childSetCommitCallback("GroupCheck", onCommitAny, this);
  1926. childSetCommitCallback("PassCheck", onCommitAny, this);
  1927. childSetCommitCallback("pass_combo", onCommitAny, this);
  1928. childSetCommitCallback("PriceSpin", onCommitAny, this);
  1929. childSetCommitCallback("HoursSpin", onCommitAny, this);
  1930. childSetAction("add_allowed", boost::bind(&LLPanelLandAccess::onClickAddAccess, this));
  1931. childSetAction("remove_allowed", onClickRemoveAccess, this);
  1932. childSetAction("add_banned", boost::bind(&LLPanelLandAccess::onClickAddBanned, this));
  1933. childSetAction("remove_banned", onClickRemoveBanned, this);
  1934. mListAccess = getChild<LLNameListCtrl>("AccessList");
  1935. if (mListAccess)
  1936. {
  1937. mListAccess->sortByColumnIndex(0, TRUE); // ascending
  1938. mListAccess->setContextMenu(LLScrollListCtrl::MENU_AVATAR);
  1939. }
  1940. mListBanned = getChild<LLNameListCtrl>("BannedList");
  1941. if (mListBanned)
  1942. {
  1943. mListBanned->sortByColumnIndex(0, TRUE); // ascending
  1944. mListBanned->setContextMenu(LLScrollListCtrl::MENU_AVATAR);
  1945. }
  1946. return TRUE;
  1947. }
  1948. LLPanelLandAccess::~LLPanelLandAccess()
  1949. }
  1950. void LLPanelLandAccess::refresh()
  1951. {
  1952. LLFloater* parent_floater = gFloaterView->getParentFloater(this);
  1953. if (mListAccess)
  1954. mListAccess->deleteAllItems();
  1955. if (mListBanned)
  1956. mListBanned->deleteAllItems();
  1957. LLParcel *parcel = mParcel->getParcel();
  1958. // Display options
  1959. if (parcel)
  1960. {
  1961. BOOL use_access_list = parcel->getParcelFlag(PF_USE_ACCESS_LIST);
  1962. BOOL use_group = parcel->getParcelFlag(PF_USE_ACCESS_GROUP);
  1963. BOOL public_access = !use_access_list && !use_group;
  1964. childSetValue("public_access", public_access );
  1965. childSetValue("GroupCheck", use_group );
  1966. std::string group_name;
  1967. gCacheName->getGroupName(parcel->getGroupID(), group_name);
  1968. childSetLabelArg("GroupCheck", "[GROUP]", group_name );
  1969. // Allow list
  1970. {
  1971. S32 count = parcel->mAccessList.size();
  1972. childSetToolTipArg("AccessList", "[LISTED]", llformat("%d",count));
  1973. childSetToolTipArg("AccessList", "[MAX]", llformat("%d",PARCEL_MAX_ACCESS_LIST));
  1974. for (access_map_const_iterator cit = parcel->mAccessList.begin();
  1975.  cit != parcel->mAccessList.end(); ++cit)
  1976. {
  1977. const LLAccessEntry& entry = (*cit).second;
  1978. std::string suffix;
  1979. if (entry.mTime != 0)
  1980. {
  1981. LLStringUtil::format_map_t args;
  1982. S32 now = time(NULL);
  1983. S32 seconds = entry.mTime - now;
  1984. if (seconds < 0) seconds = 0;
  1985. suffix.assign(" (");
  1986. if (seconds >= 120)
  1987. {
  1988. args["[MINUTES]"] = llformat("%d", (seconds/60));
  1989. std::string buf = parent_floater->getString ("Minutes", args);
  1990. suffix.append(buf);
  1991. }
  1992. else if (seconds >= 60)
  1993. {
  1994. suffix.append("1 " + parent_floater->getString("Minute"));
  1995. }
  1996. else
  1997. {
  1998. args["[SECONDS]"] = llformat("%d", seconds);
  1999. std::string buf = parent_floater->getString ("Seconds", args);
  2000. suffix.append(buf);
  2001. }
  2002. suffix.append(" " + parent_floater->getString("Remaining") + ")");
  2003. }
  2004. if (mListAccess)
  2005. mListAccess->addNameItem(entry.mID, ADD_SORTED, TRUE, suffix);
  2006. }
  2007. }
  2008. // Ban List
  2009. {
  2010. S32 count = parcel->mBanList.size();
  2011. childSetToolTipArg("BannedList", "[LISTED]", llformat("%d",count));
  2012. childSetToolTipArg("BannedList", "[MAX]", llformat("%d",PARCEL_MAX_ACCESS_LIST));
  2013. for (access_map_const_iterator cit = parcel->mBanList.begin();
  2014.  cit != parcel->mBanList.end(); ++cit)
  2015. {
  2016. const LLAccessEntry& entry = (*cit).second;
  2017. std::string suffix;
  2018. if (entry.mTime != 0)
  2019. {
  2020. LLStringUtil::format_map_t args;
  2021. S32 now = time(NULL);
  2022. S32 seconds = entry.mTime - now;
  2023. if (seconds < 0) seconds = 0;
  2024. suffix.assign(" (");
  2025. if (seconds >= 120)
  2026. {
  2027. args["[MINUTES]"] = llformat("%d", (seconds/60));
  2028. std::string buf = parent_floater->getString ("Minutes", args);
  2029. suffix.append(buf);
  2030. }
  2031. else if (seconds >= 60)
  2032. {
  2033. suffix.append("1 " + parent_floater->getString("Minute"));
  2034. }
  2035. else
  2036. {
  2037. args["[SECONDS]"] = llformat("%d", seconds);
  2038. std::string buf = parent_floater->getString ("Seconds", args);
  2039. suffix.append(buf);
  2040. }
  2041. suffix.append(" " + parent_floater->getString("Remaining") + ")");
  2042. }
  2043. mListBanned->addNameItem(entry.mID, ADD_SORTED, TRUE, suffix);
  2044. }
  2045. }
  2046. LLViewerRegion* region = LLViewerParcelMgr::getInstance()->getSelectionRegion();
  2047. if(region)
  2048. {
  2049. std::string region_access = "(";
  2050. region_access += region->getSimAccessString();
  2051. region_access += ")";
  2052. childSetLabelArg( "public_access", "[MATURITY]", region_access );
  2053. }
  2054. else
  2055. {
  2056. childSetLabelArg( "public_access", "[MATURITY]", std::string() );
  2057. }
  2058. if(parcel->getRegionDenyAnonymousOverride())
  2059. {
  2060. childSetValue("limit_payment", TRUE);
  2061. childSetLabelArg( "limit_payment", "[ESTATE_PAYMENT_LIMIT]", getString("access_estate_defined") );
  2062. }
  2063. else
  2064. {
  2065. childSetValue("limit_payment", (parcel->getParcelFlag(PF_DENY_ANONYMOUS)));
  2066. childSetLabelArg( "limit_payment", "[ESTATE_PAYMENT_LIMIT]", std::string() );
  2067. }
  2068. if(parcel->getRegionDenyAgeUnverifiedOverride())
  2069. {
  2070. childSetValue("limit_age_verified", TRUE);
  2071. childSetLabelArg( "limit_age_verified", "[ESTATE_AGE_LIMIT]", getString("access_estate_defined") );
  2072. }
  2073. else
  2074. {
  2075. childSetValue("limit_age_verified", (parcel->getParcelFlag(PF_DENY_AGEUNVERIFIED)));
  2076. childSetLabelArg( "limit_age_verified", "[ESTATE_AGE_LIMIT]", std::string() );
  2077. }
  2078. BOOL use_pass = parcel->getParcelFlag(PF_USE_PASS_LIST);
  2079. childSetValue("PassCheck",  use_pass );
  2080. LLCtrlSelectionInterface* passcombo = childGetSelectionInterface("pass_combo");
  2081. if (passcombo)
  2082. {
  2083. if (public_access || !use_pass || !use_group)
  2084. {
  2085. passcombo->selectByValue("anyone");
  2086. }
  2087. }
  2088. S32 pass_price = parcel->getPassPrice();
  2089. childSetValue( "PriceSpin", (F32)pass_price );
  2090. F32 pass_hours = parcel->getPassHours();
  2091. childSetValue( "HoursSpin", pass_hours );
  2092. }
  2093. else
  2094. {
  2095. childSetValue("public_access", FALSE);
  2096. childSetValue("limit_payment", FALSE);
  2097. childSetValue("limit_age_verified", FALSE);
  2098. childSetValue("GroupCheck", FALSE);
  2099. childSetLabelArg("GroupCheck", "[GROUP]", LLStringUtil::null );
  2100. childSetValue("PassCheck", FALSE);
  2101. childSetValue("PriceSpin", (F32)PARCEL_PASS_PRICE_DEFAULT);
  2102. childSetValue( "HoursSpin", PARCEL_PASS_HOURS_DEFAULT );
  2103. childSetToolTipArg("AccessList", "[LISTED]", llformat("%d",0));
  2104. childSetToolTipArg("AccessList", "[MAX]", llformat("%d",0));
  2105. childSetToolTipArg("BannedList", "[LISTED]", llformat("%d",0));
  2106. childSetToolTipArg("BannedList", "[MAX]", llformat("%d",0));
  2107. }
  2108. }
  2109. void LLPanelLandAccess::refresh_ui()
  2110. {
  2111. childSetEnabled("public_access", FALSE);
  2112. childSetEnabled("limit_payment", FALSE);
  2113. childSetEnabled("limit_age_verified", FALSE);
  2114. childSetEnabled("GroupCheck", FALSE);
  2115. childSetEnabled("PassCheck", FALSE);
  2116. childSetEnabled("pass_combo", FALSE);
  2117. childSetEnabled("PriceSpin", FALSE);
  2118. childSetEnabled("HoursSpin", FALSE);
  2119. childSetEnabled("AccessList", FALSE);
  2120. childSetEnabled("BannedList", FALSE);
  2121. LLParcel *parcel = mParcel->getParcel();
  2122. if (parcel)
  2123. {
  2124. BOOL can_manage_allowed = LLViewerParcelMgr::isParcelModifiableByAgent(parcel, GP_LAND_MANAGE_ALLOWED);
  2125. BOOL can_manage_banned = LLViewerParcelMgr::isParcelModifiableByAgent(parcel, GP_LAND_MANAGE_BANNED);
  2126. childSetEnabled("public_access", can_manage_allowed);
  2127. BOOL public_access = childGetValue("public_access").asBoolean();
  2128. if (public_access)
  2129. {
  2130. bool override = false;
  2131. if(parcel->getRegionDenyAnonymousOverride())
  2132. {
  2133. override = true;
  2134. childSetEnabled("limit_payment", FALSE);
  2135. }
  2136. else
  2137. {
  2138. childSetEnabled("limit_payment", can_manage_allowed);
  2139. }
  2140. if(parcel->getRegionDenyAgeUnverifiedOverride())
  2141. {
  2142. override = true;
  2143. childSetEnabled("limit_age_verified", FALSE);
  2144. }
  2145. else
  2146. {
  2147. childSetEnabled("limit_age_verified", can_manage_allowed);
  2148. }
  2149. if (override)
  2150. {
  2151. childSetToolTip("Only Allow", getString("estate_override"));
  2152. }
  2153. else
  2154. {
  2155. childSetToolTip("Only Allow", std::string());
  2156. }
  2157. childSetEnabled("GroupCheck", FALSE);
  2158. childSetEnabled("PassCheck", FALSE);
  2159. childSetEnabled("pass_combo", FALSE);
  2160. childSetEnabled("AccessList", FALSE);
  2161. }
  2162. else
  2163. {
  2164. childSetEnabled("limit_payment", FALSE);
  2165. childSetEnabled("limit_age_verified", FALSE);
  2166. std::string group_name;
  2167. if (gCacheName->getGroupName(parcel->getGroupID(), group_name))
  2168. {
  2169. childSetEnabled("GroupCheck", can_manage_allowed);
  2170. }
  2171. BOOL group_access = childGetValue("GroupCheck").asBoolean();
  2172. BOOL sell_passes = childGetValue("PassCheck").asBoolean();
  2173. childSetEnabled("PassCheck", can_manage_allowed);
  2174. if (sell_passes)
  2175. {
  2176. childSetEnabled("pass_combo", group_access && can_manage_allowed);
  2177. childSetEnabled("PriceSpin", can_manage_allowed);
  2178. childSetEnabled("HoursSpin", can_manage_allowed);
  2179. }
  2180. }
  2181. childSetEnabled("AccessList", can_manage_allowed);
  2182. S32 allowed_list_count = parcel->mAccessList.size();
  2183. childSetEnabled("add_allowed", can_manage_allowed && allowed_list_count < PARCEL_MAX_ACCESS_LIST);
  2184. BOOL has_selected = mListAccess->getSelectionInterface()->getFirstSelectedIndex() >= 0;
  2185. childSetEnabled("remove_allowed", can_manage_allowed && has_selected);
  2186. childSetEnabled("BannedList", can_manage_banned);
  2187. S32 banned_list_count = parcel->mBanList.size();
  2188. childSetEnabled("add_banned", can_manage_banned && banned_list_count < PARCEL_MAX_ACCESS_LIST);
  2189. has_selected = mListBanned->getSelectionInterface()->getFirstSelectedIndex() >= 0;
  2190. childSetEnabled("remove_banned", can_manage_banned && has_selected);
  2191. }
  2192. }
  2193. // public
  2194. void LLPanelLandAccess::refreshNames()
  2195. {
  2196. LLParcel* parcel = mParcel->getParcel();
  2197. std::string group_name;
  2198. if(parcel)
  2199. {
  2200. gCacheName->getGroupName(parcel->getGroupID(), group_name);
  2201. }
  2202. childSetLabelArg("GroupCheck", "[GROUP]", group_name);
  2203. }
  2204. // virtual
  2205. void LLPanelLandAccess::draw()
  2206. {
  2207. refresh_ui();
  2208. refreshNames();
  2209. LLPanel::draw();
  2210. }
  2211. // static
  2212. void LLPanelLandAccess::onCommitPublicAccess(LLUICtrl *ctrl, void *userdata)
  2213. {
  2214. LLPanelLandAccess *self = (LLPanelLandAccess *)userdata;
  2215. LLParcel* parcel = self->mParcel->getParcel();
  2216. if (!parcel)
  2217. {
  2218. return;
  2219. }
  2220. // If we disabled public access, enable group access by default (if applicable)
  2221. BOOL public_access = self->childGetValue("public_access").asBoolean();
  2222. if (public_access == FALSE)
  2223. {
  2224. std::string group_name;
  2225. if (gCacheName->getGroupName(parcel->getGroupID(), group_name))
  2226. {
  2227. self->childSetValue("GroupCheck", public_access ? FALSE : TRUE);
  2228. }
  2229. }
  2230. onCommitAny(ctrl, userdata);
  2231. }
  2232. // static
  2233. void LLPanelLandAccess::onCommitAny(LLUICtrl *ctrl, void *userdata)
  2234. {
  2235. LLPanelLandAccess *self = (LLPanelLandAccess *)userdata;
  2236. LLParcel* parcel = self->mParcel->getParcel();
  2237. if (!parcel)
  2238. {
  2239. return;
  2240. }
  2241. // Extract data from UI
  2242. BOOL public_access = self->childGetValue("public_access").asBoolean();
  2243. BOOL use_access_group = self->childGetValue("GroupCheck").asBoolean();
  2244. if (use_access_group)
  2245. {
  2246. std::string group_name;
  2247. if (!gCacheName->getGroupName(parcel->getGroupID(), group_name))
  2248. {
  2249. use_access_group = FALSE;
  2250. }
  2251. }
  2252. BOOL limit_payment = FALSE, limit_age_verified = FALSE;
  2253. BOOL use_access_list = FALSE;
  2254. BOOL use_pass_list = FALSE;
  2255. if (public_access)
  2256. {
  2257. use_access_list = FALSE;
  2258. use_access_group = FALSE;
  2259. limit_payment = self->childGetValue("limit_payment").asBoolean();
  2260. limit_age_verified = self->childGetValue("limit_age_verified").asBoolean();
  2261. }
  2262. else
  2263. {
  2264. use_access_list = TRUE;
  2265. use_pass_list = self->childGetValue("PassCheck").asBoolean();
  2266. if (use_access_group && use_pass_list)
  2267. {
  2268. LLCtrlSelectionInterface* passcombo = self->childGetSelectionInterface("pass_combo");
  2269. if (passcombo)
  2270. {
  2271. if (passcombo->getSelectedValue().asString() == "group")
  2272. {
  2273. use_access_list = FALSE;
  2274. }
  2275. }
  2276. }
  2277. }
  2278. S32 pass_price = llfloor((F32)self->childGetValue("PriceSpin").asReal());
  2279. F32 pass_hours = (F32)self->childGetValue("HoursSpin").asReal();
  2280. // Push data into current parcel
  2281. parcel->setParcelFlag(PF_USE_ACCESS_GROUP, use_access_group);
  2282. parcel->setParcelFlag(PF_USE_ACCESS_LIST, use_access_list);
  2283. parcel->setParcelFlag(PF_USE_PASS_LIST, use_pass_list);
  2284. parcel->setParcelFlag(PF_USE_BAN_LIST, TRUE);
  2285. parcel->setParcelFlag(PF_DENY_ANONYMOUS,  limit_payment);
  2286. parcel->setParcelFlag(PF_DENY_AGEUNVERIFIED, limit_age_verified);
  2287. parcel->setPassPrice( pass_price );
  2288. parcel->setPassHours( pass_hours );
  2289. // Send current parcel data upstream to server
  2290. LLViewerParcelMgr::getInstance()->sendParcelPropertiesUpdate( parcel );
  2291. // Might have changed properties, so let's redraw!
  2292. self->refresh();
  2293. }
  2294. void LLPanelLandAccess::onClickAddAccess()
  2295. {
  2296. gFloaterView->getParentFloater(this)->addDependentFloater(LLFloaterAvatarPicker::show(boost::bind(&LLPanelLandAccess::callbackAvatarCBAccess, this, _1,_2)) );
  2297. }
  2298. void LLPanelLandAccess::callbackAvatarCBAccess(const std::vector<std::string>& names, const std::vector<LLUUID>& ids)
  2299. {
  2300. if (!names.empty() && !ids.empty())
  2301. {
  2302. LLUUID id = ids[0];
  2303. LLParcel* parcel = mParcel->getParcel();
  2304. if (parcel)
  2305. {
  2306. parcel->addToAccessList(id, 0);
  2307. LLViewerParcelMgr::getInstance()->sendParcelAccessListUpdate(AL_ACCESS);
  2308. refresh();
  2309. }
  2310. }
  2311. }
  2312. // static
  2313. void LLPanelLandAccess::onClickRemoveAccess(void* data)
  2314. {
  2315. LLPanelLandAccess* panelp = (LLPanelLandAccess*)data;
  2316. if (panelp && panelp->mListAccess)
  2317. {
  2318. LLParcel* parcel = panelp->mParcel->getParcel();
  2319. if (parcel)
  2320. {
  2321. std::vector<LLScrollListItem*> names = panelp->mListAccess->getAllSelected();
  2322. for (std::vector<LLScrollListItem*>::iterator iter = names.begin();
  2323.  iter != names.end(); )
  2324. {
  2325. LLScrollListItem* item = *iter++;
  2326. const LLUUID& agent_id = item->getUUID();
  2327. parcel->removeFromAccessList(agent_id);
  2328. }
  2329. LLViewerParcelMgr::getInstance()->sendParcelAccessListUpdate(AL_ACCESS);
  2330. panelp->refresh();
  2331. }
  2332. }
  2333. }
  2334. // static
  2335. void LLPanelLandAccess::onClickAddBanned()
  2336. {
  2337. gFloaterView->getParentFloater(this)->addDependentFloater(LLFloaterAvatarPicker::show(boost::bind(&LLPanelLandAccess::callbackAvatarCBBanned, this, _1,_2)));
  2338. }
  2339. // static
  2340. void LLPanelLandAccess::callbackAvatarCBBanned(const std::vector<std::string>& names, const std::vector<LLUUID>& ids)
  2341. {
  2342. if (!names.empty() && !ids.empty())
  2343. {
  2344. LLUUID id = ids[0];
  2345. LLParcel* parcel = mParcel->getParcel();
  2346. if (parcel)
  2347. {
  2348. parcel->addToBanList(id, 0);
  2349. LLViewerParcelMgr::getInstance()->sendParcelAccessListUpdate(AL_BAN);
  2350. refresh();
  2351. }
  2352. }
  2353. }
  2354. // static
  2355. void LLPanelLandAccess::onClickRemoveBanned(void* data)
  2356. {
  2357. LLPanelLandAccess* panelp = (LLPanelLandAccess*)data;
  2358. if (panelp && panelp->mListBanned)
  2359. {
  2360. LLParcel* parcel = panelp->mParcel->getParcel();
  2361. if (parcel)
  2362. {
  2363. std::vector<LLScrollListItem*> names = panelp->mListBanned->getAllSelected();
  2364. for (std::vector<LLScrollListItem*>::iterator iter = names.begin();
  2365.  iter != names.end(); )
  2366. {
  2367. LLScrollListItem* item = *iter++;
  2368. const LLUUID& agent_id = item->getUUID();
  2369. parcel->removeFromBanList(agent_id);
  2370. }
  2371. LLViewerParcelMgr::getInstance()->sendParcelAccessListUpdate(AL_BAN);
  2372. panelp->refresh();
  2373. }
  2374. }
  2375. }
  2376. //---------------------------------------------------------------------------
  2377. // LLPanelLandCovenant
  2378. //---------------------------------------------------------------------------
  2379. LLPanelLandCovenant::LLPanelLandCovenant(LLParcelSelectionHandle& parcel)
  2380. : LLPanel(),
  2381.   mParcel(parcel)
  2382. {
  2383. }
  2384. LLPanelLandCovenant::~LLPanelLandCovenant()
  2385. {
  2386. }
  2387. // virtual
  2388. void LLPanelLandCovenant::refresh()
  2389. {
  2390. LLViewerRegion* region = LLViewerParcelMgr::getInstance()->getSelectionRegion();
  2391. if(!region) return;
  2392. LLTextBox* region_name = getChild<LLTextBox>("region_name_text");
  2393. if (region_name)
  2394. {
  2395. region_name->setText(region->getName());
  2396. }
  2397. LLTextBox* region_landtype = getChild<LLTextBox>("region_landtype_text");
  2398. if (region_landtype)
  2399. {
  2400. region_landtype->setText(region->getSimProductName());
  2401. }
  2402. LLTextBox* region_maturity = getChild<LLTextBox>("region_maturity_text");
  2403. if (region_maturity)
  2404. {
  2405. region_maturity->setText(region->getSimAccessString());
  2406. }
  2407. LLTextBox* resellable_clause = getChild<LLTextBox>("resellable_clause");
  2408. if (resellable_clause)
  2409. {
  2410. if (region->getRegionFlags() & REGION_FLAGS_BLOCK_LAND_RESELL)
  2411. {
  2412. resellable_clause->setText(getString("can_not_resell"));
  2413. }
  2414. else
  2415. {
  2416. resellable_clause->setText(getString("can_resell"));
  2417. }
  2418. }
  2419. LLTextBox* changeable_clause = getChild<LLTextBox>("changeable_clause");
  2420. if (changeable_clause)
  2421. {
  2422. if (region->getRegionFlags() & REGION_FLAGS_ALLOW_PARCEL_CHANGES)
  2423. {
  2424. changeable_clause->setText(getString("can_change"));
  2425. }
  2426. else
  2427. {
  2428. changeable_clause->setText(getString("can_not_change"));
  2429. }
  2430. }
  2431. // send EstateCovenantInfo message
  2432. LLMessageSystem *msg = gMessageSystem;
  2433. msg->newMessage("EstateCovenantRequest");
  2434. msg->nextBlockFast(_PREHASH_AgentData);
  2435. msg->addUUIDFast(_PREHASH_AgentID, gAgent.getID());
  2436. msg->addUUIDFast(_PREHASH_SessionID,gAgent.getSessionID());
  2437. msg->sendReliable(region->getHost());
  2438. }
  2439. // static
  2440. void LLPanelLandCovenant::updateCovenantText(const std::string &string)
  2441. {
  2442. LLPanelLandCovenant* self = LLFloaterLand::getCurrentPanelLandCovenant();
  2443. if (self)
  2444. {
  2445. LLViewerTextEditor* editor = self->getChild<LLViewerTextEditor>("covenant_editor");
  2446. editor->setText(string);
  2447. }
  2448. }
  2449. // static
  2450. void LLPanelLandCovenant::updateEstateName(const std::string& name)
  2451. {
  2452. LLPanelLandCovenant* self = LLFloaterLand::getCurrentPanelLandCovenant();
  2453. if (self)
  2454. {
  2455. LLTextBox* editor = self->getChild<LLTextBox>("estate_name_text");
  2456. if (editor) editor->setText(name);
  2457. }
  2458. }
  2459. // static
  2460. void LLPanelLandCovenant::updateLastModified(const std::string& text)
  2461. {
  2462. LLPanelLandCovenant* self = LLFloaterLand::getCurrentPanelLandCovenant();
  2463. if (self)
  2464. {
  2465. LLTextBox* editor = self->getChild<LLTextBox>("covenant_timestamp_text");
  2466. if (editor) editor->setText(text);
  2467. }
  2468. }
  2469. // static
  2470. void LLPanelLandCovenant::updateEstateOwnerName(const std::string& name)
  2471. {
  2472. LLPanelLandCovenant* self = LLFloaterLand::getCurrentPanelLandCovenant();
  2473. if (self)
  2474. {
  2475. LLTextBox* editor = self->getChild<LLTextBox>("estate_owner_text");
  2476. if (editor) editor->setText(name);
  2477. }
  2478. }