master
Rider Linden 2018-06-21 09:13:19 -07:00
commit f07dc421e8
215 changed files with 2961 additions and 4440 deletions

View File

@ -537,3 +537,4 @@ ad0e15543836d64d6399d28b32852510435e344a 5.1.0-release
7c00e5b6cb3d95712e9d8e29277c805bca2bda90 5.1.3-release
7b6b020fd5ad9a8dc3670c5c92d1ca92e55fc485 5.1.4-release
2ea47f358b171178eb9a95503a1670d519c2886f 5.1.5-release
04538b8157c1f5cdacd9403f0a395452d4a93689 5.1.6-release

View File

@ -3326,9 +3326,9 @@ Copyright (c) 2012, 2014, 2015, 2016 nghttp2 contributors</string>
<key>archive</key>
<map>
<key>hash</key>
<string>4aefe12a3825d1b4b8370986d84792a2</string>
<string>86f6708f393c162cd4f92426b0a3cde7</string>
<key>url</key>
<string>http://automated-builds-secondlife-com.s3.amazonaws.com/ct2/15295/98583/viewer_manager-1.0.513540-darwin64-513540.tar.bz2</string>
<string>http://automated-builds-secondlife-com.s3.amazonaws.com/ct2/15341/99062/viewer_manager-1.0.513570-darwin64-513570.tar.bz2</string>
</map>
<key>name</key>
<string>darwin64</string>
@ -3350,9 +3350,9 @@ Copyright (c) 2012, 2014, 2015, 2016 nghttp2 contributors</string>
<key>archive</key>
<map>
<key>hash</key>
<string>db96bc8a83e6577d31657586100bfc35</string>
<string>c4dec51062ad78c09b11f7432aff4d1d</string>
<key>url</key>
<string>http://automated-builds-secondlife-com.s3.amazonaws.com/ct2/15298/98589/viewer_manager-1.0.513540-windows-513540.tar.bz2</string>
<string>http://automated-builds-secondlife-com.s3.amazonaws.com/ct2/17857/121832/viewer_manager-1.0.515286-windows-515286.tar.bz2</string>
</map>
<key>name</key>
<string>windows</string>
@ -3363,7 +3363,7 @@ Copyright (c) 2012, 2014, 2015, 2016 nghttp2 contributors</string>
<key>source_type</key>
<string>hg</string>
<key>version</key>
<string>1.0.513540</string>
<string>1.0.515286</string>
</map>
<key>vlc-bin</key>
<map>

View File

@ -220,6 +220,7 @@ Ansariel Hiller
STORM-2151
MAINT-6917
MAINT-8085
STORM-2122
Aralara Rajal
Arare Chantilly
CHUIBUG-191

View File

@ -184,7 +184,7 @@ void LLWearable::createLayers(S32 te, LLAvatarAppearance *avatarp)
{
LLTexLayerSet *layer_set = NULL;
const LLAvatarAppearanceDictionary::TextureEntry *texture_dict = LLAvatarAppearanceDictionary::getInstance()->getTexture((ETextureIndex)te);
if (texture_dict->mIsUsedByBakedTexture)
if (texture_dict && texture_dict->mIsUsedByBakedTexture)
{
const EBakedTextureIndex baked_index = texture_dict->mBakedTextureIndex;
@ -197,7 +197,7 @@ void LLWearable::createLayers(S32 te, LLAvatarAppearance *avatarp)
}
else
{
LL_ERRS() << "could not find layerset for LTO in wearable!" << LL_ENDL;
LL_WARNS() << "could not find layerset for LTO in wearable!" << LL_ENDL;
}
}
@ -437,7 +437,13 @@ LLWearable::EImportResult LLWearable::importStream( std::istream& input_stream,
LL_WARNS() << "Bad Wearable asset: bad texture, #" << i << LL_ENDL;
return LLWearable::FAILURE;
}
if (te >= ETextureIndex::TEX_NUM_INDICES) //createLayers() converts to ETextureIndex
{
LL_WARNS() << "Bad Wearable asset: bad texture index: " << te << LL_ENDL;
return LLWearable::FAILURE;
}
if( !LLUUID::validate( uuid_buffer ) )
{
LL_WARNS() << "Bad Wearable asset: bad texture uuid: "

View File

@ -258,7 +258,7 @@ int LLFile::remove(const std::string& filename, int supress_error)
return warnif("remove", filename, rc, supress_error);
}
int LLFile::rename(const std::string& filename, const std::string& newname)
int LLFile::rename(const std::string& filename, const std::string& newname, int supress_error)
{
#if LL_WINDOWS
std::string utf8filename = filename;
@ -269,7 +269,7 @@ int LLFile::rename(const std::string& filename, const std::string& newname)
#else
int rc = ::rename(filename.c_str(),newname.c_str());
#endif
return warnif(STRINGIZE("rename to '" << newname << "' from"), filename, rc);
return warnif(STRINGIZE("rename to '" << newname << "' from"), filename, rc, supress_error);
}
bool LLFile::copy(const std::string from, const std::string to)

View File

@ -74,7 +74,7 @@ public:
static int rmdir(const std::string& filename);
static int remove(const std::string& filename, int supress_error = 0);
static int rename(const std::string& filename,const std::string& newname);
static int rename(const std::string& filename,const std::string& newname, int supress_error = 0);
static bool copy(const std::string from, const std::string to);
static int stat(const std::string& filename,llstat* file_status);

View File

@ -513,19 +513,20 @@ namespace tut
const std::string& msg,
const std::string& in,
const LLSD& expected_value,
S32 expected_count)
S32 expected_count,
S32 depth_limit = -1)
{
std::stringstream input;
input.str(in);
LLSD parsed_result;
mParser->reset(); // reset() call is needed since test code re-uses mParser
S32 parsed_count = mParser->parse(input, parsed_result, in.size());
S32 parsed_count = mParser->parse(input, parsed_result, in.size(), depth_limit);
ensure_equals(msg.c_str(), parsed_result, expected_value);
// This count check is really only useful for expected
// parse failures, since the ensures equal will already
// require eqality.
// require equality.
std::string count_msg(msg);
count_msg += " (count)";
ensure_equals(count_msg, parsed_count, expected_count);
@ -714,6 +715,43 @@ namespace tut
expected,
1);
}
template<> template<>
void TestLLSDXMLParsingObject::test<5>()
{
// test deeper nested levels
LLSD level_5 = LLSD::emptyMap(); level_5["level_5"] = 42.f;
LLSD level_4 = LLSD::emptyMap(); level_4["level_4"] = level_5;
LLSD level_3 = LLSD::emptyMap(); level_3["level_3"] = level_4;
LLSD level_2 = LLSD::emptyMap(); level_2["level_2"] = level_3;
LLSD level_1 = LLSD::emptyMap(); level_1["level_1"] = level_2;
LLSD level_0 = LLSD::emptyMap(); level_0["level_0"] = level_1;
LLSD v;
v["deep"] = level_0;
ensureParse(
"deep llsd xml map",
"<llsd><map>"
"<key>deep</key><map>"
"<key>level_0</key><map>"
"<key>level_1</key><map>"
"<key>level_2</key><map>"
"<key>level_3</key><map>"
"<key>level_4</key><map>"
"<key>level_5</key><real>42.0</real>"
"</map>"
"</map>"
"</map>"
"</map>"
"</map>"
"</map>"
"</map></llsd>",
v,
8);
}
/*
TODO:
test XML parsing
@ -975,6 +1013,146 @@ namespace tut
LLSDParser::PARSE_FAILURE);
}
template<> template<>
void TestLLSDNotationParsingObject::test<18>()
{
LLSD level_1 = LLSD::emptyMap(); level_1["level_2"] = 99;
LLSD level_0 = LLSD::emptyMap(); level_0["level_1"] = level_1;
LLSD deep = LLSD::emptyMap();
deep["level_0"] = level_0;
LLSD root = LLSD::emptyMap();
root["deep"] = deep;
ensureParse(
"nested notation 3 deep",
"{'deep' : {'level_0':{'level_1':{'level_2': i99} } } }",
root,
5,
5); // 4 '{' plus i99 also counts as llsd, so real depth is 5
}
template<> template<>
void TestLLSDNotationParsingObject::test<19>()
{
LLSD level_9 = LLSD::emptyMap(); level_9["level_9"] = (S32)99;
LLSD level_8 = LLSD::emptyMap(); level_8["level_8"] = level_9;
LLSD level_7 = LLSD::emptyMap(); level_7["level_7"] = level_8;
LLSD level_6 = LLSD::emptyMap(); level_6["level_6"] = level_7;
LLSD level_5 = LLSD::emptyMap(); level_5["level_5"] = level_6;
LLSD level_4 = LLSD::emptyMap(); level_4["level_4"] = level_5;
LLSD level_3 = LLSD::emptyMap(); level_3["level_3"] = level_4;
LLSD level_2 = LLSD::emptyMap(); level_2["level_2"] = level_3;
LLSD level_1 = LLSD::emptyMap(); level_1["level_1"] = level_2;
LLSD level_0 = LLSD::emptyMap(); level_0["level_0"] = level_1;
LLSD deep = LLSD::emptyMap();
deep["deep"] = level_0;
ensureParse(
"nested notation 10 deep",
"{'deep' : {'level_0':{'level_1':{'level_2':{'level_3':{'level_4':{'level_5':{'level_6':{'level_7':{'level_8':{'level_9':i99}"
"} } } } } } } } } }",
deep,
12,
15);
}
template<> template<>
void TestLLSDNotationParsingObject::test<20>()
{
LLSD end = LLSD::emptyMap(); end["end"] = (S32)99;
LLSD level_49 = LLSD::emptyMap(); level_49["level_49"] = end;
LLSD level_48 = LLSD::emptyMap(); level_48["level_48"] = level_49;
LLSD level_47 = LLSD::emptyMap(); level_47["level_47"] = level_48;
LLSD level_46 = LLSD::emptyMap(); level_46["level_46"] = level_47;
LLSD level_45 = LLSD::emptyMap(); level_45["level_45"] = level_46;
LLSD level_44 = LLSD::emptyMap(); level_44["level_44"] = level_45;
LLSD level_43 = LLSD::emptyMap(); level_43["level_43"] = level_44;
LLSD level_42 = LLSD::emptyMap(); level_42["level_42"] = level_43;
LLSD level_41 = LLSD::emptyMap(); level_41["level_41"] = level_42;
LLSD level_40 = LLSD::emptyMap(); level_40["level_40"] = level_41;
LLSD level_39 = LLSD::emptyMap(); level_39["level_39"] = level_40;
LLSD level_38 = LLSD::emptyMap(); level_38["level_38"] = level_39;
LLSD level_37 = LLSD::emptyMap(); level_37["level_37"] = level_38;
LLSD level_36 = LLSD::emptyMap(); level_36["level_36"] = level_37;
LLSD level_35 = LLSD::emptyMap(); level_35["level_35"] = level_36;
LLSD level_34 = LLSD::emptyMap(); level_34["level_34"] = level_35;
LLSD level_33 = LLSD::emptyMap(); level_33["level_33"] = level_34;
LLSD level_32 = LLSD::emptyMap(); level_32["level_32"] = level_33;
LLSD level_31 = LLSD::emptyMap(); level_31["level_31"] = level_32;
LLSD level_30 = LLSD::emptyMap(); level_30["level_30"] = level_31;
LLSD level_29 = LLSD::emptyMap(); level_29["level_29"] = level_30;
LLSD level_28 = LLSD::emptyMap(); level_28["level_28"] = level_29;
LLSD level_27 = LLSD::emptyMap(); level_27["level_27"] = level_28;
LLSD level_26 = LLSD::emptyMap(); level_26["level_26"] = level_27;
LLSD level_25 = LLSD::emptyMap(); level_25["level_25"] = level_26;
LLSD level_24 = LLSD::emptyMap(); level_24["level_24"] = level_25;
LLSD level_23 = LLSD::emptyMap(); level_23["level_23"] = level_24;
LLSD level_22 = LLSD::emptyMap(); level_22["level_22"] = level_23;
LLSD level_21 = LLSD::emptyMap(); level_21["level_21"] = level_22;
LLSD level_20 = LLSD::emptyMap(); level_20["level_20"] = level_21;
LLSD level_19 = LLSD::emptyMap(); level_19["level_19"] = level_20;
LLSD level_18 = LLSD::emptyMap(); level_18["level_18"] = level_19;
LLSD level_17 = LLSD::emptyMap(); level_17["level_17"] = level_18;
LLSD level_16 = LLSD::emptyMap(); level_16["level_16"] = level_17;
LLSD level_15 = LLSD::emptyMap(); level_15["level_15"] = level_16;
LLSD level_14 = LLSD::emptyMap(); level_14["level_14"] = level_15;
LLSD level_13 = LLSD::emptyMap(); level_13["level_13"] = level_14;
LLSD level_12 = LLSD::emptyMap(); level_12["level_12"] = level_13;
LLSD level_11 = LLSD::emptyMap(); level_11["level_11"] = level_12;
LLSD level_10 = LLSD::emptyMap(); level_10["level_10"] = level_11;
LLSD level_9 = LLSD::emptyMap(); level_9["level_9"] = level_10;
LLSD level_8 = LLSD::emptyMap(); level_8["level_8"] = level_9;
LLSD level_7 = LLSD::emptyMap(); level_7["level_7"] = level_8;
LLSD level_6 = LLSD::emptyMap(); level_6["level_6"] = level_7;
LLSD level_5 = LLSD::emptyMap(); level_5["level_5"] = level_6;
LLSD level_4 = LLSD::emptyMap(); level_4["level_4"] = level_5;
LLSD level_3 = LLSD::emptyMap(); level_3["level_3"] = level_4;
LLSD level_2 = LLSD::emptyMap(); level_2["level_2"] = level_3;
LLSD level_1 = LLSD::emptyMap(); level_1["level_1"] = level_2;
LLSD level_0 = LLSD::emptyMap(); level_0["level_0"] = level_1;
LLSD deep = LLSD::emptyMap();
deep["deep"] = level_0;
ensureParse(
"nested notation deep",
"{'deep':"
"{'level_0' :{'level_1' :{'level_2' :{'level_3' :{'level_4' :{'level_5' :{'level_6' :{'level_7' :{'level_8' :{'level_9' :"
"{'level_10':{'level_11':{'level_12':{'level_13':{'level_14':{'level_15':{'level_16':{'level_17':{'level_18':{'level_19':"
"{'level_20':{'level_21':{'level_22':{'level_23':{'level_24':{'level_25':{'level_26':{'level_27':{'level_28':{'level_29':"
"{'level_30':{'level_31':{'level_32':{'level_33':{'level_34':{'level_35':{'level_36':{'level_37':{'level_38':{'level_39':"
"{'level_40':{'level_41':{'level_42':{'level_43':{'level_44':{'level_45':{'level_46':{'level_47':{'level_48':{'level_49':"
"{'end':i99}"
"} } } } } } } } } }"
"} } } } } } } } } }"
"} } } } } } } } } }"
"} } } } } } } } } }"
"} } } } } } } } } }"
"}",
deep,
53);
}
template<> template<>
void TestLLSDNotationParsingObject::test<21>()
{
ensureParse(
"nested notation 10 deep",
"{'deep' : {'level_0':{'level_1':{'level_2':{'level_3':{'level_4':{'level_5':{'level_6':{'level_7':{'level_8':{'level_9':i99}"
"} } } } } } } } } }",
LLSD(),
LLSDParser::PARSE_FAILURE,
9);
}
/**
* @class TestLLSDBinaryParsing
* @brief Concrete instance of a parse tester.

View File

@ -51,98 +51,6 @@ const std::string INTERACTIVE_SYSTEM_FROM("F387446C-37C4-45f2-A438-D99CBDBB563B"
const S32 IM_TTL = 1;
/**
* LLIMInfo
*/
LLIMInfo::LLIMInfo() :
mFromGroup(FALSE),
mParentEstateID(0),
mOffline(0),
mViewerThinksToIsOnline(false),
mIMType(IM_NOTHING_SPECIAL),
mTimeStamp(0),
mTTL(IM_TTL)
{
}
LLIMInfo::LLIMInfo(
const LLUUID& from_id,
BOOL from_group,
const LLUUID& to_id,
EInstantMessage im_type,
const std::string& name,
const std::string& message,
const LLUUID& id,
U32 parent_estate_id,
const LLUUID& region_id,
const LLVector3& position,
LLSD data,
U8 offline,
U32 timestamp,
S32 ttl) :
mFromID(from_id),
mFromGroup(from_group),
mToID(to_id),
mParentEstateID(0),
mRegionID(region_id),
mPosition(position),
mOffline(offline),
mViewerThinksToIsOnline(false),
mIMType(im_type),
mID(id),
mTimeStamp(timestamp),
mName(name),
mMessage(message),
mData(data),
mTTL(ttl)
{
}
LLIMInfo::LLIMInfo(LLMessageSystem* msg, S32 ttl) :
mViewerThinksToIsOnline(false),
mTTL(ttl)
{
unpackMessageBlock(msg);
}
LLIMInfo::~LLIMInfo()
{
}
void LLIMInfo::packInstantMessage(LLMessageSystem* msg) const
{
LL_DEBUGS() << "LLIMInfo::packInstantMessage()" << LL_ENDL;
msg->newMessageFast(_PREHASH_ImprovedInstantMessage);
packMessageBlock(msg);
}
void LLIMInfo::packMessageBlock(LLMessageSystem* msg) const
{
// Construct binary bucket
std::vector<U8> bucket;
if (mData.has("binary_bucket"))
{
bucket = mData["binary_bucket"].asBinary();
}
pack_instant_message_block(
msg,
mFromID,
mFromGroup,
LLUUID::null,
mToID,
mName,
mMessage,
mOffline,
mIMType,
mID,
mParentEstateID,
mRegionID,
mPosition,
mTimeStamp,
&bucket[0],
bucket.size());
}
void pack_instant_message(
LLMessageSystem* msg,
const LLUUID& from_id,
@ -253,120 +161,4 @@ void pack_instant_message_block(
msg->addBinaryDataFast(_PREHASH_BinaryBucket, bb, binary_bucket_size);
}
void LLIMInfo::unpackMessageBlock(LLMessageSystem* msg)
{
msg->getUUIDFast(_PREHASH_AgentData, _PREHASH_AgentID, mFromID);
msg->getBOOLFast(_PREHASH_MessageBlock, _PREHASH_FromGroup, mFromGroup);
msg->getUUIDFast(_PREHASH_MessageBlock, _PREHASH_ToAgentID, mToID);
msg->getU32Fast(_PREHASH_MessageBlock, _PREHASH_ParentEstateID, mParentEstateID);
msg->getUUIDFast(_PREHASH_MessageBlock, _PREHASH_RegionID, mRegionID);
msg->getVector3Fast(_PREHASH_MessageBlock, _PREHASH_Position, mPosition);
msg->getU8Fast(_PREHASH_MessageBlock, _PREHASH_Offline, mOffline);
U8 dialog;
msg->getU8Fast(_PREHASH_MessageBlock, _PREHASH_Dialog, dialog);
mIMType = (EInstantMessage) dialog;
msg->getUUIDFast(_PREHASH_MessageBlock, _PREHASH_ID, mID);
msg->getU32Fast(_PREHASH_MessageBlock, _PREHASH_Timestamp, mTimeStamp);
msg->getStringFast(_PREHASH_MessageBlock, _PREHASH_FromAgentName, mName);
msg->getStringFast(_PREHASH_MessageBlock, _PREHASH_Message, mMessage);
S32 binary_bucket_size = llmin(
MTUBYTES,
msg->getSizeFast(
_PREHASH_MessageBlock,
_PREHASH_BinaryBucket));
if(binary_bucket_size > 0)
{
std::vector<U8> bucket;
bucket.resize(binary_bucket_size);
msg->getBinaryDataFast(
_PREHASH_MessageBlock,
_PREHASH_BinaryBucket,
&bucket[0],
0,
0,
binary_bucket_size);
mData["binary_bucket"] = bucket;
}
else
{
mData.clear();
}
}
LLSD im_info_to_llsd(LLPointer<LLIMInfo> im_info)
{
LLSD param_version;
param_version["version"] = 1;
LLSD param_message;
param_message["from_id"] = im_info->mFromID;
param_message["from_group"] = im_info->mFromGroup;
param_message["to_id"] = im_info->mToID;
param_message["from_name"] = im_info->mName;
param_message["message"] = im_info->mMessage;
param_message["type"] = (S32)im_info->mIMType;
param_message["id"] = im_info->mID;
param_message["timestamp"] = (S32)im_info->mTimeStamp;
param_message["offline"] = (S32)im_info->mOffline;
param_message["parent_estate_id"] = (S32)im_info->mParentEstateID;
param_message["region_id"] = im_info->mRegionID;
param_message["position"] = ll_sd_from_vector3(im_info->mPosition);
param_message["data"] = im_info->mData;
param_message["ttl"] = im_info->mTTL;
LLSD param_agent;
param_agent["agent_id"] = im_info->mFromID;
LLSD params;
params["version_params"] = param_version;
params["message_params"] = param_message;
params["agent_params"] = param_agent;
return params;
}
LLPointer<LLIMInfo> llsd_to_im_info(const LLSD& im_info_sd)
{
LLSD param_message = im_info_sd["message_params"];
LLSD param_agent = im_info_sd["agent_params"];
LLPointer<LLIMInfo> im_info = new LLIMInfo(
param_message["from_id"].asUUID(),
param_message["from_group"].asBoolean(),
param_message["to_id"].asUUID(),
(EInstantMessage) param_message["type"].asInteger(),
param_message["from_name"].asString(),
param_message["message"].asString(),
param_message["id"].asUUID(),
(U32) param_message["parent_estate_id"].asInteger(),
param_message["region_id"].asUUID(),
ll_vector3_from_sd(param_message["position"]),
param_message["data"],
(U8) param_message["offline"].asInteger(),
(U32) param_message["timestamp"].asInteger(),
param_message["ttl"].asInteger());
return im_info;
}
LLPointer<LLIMInfo> LLIMInfo::clone()
{
return new LLIMInfo(
mFromID,
mFromGroup,
mToID,
mIMType,
mName,
mMessage,
mID,
mParentEstateID,
mRegionID,
mPosition,
mData,
mOffline,
mTimeStamp,
mTTL);
}

View File

@ -177,59 +177,6 @@ extern const std::string INTERACTIVE_SYSTEM_FROM;
// Number of retry attempts on sending the im.
extern const S32 IM_TTL;
class LLIMInfo : public LLRefCount
{
protected:
LLIMInfo();
~LLIMInfo();
public:
LLIMInfo(LLMessageSystem* msg,
S32 ttl = IM_TTL);
LLIMInfo(
const LLUUID& from_id,
BOOL from_group,
const LLUUID& to_id,
EInstantMessage im_type,
const std::string& name,
const std::string& message,
const LLUUID& id,
U32 parent_estate_id,
const LLUUID& region_id,
const LLVector3& position,
LLSD data,
U8 offline,
U32 timestamp,
S32 ttl = IM_TTL);
void packInstantMessage(LLMessageSystem* msg) const;
void packMessageBlock(LLMessageSystem* msg) const;
void unpackMessageBlock(LLMessageSystem* msg);
LLPointer<LLIMInfo> clone();
public:
LLUUID mFromID;
BOOL mFromGroup;
LLUUID mToID;
U32 mParentEstateID;
LLUUID mRegionID;
LLVector3 mPosition;
U8 mOffline;
bool mViewerThinksToIsOnline;
EInstantMessage mIMType;
LLUUID mID;
U32 mTimeStamp;
std::string mName;
std::string mMessage;
LLSD mData;
S32 mTTL;
};
LLPointer<LLIMInfo> llsd_to_im_info(const LLSD& im_info_sd);
LLSD im_info_to_llsd(LLPointer<LLIMInfo> im_info);
void pack_instant_message(
LLMessageSystem* msgsystem,
const LLUUID& from_id,

View File

@ -63,7 +63,6 @@ void LLXfer::init (S32 chunk_size)
mXferSize = 0;
mStatus = e_LL_XFER_UNINITIALIZED;
mNext = NULL;
mWaitingForACK = FALSE;
mCallback = NULL;
@ -99,7 +98,22 @@ void LLXfer::cleanup ()
S32 LLXfer::startSend (U64 xfer_id, const LLHost &remote_host)
{
LL_WARNS() << "undifferentiated LLXfer::startSend for " << getFileName() << LL_ENDL;
LL_WARNS("Xfer") << "unexpected call to base class LLXfer::startSend for " << getFileName() << LL_ENDL;
return (-1);
}
///////////////////////////////////////////////////////////
void LLXfer::closeFileHandle()
{
LL_WARNS("Xfer") << "unexpected call to base class LLXfer::closeFileHandle for " << getFileName() << LL_ENDL;
}
///////////////////////////////////////////////////////////
S32 LLXfer::reopenFileHandle()
{
LL_WARNS("Xfer") << "unexpected call to base class LLXfer::reopenFileHandle for " << getFileName() << LL_ENDL;
return (-1);
}
@ -115,7 +129,7 @@ void LLXfer::setXferSize (S32 xfer_size)
S32 LLXfer::startDownload()
{
LL_WARNS() << "undifferentiated LLXfer::startDownload for " << getFileName()
LL_WARNS("Xfer") << "undifferentiated LLXfer::startDownload for " << getFileName()
<< LL_ENDL;
return (-1);
}
@ -127,20 +141,20 @@ S32 LLXfer::receiveData (char *datap, S32 data_size)
S32 retval = 0;
if (((S32) mBufferLength + data_size) > getMaxBufferSize())
{
{ // Write existing data to disk if it's larger than the buffer size
retval = flush();
}
if (!retval)
{
if (datap != NULL)
{
{ // Append new data to mBuffer
memcpy(&mBuffer[mBufferLength],datap,data_size); /*Flawfinder: ignore*/
mBufferLength += data_size;
}
else
{
LL_ERRS() << "NULL data passed in receiveData" << LL_ENDL;
LL_ERRS("Xfer") << "NULL data passed in receiveData" << LL_ENDL;
}
}
@ -163,7 +177,7 @@ S32 LLXfer::flush()
S32 LLXfer::suck(S32 start_position)
{
LL_WARNS() << "Attempted to send a packet outside the buffer bounds in LLXfer::suck()" << LL_ENDL;
LL_WARNS("Xfer") << "Attempted to send a packet outside the buffer bounds in LLXfer::suck()" << LL_ENDL;
return (-1);
}
@ -196,7 +210,7 @@ void LLXfer::sendPacket(S32 packet_num)
if (fdata_size < 0)
{
LL_WARNS() << "negative data size in xfer send, aborting" << LL_ENDL;
LL_WARNS("Xfer") << "negative data size in xfer send, aborting" << LL_ENDL;
abort(LL_ERR_EOF);
return;
}
@ -248,7 +262,12 @@ void LLXfer::sendPacket(S32 packet_num)
gMessageSystem->nextBlockFast(_PREHASH_DataPacket);
gMessageSystem->addBinaryDataFast(_PREHASH_Data, &fdata_buf,fdata_size);
gMessageSystem->sendMessage(mRemoteHost);
S32 sent_something = gMessageSystem->sendMessage(mRemoteHost);
if (sent_something == 0)
{
abort(LL_ERR_CIRCUIT_GONE);
return;
}
ACKTimer.reset();
mWaitingForACK = TRUE;
@ -289,12 +308,12 @@ S32 LLXfer::processEOF()
if (LL_ERR_NOERR == mCallbackResult)
{
LL_INFOS() << "xfer from " << mRemoteHost << " complete: " << getFileName()
LL_INFOS("Xfer") << "xfer from " << mRemoteHost << " complete: " << getFileName()
<< LL_ENDL;
}
else
{
LL_INFOS() << "xfer from " << mRemoteHost << " failed or aborted, code "
LL_INFOS("Xfer") << "xfer from " << mRemoteHost << " failed, code "
<< mCallbackResult << ": " << getFileName() << LL_ENDL;
}
@ -323,15 +342,18 @@ void LLXfer::abort (S32 result_code)
{
mCallbackResult = result_code;
LL_INFOS() << "Aborting xfer from " << mRemoteHost << " named " << getFileName()
LL_INFOS("Xfer") << "Aborting xfer from " << mRemoteHost << " named " << getFileName()
<< " - error: " << result_code << LL_ENDL;
gMessageSystem->newMessageFast(_PREHASH_AbortXfer);
gMessageSystem->nextBlockFast(_PREHASH_XferID);
gMessageSystem->addU64Fast(_PREHASH_ID, mID);
gMessageSystem->addS32Fast(_PREHASH_Result, result_code);
gMessageSystem->sendMessage(mRemoteHost);
if (result_code != LL_ERR_CIRCUIT_GONE)
{
gMessageSystem->newMessageFast(_PREHASH_AbortXfer);
gMessageSystem->nextBlockFast(_PREHASH_XferID);
gMessageSystem->addU64Fast(_PREHASH_ID, mID);
gMessageSystem->addS32Fast(_PREHASH_Result, result_code);
gMessageSystem->sendMessage(mRemoteHost);
}
mStatus = e_LL_XFER_ABORTED;
}

View File

@ -54,7 +54,6 @@ class LLXfer
S32 mChunkSize;
public:
LLXfer *mNext;
U64 mID;
S32 mPacketNum;
@ -62,7 +61,7 @@ class LLXfer
S32 mXferSize;
char *mBuffer;
U32 mBufferLength;
U32 mBufferLength; // Size of valid data, not actual allocated buffer size
U32 mBufferStartOffset;
BOOL mBufferContainsEOF;
@ -90,7 +89,9 @@ class LLXfer
void init(S32 chunk_size);
virtual void cleanup();
virtual S32 startSend (U64 xfer_id, const LLHost &remote_host);
virtual S32 startSend(U64 xfer_id, const LLHost &remote_host);
virtual void closeFileHandle();
virtual S32 reopenFileHandle();
virtual void sendPacket(S32 packet_num);
virtual void sendNextPacket();
virtual void resendLastPacket();

View File

@ -102,12 +102,12 @@ void LLXfer_File::cleanup ()
if (mDeleteLocalOnCompletion)
{
LL_DEBUGS() << "Removing file: " << mLocalFilename << LL_ENDL;
LL_DEBUGS("Xfer") << "Removing file: " << mLocalFilename << LL_ENDL;
LLFile::remove(mLocalFilename, ENOENT);
}
else
{
LL_DEBUGS() << "Keeping local file: " << mLocalFilename << LL_ENDL;
LL_DEBUGS("Xfer") << "Keeping local file: " << mLocalFilename << LL_ENDL;
}
LLXfer::cleanup();
@ -139,7 +139,7 @@ S32 LLXfer_File::initializeRequest(U64 xfer_id,
mCallbackDataHandle = user_data;
mCallbackResult = LL_ERR_NOERR;
LL_INFOS() << "Requesting xfer from " << remote_host << " for file: " << mLocalFilename << LL_ENDL;
LL_INFOS("Xfer") << "Requesting xfer from " << remote_host << " for file: " << mLocalFilename << LL_ENDL;
if (mBuffer)
{
@ -167,6 +167,7 @@ S32 LLXfer_File::startDownload()
fclose(mFp);
mFp = NULL;
// tbd - is it premature to send this message if the queue is backed up?
gMessageSystem->newMessageFast(_PREHASH_RequestXfer);
gMessageSystem->nextBlockFast(_PREHASH_XferID);
gMessageSystem->addU64Fast(_PREHASH_ID, mID);
@ -182,7 +183,7 @@ S32 LLXfer_File::startDownload()
}
else
{
LL_WARNS() << "Couldn't create file to be received!" << LL_ENDL;
LL_WARNS("Xfer") << "Couldn't create file to be received!" << LL_ENDL;
retval = -1;
}
@ -206,7 +207,8 @@ S32 LLXfer_File::startSend (U64 xfer_id, const LLHost &remote_host)
mBufferLength = 0;
mBufferStartOffset = 0;
// We leave the file open, assuming we'll start reading and sending soon
mFp = LLFile::fopen(mLocalFilename,"rb"); /* Flawfinder : ignore */
if (mFp)
{
@ -223,7 +225,7 @@ S32 LLXfer_File::startSend (U64 xfer_id, const LLHost &remote_host)
}
else
{
LL_INFOS() << "Warning: " << mLocalFilename << " not found." << LL_ENDL;
LL_INFOS("Xfer") << "Warning: " << mLocalFilename << " not found." << LL_ENDL;
return (LL_ERR_FILE_NOT_FOUND);
}
@ -232,6 +234,36 @@ S32 LLXfer_File::startSend (U64 xfer_id, const LLHost &remote_host)
return (retval);
}
///////////////////////////////////////////////////////////
void LLXfer_File::closeFileHandle()
{
if (mFp)
{
fclose(mFp);
mFp = NULL;
}
}
///////////////////////////////////////////////////////////
S32 LLXfer_File::reopenFileHandle()
{
S32 retval = LL_ERR_NOERR; // presume success
if (mFp == NULL)
{
mFp = LLFile::fopen(mLocalFilename,"rb"); /* Flawfinder : ignore */
if (mFp == NULL)
{
LL_INFOS("Xfer") << "Warning: " << mLocalFilename << " not found when re-opening file" << LL_ENDL;
retval = LL_ERR_FILE_NOT_FOUND;
}
}
return retval;
}
///////////////////////////////////////////////////////////
S32 LLXfer_File::getMaxBufferSize ()
@ -279,18 +311,21 @@ S32 LLXfer_File::flush()
{
if (mFp)
{
LL_ERRS() << "Overwriting open file pointer!" << LL_ENDL;
LL_ERRS("Xfer") << "Overwriting open file pointer!" << LL_ENDL;
}
mFp = LLFile::fopen(mTempFilename,"a+b"); /* Flawfinder : ignore */
if (mFp)
{
if (fwrite(mBuffer,1,mBufferLength,mFp) != mBufferLength)
S32 write_size = fwrite(mBuffer,1,mBufferLength,mFp);
if (write_size != mBufferLength)
{
LL_WARNS() << "Short write" << LL_ENDL;
LL_WARNS("Xfer") << "Non-matching write size, requested " << mBufferLength
<< " but wrote " << write_size
<< LL_ENDL;
}
// LL_INFOS() << "******* wrote " << mBufferLength << " bytes of file xfer" << LL_ENDL;
// LL_INFOS("Xfer") << "******* wrote " << mBufferLength << " bytes of file xfer" << LL_ENDL;
fclose(mFp);
mFp = NULL;
@ -298,7 +333,7 @@ S32 LLXfer_File::flush()
}
else
{
LL_WARNS() << "LLXfer_File::flush() unable to open " << mTempFilename << " for writing!" << LL_ENDL;
LL_WARNS("Xfer") << "LLXfer_File::flush() unable to open " << mTempFilename << " for writing!" << LL_ENDL;
retval = LL_ERR_CANNOT_OPEN_FILE;
}
}
@ -329,18 +364,18 @@ S32 LLXfer_File::processEOF()
{
#if !LL_WINDOWS
S32 error_number = errno;
LL_INFOS() << "Rename failure (" << error_number << ") - "
LL_INFOS("Xfer") << "Rename failure (" << error_number << ") - "
<< mTempFilename << " to " << mLocalFilename << LL_ENDL;
if(EXDEV == error_number)
{
if(copy_file(mTempFilename, mLocalFilename) == 0)
{
LL_INFOS() << "Rename across mounts; copying+unlinking the file instead." << LL_ENDL;
LL_INFOS("Xfer") << "Rename across mounts; copying+unlinking the file instead." << LL_ENDL;
unlink(mTempFilename.c_str());
}
else
{
LL_WARNS() << "Copy failure - " << mTempFilename << " to "
LL_WARNS("Xfer") << "Copy failure - " << mTempFilename << " to "
<< mLocalFilename << LL_ENDL;
}
}
@ -354,11 +389,11 @@ S32 LLXfer_File::processEOF()
//LL_WARNS() << "File " << mLocalFilename << " does "
// << (!fp ? "not" : "" ) << " exit." << LL_ENDL;
//if(fp) fclose(fp);
LL_WARNS() << "Rename fatally failed, can only handle EXDEV ("
LL_WARNS("Xfer") << "Rename fatally failed, can only handle EXDEV ("
<< EXDEV << ")" << LL_ENDL;
}
#else
LL_WARNS() << "Rename failure - " << mTempFilename << " to "
LL_WARNS("Xfer") << "Rename failure - " << mTempFilename << " to "
<< mLocalFilename << LL_ENDL;
#endif
}
@ -437,3 +472,4 @@ S32 copy_file(const std::string& from, const std::string& to)
return rv;
}
#endif

View File

@ -61,8 +61,10 @@ class LLXfer_File : public LLXfer
virtual S32 startDownload();
virtual S32 processEOF();
virtual S32 startSend (U64 xfer_id, const LLHost &remote_host);
virtual S32 startSend(U64 xfer_id, const LLHost &remote_host);
virtual void closeFileHandle();
virtual S32 reopenFileHandle();
virtual S32 suck(S32 start_position);
virtual S32 flush();

View File

@ -80,28 +80,6 @@ void LLXfer_Mem::setXferSize (S32 xfer_size)
///////////////////////////////////////////////////////////
U64 LLXfer_Mem::registerXfer(U64 xfer_id, const void *datap, const S32 length)
{
mID = xfer_id;
if (datap)
{
setXferSize(length);
if (mBuffer)
{
memcpy(mBuffer,datap,length); /* Flawfinder : ignore */
mBufferLength = length;
}
else
{
xfer_id = 0;
}
}
mStatus = e_LL_XFER_REGISTERED;
return (xfer_id);
}
S32 LLXfer_Mem::startSend (U64 xfer_id, const LLHost &remote_host)
{
S32 retval = LL_ERR_NOERR; // presume success

View File

@ -53,7 +53,6 @@ class LLXfer_Mem : public LLXfer
virtual void cleanup();
virtual S32 startSend (U64 xfer_id, const LLHost &remote_host);
virtual U64 registerXfer(U64 xfer_id, const void *datap, const S32 length);
virtual void setXferSize (S32 data_size);
virtual S32 initializeRequest(U64 xfer_id,

View File

@ -79,8 +79,20 @@ void LLXfer_VFile::init (LLVFS *vfs, const LLUUID &local_id, LLAssetType::EType
void LLXfer_VFile::cleanup ()
{
LLVFile file(mVFS, mTempID, mType, LLVFile::WRITE);
file.remove();
if (mTempID.notNull() &&
mDeleteTempFile)
{
if (mVFS->getExists(mTempID, mType))
{
LLVFile file(mVFS, mTempID, mType, LLVFile::WRITE);
file.remove();
}
else
{
LL_WARNS("Xfer") << "LLXfer_VFile::cleanup() can't open to delete VFS file " << mTempID << "." << LLAssetType::lookup(mType)
<< ", mRemoteID is " << mRemoteID << LL_ENDL;
}
}
delete mVFile;
mVFile = NULL;
@ -118,7 +130,7 @@ S32 LLXfer_VFile::initializeRequest(U64 xfer_id,
mName = llformat("VFile %s:%s", id_string.c_str(), LLAssetType::lookup(mType));
LL_INFOS() << "Requesting " << mName << LL_ENDL;
LL_INFOS("Xfer") << "Requesting " << mName << LL_ENDL;
if (mBuffer)
{
@ -131,6 +143,7 @@ S32 LLXfer_VFile::initializeRequest(U64 xfer_id,
mBufferLength = 0;
mPacketNum = 0;
mTempID.generate();
mDeleteTempFile = TRUE;
mStatus = e_LL_XFER_PENDING;
return retval;
}
@ -140,7 +153,8 @@ S32 LLXfer_VFile::initializeRequest(U64 xfer_id,
S32 LLXfer_VFile::startDownload()
{
S32 retval = 0; // presume success
LLVFile file(mVFS, mTempID, mType, LLVFile::APPEND);
// Don't need to create the file here, it will happen when data arrives
gMessageSystem->newMessageFast(_PREHASH_RequestXfer);
gMessageSystem->nextBlockFast(_PREHASH_XferID);
@ -184,6 +198,8 @@ S32 LLXfer_VFile::startSend (U64 xfer_id, const LLHost &remote_host)
if (mVFile->getSize() <= 0)
{
LL_WARNS("Xfer") << "LLXfer_VFile::startSend() VFS file " << mLocalID << "." << LLAssetType::lookup(mType)
<< " has unexpected file size of " << mVFile->getSize() << LL_ENDL;
delete mVFile;
mVFile = NULL;
@ -198,6 +214,7 @@ S32 LLXfer_VFile::startSend (U64 xfer_id, const LLHost &remote_host)
}
else
{
LL_WARNS("Xfer") << "LLXfer_VFile::startSend() can't read VFS file " << mLocalID << "." << LLAssetType::lookup(mType) << LL_ENDL;
retval = LL_ERR_FILE_NOT_FOUND;
}
@ -205,6 +222,41 @@ S32 LLXfer_VFile::startSend (U64 xfer_id, const LLHost &remote_host)
}
///////////////////////////////////////////////////////////
void LLXfer_VFile::closeFileHandle()
{
if (mVFile)
{
delete mVFile;
mVFile = NULL;
}
}
///////////////////////////////////////////////////////////
S32 LLXfer_VFile::reopenFileHandle()
{
S32 retval = LL_ERR_NOERR; // presume success
if (mVFile == NULL)
{
if (mVFS->getExists(mLocalID, mType))
{
mVFile = new LLVFile(mVFS, mLocalID, mType, LLVFile::READ);
}
else
{
LL_WARNS("Xfer") << "LLXfer_VFile::reopenFileHandle() can't read VFS file " << mLocalID << "." << LLAssetType::lookup(mType) << LL_ENDL;
retval = LL_ERR_FILE_NOT_FOUND;
}
}
return retval;
}
///////////////////////////////////////////////////////////
void LLXfer_VFile::setXferSize (S32 xfer_size)
{
LLXfer::setXferSize(xfer_size);
@ -236,8 +288,8 @@ S32 LLXfer_VFile::suck(S32 start_position)
// grab a buffer from the right place in the file
if (! mVFile->seek(start_position, 0))
{
LL_WARNS() << "VFile Xfer Can't seek to position " << start_position << ", file length " << mVFile->getSize() << LL_ENDL;
LL_WARNS() << "While sending file " << mLocalID << LL_ENDL;
LL_WARNS("Xfer") << "VFile Xfer Can't seek to position " << start_position << ", file length " << mVFile->getSize() << LL_ENDL;
LL_WARNS("Xfer") << "While sending file " << mLocalID << LL_ENDL;
return -1;
}
@ -288,12 +340,31 @@ S32 LLXfer_VFile::processEOF()
if (!mCallbackResult)
{
LLVFile file(mVFS, mTempID, mType, LLVFile::WRITE);
if (! file.rename(mLocalID, mType))
if (mVFS->getExists(mTempID, mType))
{
LL_INFOS() << "copy from temp file failed: unable to rename to " << mLocalID << LL_ENDL;
LLVFile file(mVFS, mTempID, mType, LLVFile::WRITE);
if (!file.rename(mLocalID, mType))
{
LL_WARNS("Xfer") << "VFS rename of temp file failed: unable to rename " << mTempID << " to " << mLocalID << LL_ENDL;
}
else
{
#ifdef VFS_SPAM
// Debugging spam
LL_INFOS("Xfer") << "VFS rename of temp file done: renamed " << mTempID << " to " << mLocalID
<< " LLVFile size is " << file.getSize()
<< LL_ENDL;
#endif
// Rename worked: the original file is gone. Clear mDeleteTempFile
// so we don't attempt to delete the file in cleanup()
mDeleteTempFile = FALSE;
}
}
else
{
LL_WARNS("Xfer") << "LLXfer_VFile::processEOF() can't open for renaming VFS file " << mTempID << "." << LLAssetType::lookup(mType) << LL_ENDL;
}
}
if (mVFile)
@ -336,3 +407,4 @@ U32 LLXfer_VFile::getXferTypeTag()
{
return LLXfer::XFER_VFILE;
}

View File

@ -47,6 +47,8 @@ class LLXfer_VFile : public LLXfer
std::string mName;
BOOL mDeleteTempFile;
public:
LLXfer_VFile ();
LLXfer_VFile (LLVFS *vfs, const LLUUID &local_id, LLAssetType::EType type);
@ -66,8 +68,10 @@ class LLXfer_VFile : public LLXfer
virtual S32 startDownload();
virtual S32 processEOF();
virtual S32 startSend (U64 xfer_id, const LLHost &remote_host);
virtual S32 startSend(U64 xfer_id, const LLHost &remote_host);
virtual void closeFileHandle();
virtual S32 reopenFileHandle();
virtual S32 suck(S32 start_position);
virtual S32 flush();

File diff suppressed because it is too large Load Diff

View File

@ -77,6 +77,7 @@ class LLXferManager
protected:
S32 mMaxOutgoingXfersPerCircuit;
S32 mHardLimitOutgoingXfersPerCircuit; // At this limit, kill off the connection
S32 mMaxIncomingXfers;
BOOL mUseAckThrottling; // Use ack throttling to cap file xfer bandwidth
@ -92,19 +93,22 @@ class LLXferManager
HIGH_PRIORITY = TRUE,
};
LLXfer *mSendList;
LLXfer *mReceiveList;
// Linked FIFO list, add to the front and pull from back
typedef std::deque<LLXfer *> xfer_list_t;
xfer_list_t mSendList;
xfer_list_t mReceiveList;
typedef std::list<LLHostStatus*> status_list_t;
status_list_t mOutgoingHosts;
private:
protected:
// implementation methods
virtual void startPendingDownloads();
virtual void addToList(LLXfer* xferp, LLXfer*& head, BOOL is_priority);
virtual void addToList(LLXfer* xferp, xfer_list_t & xfer_list, BOOL is_priority);
std::multiset<std::string> mExpectedTransfers; // files that are authorized to transfer out
std::multiset<std::string> mExpectedRequests; // files that are authorized to be downloaded on top of
std::multiset<std::string> mExpectedVFileTransfers; // files that are authorized to transfer out
std::multiset<std::string> mExpectedVFileRequests; // files that are authorized to be downloaded on top of
public:
LLXferManager(LLVFS *vfs);
@ -117,14 +121,17 @@ class LLXferManager
void setAckThrottleBPS(const F32 bps);
// list management routines
virtual LLXfer *findXfer(U64 id, LLXfer *list_head);
virtual void removeXfer (LLXfer *delp, LLXfer **list_head);
virtual U32 numActiveListEntries(LLXfer *list_head);
virtual LLXfer *findXferByID(U64 id, xfer_list_t & xfer_list);
virtual void removeXfer (LLXfer *delp, xfer_list_t & xfer_list);
LLHostStatus * findHostStatus(const LLHost &host);
virtual S32 numActiveXfers(const LLHost &host);
virtual S32 numPendingXfers(const LLHost &host);
virtual void changeNumActiveXfers(const LLHost &host, S32 delta);
virtual void setMaxOutgoingXfersPerCircuit (S32 max_num);
virtual void setHardLimitOutgoingXfersPerCircuit(S32 max_num);
virtual void setMaxIncomingXfers(S32 max_num);
virtual void updateHostStatus();
virtual void printHostStatus();
@ -136,8 +143,6 @@ class LLXferManager
virtual S32 decodePacketNum(S32 packet_num);
virtual BOOL isLastPacket(S32 packet_num);
virtual U64 registerXfer(const void *datap, const S32 length);
// file requesting routines
// .. to file
virtual U64 requestFile(const std::string& local_filename,
@ -148,7 +153,7 @@ class LLXferManager
void (*callback)(void**,S32,LLExtStat), void** user_data,
BOOL is_priority = FALSE,
BOOL use_big_packets = FALSE);
/*
// .. to memory
virtual void requestFile(const std::string& remote_filename,
ELLPath remote_path,
@ -157,7 +162,7 @@ class LLXferManager
void (*callback)(void*, S32, void**, S32, LLExtStat),
void** user_data,
BOOL is_priority = FALSE);
*/
// vfile requesting
// .. to vfile
virtual void requestVFile(const LLUUID &local_id, const LLUUID& remote_id,
@ -180,18 +185,15 @@ class LLXferManager
virtual void expectFileForRequest(const std::string& filename);
virtual bool validateFileForRequest(const std::string& filename);
/*
// xfer request (may be memory or file)
// .. to file
virtual void requestXfer(const char *local_filename, U64 xfer_id,
BOOL delete_remote_on_completion,
const LLHost &remote_host, void (*callback)(void **,S32),void **user_data);
// .. to memory
virtual void requestXfer(U64 xfer_id,
const LLHost &remote_host,
BOOL delete_remote_on_completion,
void (*callback)(void *, S32, void **, S32),void **user_data);
*/
/**
Same idea but for VFiles, kept separate to avoid namespace overlap
*/
/* Present in fireengine, not used by viewer
virtual void expectVFileForTransfer(const std::string& filename);
virtual bool validateVFileForTransfer(const std::string& filename);
virtual void expectVFileForRequest(const std::string& filename);
virtual bool validateVFileForRequest(const std::string& filename);
*/
virtual void processReceiveData (LLMessageSystem *mesgsys, void **user_data);
virtual void sendConfirmPacket (LLMessageSystem *mesgsys, U64 id, S32 packetnum, const LLHost &remote_host);
@ -204,6 +206,8 @@ class LLXferManager
// error handling
void abortRequestById(U64 xfer_id, S32 result_code);
virtual void processAbort (LLMessageSystem *mesgsys, void **user_data);
virtual bool isHostFlooded(const LLHost & host);
};
extern LLXferManager* gXferManager;

View File

@ -317,6 +317,8 @@ public:
// "init_history" message
void initializeUrlHistory(const LLSD& url_history);
boost::shared_ptr<LLPluginClassMedia> getSharedPrt() { return boost::dynamic_pointer_cast<LLPluginClassMedia>(shared_from_this()); } // due to enable_shared_from_this
protected:
LLPluginClassMediaOwner *mOwner;

View File

@ -845,6 +845,14 @@ void LLComboBox::setTextEntry(const LLStringExplicit& text)
}
}
void LLComboBox::setKeystrokeOnEsc(BOOL enable)
{
if (mTextEntry)
{
mTextEntry->setKeystrokeOnEsc(enable);
}
}
void LLComboBox::onTextEntry(LLLineEditor* line_editor)
{
if (mTextEntryCallback != NULL)

View File

@ -126,6 +126,7 @@ public:
virtual LLSD getValue() const;
void setTextEntry(const LLStringExplicit& text);
void setKeystrokeOnEsc(BOOL enable);
LLScrollListItem* add(const std::string& name, EAddPosition pos = ADD_BOTTOM, BOOL enabled = TRUE); // add item "name" to menu
LLScrollListItem* add(const std::string& name, const LLUUID& id, EAddPosition pos = ADD_BOTTOM, BOOL enabled = TRUE);

View File

@ -125,6 +125,7 @@ LLLineEditor::LLLineEditor(const LLLineEditor::Params& p)
mTextLeftEdge(0), // computed in updateTextPadding() below
mTextRightEdge(0), // computed in updateTextPadding() below
mCommitOnFocusLost( p.commit_on_focus_lost ),
mKeystrokeOnEsc(FALSE),
mRevertOnEsc( p.revert_on_esc ),
mKeystrokeCallback( p.keystroke_callback() ),
mIsSelecting( FALSE ),
@ -1494,6 +1495,10 @@ BOOL LLLineEditor::handleSpecialKey(KEY key, MASK mask)
{
setText(mPrevText);
// Note, don't set handled, still want to loose focus (won't commit becase text is now unchanged)
if (mKeystrokeOnEsc)
{
onKeystroke();
}
}
break;

View File

@ -214,6 +214,7 @@ public:
void setCommitOnFocusLost( BOOL b ) { mCommitOnFocusLost = b; }
void setRevertOnEsc( BOOL b ) { mRevertOnEsc = b; }
void setKeystrokeOnEsc(BOOL b) { mKeystrokeOnEsc = b; }
void setCursorColor(const LLColor4& c) { mCursorColor = c; }
const LLColor4& getCursorColor() const { return mCursorColor.get(); }
@ -338,6 +339,7 @@ protected:
BOOL mCommitOnFocusLost;
BOOL mRevertOnEsc;
BOOL mKeystrokeOnEsc;
keystroke_callback_t mKeystrokeCallback;

View File

@ -2493,11 +2493,11 @@ void LLTextEditor::updateLinkSegments()
}
}
}
// if the link's label (what the user can edit) is a valid Url,
// then update the link's HREF to be the same as the label text.
// This lets users edit Urls in-place.
if (LLUrlRegistry::instance().hasUrl(url_label))
if (acceptsTextInput() && LLUrlRegistry::instance().hasUrl(url_label))
{
std::string new_url = wstring_to_utf8str(url_label);
LLStringUtil::trim(new_url);

View File

@ -298,7 +298,7 @@ std::string LLUrlEntryHTTPLabel::getUrl(const std::string &string) const
LLUrlEntryInvalidSLURL::LLUrlEntryInvalidSLURL()
: LLUrlEntryBase()
{
mPattern = boost::regex("(http://(maps.secondlife.com|slurl.com)/secondlife/|secondlife://(/app/(worldmap|teleport)/)?)[^ /]+(/-?[0-9]+){1,3}(/?(\\?title|\\?img|\\?msg)=\\S*)?/?",
mPattern = boost::regex("(https?://(maps.secondlife.com|slurl.com)/secondlife/|secondlife://(/app/(worldmap|teleport)/)?)[^ /]+(/-?[0-9]+){1,3}(/?(\\?title|\\?img|\\?msg)=\\S*)?/?",
boost::regex::perl|boost::regex::icase);
mMenuName = "menu_url_http.xml";
mTooltip = LLTrans::getString("TooltipHttpUrl");
@ -385,8 +385,9 @@ bool LLUrlEntryInvalidSLURL::isSLURLvalid(const std::string &url) const
LLUrlEntrySLURL::LLUrlEntrySLURL()
{
// see http://slurl.com/about.php for details on the SLURL format
mPattern = boost::regex("http://(maps.secondlife.com|slurl.com)/secondlife/[^ /]+(/\\d+){0,3}(/?(\\?title|\\?img|\\?msg)=\\S*)?/?",
mPattern = boost::regex("https?://(maps.secondlife.com|slurl.com)/secondlife/[^ /]+(/\\d+){0,3}(/?(\\?title|\\?img|\\?msg)=\\S*)?/?",
boost::regex::perl|boost::regex::icase);
mIcon = "Hand";
mMenuName = "menu_url_slurl.xml";
mTooltip = LLTrans::getString("TooltipSLURL");
}

View File

@ -175,6 +175,7 @@ class LLUrlEntrySLURL : public LLUrlEntryBase
{
public:
LLUrlEntrySLURL();
/*virtual*/ bool isTrusted() const { return true; }
/*virtual*/ std::string getLabel(const std::string &url, const LLUrlLabelCallback &cb);
/*virtual*/ std::string getLocation(const std::string &url) const;
};

View File

@ -34,11 +34,11 @@ LLViewerEventRecorder::LLViewerEventRecorder() {
logEvents = false;
// Remove any previous event log file
std::string old_log_ui_events_to_llsd_file = gDirUtilp->getExpandedFilename(LL_PATH_LOGS, "SecondLife_Events_log.old");
LLFile::remove(old_log_ui_events_to_llsd_file);
LLFile::remove(old_log_ui_events_to_llsd_file, ENOENT);
mLogFilename = gDirUtilp->getExpandedFilename(LL_PATH_LOGS, "SecondLife_Events_log.llsd");
LLFile::rename(mLogFilename, old_log_ui_events_to_llsd_file);
LLFile::rename(mLogFilename, old_log_ui_events_to_llsd_file, ENOENT);
}

View File

@ -1515,6 +1515,7 @@ void LLWindowMacOSX::updateCursor()
case UI_CURSOR_NOLOCKED:
case UI_CURSOR_ARROWLOCKED:
case UI_CURSOR_GRABLOCKED:
case UI_CURSOR_PIPETTE:
case UI_CURSOR_TOOLTRANSLATE:
case UI_CURSOR_TOOLROTATE:
case UI_CURSOR_TOOLSCALE:
@ -1565,6 +1566,7 @@ void LLWindowMacOSX::initCursors()
initPixmapCursor(UI_CURSOR_NOLOCKED, 8, 8);
initPixmapCursor(UI_CURSOR_ARROWLOCKED, 1, 1);
initPixmapCursor(UI_CURSOR_GRABLOCKED, 2, 14);
initPixmapCursor(UI_CURSOR_PIPETTE, 3, 29);
initPixmapCursor(UI_CURSOR_TOOLTRANSLATE, 1, 1);
initPixmapCursor(UI_CURSOR_TOOLROTATE, 1, 1);
initPixmapCursor(UI_CURSOR_TOOLSCALE, 1, 1);

View File

@ -2708,6 +2708,14 @@ LRESULT CALLBACK LLWindowWin32::mainWindowProc(HWND h_wnd, UINT u_msg, WPARAM w_
}
}
break;
default:
{
if (gDebugWindowProc)
{
LL_INFOS("Window") << "Unhandled windows message code: " << U32(u_msg) << LL_ENDL;
}
}
break;
}
window_imp->mCallbacks->handlePauseWatchdog(window_imp);

View File

@ -810,8 +810,9 @@ void MediaPluginCEF::keyEvent(dullahan::EKeyEvent key_event, LLSD native_key_dat
bool event_isrepeat = native_key_data["event_isrepeat"].asBoolean();
// adding new code below in unicodeInput means we don't send ascii chars
// here too or we get double key presses on a mac.
if (((unsigned char)event_chars < 0x10 || (unsigned char)event_chars >= 0x7f ))
// here too or we get double key presses on a mac.
bool esc_key = (event_umodchars == 27);
if (esc_key || ((unsigned char)event_chars < 0x10 || (unsigned char)event_chars >= 0x7f ))
{
mCEFLib->nativeKeyboardEventOSX(key_event, event_modifiers,
event_keycode, event_chars,

View File

@ -200,7 +200,6 @@ set(viewer_SOURCE_FILES
llflickrconnect.cpp
llfloaterabout.cpp
llfloaterbvhpreview.cpp
llfloaterauction.cpp
llfloaterautoreplacesettings.cpp
llfloateravatar.cpp
llfloateravatarpicker.cpp
@ -820,7 +819,6 @@ set(viewer_HEADER_FILES
llflickrconnect.h
llfloaterabout.h
llfloaterbvhpreview.h
llfloaterauction.h
llfloaterautoreplacesettings.h
llfloateravatar.h
llfloateravatarpicker.h

View File

@ -1 +1 @@
5.1.6
5.1.7

View File

@ -4809,7 +4809,7 @@
<key>Type</key>
<string>Boolean</string>
<key>Value</key>
<integer>0</integer>
<integer>1</integer>
</map>
<key>InventoryOutboxDisplayBoth</key>
<map>
@ -12372,7 +12372,7 @@
<key>Type</key>
<string>F32</string>
<key>Value</key>
<real>500.0</real>
<real>3000.0</real>
</map>
<key>UpdaterMaximumBandwidth</key>
<map>

View File

@ -392,5 +392,27 @@
<key>Value</key>
<string></string>
</map>
<key>SnapshotBaseDir</key>
<map>
<key>Comment</key>
<string>Path to last snapshot save location</string>
<key>Persist</key>
<integer>1</integer>
<key>Type</key>
<string>String</string>
<key>Value</key>
<string></string>
</map>
<key>SnapshotBaseName</key>
<map>
<key>Comment</key>
<string>Pattern for naming snapshots</string>
<key>Persist</key>
<integer>1</integer>
<key>Type</key>
<string>String</string>
<key>Value</key>
<string>Snapshot</string>
</map>
</map>
</llsd>

Binary file not shown.

After

Width:  |  Height:  |  Size: 326 B

View File

@ -282,7 +282,6 @@ StrCpy $INSTSHORTCUT "${SHORTCUT}"
Call CheckIfAdministrator # Make sure the user can install/uninstall
Call CloseSecondLife # Make sure Second Life not currently running
Call CheckNetworkConnection # Ping secondlife.com
Call CheckWillUninstallV2 # Check if Second Life is already installed
StrCmp $DO_UNINSTALL_V2 "" PRESERVE_DONE
@ -347,16 +346,17 @@ WriteRegDWORD HKEY_LOCAL_MACHINE "Software\Microsoft\Windows NT\CurrentVersion\I
# Write URL registry info
WriteRegStr HKEY_CLASSES_ROOT "${URLNAME}" "(default)" "URL:Second Life"
WriteRegStr HKEY_CLASSES_ROOT "${URLNAME}" "URL Protocol" ""
WriteRegStr HKEY_CLASSES_ROOT "${URLNAME}\DefaultIcon" "" '"$INSTDIR\$INSTEXE"'
WriteRegStr HKEY_CLASSES_ROOT "${URLNAME}\DefaultIcon" "" '"$INSTDIR\$VIEWER_EXE"'
# URL param must be last item passed to viewer, it ignores subsequent params to avoid parameter injection attacks.
WriteRegExpandStr HKEY_CLASSES_ROOT "${URLNAME}\shell\open\command" "" '"$INSTDIR\$INSTEXE" -url "%1"'
WriteRegStr HKEY_CLASSES_ROOT "x-grid-location-info"(default)" "URL:Second Life"
# MAINT-8305: On SLURL click, directly invoke the viewer, not the launcher.
WriteRegExpandStr HKEY_CLASSES_ROOT "${URLNAME}\shell\open\command" "" '"$INSTDIR\$VIEWER_EXE" -url "%1"'
WriteRegStr HKEY_CLASSES_ROOT "x-grid-location-info" "(default)" "URL:Second Life"
WriteRegStr HKEY_CLASSES_ROOT "x-grid-location-info" "URL Protocol" ""
WriteRegStr HKEY_CLASSES_ROOT "x-grid-location-info\DefaultIcon" "" '"$INSTDIR\$INSTEXE"'
WriteRegStr HKEY_CLASSES_ROOT "x-grid-location-info\DefaultIcon" "" '"$INSTDIR\$VIEWER_EXE"'
# URL param must be last item passed to viewer, it ignores subsequent params to avoid parameter injection attacks.
WriteRegExpandStr HKEY_CLASSES_ROOT "x-grid-location-info\shell\open\command" "" '"$INSTDIR\$INSTEXE" -url "%1"'
WriteRegExpandStr HKEY_CLASSES_ROOT "x-grid-location-info\shell\open\command" "" '"$INSTDIR\$VIEWER_EXE" -url "%1"'
# Only allow Launcher to be the icon
WriteRegStr HKEY_CLASSES_ROOT "Applications\$INSTEXE" "IsHostApp" ""
@ -530,41 +530,6 @@ Function un.CloseSecondLife
FunctionEnd
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
;; Test our connection to secondlife.com
;; Also allows us to count attempted installs by examining web logs.
;; *TODO: Return current SL version info and have installer check
;; if it is up to date.
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
Function CheckNetworkConnection
Push $0
Push $1
Push $2 # Option value for GetOptions
DetailPrint $(CheckNetworkConnectionDP)
# Look for a tag value from the stub installer, used for statistics to correlate installs.
# Default to "" if not found on command line.
StrCpy $2 ""
${GetOptions} $COMMANDLINE "/STUBTAG=" $2
GetTempFileName $0
!define HTTP_TIMEOUT 5000 # Milliseconds
# Don't show secondary progress bar, this will be quick.
NSISdl::download_quiet \
/TIMEOUT=${HTTP_TIMEOUT} \
"http://install.secondlife.com/check/?stubtag=$2&version=${VERSION_LONG}" \
$0
Pop $1 # Return value, either "success", "cancel" or an error message
; MessageBox MB_OK "Download result: $1"
; Result ignored for now
; StrCmp $1 "success" +2
; DetailPrint "Connection failed: $1"
Delete $0 # Temporary file
Pop $2
Pop $1
Pop $0
Return
FunctionEnd
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
;; Delete files on install if previous install exists to prevent undesired behavior
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;

View File

@ -1593,6 +1593,8 @@ void LLAgent::setAutoPilotTargetGlobal(const LLVector3d &target_global)
LLViewerObject *obj;
LLWorld::getInstance()->resolveStepHeightGlobal(NULL, target_global, traceEndPt, targetOnGround, groundNorm, &obj);
// Note: this might malfunction for sitting agent, since pelvis stays same, but agent's position becomes lower
// But for autopilot to work we assume that agent is standing and ready to go.
F64 target_height = llmax((F64)gAgentAvatarp->getPelvisToFoot(), target_global.mdV[VZ] - targetOnGround.mdV[VZ]);
// clamp z value of target to minimum height above ground

File diff suppressed because it is too large Load Diff

View File

@ -286,6 +286,9 @@ void LLAvatarRenderInfoAccountant::sendRenderInfoToRegion(LLViewerRegion * regio
&& regionp->getRenderInfoReportTimer().hasExpired() // Time to make request)
)
{
// make sure we won't re-report, coro will update timer with correct time later
regionp->getRenderInfoReportTimer().resetWithExpiry(SECS_BETWEEN_REGION_REPORTS);
std::string coroname =
LLCoros::instance().launch("LLAvatarRenderInfoAccountant::avatarRenderInfoReportCoro",
boost::bind(&LLAvatarRenderInfoAccountant::avatarRenderInfoReportCoro, url, regionp->getHandle()));
@ -306,6 +309,9 @@ void LLAvatarRenderInfoAccountant::getRenderInfoFromRegion(LLViewerRegion * regi
<< " from " << url
<< LL_ENDL;
// make sure we won't re-request, coro will update timer with correct time later
regionp->getRenderInfoRequestTimer().resetWithExpiry(SECS_BETWEEN_REGION_REQUEST);
// First send a request to get the latest data
std::string coroname =
LLCoros::instance().launch("LLAvatarRenderInfoAccountant::avatarRenderInfoGetCoro",

View File

@ -53,6 +53,7 @@
#include "llstylemap.h"
#include "llslurl.h"
#include "lllayoutstack.h"
#include "llnotifications.h"
#include "llnotificationsutil.h"
#include "lltoastnotifypanel.h"
#include "lltooltip.h"
@ -1315,44 +1316,52 @@ void LLChatHistory::appendMessage(const LLChat& chat, const LLSD &args, const LL
// notify processing
if (chat.mNotifId.notNull())
{
bool create_toast = true;
for (LLToastNotifyPanel::instance_iter ti(LLToastNotifyPanel::beginInstances())
, tend(LLToastNotifyPanel::endInstances()); ti != tend; ++ti)
{
LLToastNotifyPanel& panel = *ti;
LLIMToastNotifyPanel * imtoastp = dynamic_cast<LLIMToastNotifyPanel *>(&panel);
const std::string& notification_name = panel.getNotificationName();
if (notification_name == "OfferFriendship" && panel.isControlPanelEnabled() && imtoastp)
{
create_toast = false;
break;
}
}
if (create_toast)
{
LLNotificationPtr notification = LLNotificationsUtil::find(chat.mNotifId);
if (notification != NULL)
{
LLIMToastNotifyPanel* notify_box = new LLIMToastNotifyPanel(
notification, chat.mSessionID, LLRect::null, !use_plain_text_chat_history, mEditor);
bool create_toast = true;
if (notification->getName() == "OfferFriendship")
{
// We don't want multiple friendship offers to appear, this code checks if there are previous offers
// by iterating though all panels.
// Note: it might be better to simply add a "pending offer" flag somewhere
for (LLToastNotifyPanel::instance_iter ti(LLToastNotifyPanel::beginInstances())
, tend(LLToastNotifyPanel::endInstances()); ti != tend; ++ti)
{
LLToastNotifyPanel& panel = *ti;
LLIMToastNotifyPanel * imtoastp = dynamic_cast<LLIMToastNotifyPanel *>(&panel);
const std::string& notification_name = panel.getNotificationName();
if (notification_name == "OfferFriendship"
&& panel.isControlPanelEnabled()
&& imtoastp)
{
create_toast = false;
break;
}
}
}
//Prepare the rect for the view
LLRect target_rect = mEditor->getDocumentView()->getRect();
// squeeze down the widget by subtracting padding off left and right
target_rect.mLeft += mLeftWidgetPad + mEditor->getHPad();
target_rect.mRight -= mRightWidgetPad;
notify_box->reshape(target_rect.getWidth(), notify_box->getRect().getHeight());
notify_box->setOrigin(target_rect.mLeft, notify_box->getRect().mBottom);
if (create_toast)
{
LLIMToastNotifyPanel* notify_box = new LLIMToastNotifyPanel(
notification, chat.mSessionID, LLRect::null, !use_plain_text_chat_history, mEditor);
LLInlineViewSegment::Params params;
params.view = notify_box;
params.left_pad = mLeftWidgetPad;
params.right_pad = mRightWidgetPad;
mEditor->appendWidget(params, "\n", false);
//Prepare the rect for the view
LLRect target_rect = mEditor->getDocumentView()->getRect();
// squeeze down the widget by subtracting padding off left and right
target_rect.mLeft += mLeftWidgetPad + mEditor->getHPad();
target_rect.mRight -= mRightWidgetPad;
notify_box->reshape(target_rect.getWidth(), notify_box->getRect().getHeight());
notify_box->setOrigin(target_rect.mLeft, notify_box->getRect().mBottom);
LLInlineViewSegment::Params params;
params.view = notify_box;
params.left_pad = mLeftWidgetPad;
params.right_pad = mRightWidgetPad;
mEditor->appendWidget(params, "\n", false);
}
}
}
}
// usual messages showing
else

View File

@ -325,6 +325,9 @@ void LLDrawPoolAlpha::render(S32 pass)
pushBatches(LLRenderPass::PASS_FULLBRIGHT_ALPHA_MASK, LLVertexBuffer::MAP_VERTEX | LLVertexBuffer::MAP_TEXCOORD0, FALSE);
pushBatches(LLRenderPass::PASS_ALPHA_INVISIBLE, LLVertexBuffer::MAP_VERTEX | LLVertexBuffer::MAP_TEXCOORD0, FALSE);
gGL.diffuseColor4f(0, 0, 1, 1);
pushBatches(LLRenderPass::PASS_MATERIAL_ALPHA_MASK, LLVertexBuffer::MAP_VERTEX | LLVertexBuffer::MAP_TEXCOORD0, FALSE);
if(shaders)
{
gHighlightProgram.unbind();

View File

@ -1223,6 +1223,12 @@ BOOL LLFace::getGeometryVolume(const LLVolume& volume,
{
LL_RECORD_BLOCK_TIME(FTM_FACE_GET_GEOM);
llassert(verify());
if (volume.getNumVolumeFaces() <= f) {
LL_WARNS() << "Attempt get volume face out of range! Total Faces: " << volume.getNumVolumeFaces() << " Attempt get access to: " << f << LL_ENDL;
return FALSE;
}
const LLVolumeFace &vf = volume.getVolumeFace(f);
S32 num_vertices = (S32)vf.mNumVertices;
S32 num_indices = (S32) vf.mNumIndices;

View File

@ -283,7 +283,7 @@ BOOL LLFilePicker::getOpenFile(ELoadFilter filter, bool blocking)
return success;
}
BOOL LLFilePicker::getMultipleOpenFiles(ELoadFilter filter)
BOOL LLFilePicker::getMultipleOpenFiles(ELoadFilter filter, bool blocking)
{
if( mLocked )
{
@ -310,9 +310,13 @@ BOOL LLFilePicker::getMultipleOpenFiles(ELoadFilter filter)
setupFilter(filter);
reset();
// Modal, so pause agent
send_agent_pause();
if (blocking)
{
// Modal, so pause agent
send_agent_pause();
}
// NOTA BENE: hitting the file dialog triggers a window focus event, destroying the selection manager!!
success = GetOpenFileName(&mOFN); // pauses until ok or cancel.
if( success )
@ -345,14 +349,18 @@ BOOL LLFilePicker::getMultipleOpenFiles(ELoadFilter filter)
}
}
}
send_agent_resume();
if (blocking)
{
send_agent_resume();
}
// Account for the fact that the app has been stalled.
LLFrameTimer::updateFrameTime();
return success;
}
BOOL LLFilePicker::getSaveFile(ESaveFilter filter, const std::string& filename)
BOOL LLFilePicker::getSaveFile(ESaveFilter filter, const std::string& filename, bool blocking)
{
if( mLocked )
{
@ -540,8 +548,12 @@ BOOL LLFilePicker::getSaveFile(ESaveFilter filter, const std::string& filename)
reset();
// Modal, so pause agent
send_agent_pause();
if (blocking)
{
// Modal, so pause agent
send_agent_pause();
}
{
// NOTA BENE: hitting the file dialog triggers a window focus event, destroying the selection manager!!
try
@ -559,7 +571,11 @@ BOOL LLFilePicker::getSaveFile(ESaveFilter filter, const std::string& filename)
}
gKeyboard->resetKeys();
}
send_agent_resume();
if (blocking)
{
send_agent_resume();
}
// Account for the fact that the app has been stalled.
LLFrameTimer::updateFrameTime();
@ -809,7 +825,7 @@ BOOL LLFilePicker::getOpenFile(ELoadFilter filter, bool blocking)
mPickOptions |= F_NAV_SUPPORT;
}
if (blocking)
if (blocking) // always true for linux/mac
{
// Modal, so pause agent
send_agent_pause();
@ -834,7 +850,7 @@ BOOL LLFilePicker::getOpenFile(ELoadFilter filter, bool blocking)
return success;
}
BOOL LLFilePicker::getMultipleOpenFiles(ELoadFilter filter)
BOOL LLFilePicker::getMultipleOpenFiles(ELoadFilter filter, bool blocking)
{
if( mLocked )
return FALSE;
@ -852,13 +868,20 @@ BOOL LLFilePicker::getMultipleOpenFiles(ELoadFilter filter)
mPickOptions |= F_FILE;
mPickOptions |= F_MULTIPLE;
// Modal, so pause agent
send_agent_pause();
if (blocking) // always true for linux/mac
{
// Modal, so pause agent
send_agent_pause();
}
success = doNavChooseDialog(filter);
send_agent_resume();
if (blocking)
{
send_agent_resume();
}
if (success)
{
if (!getFileCount())
@ -872,7 +895,7 @@ BOOL LLFilePicker::getMultipleOpenFiles(ELoadFilter filter)
return success;
}
BOOL LLFilePicker::getSaveFile(ESaveFilter filter, const std::string& filename)
BOOL LLFilePicker::getSaveFile(ESaveFilter filter, const std::string& filename, bool blocking)
{
if( mLocked )
@ -889,8 +912,11 @@ BOOL LLFilePicker::getSaveFile(ESaveFilter filter, const std::string& filename)
mPickOptions &= ~F_MULTIPLE;
// Modal, so pause agent
send_agent_pause();
if (blocking)
{
// Modal, so pause agent
send_agent_pause();
}
success = doNavSaveDialog(filter, filename);
@ -900,7 +926,10 @@ BOOL LLFilePicker::getSaveFile(ESaveFilter filter, const std::string& filename)
success = false;
}
send_agent_resume();
if (blocking)
{
send_agent_resume();
}
// Account for the fact that the app has been stalled.
LLFrameTimer::updateFrameTime();
@ -1354,7 +1383,7 @@ BOOL LLFilePicker::getOpenFile( ELoadFilter filter, bool blocking )
return rtn;
}
BOOL LLFilePicker::getMultipleOpenFiles( ELoadFilter filter )
BOOL LLFilePicker::getMultipleOpenFiles( ELoadFilter filter, bool blocking)
{
BOOL rtn = FALSE;
@ -1438,7 +1467,7 @@ BOOL LLFilePicker::getOpenFile( ELoadFilter filter, bool blocking )
return TRUE;
}
BOOL LLFilePicker::getMultipleOpenFiles( ELoadFilter filter )
BOOL LLFilePicker::getMultipleOpenFiles( ELoadFilter filter, bool blocking)
{
// if local file browsing is turned off, return without opening dialog
// (Even though this is a stub, I think we still should not return anything at all)
@ -1467,7 +1496,7 @@ BOOL LLFilePicker::getOpenFile( ELoadFilter filter )
return FALSE;
}
BOOL LLFilePicker::getMultipleOpenFiles( ELoadFilter filter )
BOOL LLFilePicker::getMultipleOpenFiles( ELoadFilter filter, bool blocking)
{
reset();
return FALSE;

View File

@ -113,9 +113,9 @@ public:
};
// open the dialog. This is a modal operation
BOOL getSaveFile( ESaveFilter filter = FFSAVE_ALL, const std::string& filename = LLStringUtil::null );
BOOL getSaveFile( ESaveFilter filter = FFSAVE_ALL, const std::string& filename = LLStringUtil::null, bool blocking = true);
BOOL getOpenFile( ELoadFilter filter = FFLOAD_ALL, bool blocking = true );
BOOL getMultipleOpenFiles( ELoadFilter filter = FFLOAD_ALL );
BOOL getMultipleOpenFiles( ELoadFilter filter = FFLOAD_ALL, bool blocking = true );
// Get the filename(s) found. getFirstFile() sets the pointer to
// the start of the structure and allows the start of iteration.
@ -198,6 +198,4 @@ public:
~LLFilePicker();
};
const std::string upload_pick(void* data);
#endif

View File

@ -1,552 +0,0 @@
/**
* @file llfloaterauction.cpp
* @author James Cook, Ian Wilkes
* @brief Implementation of the auction floater.
*
* $LicenseInfo:firstyear=2004&license=viewerlgpl$
* Second Life Viewer Source Code
* Copyright (C) 2010, Linden Research, Inc.
*
* This library is free software; you can redistribute it and/or
* modify it under the terms of the GNU Lesser General Public
* License as published by the Free Software Foundation;
* version 2.1 of the License only.
*
* This library is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
* Lesser General Public License for more details.
*
* You should have received a copy of the GNU Lesser General Public
* License along with this library; if not, write to the Free Software
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
*
* Linden Research, Inc., 945 Battery Street, San Francisco, CA 94111 USA
* $/LicenseInfo$
*/
#include "llviewerprecompiledheaders.h"
#include "llfloaterauction.h"
#include "llgl.h"
#include "llimagej2c.h"
#include "llimagetga.h"
#include "llparcel.h"
#include "llvfile.h"
#include "llvfs.h"
#include "llwindow.h"
#include "message.h"
#include "llagent.h"
#include "llassetstorage.h"
#include "llcombobox.h"
#include "llestateinfomodel.h"
#include "llmimetypes.h"
#include "llnotifications.h"
#include "llnotificationsutil.h"
#include "llsavedsettingsglue.h"
#include "llviewertexturelist.h"
#include "llviewerparcelmgr.h"
#include "llviewerregion.h"
#include "lluictrlfactory.h"
#include "llviewerwindow.h"
#include "llviewerdisplay.h"
#include "llviewercontrol.h"
#include "llui.h"
#include "llrender.h"
#include "llsdutil.h"
#include "llsdutil_math.h"
#include "lltrans.h"
#include "llcorehttputil.h"
///----------------------------------------------------------------------------
/// Local function declarations, constants, enums, and typedefs
///----------------------------------------------------------------------------
void auction_j2c_upload_done(const LLUUID& asset_id,
void* user_data, S32 status, LLExtStat ext_status);
void auction_tga_upload_done(const LLUUID& asset_id,
void* user_data, S32 status, LLExtStat ext_status);
///----------------------------------------------------------------------------
/// Class llfloaterauction
///----------------------------------------------------------------------------
// Default constructor
LLFloaterAuction::LLFloaterAuction(const LLSD& key)
: LLFloater(key),
mParcelID(-1)
{
mCommitCallbackRegistrar.add("ClickSnapshot", boost::bind(&LLFloaterAuction::onClickSnapshot, this));
mCommitCallbackRegistrar.add("ClickSellToAnyone", boost::bind(&LLFloaterAuction::onClickSellToAnyone, this));
mCommitCallbackRegistrar.add("ClickStartAuction", boost::bind(&LLFloaterAuction::onClickStartAuction, this));
mCommitCallbackRegistrar.add("ClickResetParcel", boost::bind(&LLFloaterAuction::onClickResetParcel, this));
}
// Destroys the object
LLFloaterAuction::~LLFloaterAuction()
{
}
BOOL LLFloaterAuction::postBuild()
{
return TRUE;
}
void LLFloaterAuction::onOpen(const LLSD& key)
{
initialize();
}
void LLFloaterAuction::initialize()
{
mParcelUpdateCapUrl.clear();
mParcelp = LLViewerParcelMgr::getInstance()->getParcelSelection();
LLViewerRegion* region = LLViewerParcelMgr::getInstance()->getSelectionRegion();
LLParcel* parcelp = mParcelp->getParcel();
if(parcelp && region && !parcelp->getForSale())
{
mParcelHost = region->getHost();
mParcelID = parcelp->getLocalID();
mParcelUpdateCapUrl = region->getCapability("ParcelPropertiesUpdate");
getChild<LLUICtrl>("parcel_text")->setValue(parcelp->getName());
getChildView("snapshot_btn")->setEnabled(TRUE);
getChildView("reset_parcel_btn")->setEnabled(TRUE);
getChildView("start_auction_btn")->setEnabled(TRUE);
U32 estate_id = LLEstateInfoModel::instance().getID();
// Only enable "Sell to Anyone" on Teen grid or if we don't know the ID yet
getChildView("sell_to_anyone_btn")->setEnabled(estate_id == ESTATE_TEEN || estate_id == 0);
}
else
{
mParcelHost.invalidate();
if(parcelp && parcelp->getForSale())
{
getChild<LLUICtrl>("parcel_text")->setValue(getString("already for sale"));
}
else
{
getChild<LLUICtrl>("parcel_text")->setValue(LLStringUtil::null);
}
mParcelID = -1;
getChildView("snapshot_btn")->setEnabled(false);
getChildView("reset_parcel_btn")->setEnabled(false);
getChildView("sell_to_anyone_btn")->setEnabled(false);
getChildView("start_auction_btn")->setEnabled(false);
}
mImageID.setNull();
mImage = NULL;
}
void LLFloaterAuction::draw()
{
LLFloater::draw();
if(!isMinimized() && mImage.notNull())
{
LLView* snapshot_icon = findChildView("snapshot_icon");
if (snapshot_icon)
{
LLRect rect = snapshot_icon->getRect();
{
gGL.getTexUnit(0)->unbind(LLTexUnit::TT_TEXTURE);
gl_rect_2d(rect, LLColor4(0.f, 0.f, 0.f, 1.f));
rect.stretch(-1);
}
{
LLGLSUIDefault gls_ui;
gGL.color3f(1.f, 1.f, 1.f);
gl_draw_scaled_image(rect.mLeft,
rect.mBottom,
rect.getWidth(),
rect.getHeight(),
mImage);
}
}
}
}
// static
void LLFloaterAuction::onClickSnapshot(void* data)
{
LLFloaterAuction* self = (LLFloaterAuction*)(data);
LLPointer<LLImageRaw> raw = new LLImageRaw;
gForceRenderLandFence = self->getChild<LLUICtrl>("fence_check")->getValue().asBoolean();
BOOL success = gViewerWindow->rawSnapshot(raw,
gViewerWindow->getWindowWidthScaled(),
gViewerWindow->getWindowHeightScaled(),
TRUE, FALSE,
FALSE, FALSE);
gForceRenderLandFence = FALSE;
if (success)
{
self->mTransactionID.generate();
self->mImageID = self->mTransactionID.makeAssetID(gAgent.getSecureSessionID());
if(!gSavedSettings.getBOOL("QuietSnapshotsToDisk"))
{
gViewerWindow->playSnapshotAnimAndSound();
}
LL_INFOS() << "Writing TGA..." << LL_ENDL;
LLPointer<LLImageTGA> tga = new LLImageTGA;
tga->encode(raw);
LLVFile::writeFile(tga->getData(), tga->getDataSize(), gVFS, self->mImageID, LLAssetType::AT_IMAGE_TGA);
raw->biasedScaleToPowerOfTwo(LLViewerTexture::MAX_IMAGE_SIZE_DEFAULT);
LL_INFOS() << "Writing J2C..." << LL_ENDL;
LLPointer<LLImageJ2C> j2c = new LLImageJ2C;
j2c->encode(raw, 0.0f);
LLVFile::writeFile(j2c->getData(), j2c->getDataSize(), gVFS, self->mImageID, LLAssetType::AT_TEXTURE);
self->mImage = LLViewerTextureManager::getLocalTexture((LLImageRaw*)raw, FALSE);
gGL.getTexUnit(0)->bind(self->mImage);
self->mImage->setAddressMode(LLTexUnit::TAM_CLAMP);
}
else
{
LL_WARNS() << "Unable to take snapshot" << LL_ENDL;
}
}
// static
void LLFloaterAuction::onClickStartAuction(void* data)
{
LLFloaterAuction* self = (LLFloaterAuction*)(data);
if(self->mImageID.notNull())
{
LLSD parcel_name = self->getChild<LLUICtrl>("parcel_text")->getValue();
// create the asset
std::string* name = new std::string(parcel_name.asString());
gAssetStorage->storeAssetData(self->mTransactionID, LLAssetType::AT_IMAGE_TGA,
&auction_tga_upload_done,
(void*)name,
FALSE);
self->getWindow()->incBusyCount();
std::string* j2c_name = new std::string(parcel_name.asString());
gAssetStorage->storeAssetData(self->mTransactionID, LLAssetType::AT_TEXTURE,
&auction_j2c_upload_done,
(void*)j2c_name,
FALSE);
self->getWindow()->incBusyCount();
LLNotificationsUtil::add("UploadingAuctionSnapshot");
}
LLMessageSystem* msg = gMessageSystem;
msg->newMessage("ViewerStartAuction");
msg->nextBlock("AgentData");
msg->addUUID("AgentID", gAgent.getID());
msg->addUUID("SessionID", gAgent.getSessionID());
msg->nextBlock("ParcelData");
msg->addS32("LocalID", self->mParcelID);
msg->addUUID("SnapshotID", self->mImageID);
msg->sendReliable(self->mParcelHost);
// clean up floater, and get out
self->cleanupAndClose();
}
void LLFloaterAuction::cleanupAndClose()
{
mImageID.setNull();
mImage = NULL;
mParcelID = -1;
mParcelHost.invalidate();
closeFloater();
}
// static glue
void LLFloaterAuction::onClickResetParcel(void* data)
{
LLFloaterAuction* self = (LLFloaterAuction*)(data);
if (self)
{
self->doResetParcel();
}
}
// Reset all the values for the parcel in preparation for a sale
void LLFloaterAuction::doResetParcel()
{
LLParcel* parcelp = mParcelp->getParcel();
LLViewerRegion* region = LLViewerParcelMgr::getInstance()->getSelectionRegion();
if (parcelp
&& region
&& !mParcelUpdateCapUrl.empty())
{
LLSD body;
std::string empty;
// request new properties update from simulator
U32 message_flags = 0x01;
body["flags"] = ll_sd_from_U32(message_flags);
// Set all the default parcel properties for auction
body["local_id"] = parcelp->getLocalID();
U32 parcel_flags = PF_ALLOW_LANDMARK |
PF_ALLOW_FLY |
PF_CREATE_GROUP_OBJECTS |
PF_ALLOW_ALL_OBJECT_ENTRY |
PF_ALLOW_GROUP_OBJECT_ENTRY |
PF_ALLOW_GROUP_SCRIPTS |
PF_RESTRICT_PUSHOBJECT |
PF_SOUND_LOCAL |
PF_ALLOW_VOICE_CHAT |
PF_USE_ESTATE_VOICE_CHAN;
body["parcel_flags"] = ll_sd_from_U32(parcel_flags);
// Build a parcel name like "Ahern (128,128) PG 4032m"
std::ostringstream parcel_name;
LLVector3 center_point( parcelp->getCenterpoint() );
center_point.snap(0); // Get rid of fractions
parcel_name << region->getName()
<< " ("
<< (S32) center_point.mV[VX]
<< ","
<< (S32) center_point.mV[VY]
<< ") "
<< region->getSimAccessString()
<< " "
<< parcelp->getArea()
<< "m";
std::string new_name(parcel_name.str().c_str());
body["name"] = new_name;
getChild<LLUICtrl>("parcel_text")->setValue(new_name); // Set name in dialog as well, since it won't get updated otherwise
body["sale_price"] = (S32) 0;
body["description"] = empty;
body["music_url"] = empty;
body["media_url"] = empty;
body["media_desc"] = empty;
body["media_type"] = LLMIMETypes::getDefaultMimeType();
body["media_width"] = (S32) 0;
body["media_height"] = (S32) 0;
body["auto_scale"] = (S32) 0;
body["media_loop"] = (S32) 0;
body["obscure_media"] = (S32) 0; // OBSOLETE - no longer used
body["obscure_music"] = (S32) 0; // OBSOLETE - no longer used
body["media_id"] = LLUUID::null;
body["group_id"] = MAINTENANCE_GROUP_ID; // Use maintenance group
body["pass_price"] = (S32) 10; // Defaults to $10
body["pass_hours"] = 0.0f;
body["category"] = (U8) LLParcel::C_NONE;
body["auth_buyer_id"] = LLUUID::null;
body["snapshot_id"] = LLUUID::null;
body["user_location"] = ll_sd_from_vector3( LLVector3::zero );
body["user_look_at"] = ll_sd_from_vector3( LLVector3::zero );
body["landing_type"] = (U8) LLParcel::L_DIRECT;
LL_INFOS() << "Sending parcel update to reset for auction via capability to: "
<< mParcelUpdateCapUrl << LL_ENDL;
LLCoreHttpUtil::HttpCoroutineAdapter::messageHttpPost(mParcelUpdateCapUrl, body,
"Parcel reset for auction",
"Parcel not set for auction.");
// Send a message to clear the object return time
LLMessageSystem *msg = gMessageSystem;
msg->newMessageFast(_PREHASH_ParcelSetOtherCleanTime);
msg->nextBlockFast(_PREHASH_AgentData);
msg->addUUIDFast(_PREHASH_AgentID, gAgent.getID());
msg->addUUIDFast(_PREHASH_SessionID, gAgent.getSessionID());
msg->nextBlockFast(_PREHASH_ParcelData);
msg->addS32Fast(_PREHASH_LocalID, parcelp->getLocalID());
msg->addS32Fast(_PREHASH_OtherCleanTime, 5); // 5 minute object auto-return
msg->sendReliable(region->getHost());
// Clear the access lists
clearParcelAccessList(parcelp, region, AL_ACCESS);
clearParcelAccessList(parcelp, region, AL_BAN);
clearParcelAccessList(parcelp, region, AL_ALLOW_EXPERIENCE);
clearParcelAccessList(parcelp, region, AL_BLOCK_EXPERIENCE);
}
}
void LLFloaterAuction::clearParcelAccessList(LLParcel* parcel, LLViewerRegion* region, U32 list)
{
if (!region || !parcel) return;
LLUUID transactionUUID;
transactionUUID.generate();
LLMessageSystem* msg = gMessageSystem;
msg->newMessageFast(_PREHASH_ParcelAccessListUpdate);
msg->nextBlockFast(_PREHASH_AgentData);
msg->addUUIDFast(_PREHASH_AgentID, gAgent.getID() );
msg->addUUIDFast(_PREHASH_SessionID, gAgent.getSessionID() );
msg->nextBlockFast(_PREHASH_Data);
msg->addU32Fast(_PREHASH_Flags, list);
msg->addS32(_PREHASH_LocalID, parcel->getLocalID() );
msg->addUUIDFast(_PREHASH_TransactionID, transactionUUID);
msg->addS32Fast(_PREHASH_SequenceID, 1); // sequence_id
msg->addS32Fast(_PREHASH_Sections, 0); // num_sections
// pack an empty block since there will be no data
msg->nextBlockFast(_PREHASH_List);
msg->addUUIDFast(_PREHASH_ID, LLUUID::null );
msg->addS32Fast(_PREHASH_Time, 0 );
msg->addU32Fast(_PREHASH_Flags, 0 );
msg->sendReliable( region->getHost() );
}
// static - 'Sell to Anyone' clicked, throw up a confirmation dialog
void LLFloaterAuction::onClickSellToAnyone(void* data)
{
LLFloaterAuction* self = (LLFloaterAuction*)(data);
if (self)
{
LLParcel* parcelp = self->mParcelp->getParcel();
// Do a confirmation
S32 sale_price = parcelp->getArea(); // Selling for L$1 per meter
S32 area = parcelp->getArea();
LLSD args;
args["LAND_SIZE"] = llformat("%d", area);
args["SALE_PRICE"] = llformat("%d", sale_price);
args["NAME"] = LLTrans::getString("Anyone");
LLNotification::Params params("ConfirmLandSaleChange"); // Re-use existing dialog
params.substitutions(args)
.functor.function(boost::bind(&LLFloaterAuction::onSellToAnyoneConfirmed, self, _1, _2));
params.name("ConfirmLandSaleToAnyoneChange");
// ask away
LLNotifications::instance().add(params);
}
}
// Sell confirmation clicked
bool LLFloaterAuction::onSellToAnyoneConfirmed(const LLSD& notification, const LLSD& response)
{
S32 option = LLNotificationsUtil::getSelectedOption(notification, response);
if (option == 0)
{
doSellToAnyone();
}
return false;
}
// Reset all the values for the parcel in preparation for a sale
void LLFloaterAuction::doSellToAnyone()
{
LLParcel* parcelp = mParcelp->getParcel();
LLViewerRegion* region = LLViewerParcelMgr::getInstance()->getSelectionRegion();
if (parcelp
&& region
&& !mParcelUpdateCapUrl.empty())
{
LLSD body;
std::string empty;
// request new properties update from simulator
U32 message_flags = 0x01;
body["flags"] = ll_sd_from_U32(message_flags);
// Set all the default parcel properties for auction
body["local_id"] = parcelp->getLocalID();
// Set 'for sale' flag
U32 parcel_flags = parcelp->getParcelFlags() | PF_FOR_SALE;
// Ensure objects not included
parcel_flags &= ~PF_FOR_SALE_OBJECTS;
body["parcel_flags"] = ll_sd_from_U32(parcel_flags);
body["sale_price"] = parcelp->getArea(); // Sell for L$1 per square meter
body["auth_buyer_id"] = LLUUID::null; // To anyone
LL_INFOS() << "Sending parcel update to sell to anyone for L$1 via capability to: "
<< mParcelUpdateCapUrl << LL_ENDL;
LLCoreHttpUtil::HttpCoroutineAdapter::messageHttpPost(mParcelUpdateCapUrl, body,
"Parcel set as sell to everyone.",
"Parcel sell to everyone failed.");
// clean up floater, and get out
cleanupAndClose();
}
}
///----------------------------------------------------------------------------
/// Local function definitions
///----------------------------------------------------------------------------
void auction_tga_upload_done(const LLUUID& asset_id, void* user_data, S32 status, LLExtStat ext_status) // StoreAssetData callback (fixed)
{
std::string* name = (std::string*)(user_data);
LL_INFOS() << "Upload of asset '" << *name << "' " << asset_id
<< " returned " << status << LL_ENDL;
delete name;
gViewerWindow->getWindow()->decBusyCount();
if (0 == status)
{
LLNotificationsUtil::add("UploadWebSnapshotDone");
}
else
{
LLSD args;
args["REASON"] = std::string(LLAssetStorage::getErrorString(status));
LLNotificationsUtil::add("UploadAuctionSnapshotFail", args);
}
}
void auction_j2c_upload_done(const LLUUID& asset_id, void* user_data, S32 status, LLExtStat ext_status) // StoreAssetData callback (fixed)
{
std::string* name = (std::string*)(user_data);
LL_INFOS() << "Upload of asset '" << *name << "' " << asset_id
<< " returned " << status << LL_ENDL;
delete name;
gViewerWindow->getWindow()->decBusyCount();
if (0 == status)
{
LLNotificationsUtil::add("UploadSnapshotDone");
}
else
{
LLSD args;
args["REASON"] = std::string(LLAssetStorage::getErrorString(status));
LLNotificationsUtil::add("UploadAuctionSnapshotFail", args);
}
}

View File

@ -1,86 +0,0 @@
/**
* @file llfloaterauction.h
* @author James Cook, Ian Wilkes
* @brief llfloaterauction class header file
*
* $LicenseInfo:firstyear=2004&license=viewerlgpl$
* Second Life Viewer Source Code
* Copyright (C) 2010, Linden Research, Inc.
*
* This library is free software; you can redistribute it and/or
* modify it under the terms of the GNU Lesser General Public
* License as published by the Free Software Foundation;
* version 2.1 of the License only.
*
* This library is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
* Lesser General Public License for more details.
*
* You should have received a copy of the GNU Lesser General Public
* License along with this library; if not, write to the Free Software
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
*
* Linden Research, Inc., 945 Battery Street, San Francisco, CA 94111 USA
* $/LicenseInfo$
*/
#ifndef LL_LLFLOATERAUCTION_H
#define LL_LLFLOATERAUCTION_H
#include "llfloater.h"
#include "lluuid.h"
#include "llpointer.h"
#include "llviewertexture.h"
//~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
// Class LLFloaterAuction
//
// Class which holds the functionality to start auctions.
//~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
class LLParcelSelection;
class LLParcel;
class LLViewerRegion;
class LLFloaterAuction : public LLFloater
{
friend class LLFloaterReg;
public:
// LLFloater interface
/*virtual*/ void onOpen(const LLSD& key);
/*virtual*/ void draw();
private:
LLFloaterAuction(const LLSD& key);
~LLFloaterAuction();
void initialize();
static void onClickSnapshot(void* data);
static void onClickResetParcel(void* data);
static void onClickSellToAnyone(void* data); // Sell to anyone clicked
bool onSellToAnyoneConfirmed(const LLSD& notification, const LLSD& response); // Sell confirmation clicked
static void onClickStartAuction(void* data);
/*virtual*/ BOOL postBuild();
void doResetParcel();
void doSellToAnyone();
void clearParcelAccessList( LLParcel* parcel, LLViewerRegion* region, U32 list);
void cleanupAndClose();
private:
LLTransactionID mTransactionID;
LLAssetID mImageID;
LLPointer<LLViewerTexture> mImage;
LLSafeHandle<LLParcelSelection> mParcelp;
S32 mParcelID;
LLHost mParcelHost;
std::string mParcelUpdateCapUrl; // "ParcelPropertiesUpdate" capability
};
#endif // LL_LLFLOATERAUCTION_H

View File

@ -54,6 +54,7 @@
#include "llhost.h"
#include "llassetstorage.h"
#include "roles_constants.h"
#include "llviewermenufile.h" // LLFilePickerReplyThread
#include "llviewertexteditor.h"
#include <boost/tokenizer.hpp>
@ -349,62 +350,58 @@ void LLFloaterAutoReplaceSettings::onDeleteEntry()
// called when the Import List button is pressed
void LLFloaterAutoReplaceSettings::onImportList()
{
LLFilePicker& picker = LLFilePicker::instance();
if( picker.getOpenFile( LLFilePicker::FFLOAD_XML) )
(new LLFilePickerReplyThread(boost::bind(&LLFloaterAutoReplaceSettings::loadListFromFile, this, _1), LLFilePicker::FFLOAD_XML, false))->getFile();
}
void LLFloaterAutoReplaceSettings::loadListFromFile(const std::vector<std::string>& filenames)
{
llifstream file;
file.open(filenames[0].c_str());
LLSD newList;
if (file.is_open())
{
llifstream file;
file.open(picker.getFirstFile().c_str());
LLSD newList;
if (file.is_open())
{
LLSDSerialize::fromXMLDocument(newList, file);
}
file.close();
switch ( mSettings.addList(newList) )
{
case LLAutoReplaceSettings::AddListOk:
mSelectedListName = LLAutoReplaceSettings::getListName(newList);
updateListNames();
updateListNamesControls();
updateReplacementsList();
break;
case LLAutoReplaceSettings::AddListDuplicateName:
{
std::string newName = LLAutoReplaceSettings::getListName(newList);
LL_WARNS("AutoReplace")<<"name '"<<newName<<"' is in use; prompting for new name"<<LL_ENDL;
LLSD newPayload;
newPayload["list"] = newList;
LLSD args;
args["DUPNAME"] = newName;
LLNotificationsUtil::add("RenameAutoReplaceList", args, newPayload,
boost::bind(&LLFloaterAutoReplaceSettings::callbackListNameConflict, this, _1, _2));
}
break;
case LLAutoReplaceSettings::AddListInvalidList:
LLNotificationsUtil::add("InvalidAutoReplaceList");
LL_WARNS("AutoReplace") << "imported list was invalid" << LL_ENDL;
mSelectedListName.clear();
updateListNames();
updateListNamesControls();
updateReplacementsList();
break;
default:
LL_ERRS("AutoReplace") << "invalid AddListResult" << LL_ENDL;
}
LLSDSerialize::fromXMLDocument(newList, file);
}
else
file.close();
switch ( mSettings.addList(newList) )
{
LL_DEBUGS("AutoReplace") << "file selection failed for import list" << LL_ENDL;
}
case LLAutoReplaceSettings::AddListOk:
mSelectedListName = LLAutoReplaceSettings::getListName(newList);
updateListNames();
updateListNamesControls();
updateReplacementsList();
break;
case LLAutoReplaceSettings::AddListDuplicateName:
{
std::string newName = LLAutoReplaceSettings::getListName(newList);
LL_WARNS("AutoReplace")<<"name '"<<newName<<"' is in use; prompting for new name"<<LL_ENDL;
LLSD newPayload;
newPayload["list"] = newList;
LLSD args;
args["DUPNAME"] = newName;
LLNotificationsUtil::add("RenameAutoReplaceList", args, newPayload,
boost::bind(&LLFloaterAutoReplaceSettings::callbackListNameConflict, this, _1, _2));
}
break;
case LLAutoReplaceSettings::AddListInvalidList:
LLNotificationsUtil::add("InvalidAutoReplaceList");
LL_WARNS("AutoReplace") << "imported list was invalid" << LL_ENDL;
mSelectedListName.clear();
updateListNames();
updateListNamesControls();
updateReplacementsList();
break;
default:
LL_ERRS("AutoReplace") << "invalid AddListResult" << LL_ENDL;
}
}
void LLFloaterAutoReplaceSettings::onNewList()
@ -539,16 +536,17 @@ void LLFloaterAutoReplaceSettings::onDeleteList()
void LLFloaterAutoReplaceSettings::onExportList()
{
std::string listName=mListNames->getFirstSelected()->getColumn(0)->getValue().asString();
const LLSD* list = mSettings.exportList(listName);
std::string listFileName = listName + ".xml";
LLFilePicker& picker = LLFilePicker::instance();
if( picker.getSaveFile( LLFilePicker::FFSAVE_XML, listFileName) )
{
llofstream file;
file.open(picker.getFirstFile().c_str());
LLSDSerialize::toPrettyXML(*list, file);
file.close();
}
(new LLFilePickerReplyThread(boost::bind(&LLFloaterAutoReplaceSettings::saveListToFile, this, _1, listName), LLFilePicker::FFSAVE_XML, listFileName))->getFile();
}
void LLFloaterAutoReplaceSettings::saveListToFile(const std::vector<std::string>& filenames, std::string listName)
{
llofstream file;
const LLSD* list = mSettings.exportList(listName);
file.open(filenames[0].c_str());
LLSDSerialize::toPrettyXML(*list, file);
file.close();
}
void LLFloaterAutoReplaceSettings::onAddEntry()

View File

@ -112,6 +112,9 @@ private:
bool selectedListIsLast();
void cleanUp();
void loadListFromFile(const std::vector<std::string>& filenames);
void saveListToFile(const std::vector<std::string>& filenames, std::string listName);
};
#endif // LLFLOATERAUTOREPLACESETTINGS_H

View File

@ -78,7 +78,7 @@ static void update_texture_ctrl(LLVOAvatar* avatarp,
{
LLUUID id = IMG_DEFAULT_AVATAR;
const LLAvatarAppearanceDictionary::TextureEntry* tex_entry = LLAvatarAppearanceDictionary::getInstance()->getTexture(te);
if (tex_entry->mIsLocalTexture)
if (tex_entry && tex_entry->mIsLocalTexture)
{
if (avatarp->isSelf())
{
@ -96,7 +96,7 @@ static void update_texture_ctrl(LLVOAvatar* avatarp,
}
else
{
id = avatarp->getTE(te)->getID();
id = tex_entry ? avatarp->getTE(te)->getID() : IMG_DEFAULT_AVATAR;
}
//id = avatarp->getTE(te)->getID();
if (id == IMG_DEFAULT_AVATAR)

View File

@ -82,8 +82,7 @@ LLFloaterIMSession::LLFloaterIMSession(const LLUUID& session_id)
mPositioned(false),
mSessionInitialized(false),
mMeTypingTimer(),
mOtherTypingTimer(),
mImInfo()
mOtherTypingTimer()
{
mIsNearbyChat = false;
@ -125,7 +124,7 @@ void LLFloaterIMSession::refresh()
if (mOtherTyping && mOtherTypingTimer.getElapsedTimeF32() > OTHER_TYPING_TIMEOUT)
{
LL_DEBUGS("TypingMsgs") << "Received: is typing cleared due to timeout" << LL_ENDL;
removeTypingIndicator(mImInfo);
removeTypingIndicator(mImFromId);
mOtherTyping = false;
}
@ -1006,19 +1005,19 @@ void LLFloaterIMSession::setTyping(bool typing)
}
}
void LLFloaterIMSession::processIMTyping(const LLIMInfo* im_info, BOOL typing)
void LLFloaterIMSession::processIMTyping(const LLUUID& from_id, BOOL typing)
{
LL_DEBUGS("TypingMsgs") << "typing=" << typing << LL_ENDL;
if ( typing )
{
// other user started typing
addTypingIndicator(im_info);
addTypingIndicator(from_id);
mOtherTypingTimer.reset();
}
else
{
// other user stopped typing
removeTypingIndicator(im_info);
removeTypingIndicator(from_id);
}
}
@ -1218,7 +1217,7 @@ BOOL LLFloaterIMSession::inviteToSession(const uuid_vec_t& ids)
return is_region_exist;
}
void LLFloaterIMSession::addTypingIndicator(const LLIMInfo* im_info)
void LLFloaterIMSession::addTypingIndicator(const LLUUID& from_id)
{
/* Operation of "<name> is typing" state machine:
Not Typing state:
@ -1248,35 +1247,35 @@ Note: OTHER_TYPING_TIMEOUT must be > ME_TYPING_TIMEOUT for proper operation of t
*/
// We may have lost a "stop-typing" packet, don't add it twice
if (im_info && !mOtherTyping)
if (from_id.notNull() && !mOtherTyping)
{
mOtherTyping = true;
mOtherTypingTimer.reset();
// Save im_info so that removeTypingIndicator can be properly called because a timeout has occurred
mImInfo = im_info;
mImFromId = from_id;
// Update speaker
LLIMSpeakerMgr* speaker_mgr = LLIMModel::getInstance()->getSpeakerManager(mSessionID);
if ( speaker_mgr )
{
speaker_mgr->setSpeakerTyping(im_info->mFromID, TRUE);
speaker_mgr->setSpeakerTyping(from_id, TRUE);
}
}
}
void LLFloaterIMSession::removeTypingIndicator(const LLIMInfo* im_info)
void LLFloaterIMSession::removeTypingIndicator(const LLUUID& from_id)
{
if (mOtherTyping)
{
mOtherTyping = false;
if (im_info)
if (from_id.notNull())
{
// Update speaker
LLIMSpeakerMgr* speaker_mgr = LLIMModel::getInstance()->getSpeakerManager(mSessionID);
if (speaker_mgr)
{
speaker_mgr->setSpeakerTyping(im_info->mFromID, FALSE);
speaker_mgr->setSpeakerTyping(from_id, FALSE);
}
}
}

View File

@ -122,7 +122,7 @@ public:
const LLVoiceChannel::EState& old_state,
const LLVoiceChannel::EState& new_state);
void processIMTyping(const LLIMInfo* im_info, BOOL typing);
void processIMTyping(const LLUUID& from_id, BOOL typing);
void processAgentListUpdates(const LLSD& body);
void processSessionUpdate(const LLSD& session_update);
@ -165,10 +165,10 @@ private:
void boundVoiceChannel();
// Add the "User is typing..." indicator.
void addTypingIndicator(const LLIMInfo* im_info);
void addTypingIndicator(const LLUUID& from_id);
// Remove the "User is typing..." indicator.
void removeTypingIndicator(const LLIMInfo* im_info = NULL);
void removeTypingIndicator(const LLUUID& from_id = LLUUID::null);
static void closeHiddenIMToasts();
@ -199,7 +199,7 @@ private:
// connection to voice channel state change signal
boost::signals2::connection mVoiceChannelStateChangeConnection;
const LLIMInfo* mImInfo;
LLUUID mImFromId;
};
#endif // LL_FLOATERIMSESSION_H

View File

@ -45,7 +45,6 @@
#include "llcombobox.h"
#include "llfloaterreg.h"
#include "llfloateravatarpicker.h"
#include "llfloaterauction.h"
#include "llfloatergroups.h"
#include "llfloaterscriptlimits.h"
#include "llavataractions.h"
@ -80,6 +79,7 @@
#include "llpanelexperiencepicker.h"
#include "llpanelenvironment.h"
#include "llexperiencecache.h"
#include "llweb.h"
#include "llgroupactions.h"
#include "llenvironment.h"
@ -574,7 +574,6 @@ void LLPanelLandGeneral::refresh()
mBtnDeedToGroup->setEnabled(FALSE);
mBtnSetGroup->setEnabled(FALSE);
mBtnStartAuction->setEnabled(FALSE);
mCheckDeedToGroup ->set(FALSE);
mCheckDeedToGroup ->setEnabled(FALSE);
@ -672,7 +671,6 @@ void LLPanelLandGeneral::refresh()
mTextClaimDate->setEnabled(FALSE);
mTextGroup->setText(getString("none_text"));
mTextGroup->setEnabled(FALSE);
mBtnStartAuction->setEnabled(FALSE);
}
else
{
@ -724,11 +722,6 @@ void LLPanelLandGeneral::refresh()
LLStringUtil::format (claim_date_str, substitution);
mTextClaimDate->setText(claim_date_str);
mTextClaimDate->setEnabled(is_leased);
BOOL enable_auction = (gAgent.getGodLevel() >= GOD_LIAISON)
&& (owner_id == GOVERNOR_LINDEN_ID)
&& (parcel->getAuctionID() == 0);
mBtnStartAuction->setEnabled(enable_auction);
}
// Display options
@ -1056,20 +1049,8 @@ void LLPanelLandGeneral::onClickBuyPass(void* data)
// static
void LLPanelLandGeneral::onClickStartAuction(void* data)
{
LLPanelLandGeneral* panelp = (LLPanelLandGeneral*)data;
LLParcel* parcelp = panelp->mParcel->getParcel();
if(parcelp)
{
if(parcelp->getForSale())
{
LLNotificationsUtil::add("CannotStartAuctionAlreadyForSale");
}
else
{
//LLFloaterAuction::showInstance();
LLFloaterReg::showInstance("auction");
}
}
std::string auction_url = "https://places.[GRID]/auctions/";
LLWeb::loadURLExternal(LLWeb::expandURLSubstitutions(auction_url, LLSD()));
}
// static

View File

@ -218,9 +218,17 @@ LLMeshFilePicker::LLMeshFilePicker(LLModelPreview* mp, S32 lod)
mLOD = lod;
}
void LLMeshFilePicker::notify(const std::string& filename)
void LLMeshFilePicker::notify(const std::vector<std::string>& filenames)
{
mMP->loadModel(mFile, mLOD);
if (filenames.size() > 0)
{
mMP->loadModel(filenames[0], mLOD);
}
else
{
//closes floater
mMP->loadModel(std::string(), mLOD);
}
}
void FindModel(LLModelLoader::scene& scene, const std::string& name_to_match, LLModel*& baseModelOut, LLMatrix4& matOut)

View File

@ -219,7 +219,7 @@ class LLMeshFilePicker : public LLFilePickerThread
{
public:
LLMeshFilePicker(LLModelPreview* mp, S32 lod);
virtual void notify(const std::string& filename);
virtual void notify(const std::vector<std::string>& filenames);
private:
LLModelPreview* mMP;

View File

@ -1249,6 +1249,8 @@ void LLFloaterPreference::refreshEnabledState()
// Cannot have floater active until caps have been received
getChild<LLButton>("default_creation_permissions")->setEnabled(LLStartUp::getStartupState() < STATE_STARTED ? false : true);
getChildView("block_list")->setEnabled(LLLoginInstance::getInstance()->authSuccess());
}
void LLFloaterPreferenceGraphicsAdvanced::refreshEnabledState()
@ -1383,8 +1385,6 @@ void LLFloaterPreferenceGraphicsAdvanced::refreshEnabledState()
// now turn off any features that are unavailable
disableUnavailableSettings();
getChildView("block_list")->setEnabled(LLLoginInstance::getInstance()->authSuccess());
}
// static
@ -2563,18 +2563,6 @@ BOOL LLPanelPreferenceGraphics::postBuild()
LLFloaterReg::showInstance("prefs_graphics_advanced");
LLFloaterReg::hideInstance("prefs_graphics_advanced");
// Don't do this on Mac as their braindead GL versioning
// sets this when 8x and 16x are indeed available
//
#if !LL_DARWIN
if (gGLManager.mIsIntel || gGLManager.mGLVersion < 3.f)
{ //remove FSAA settings above "4x"
LLComboBox* combo = getChild<LLComboBox>("fsaa");
combo->remove("8x");
combo->remove("16x");
}
#endif
resetDirtyChilds();
setPresetText();
@ -2749,6 +2737,23 @@ LLFloaterPreferenceProxy::LLFloaterPreferenceProxy(const LLSD& key)
mCommitCallbackRegistrar.add("Proxy.Change", boost::bind(&LLFloaterPreferenceProxy::onChangeSocksSettings, this));
}
BOOL LLFloaterPreferenceGraphicsAdvanced::postBuild()
{
// Don't do this on Mac as their braindead GL versioning
// sets this when 8x and 16x are indeed available
//
#if !LL_DARWIN
if (gGLManager.mIsIntel || gGLManager.mGLVersion < 3.f)
{ //remove FSAA settings above "4x"
LLComboBox* combo = getChild<LLComboBox>("fsaa");
combo->remove("8x");
combo->remove("16x");
}
#endif
return TRUE;
}
void LLFloaterPreferenceGraphicsAdvanced::onOpen(const LLSD& key)
{
refresh();

View File

@ -276,6 +276,7 @@ class LLFloaterPreferenceGraphicsAdvanced : public LLFloater
public:
LLFloaterPreferenceGraphicsAdvanced(const LLSD& key);
~LLFloaterPreferenceGraphicsAdvanced();
/*virtual*/ BOOL postBuild();
void onOpen(const LLSD& key);
void onClickCloseBtn(bool app_quitting);
void disableUnavailableSettings();

View File

@ -490,7 +490,6 @@ void LLFloaterProperties::refreshFromItem(LLInventoryItem* item)
if (is_obj_modify && can_agent_sell
&& gAgent.allowOperation(PERM_TRANSFER, perm, GP_OBJECT_MANIPULATE))
{
getChildView("SaleLabel")->setEnabled(is_complete);
getChildView("CheckPurchase")->setEnabled(is_complete);
getChildView("NextOwnerLabel")->setEnabled(TRUE);
@ -498,13 +497,11 @@ void LLFloaterProperties::refreshFromItem(LLInventoryItem* item)
getChildView("CheckNextOwnerCopy")->setEnabled((base_mask & PERM_COPY) && !cannot_restrict_permissions);
getChildView("CheckNextOwnerTransfer")->setEnabled((next_owner_mask & PERM_COPY) && !cannot_restrict_permissions);
getChildView("TextPrice")->setEnabled(is_complete && is_for_sale);
combo_sale_type->setEnabled(is_complete && is_for_sale);
edit_cost->setEnabled(is_complete && is_for_sale);
}
else
{
getChildView("SaleLabel")->setEnabled(FALSE);
getChildView("CheckPurchase")->setEnabled(FALSE);
getChildView("NextOwnerLabel")->setEnabled(FALSE);
@ -512,7 +509,6 @@ void LLFloaterProperties::refreshFromItem(LLInventoryItem* item)
getChildView("CheckNextOwnerCopy")->setEnabled(FALSE);
getChildView("CheckNextOwnerTransfer")->setEnabled(FALSE);
getChildView("TextPrice")->setEnabled(FALSE);
combo_sale_type->setEnabled(FALSE);
edit_cost->setEnabled(FALSE);
}

View File

@ -214,10 +214,30 @@ BOOL LLFloaterReporter::postBuild()
std::string reporter = LLSLURL("agent", gAgent.getID(), "inspect").getSLURLString();
getChild<LLUICtrl>("reporter_field")->setValue(reporter);
// request categories
if (gAgent.getRegion()
&& gAgent.getRegion()->capabilitiesReceived())
{
std::string cap_url = gAgent.getRegionCapability("AbuseCategories");
if (!cap_url.empty())
{
std::string lang = gSavedSettings.getString("Language");
if (lang != "default" && !lang.empty())
{
cap_url += "?lc=";
cap_url += lang;
}
LLCoros::instance().launch("LLFloaterReporter::requestAbuseCategoriesCoro",
boost::bind(LLFloaterReporter::requestAbuseCategoriesCoro, cap_url, this->getHandle()));
}
}
center();
return TRUE;
}
// virtual
LLFloaterReporter::~LLFloaterReporter()
{
@ -402,6 +422,65 @@ void LLFloaterReporter::onAvatarNameCache(const LLUUID& avatar_id, const LLAvata
}
}
void LLFloaterReporter::requestAbuseCategoriesCoro(std::string url, LLHandle<LLFloater> handle)
{
LLCore::HttpRequest::policy_t httpPolicy(LLCore::HttpRequest::DEFAULT_POLICY_ID);
LLCoreHttpUtil::HttpCoroutineAdapter::ptr_t
httpAdapter(new LLCoreHttpUtil::HttpCoroutineAdapter("requestAbuseCategoriesCoro", httpPolicy));
LLCore::HttpRequest::ptr_t httpRequest(new LLCore::HttpRequest);
LLSD result = httpAdapter->getAndSuspend(httpRequest, url);
LLSD httpResults = result[LLCoreHttpUtil::HttpCoroutineAdapter::HTTP_RESULTS];
LLCore::HttpStatus status = LLCoreHttpUtil::HttpCoroutineAdapter::getStatusFromLLSD(httpResults);
if (!status || !result.has("categories")) // success = httpResults["success"].asBoolean();
{
LL_WARNS() << "Error requesting Abuse Categories from capability: " << url << LL_ENDL;
return;
}
if (handle.isDead())
{
// nothing to do
return;
}
LLFloater* floater = handle.get();
LLComboBox* combo = floater->getChild<LLComboBox>("category_combo");
if (!combo)
{
LL_WARNS() << "categories category_combo not found!" << LL_ENDL;
return;
}
//get selection (in case capability took a while)
S32 selection = combo->getCurrentIndex();
// Combobox should have a "Select category" element;
// This is a bit of workaround since there is no proper and simple way to save array of
// localizable strings in xml along with data (value). For now combobox is initialized along
// with placeholders, and first element is "Select category" which we want to keep, so remove
// everything but first element.
// Todo: once sim with capability fully releases, just remove this string and all unnecessary
// items from combobox since they will be obsolete (or depending on situation remake this to
// something better, for example move "Select category" to separate string)
while (combo->remove(1));
LLSD contents = result["categories"];
LLSD::array_iterator i = contents.beginArray();
LLSD::array_iterator iEnd = contents.endArray();
for (; i != iEnd; ++i)
{
const LLSD &message_data(*i);
std::string label = message_data["description_localized"];
combo->add(label, message_data["category"]);
}
//restore selection
combo->selectNthItem(selection);
}
// static
void LLFloaterReporter::onClickSend(void *userdata)

View File

@ -129,6 +129,7 @@ private:
void setFromAvatarID(const LLUUID& avatar_id);
void onAvatarNameCache(const LLUUID& avatar_id, const LLAvatarName& av_name);
static void requestAbuseCategoriesCoro(std::string url, LLHandle<LLFloater> handle);
static void finishedARPost(const LLSD &);
private:

View File

@ -1100,6 +1100,7 @@ void LLFloaterSnapshot::onOpen(const LLSD& key)
if(preview)
{
LL_DEBUGS() << "opened, updating snapshot" << LL_ENDL;
preview->setAllowFullScreenPreview(TRUE);
preview->updateSnapshot(TRUE);
}
focusFirstItem(FALSE);
@ -1129,6 +1130,7 @@ void LLFloaterSnapshotBase::onClose(bool app_quitting)
LLSnapshotLivePreview* previewp = getPreviewView();
if (previewp)
{
previewp->setAllowFullScreenPreview(FALSE);
previewp->setVisible(FALSE);
previewp->setEnabled(FALSE);
}

View File

@ -30,12 +30,13 @@
#include "llfilepicker.h"
#include "llfloaterreg.h"
#include "llfloaterspellchecksettings.h"
#include "llnotificationsutil.h"
#include "llscrolllistctrl.h"
#include "llsdserialize.h"
#include "llspellcheck.h"
#include "lltrans.h"
#include "llviewercontrol.h"
#include "llnotificationsutil.h"
#include "llviewermenufile.h" // LLFilePickerReplyThread
#include <boost/algorithm/string.hpp>
@ -258,13 +259,12 @@ BOOL LLFloaterSpellCheckerImport::postBuild(void)
void LLFloaterSpellCheckerImport::onBtnBrowse()
{
LLFilePicker& file_picker = LLFilePicker::instance();
if (!file_picker.getOpenFile(LLFilePicker::FFLOAD_DICTIONARY))
{
return;
}
(new LLFilePickerReplyThread(boost::bind(&LLFloaterSpellCheckerImport::importSelectedDictionary, this, _1), LLFilePicker::FFLOAD_DICTIONARY, false))->getFile();
}
std::string filepath = file_picker.getFirstFile();
void LLFloaterSpellCheckerImport::importSelectedDictionary(const std::vector<std::string>& filenames)
{
std::string filepath = filenames[0];
const std::string extension = gDirUtilp->getExtension(filepath);
if ("xcu" == extension)
@ -277,7 +277,7 @@ void LLFloaterSpellCheckerImport::onBtnBrowse()
}
getChild<LLUICtrl>("dictionary_path")->setValue(filepath);
mDictionaryDir = gDirUtilp->getDirName(filepath);
mDictionaryBasename = gDirUtilp->getBaseFileName(filepath, true);
getChild<LLUICtrl>("dictionary_name")->setValue(mDictionaryBasename);

View File

@ -58,6 +58,7 @@ protected:
void onBtnBrowse();
void onBtnCancel();
void onBtnOK();
void importSelectedDictionary(const std::vector<std::string>& filenames);
std::string parseXcuFile(const std::string& file_path) const;
std::string mDictionaryDir;

View File

@ -253,7 +253,6 @@ BOOL LLFloaterTools::postBuild()
mCheckStretchTexture = getChild<LLCheckBoxCtrl>("checkbox stretch textures");
getChild<LLUICtrl>("checkbox stretch textures")->setValue((BOOL)gSavedSettings.getBOOL("ScaleStretchTextures"));
mComboGridMode = getChild<LLComboBox>("combobox grid mode");
mCheckStretchUniformLabel = getChild<LLTextBox>("checkbox uniform label");
//
// Create Buttons
@ -1214,7 +1213,7 @@ void LLFloaterTools::getMediaState()
&&first_object->permModify()
))
{
getChildView("Add_Media")->setEnabled(FALSE);
getChildView("add_media")->setEnabled(FALSE);
media_info->clear();
clearMediaSettings();
return;
@ -1225,7 +1224,7 @@ void LLFloaterTools::getMediaState()
if(!has_media_capability)
{
getChildView("Add_Media")->setEnabled(FALSE);
getChildView("add_media")->setEnabled(FALSE);
LL_WARNS("LLFloaterTools: media") << "Media not enabled (no capability) in this region!" << LL_ENDL;
clearMediaSettings();
return;
@ -1320,7 +1319,7 @@ void LLFloaterTools::getMediaState()
// update UI depending on whether "object" (prim or face) has media
// and whether or not you are allowed to edit it.
getChildView("Add_Media")->setEnabled(editable);
getChildView("add_media")->setEnabled(editable);
// IF all the faces have media (or all dont have media)
if ( LLFloaterMediaSettings::getInstance()->mIdenticalHasMediaInfo )
{
@ -1342,10 +1341,7 @@ void LLFloaterTools::getMediaState()
media_title = multi_media_info_str;
}
getChildView("media_tex")->setEnabled(bool_has_media && editable);
getChildView("edit_media")->setEnabled(bool_has_media && LLFloaterMediaSettings::getInstance()->mIdenticalHasMediaInfo && editable );
getChildView("delete_media")->setEnabled(bool_has_media && editable );
getChildView("add_media")->setEnabled(editable);
// TODO: display a list of all media on the face - use 'identical' flag
}
else // not all face has media but at least one does.
@ -1367,10 +1363,7 @@ void LLFloaterTools::getMediaState()
}
}
getChildView("media_tex")->setEnabled(TRUE);
getChildView("edit_media")->setEnabled(LLFloaterMediaSettings::getInstance()->mIdenticalHasMediaInfo);
getChildView("delete_media")->setEnabled(TRUE);
getChildView("add_media")->setEnabled(editable);
}
navigateToTitleMedia(media_title);

View File

@ -105,6 +105,7 @@ BOOL LLFloaterWebContent::postBuild()
// these buttons are always enabled
mBtnReload->setEnabled( true );
mBtnReload->setVisible( false );
getChildView("popexternal")->setEnabled( true );
// cache image for secure browsing

View File

@ -593,45 +593,13 @@ void LLIMProcessing::processNewMessage(LLUUID from_id,
case IM_TYPING_START:
{
std::vector<U8> bucket(binary_bucket[0], binary_bucket_size);
LLSD data;
data["binary_bucket"] = bucket;
LLPointer<LLIMInfo> im_info = new LLIMInfo(from_id,
from_group,
to_id,
dialog,
agentName,
message,
session_id,
parent_estate_id,
region_id,
position,
data,
offline,
timestamp);
gIMMgr->processIMTypingStart(im_info);
gIMMgr->processIMTypingStart(from_id, dialog);
}
break;
case IM_TYPING_STOP:
{
std::vector<U8> bucket(binary_bucket[0], binary_bucket_size);
LLSD data;
data["binary_bucket"] = bucket;
LLPointer<LLIMInfo> im_info = new LLIMInfo(from_id,
from_group,
to_id,
dialog,
agentName,
message,
session_id,
parent_estate_id,
region_id,
position,
data,
offline,
timestamp);
gIMMgr->processIMTypingStop(im_info);
gIMMgr->processIMTypingStop(from_id, dialog);
}
break;

View File

@ -3432,23 +3432,23 @@ void LLIMMgr::noteMutedUsers(const LLUUID& session_id,
}
}
void LLIMMgr::processIMTypingStart(const LLIMInfo* im_info)
void LLIMMgr::processIMTypingStart(const LLUUID& from_id, const EInstantMessage im_type)
{
processIMTypingCore(im_info, TRUE);
processIMTypingCore(from_id, im_type, TRUE);
}
void LLIMMgr::processIMTypingStop(const LLIMInfo* im_info)
void LLIMMgr::processIMTypingStop(const LLUUID& from_id, const EInstantMessage im_type)
{
processIMTypingCore(im_info, FALSE);
processIMTypingCore(from_id, im_type, FALSE);
}
void LLIMMgr::processIMTypingCore(const LLIMInfo* im_info, BOOL typing)
void LLIMMgr::processIMTypingCore(const LLUUID& from_id, const EInstantMessage im_type, BOOL typing)
{
LLUUID session_id = computeSessionID(im_info->mIMType, im_info->mFromID);
LLUUID session_id = computeSessionID(im_type, from_id);
LLFloaterIMSession* im_floater = LLFloaterIMSession::findInstance(session_id);
if ( im_floater )
{
im_floater->processIMTyping(im_info, typing);
im_floater->processIMTyping(from_id, typing);
}
}

View File

@ -391,8 +391,8 @@ public:
const std::string& session_handle = LLStringUtil::null,
const std::string& session_uri = LLStringUtil::null);
void processIMTypingStart(const LLIMInfo* im_info);
void processIMTypingStop(const LLIMInfo* im_info);
void processIMTypingStart(const LLUUID& from_id, const EInstantMessage im_type);
void processIMTypingStop(const LLUUID& from_id, const EInstantMessage im_type);
// automatically start a call once the session has initialized
void autoStartCallOnStartup(const LLUUID& session_id);
@ -471,7 +471,7 @@ private:
void noteOfflineUsers(const LLUUID& session_id, const std::vector<LLUUID>& ids);
void noteMutedUsers(const LLUUID& session_id, const std::vector<LLUUID>& ids);
void processIMTypingCore(const LLIMInfo* im_info, BOOL typing);
void processIMTypingCore(const LLUUID& from_id, const EInstantMessage im_type, BOOL typing);
static void onInviteNameLookup(LLSD payload, const LLUUID& id, const LLAvatarName& name);

View File

@ -215,7 +215,9 @@ void LLInspectAvatar::onOpen(const LLSD& data)
}
// Generate link to avatar profile.
getChild<LLUICtrl>("avatar_profile_link")->setTextArg("[LINK]", LLSLURL("agent", mAvatarID, "about").getSLURLString());
LLTextBase* avatar_profile_link = getChild<LLTextBase>("avatar_profile_link");
avatar_profile_link->setTextArg("[LINK]", LLSLURL("agent", mAvatarID, "about").getSLURLString());
avatar_profile_link->setIsFriendCallback(LLAvatarActions::isFriend);
// can't call from constructor as widgets are not built yet
requestUpdate();

View File

@ -783,6 +783,14 @@ void LLInvFVBridge::getClipboardEntries(bool show_asset_id,
if (obj)
{
items.push_back(std::string("Copy Separator"));
items.push_back(std::string("Copy"));
if (!isItemCopyable())
{
disabled_items.push_back(std::string("Copy"));
}
if (obj->getIsLinkType())
{
items.push_back(std::string("Find Original"));
@ -825,13 +833,6 @@ void LLInvFVBridge::getClipboardEntries(bool show_asset_id,
disabled_items.push_back(std::string("Copy Asset UUID"));
}
}
items.push_back(std::string("Copy Separator"));
items.push_back(std::string("Copy"));
if (!isItemCopyable())
{
disabled_items.push_back(std::string("Copy"));
}
items.push_back(std::string("Cut"));
if (!isItemMovable() || !isItemRemovable())
@ -2116,12 +2117,6 @@ BOOL LLItemBridge::isItemCopyable() const
return FALSE;
}
// You can never copy a link.
if (item->getIsLinkType())
{
return FALSE;
}
return item->getPermissions().allowCopyBy(gAgent.getID()) || gSavedSettings.getBOOL("InventoryLinking");
}
return FALSE;
@ -3824,6 +3819,11 @@ void LLFolderBridge::perform_pasteFromClipboard()
break;
}
}
else if (item->getIsLinkType())
{
link_inventory_object(parent_id, item_id,
LLPointer<LLInventoryCallback>(NULL));
}
else
{
copy_inventory_item(

View File

@ -398,57 +398,66 @@ void copy_inventory_category(LLInventoryModel* model,
LLViewerInventoryCategory* cat,
const LLUUID& parent_id,
const LLUUID& root_copy_id,
bool move_no_copy_items )
bool move_no_copy_items )
{
// Create the initial folder
LLUUID new_cat_uuid = gInventory.createNewCategory(parent_id, LLFolderType::FT_NONE, cat->getName());
inventory_func_type func = boost::bind(&copy_inventory_category_content, _1, model, cat, root_copy_id, move_no_copy_items);
gInventory.createNewCategory(parent_id, LLFolderType::FT_NONE, cat->getName(), func);
}
void copy_inventory_category_content(const LLUUID& new_cat_uuid, LLInventoryModel* model, LLViewerInventoryCategory* cat, const LLUUID& root_copy_id, bool move_no_copy_items)
{
model->notifyObservers();
// We need to exclude the initial root of the copy to avoid recursively copying the copy, etc...
LLUUID root_id = (root_copy_id.isNull() ? new_cat_uuid : root_copy_id);
// Get the content of the folder
LLInventoryModel::cat_array_t* cat_array;
LLInventoryModel::item_array_t* item_array;
gInventory.getDirectDescendentsOf(cat->getUUID(),cat_array,item_array);
// If root_copy_id is null, tell the marketplace model we'll be waiting for new items to be copied over for this folder
if (root_copy_id.isNull())
{
LLMarketplaceData::instance().setValidationWaiting(root_id,count_descendants_items(cat->getUUID()));
}
gInventory.getDirectDescendentsOf(cat->getUUID(), cat_array, item_array);
// If root_copy_id is null, tell the marketplace model we'll be waiting for new items to be copied over for this folder
if (root_copy_id.isNull())
{
LLMarketplaceData::instance().setValidationWaiting(root_id, count_descendants_items(cat->getUUID()));
}
// Copy all the items
LLInventoryModel::item_array_t item_array_copy = *item_array;
for (LLInventoryModel::item_array_t::iterator iter = item_array_copy.begin(); iter != item_array_copy.end(); iter++)
{
LLInventoryItem* item = *iter;
LLPointer<LLInventoryCallback> cb = new LLBoostFuncInventoryCallback(boost::bind(update_folder_cb, new_cat_uuid));
LLPointer<LLInventoryCallback> cb = new LLBoostFuncInventoryCallback(boost::bind(update_folder_cb, new_cat_uuid));
if (!item->getPermissions().allowOperationBy(PERM_COPY, gAgent.getID(), gAgent.getGroupID()))
{
// If the item is nocopy, we do nothing or, optionally, move it
if (move_no_copy_items)
{
// Reparent the item
LLViewerInventoryItem * viewer_inv_item = (LLViewerInventoryItem *) item;
gInventory.changeItemParent(viewer_inv_item, new_cat_uuid, true);
}
// Decrement the count in root_id since that one item won't be copied over
LLMarketplaceData::instance().decrementValidationWaiting(root_id);
}
else
{
copy_inventory_item(
gAgent.getID(),
item->getPermissions().getOwner(),
item->getUUID(),
new_cat_uuid,
std::string(),
cb);
}
if (item->getIsLinkType())
{
link_inventory_object(new_cat_uuid, item->getLinkedUUID(), cb);
}
else if (!item->getPermissions().allowOperationBy(PERM_COPY, gAgent.getID(), gAgent.getGroupID()))
{
// If the item is nocopy, we do nothing or, optionally, move it
if (move_no_copy_items)
{
// Reparent the item
LLViewerInventoryItem * viewer_inv_item = (LLViewerInventoryItem *)item;
gInventory.changeItemParent(viewer_inv_item, new_cat_uuid, true);
}
// Decrement the count in root_id since that one item won't be copied over
LLMarketplaceData::instance().decrementValidationWaiting(root_id);
}
else
{
copy_inventory_item(
gAgent.getID(),
item->getPermissions().getOwner(),
item->getUUID(),
new_cat_uuid,
std::string(),
cb);
}
}
// Copy all the folders
LLInventoryModel::cat_array_t cat_array_copy = *cat_array;
for (LLInventoryModel::cat_array_t::iterator iter = cat_array_copy.begin(); iter != cat_array_copy.end(); iter++)

View File

@ -72,6 +72,8 @@ void rename_category(LLInventoryModel* model, const LLUUID& cat_id, const std::s
void copy_inventory_category(LLInventoryModel* model, LLViewerInventoryCategory* cat, const LLUUID& parent_id, const LLUUID& root_copy_id = LLUUID::null, bool move_no_copy_items = false);
void copy_inventory_category_content(const LLUUID& new_cat_uuid, LLInventoryModel* model, LLViewerInventoryCategory* cat, const LLUUID& root_copy_id, bool move_no_copy_items);
// Generates a string containing the path to the item specified by item_id.
void append_path(const LLUUID& id, std::string& path);

View File

@ -925,7 +925,20 @@ U32 LLInventoryModel::updateItem(const LLViewerInventoryItem* item, U32 mask)
new_item = old_item;
LLUUID old_parent_id = old_item->getParentUUID();
LLUUID new_parent_id = item->getParentUUID();
bool update_parent_on_server = false;
if (new_parent_id.isNull())
{
// item with null parent will end in random location and then in Lost&Found,
// either move to default folder as if it is new item or don't move at all
LL_WARNS(LOG_INV) << "Update attempts to reparent item " << item->getUUID()
<< " to null folder. Moving to Lost&Found. Old item name: " << old_item->getName()
<< ". New name: " << item->getName()
<< "." << LL_ENDL;
new_parent_id = findCategoryUUIDForType(LLFolderType::FT_LOST_AND_FOUND);
update_parent_on_server = true;
}
if(old_parent_id != new_parent_id)
{
// need to update the parent-child tree
@ -938,6 +951,11 @@ U32 LLInventoryModel::updateItem(const LLViewerInventoryItem* item, U32 mask)
item_array = get_ptr_in_map(mParentChildItemTree, new_parent_id);
if(item_array)
{
if (update_parent_on_server)
{
LLInventoryModel::LLCategoryUpdate update(new_parent_id, 1);
gInventory.accountForUpdate(update);
}
item_array->push_back(old_item);
}
mask |= LLInventoryObserver::STRUCTURE;
@ -947,6 +965,12 @@ U32 LLInventoryModel::updateItem(const LLViewerInventoryItem* item, U32 mask)
mask |= LLInventoryObserver::LABEL;
}
old_item->copyViewerItem(item);
if (update_parent_on_server)
{
// Parent id at server is null, so update server even if item already is in the same folder
old_item->setParent(new_parent_id);
new_item->updateParentOnServer(FALSE);
}
mask |= LLInventoryObserver::INTERNAL;
}
else
@ -2820,7 +2844,6 @@ bool LLInventoryModel::messageUpdateCore(LLMessageSystem* msg, bool account, U32
item_array_t items;
update_map_t update;
S32 count = msg->getNumberOfBlocksFast(_PREHASH_InventoryData);
LLUUID folder_id;
// Does this loop ever execute more than once?
for(S32 i = 0; i < count; ++i)
{
@ -2847,10 +2870,6 @@ bool LLInventoryModel::messageUpdateCore(LLMessageSystem* msg, bool account, U32
{
++update[titem->getParentUUID()];
}
if (folder_id.isNull())
{
folder_id = titem->getParentUUID();
}
}
if(account)
{

View File

@ -1453,14 +1453,16 @@ LLInventoryPanel* LLInventoryPanel::getActiveInventoryPanel(BOOL auto_open)
//static
void LLInventoryPanel::openInventoryPanelAndSetSelection(BOOL auto_open, const LLUUID& obj_id, BOOL main_panel, BOOL take_keyboard_focus, BOOL reset_filter)
{
LLInventoryPanel *active_panel;
LLSidepanelInventory* sidepanel_inventory = LLFloaterSidePanelContainer::getPanel<LLSidepanelInventory>("inventory");
sidepanel_inventory->showInventoryPanel();
bool in_inbox = (gInventory.isObjectDescendentOf(obj_id, gInventory.findCategoryUUIDForType(LLFolderType::FT_INBOX)));
if (main_panel && !in_inbox)
{
LLFloaterSidePanelContainer::getPanel<LLSidepanelInventory>("inventory")->selectAllItemsPanel();
sidepanel_inventory->selectAllItemsPanel();
}
active_panel = LLInventoryPanel::getActiveInventoryPanel(auto_open);
LLInventoryPanel *active_panel = LLInventoryPanel::getActiveInventoryPanel(auto_open);
if (active_panel)
{
@ -1473,7 +1475,7 @@ void LLInventoryPanel::openInventoryPanelAndSetSelection(BOOL auto_open, const L
if (in_inbox)
{
LLSidepanelInventory * sidepanel_inventory = LLFloaterSidePanelContainer::getPanel<LLSidepanelInventory>("inventory");
LLInventoryPanel * inventory_panel = NULL;
sidepanel_inventory->openInbox();
inventory_panel = sidepanel_inventory->getInboxPanel();

View File

@ -27,6 +27,7 @@
#include "llviewerprecompiledheaders.h"
#include "llmediadataclient.h"
#include "llviewercontrol.h"
#if LL_MSVC
// disable boost::lexical_cast warning
@ -718,6 +719,13 @@ bool LLObjectMediaDataClient::compareRequestScores(const Request::ptr_t &o1, con
void LLObjectMediaDataClient::enqueue(Request::ptr_t request)
{
static LLCachedControl<bool> audio_streaming_enabled(gSavedSettings, "AudioStreamingMedia", true);
if (!audio_streaming_enabled)
{
LL_DEBUGS("LLMediaDataClient") << "not queueing request when Media is disabled " << *request << LL_ENDL;
return;
}
if(request->isDead())
{
LL_DEBUGS("LLMediaDataClient") << "not queueing dead request " << *request << LL_ENDL;
@ -978,6 +986,13 @@ const char *LLObjectMediaNavigateClient::getCapabilityName() const
void LLObjectMediaNavigateClient::enqueue(Request::ptr_t request)
{
static LLCachedControl<bool> audio_streaming_enabled(gSavedSettings, "AudioStreamingMedia", true);
if (!audio_streaming_enabled)
{
LL_DEBUGS("LLMediaDataClient") << "not queueing request when Media is disabled " << *request << LL_ENDL;
return;
}
if(request->isDead())
{
LL_DEBUGS("LLMediaDataClient") << "not queuing dead request " << *request << LL_ENDL;

View File

@ -353,6 +353,9 @@ const U32 LARGE_MESH_FETCH_THRESHOLD = 1U << 21; // Size at which requests goes
const long SMALL_MESH_XFER_TIMEOUT = 120L; // Seconds to complete xfer, small mesh downloads
const long LARGE_MESH_XFER_TIMEOUT = 600L; // Seconds to complete xfer, large downloads
const U32 DOWNLOAD_RETRY_LIMIT = 8;
const F32 DOWNLOAD_RETRY_DELAY = 0.5f; // seconds
// Would normally like to retry on uploads as some
// retryable failures would be recoverable. Unfortunately,
// the mesh service is using 500 (retryable) rather than
@ -516,6 +519,24 @@ void get_vertex_buffer_from_mesh(LLCDMeshData& mesh, LLModel::PhysicsMesh& res,
}
}
void RequestStats::updateTime()
{
U32 modifier = 1 << mRetries; // before ++
mRetries++;
mTimer.reset();
mTimer.setTimerExpirySec(DOWNLOAD_RETRY_DELAY * (F32)modifier); // up to 32s, 64 total wait
}
bool RequestStats::canRetry() const
{
return mRetries < DOWNLOAD_RETRY_LIMIT;
}
bool RequestStats::isDelayed() const
{
return mTimer.getStarted() && !mTimer.hasExpired();
}
LLViewerFetchedTexture* LLMeshUploadThread::FindViewerTexture(const LLImportMaterial& material)
{
LLPointer< LLViewerFetchedTexture > * ppTex = static_cast< LLPointer< LLViewerFetchedTexture > * >(material.mOpaqueData);
@ -890,141 +911,225 @@ void LLMeshRepoThread::run()
sRequestWaterLevel = mHttpRequestSet.size(); // Stats data update
// NOTE: order of queue processing intentionally favors LOD requests over header requests
// Todo: we are processing mLODReqQ, mHeaderReqQ, mSkinRequests, mDecompositionRequests and mPhysicsShapeRequests
// in relatively similar manners, remake code to simplify/unify the process,
// like processRequests(&requestQ, fetchFunction); which does same thing for each element
while (!mLODReqQ.empty() && mHttpRequestSet.size() < sRequestHighWater)
{
if (! mMutex)
{
break;
}
mMutex->lock();
LODRequest req = mLODReqQ.front();
mLODReqQ.pop();
LLMeshRepository::sLODProcessing--;
mMutex->unlock();
if (!mLODReqQ.empty() && mHttpRequestSet.size() < sRequestHighWater)
{
std::list<LODRequest> incomplete;
while (!mLODReqQ.empty() && mHttpRequestSet.size() < sRequestHighWater)
{
if (!mMutex)
{
break;
}
if (!fetchMeshLOD(req.mMeshParams, req.mLOD)) // failed, resubmit
{
mMutex->lock();
mLODReqQ.push(req);
++LLMeshRepository::sLODProcessing;
mMutex->unlock();
}
}
mMutex->lock();
LODRequest req = mLODReqQ.front();
mLODReqQ.pop();
LLMeshRepository::sLODProcessing--;
mMutex->unlock();
if (req.isDelayed())
{
// failed to load before, wait a bit
incomplete.push_front(req);
}
else if (!fetchMeshLOD(req.mMeshParams, req.mLOD, req.canRetry()))
{
if (req.canRetry())
{
// failed, resubmit
req.updateTime();
incomplete.push_front(req);
}
else
{
// too many fails
mUnavailableQ.push(req);
LL_WARNS() << "Failed to load " << req.mMeshParams << " , skip" << LL_ENDL;
}
}
}
while (!mHeaderReqQ.empty() && mHttpRequestSet.size() < sRequestHighWater)
{
if (! mMutex)
{
break;
}
mMutex->lock();
HeaderRequest req = mHeaderReqQ.front();
mHeaderReqQ.pop();
mMutex->unlock();
if (!fetchMeshHeader(req.mMeshParams))//failed, resubmit
{
mMutex->lock();
mHeaderReqQ.push(req) ;
mMutex->unlock();
}
}
if (!incomplete.empty())
{
LLMutexLock locker(mMutex);
for (std::list<LODRequest>::iterator iter = incomplete.begin(); iter != incomplete.end(); iter++)
{
mLODReqQ.push(*iter);
++LLMeshRepository::sLODProcessing;
}
}
}
// For the final three request lists, similar goal to above but
// slightly different queue structures. Stay off the mutex when
// performing long-duration actions.
if (!mHeaderReqQ.empty() && mHttpRequestSet.size() < sRequestHighWater)
{
std::list<HeaderRequest> incomplete;
while (!mHeaderReqQ.empty() && mHttpRequestSet.size() < sRequestHighWater)
{
if (!mMutex)
{
break;
}
if (mHttpRequestSet.size() < sRequestHighWater
&& (! mSkinRequests.empty()
|| ! mDecompositionRequests.empty()
|| ! mPhysicsShapeRequests.empty()))
{
// Something to do probably, lock and double-check. We don't want
// to hold the lock long here. That will stall main thread activities
// so we bounce it.
mMutex->lock();
HeaderRequest req = mHeaderReqQ.front();
mHeaderReqQ.pop();
mMutex->unlock();
if (req.isDelayed())
{
// failed to load before, wait a bit
incomplete.push_front(req);
}
else if (!fetchMeshHeader(req.mMeshParams, req.canRetry()))
{
if (req.canRetry())
{
//failed, resubmit
req.updateTime();
incomplete.push_front(req);
}
else
{
LL_DEBUGS() << "mHeaderReqQ failed: " << req.mMeshParams << LL_ENDL;
}
}
}
mMutex->lock();
if (! mSkinRequests.empty() && mHttpRequestSet.size() < sRequestHighWater)
{
std::set<LLUUID> incomplete;
std::set<LLUUID>::iterator iter(mSkinRequests.begin());
while (iter != mSkinRequests.end() && mHttpRequestSet.size() < sRequestHighWater)
{
LLUUID mesh_id = *iter;
mSkinRequests.erase(iter);
mMutex->unlock();
if (!incomplete.empty())
{
LLMutexLock locker(mMutex);
for (std::list<HeaderRequest>::iterator iter = incomplete.begin(); iter != incomplete.end(); iter++)
{
mHeaderReqQ.push(*iter);
}
}
}
if (! fetchMeshSkinInfo(mesh_id))
{
incomplete.insert(mesh_id);
}
// For the final three request lists, similar goal to above but
// slightly different queue structures. Stay off the mutex when
// performing long-duration actions.
mMutex->lock();
iter = mSkinRequests.begin();
}
if (mHttpRequestSet.size() < sRequestHighWater
&& (!mSkinRequests.empty()
|| !mDecompositionRequests.empty()
|| !mPhysicsShapeRequests.empty()))
{
// Something to do probably, lock and double-check. We don't want
// to hold the lock long here. That will stall main thread activities
// so we bounce it.
if (! incomplete.empty())
{
mSkinRequests.insert(incomplete.begin(), incomplete.end());
}
}
if (!mSkinRequests.empty())
{
std::set<UUIDBasedRequest> incomplete;
while (!mSkinRequests.empty() && mHttpRequestSet.size() < sRequestHighWater)
{
mMutex->lock();
std::set<UUIDBasedRequest>::iterator iter = mSkinRequests.begin();
UUIDBasedRequest req = *iter;
mSkinRequests.erase(iter);
mMutex->unlock();
if (req.isDelayed())
{
incomplete.insert(req);
}
else if (!fetchMeshSkinInfo(req.mId))
{
if (req.canRetry())
{
req.updateTime();
incomplete.insert(req);
}
else
{
LL_DEBUGS() << "mSkinRequests failed: " << req.mId << LL_ENDL;
}
}
}
// holding lock, try next list
// *TODO: For UI/debug-oriented lists, we might drop the fine-
// grained locking as there's a lowered expectation of smoothness
// in these cases.
if (! mDecompositionRequests.empty() && mHttpRequestSet.size() < sRequestHighWater)
{
std::set<LLUUID> incomplete;
std::set<LLUUID>::iterator iter(mDecompositionRequests.begin());
while (iter != mDecompositionRequests.end() && mHttpRequestSet.size() < sRequestHighWater)
{
LLUUID mesh_id = *iter;
mDecompositionRequests.erase(iter);
mMutex->unlock();
if (! fetchMeshDecomposition(mesh_id))
{
incomplete.insert(mesh_id);
}
if (!incomplete.empty())
{
LLMutexLock locker(mMutex);
mSkinRequests.insert(incomplete.begin(), incomplete.end());
}
}
mMutex->lock();
iter = mDecompositionRequests.begin();
}
// holding lock, try next list
// *TODO: For UI/debug-oriented lists, we might drop the fine-
// grained locking as there's a lowered expectation of smoothness
// in these cases.
if (!mDecompositionRequests.empty())
{
std::set<UUIDBasedRequest> incomplete;
while (!mDecompositionRequests.empty() && mHttpRequestSet.size() < sRequestHighWater)
{
mMutex->lock();
std::set<UUIDBasedRequest>::iterator iter = mDecompositionRequests.begin();
UUIDBasedRequest req = *iter;
mDecompositionRequests.erase(iter);
mMutex->unlock();
if (req.isDelayed())
{
incomplete.insert(req);
}
else if (!fetchMeshDecomposition(req.mId))
{
if (req.canRetry())
{
req.updateTime();
incomplete.insert(req);
}
else
{
LL_DEBUGS() << "mDecompositionRequests failed: " << req.mId << LL_ENDL;
}
}
}
if (! incomplete.empty())
{
mDecompositionRequests.insert(incomplete.begin(), incomplete.end());
}
}
if (!incomplete.empty())
{
LLMutexLock locker(mMutex);
mDecompositionRequests.insert(incomplete.begin(), incomplete.end());
}
}
// holding lock, final list
if (! mPhysicsShapeRequests.empty() && mHttpRequestSet.size() < sRequestHighWater)
{
std::set<LLUUID> incomplete;
std::set<LLUUID>::iterator iter(mPhysicsShapeRequests.begin());
while (iter != mPhysicsShapeRequests.end() && mHttpRequestSet.size() < sRequestHighWater)
{
LLUUID mesh_id = *iter;
mPhysicsShapeRequests.erase(iter);
mMutex->unlock();
if (! fetchMeshPhysicsShape(mesh_id))
{
incomplete.insert(mesh_id);
}
// holding lock, final list
if (!mPhysicsShapeRequests.empty())
{
std::set<UUIDBasedRequest> incomplete;
while (!mPhysicsShapeRequests.empty() && mHttpRequestSet.size() < sRequestHighWater)
{
mMutex->lock();
std::set<UUIDBasedRequest>::iterator iter = mPhysicsShapeRequests.begin();
UUIDBasedRequest req = *iter;
mPhysicsShapeRequests.erase(iter);
mMutex->unlock();
if (req.isDelayed())
{
incomplete.insert(req);
}
else if (!fetchMeshPhysicsShape(req.mId))
{
if (req.canRetry())
{
req.updateTime();
incomplete.insert(req);
}
else
{
LL_DEBUGS() << "mPhysicsShapeRequests failed: " << req.mId << LL_ENDL;
}
}
}
mMutex->lock();
iter = mPhysicsShapeRequests.begin();
}
if (! incomplete.empty())
{
mPhysicsShapeRequests.insert(incomplete.begin(), incomplete.end());
}
}
mMutex->unlock();
}
if (!incomplete.empty())
{
LLMutexLock locker(mMutex);
mPhysicsShapeRequests.insert(incomplete.begin(), incomplete.end());
}
}
}
// For dev purposes only. A dynamic change could make this false
// and that shouldn't assert.
@ -1046,19 +1151,19 @@ void LLMeshRepoThread::run()
// Mutex: LLMeshRepoThread::mMutex must be held on entry
void LLMeshRepoThread::loadMeshSkinInfo(const LLUUID& mesh_id)
{
mSkinRequests.insert(mesh_id);
mSkinRequests.insert(UUIDBasedRequest(mesh_id));
}
// Mutex: LLMeshRepoThread::mMutex must be held on entry
void LLMeshRepoThread::loadMeshDecomposition(const LLUUID& mesh_id)
{
mDecompositionRequests.insert(mesh_id);
mDecompositionRequests.insert(UUIDBasedRequest(mesh_id));
}
// Mutex: LLMeshRepoThread::mMutex must be held on entry
void LLMeshRepoThread::loadMeshPhysicsShape(const LLUUID& mesh_id)
{
mPhysicsShapeRequests.insert(mesh_id);
mPhysicsShapeRequests.insert(UUIDBasedRequest(mesh_id));
}
void LLMeshRepoThread::lockAndLoadMeshLOD(const LLVolumeParams& mesh_params, S32 lod)
@ -1234,16 +1339,16 @@ bool LLMeshRepoThread::fetchMeshSkinInfo(const LLUUID& mesh_id)
//check VFS for mesh skin info
LLVFile file(gVFS, mesh_id, LLAssetType::AT_MESH);
if (file.getSize() >= offset+size)
{
LLMeshRepository::sCacheBytesRead += size;
++LLMeshRepository::sCacheReads;
file.seek(offset);
{
U8* buffer = new(std::nothrow) U8[size];
if (!buffer)
{
LL_WARNS(LOG_MESH) << "Failed to allocate memory for skin info" << LL_ENDL;
LL_WARNS_ONCE(LOG_MESH) << "Failed to allocate memory for skin info, size: " << size << LL_ENDL;
return false;
}
LLMeshRepository::sCacheBytesRead += size;
++LLMeshRepository::sCacheReads;
file.seek(offset);
file.read(buffer, size);
//make sure buffer isn't all 0's by checking the first 1KB (reserved block but not written)
@ -1331,16 +1436,16 @@ bool LLMeshRepoThread::fetchMeshDecomposition(const LLUUID& mesh_id)
LLVFile file(gVFS, mesh_id, LLAssetType::AT_MESH);
if (file.getSize() >= offset+size)
{
U8* buffer = new(std::nothrow) U8[size];
if (!buffer)
{
LL_WARNS_ONCE(LOG_MESH) << "Failed to allocate memory for mesh decomposition, size: " << size << LL_ENDL;
return false;
}
LLMeshRepository::sCacheBytesRead += size;
++LLMeshRepository::sCacheReads;
file.seek(offset);
U8* buffer = new(std::nothrow) U8[size];
if (!buffer)
{
LL_WARNS(LOG_MESH) << "Failed to allocate memory for mesh decomposition" << LL_ENDL;
return false;
}
file.read(buffer, size);
//make sure buffer isn't all 0's by checking the first 1KB (reserved block but not written)
@ -1434,7 +1539,7 @@ bool LLMeshRepoThread::fetchMeshPhysicsShape(const LLUUID& mesh_id)
U8* buffer = new(std::nothrow) U8[size];
if (!buffer)
{
LL_WARNS(LOG_MESH) << "Failed to allocate memory for physics shape" << LL_ENDL;
LL_WARNS_ONCE(LOG_MESH) << "Failed to allocate memory for physics shape, size: " << size << LL_ENDL;
return false;
}
file.read(buffer, size);
@ -1524,7 +1629,7 @@ void LLMeshRepoThread::decActiveHeaderRequests()
}
//return false if failed to get header
bool LLMeshRepoThread::fetchMeshHeader(const LLVolumeParams& mesh_params)
bool LLMeshRepoThread::fetchMeshHeader(const LLVolumeParams& mesh_params, bool can_retry)
{
++LLMeshRepository::sMeshRequestCount;
@ -1571,7 +1676,7 @@ bool LLMeshRepoThread::fetchMeshHeader(const LLVolumeParams& mesh_params)
<< LL_ENDL;
retval = false;
}
else
else if (can_retry)
{
handler->mHttpHandle = handle;
mHttpRequestSet.insert(handler);
@ -1582,7 +1687,7 @@ bool LLMeshRepoThread::fetchMeshHeader(const LLVolumeParams& mesh_params)
}
//return false if failed to get mesh lod.
bool LLMeshRepoThread::fetchMeshLOD(const LLVolumeParams& mesh_params, S32 lod)
bool LLMeshRepoThread::fetchMeshLOD(const LLVolumeParams& mesh_params, S32 lod, bool can_retry)
{
if (!mHeaderMutex)
{
@ -1612,15 +1717,17 @@ bool LLMeshRepoThread::fetchMeshLOD(const LLVolumeParams& mesh_params, S32 lod)
LLVFile file(gVFS, mesh_id, LLAssetType::AT_MESH);
if (file.getSize() >= offset+size)
{
LLMeshRepository::sCacheBytesRead += size;
++LLMeshRepository::sCacheReads;
file.seek(offset);
U8* buffer = new(std::nothrow) U8[size];
if (!buffer)
{
LL_WARNS(LOG_MESH) << "Can't allocate memory for mesh LOD" << LL_ENDL;
LL_WARNS_ONCE(LOG_MESH) << "Can't allocate memory for mesh " << mesh_id << " LOD " << lod << ", size: " << size << LL_ENDL;
// todo: for now it will result in indefinite constant retries, should result in timeout
// or in retry-count and disabling mesh. (but usually viewer is beyond saving at this point)
return false;
}
LLMeshRepository::sCacheBytesRead += size;
++LLMeshRepository::sCacheReads;
file.seek(offset);
file.read(buffer, size);
//make sure buffer isn't all 0's by checking the first 1KB (reserved block but not written)
@ -1658,12 +1765,16 @@ bool LLMeshRepoThread::fetchMeshLOD(const LLVolumeParams& mesh_params, S32 lod)
<< LL_ENDL;
retval = false;
}
else
else if (can_retry)
{
handler->mHttpHandle = handle;
mHttpRequestSet.insert(handler);
// *NOTE: Allowing a re-request, not marking as unavailable. Is that correct?
}
else
{
mUnavailableQ.push(LODRequest(mesh_params, lod));
}
}
else
{

View File

@ -177,6 +177,21 @@ public:
};
class RequestStats
{
public:
RequestStats() : mRetries(0) {};
void updateTime();
bool canRetry() const;
bool isDelayed() const;
U32 getRetries() { return mRetries; }
private:
U32 mRetries;
LLFrameTimer mTimer;
};
class LLMeshRepoThread : public LLThread
{
public:
@ -197,14 +212,14 @@ public:
mesh_header_map mMeshHeader;
std::map<LLUUID, U32> mMeshHeaderSize;
class HeaderRequest
class HeaderRequest : public RequestStats
{
public:
const LLVolumeParams mMeshParams;
HeaderRequest(const LLVolumeParams& mesh_params)
: mMeshParams(mesh_params)
: RequestStats(), mMeshParams(mesh_params)
{
}
@ -214,7 +229,7 @@ public:
}
};
class LODRequest
class LODRequest : public RequestStats
{
public:
LLVolumeParams mMeshParams;
@ -222,7 +237,7 @@ public:
F32 mScore;
LODRequest(const LLVolumeParams& mesh_params, S32 lod)
: mMeshParams(mesh_params), mLOD(lod), mScore(0.f)
: RequestStats(), mMeshParams(mesh_params), mLOD(lod), mScore(0.f)
{
}
};
@ -234,7 +249,22 @@ public:
return lhs.mScore > rhs.mScore; // greatest = first
}
};
class UUIDBasedRequest : public RequestStats
{
public:
LLUUID mId;
UUIDBasedRequest(const LLUUID& id)
: RequestStats(), mId(id)
{
}
bool operator<(const UUIDBasedRequest& rhs) const
{
return mId < rhs.mId;
}
};
class LoadedMesh
{
@ -251,16 +281,16 @@ public:
};
//set of requested skin info
std::set<LLUUID> mSkinRequests;
std::set<UUIDBasedRequest> mSkinRequests;
// list of completed skin info requests
std::list<LLMeshSkinInfo> mSkinInfoQ;
//set of requested decompositions
std::set<LLUUID> mDecompositionRequests;
std::set<UUIDBasedRequest> mDecompositionRequests;
//set of requested physics shapes
std::set<LLUUID> mPhysicsShapeRequests;
std::set<UUIDBasedRequest> mPhysicsShapeRequests;
// list of completed Decomposition info requests
std::list<LLModel::Decomposition*> mDecompositionQ;
@ -304,8 +334,8 @@ public:
void lockAndLoadMeshLOD(const LLVolumeParams& mesh_params, S32 lod);
void loadMeshLOD(const LLVolumeParams& mesh_params, S32 lod);
bool fetchMeshHeader(const LLVolumeParams& mesh_params);
bool fetchMeshLOD(const LLVolumeParams& mesh_params, S32 lod);
bool fetchMeshHeader(const LLVolumeParams& mesh_params, bool can_retry = true);
bool fetchMeshLOD(const LLVolumeParams& mesh_params, S32 lod, bool can_retry = true);
bool headerReceived(const LLVolumeParams& mesh_params, U8* data, S32 data_size);
EMeshProcessingResult lodReceived(const LLVolumeParams& mesh_params, S32 lod, U8* data, S32 data_size);
bool skinInfoReceived(const LLUUID& mesh_id, U8* data, S32 data_size);

View File

@ -716,9 +716,9 @@ void LLPanelStandStopFlying::updatePosition()
left_tb_width = toolbar_left->getRect().getWidth();
}
if (!mStateManagementButtons.get())
if (!mStateManagementButtons.get()) // Obsolete?!!
{
LLPanel* panel_ssf_container = getRootView()->getChild<LLPanel>("state_management_buttons_container");
LLPanel* panel_ssf_container = gToolBarView->getChild<LLPanel>("state_management_buttons_container");
if (panel_ssf_container)
{
mStateManagementButtons = panel_ssf_container->getHandle();

View File

@ -443,6 +443,7 @@ void LLNavigationBar::onLocationSelection()
{
gAgent.teleportViaLandmark( LLUUID(value["AssetUUID"].asString()));
mSaveToLocationHistory = true;
return;
}
else
@ -453,6 +454,7 @@ void LLNavigationBar::onLocationSelection()
if (!landmark_items.empty())
{
gAgent.teleportViaLandmark( landmark_items[0]->getAssetUUID());
mSaveToLocationHistory = true;
return;
}
}

View File

@ -288,9 +288,7 @@ BOOL LLGroupInviteNotificationListItem::postBuild()
//invitation with any non-default group role, doesn't have newline characters at the end unlike simple invitations
std::string invitation_desc = mNoticeTextExp->getValue().asString();
boost::regex pattern = boost::regex("\n\n$", boost::regex::perl|boost::regex::icase);
boost::match_results<std::string::const_iterator> matches;
if(!boost::regex_search(invitation_desc, matches, pattern))
if (invitation_desc.substr(invitation_desc.size() - 2) != "\n\n")
{
invitation_desc += "\n\n";
mNoticeTextExp->setValue(invitation_desc);

View File

@ -1165,16 +1165,6 @@ void LLPanelFace::updateUI(bool force_set_values /*false*/)
getChild<LLUICtrl>("combobox texgen")->setTentative(!identical);
getChildView("tex gen")->setEnabled(editable);
if (selected_texgen == LLTextureEntry::TEX_GEN_PLANAR)
{
// EXP-1507 (change label based on the mapping mode)
getChild<LLUICtrl>("rpt")->setValue(getString("string repeats per meter"));
}
else
if (selected_texgen == LLTextureEntry::TEX_GEN_DEFAULT)
{
getChild<LLUICtrl>("rpt")->setValue(getString("string repeats per face"));
}
}
{
@ -1390,8 +1380,7 @@ void LLPanelFace::updateUI(bool force_set_values /*false*/)
mColorSwatch->setValid(FALSE);
}
getChildView("color trans")->setEnabled(FALSE);
getChildView("rpt")->setEnabled(FALSE);
getChildView("tex offset")->setEnabled(FALSE);
getChildView("rptctrl")->setEnabled(FALSE);
getChildView("tex gen")->setEnabled(FALSE);
getChildView("label shininess")->setEnabled(FALSE);
getChildView("label bumpiness")->setEnabled(FALSE);

View File

@ -159,9 +159,6 @@ BOOL LLPanelGroup::postBuild()
button = getChild<LLButton>("btn_chat");
button->setClickedCallback(onBtnGroupChatClicked, this);
button = getChild<LLButton>("btn_cancel");
button->setVisible(false); button->setEnabled(true);
button = getChild<LLButton>("btn_refresh");
button->setClickedCallback(onBtnRefresh, this);
@ -170,8 +167,6 @@ BOOL LLPanelGroup::postBuild()
childSetCommitCallback("back",boost::bind(&LLPanelGroup::onBackBtnClick,this),NULL);
childSetCommitCallback("btn_create",boost::bind(&LLPanelGroup::onBtnCreate,this),NULL);
childSetCommitCallback("btn_cancel",boost::bind(&LLPanelGroup::onBtnCancel,this),NULL);
LLPanelGroupTab* panel_general = findChild<LLPanelGroupTab>("group_general_tab_panel");
LLPanelGroupTab* panel_roles = findChild<LLPanelGroupTab>("group_roles_tab_panel");
@ -299,11 +294,6 @@ void LLPanelGroup::onBtnJoin()
LLGroupActions::join(mID);
}
void LLPanelGroup::onBtnCancel()
{
onBackBtnClick();
}
void LLPanelGroup::changed(LLGroupChange gc)
{
for(std::vector<LLPanelGroupTab* >::iterator it = mTabs.begin();it!=mTabs.end();++it)

View File

@ -95,7 +95,6 @@ protected:
void onBtnCreate();
void onBackBtnClick();
void onBtnJoin();
void onBtnCancel();
static void onBtnApply(void*);
static void onBtnRefresh(void*);

View File

@ -194,6 +194,7 @@ void LLPanelGroupGeneral::setupCtrls(LLPanel* panel_group)
if (mInsignia)
{
mInsignia->setCommitCallback(onCommitAny, this);
mInsignia->setAllowLocalTexture(FALSE);
}
mFounderName = getChild<LLTextBox>("founder_name");

View File

@ -576,6 +576,7 @@ void LLPanelGroupNotices::processNotices(LLMessageSystem* msg)
mNoticesList->setNeedsSort(save_sort);
mNoticesList->updateSort();
mNoticesList->selectFirstItem();
}
void LLPanelGroupNotices::onSelectNotice(LLUICtrl* ctrl, void* data)

View File

@ -465,12 +465,12 @@ BOOL LLPanelGroupSubTab::postBuild()
{
// Hook up the search widgets.
bool recurse = true;
mSearchEditor = getChild<LLFilterEditor>("filter_input", recurse);
if (!mSearchEditor)
return FALSE;
mSearchEditor->setCommitCallback(boost::bind(&LLPanelGroupSubTab::setSearchFilter, this, _2));
mSearchEditor = findChild<LLFilterEditor>("filter_input", recurse);
if (mSearchEditor) // SubTab doesn't implement this, only some of derived classes
{
mSearchEditor->setCommitCallback(boost::bind(&LLPanelGroupSubTab::setSearchFilter, this, _2));
}
return LLPanelGroupTab::postBuild();
}
@ -815,14 +815,18 @@ BOOL LLPanelGroupMembersSubTab::postBuildSubTab(LLView* root)
// Look recursively from the parent to find all our widgets.
bool recurse = true;
mHeader = parent->getChild<LLPanel>("members_header", recurse);
mFooter = parent->getChild<LLPanel>("members_footer", recurse);
mHeader = parent->findChild<LLPanel>("members_header", recurse);
mFooter = parent->findChild<LLPanel>("members_footer", recurse);
mMembersList = parent->getChild<LLNameListCtrl>("member_list", recurse);
mAssignedRolesList = parent->getChild<LLScrollListCtrl>("member_assigned_roles", recurse);
mAllowedActionsList = parent->getChild<LLScrollListCtrl>("member_allowed_actions", recurse);
mActionDescription = parent->getChild<LLTextEditor>("member_action_description", recurse);
if (!mMembersList || !mAssignedRolesList || !mAllowedActionsList) return FALSE;
if (!mMembersList || !mAssignedRolesList || !mAllowedActionsList || !mActionDescription) return FALSE;
mAllowedActionsList->setCommitOnSelectionChange(TRUE);
mAllowedActionsList->setCommitCallback(boost::bind(&LLPanelGroupMembersSubTab::updateActionDescription, this));
// We want to be notified whenever a member is selected.
mMembersList->setCommitOnSelectionChange(TRUE);
@ -889,6 +893,7 @@ void LLPanelGroupMembersSubTab::handleMemberSelect()
mAssignedRolesList->deleteAllItems();
mAllowedActionsList->deleteAllItems();
mActionDescription->clear();
LLGroupMgrGroupData* gdatap = LLGroupMgr::getInstance()->getGroupData(mGroupID);
if (!gdatap)
@ -1386,6 +1391,7 @@ void LLPanelGroupMembersSubTab::activate()
update(GC_MEMBER_DATA);
}
}
mActionDescription->clear();
}
void LLPanelGroupMembersSubTab::deactivate()
@ -1894,6 +1900,23 @@ bool LLPanelGroupMembersSubTab::handleBanCallback(const LLSD& notification, cons
return false;
}
void LLPanelGroupMembersSubTab::updateActionDescription()
{
mActionDescription->setText(std::string());
LLScrollListItem* action_item = mAllowedActionsList->getFirstSelected();
if (!action_item || !mAllowedActionsList->getCanSelect())
{
return;
}
LLRoleAction* rap = (LLRoleAction*)action_item->getUserdata();
if (rap)
{
std::string desc = rap->mLongDescription.empty() ? rap->mDescription : rap->mLongDescription;
mActionDescription->setText(desc);
}
}
void LLPanelGroupMembersSubTab::handleBanMember()
{
LLGroupMgrGroupData* gdatap = LLGroupMgr::getInstance()->getGroupData(mGroupID);
@ -1957,13 +1980,14 @@ BOOL LLPanelGroupRolesSubTab::postBuildSubTab(LLView* root)
// Look recursively from the parent to find all our widgets.
bool recurse = true;
mHeader = parent->getChild<LLPanel>("roles_header", recurse);
mFooter = parent->getChild<LLPanel>("roles_footer", recurse);
mHeader = parent->findChild<LLPanel>("roles_header", recurse);
mFooter = parent->findChild<LLPanel>("roles_footer", recurse);
mRolesList = parent->getChild<LLScrollListCtrl>("role_list", recurse);
mAssignedMembersList = parent->getChild<LLNameListCtrl>("role_assigned_members", recurse);
mAllowedActionsList = parent->getChild<LLScrollListCtrl>("role_allowed_actions", recurse);
mActionDescription = parent->getChild<LLTextEditor>("role_action_description", recurse);
mRoleName = parent->getChild<LLLineEditor>("role_name", recurse);
mRoleTitle = parent->getChild<LLLineEditor>("role_title", recurse);
@ -1971,7 +1995,7 @@ BOOL LLPanelGroupRolesSubTab::postBuildSubTab(LLView* root)
mMemberVisibleCheck = parent->getChild<LLCheckBoxCtrl>("role_visible_in_list", recurse);
if (!mRolesList || !mAssignedMembersList || !mAllowedActionsList
if (!mRolesList || !mAssignedMembersList || !mAllowedActionsList || !mActionDescription
|| !mRoleName || !mRoleTitle || !mRoleDescription || !mMemberVisibleCheck)
{
LL_WARNS() << "ARG! element not found." << LL_ENDL;
@ -2004,6 +2028,7 @@ BOOL LLPanelGroupRolesSubTab::postBuildSubTab(LLView* root)
mMemberVisibleCheck->setCommitCallback(onMemberVisibilityChange, this);
mAllowedActionsList->setCommitOnSelectionChange(TRUE);
mAllowedActionsList->setCommitCallback(boost::bind(&LLPanelGroupRolesSubTab::updateActionDescription, this));
mRoleName->setCommitOnFocusLost(TRUE);
mRoleName->setKeystrokeCallback(onPropertiesKey, this);
@ -2023,6 +2048,7 @@ void LLPanelGroupRolesSubTab::activate()
{
LLPanelGroupSubTab::activate();
mActionDescription->clear();
mRolesList->deselectAllItems();
mAssignedMembersList->deleteAllItems();
mAllowedActionsList->deleteAllItems();
@ -2707,6 +2733,23 @@ void LLPanelGroupRolesSubTab::saveRoleChanges(bool select_saved_role)
}
}
void LLPanelGroupRolesSubTab::updateActionDescription()
{
mActionDescription->setText(std::string());
LLScrollListItem* action_item = mAllowedActionsList->getFirstSelected();
if (!action_item || !mAllowedActionsList->getCanSelect())
{
return;
}
LLRoleAction* rap = (LLRoleAction*)action_item->getUserdata();
if (rap)
{
std::string desc = rap->mLongDescription.empty() ? rap->mDescription : rap->mLongDescription;
mActionDescription->setText(desc);
}
}
void LLPanelGroupRolesSubTab::setGroupID(const LLUUID& id)
{
if(mRolesList) mRolesList->deleteAllItems();
@ -2746,8 +2789,8 @@ BOOL LLPanelGroupActionsSubTab::postBuildSubTab(LLView* root)
// Look recursively from the parent to find all our widgets.
bool recurse = true;
mHeader = parent->getChild<LLPanel>("actions_header", recurse);
mFooter = parent->getChild<LLPanel>("actions_footer", recurse);
mHeader = parent->findChild<LLPanel>("actions_header", recurse);
mFooter = parent->findChild<LLPanel>("actions_footer", recurse);
mActionDescription = parent->getChild<LLTextEditor>("action_description", recurse);
@ -2953,10 +2996,10 @@ BOOL LLPanelGroupBanListSubTab::postBuildSubTab(LLView* root)
// Look recursively from the parent to find all our widgets.
bool recurse = true;
mHeader = parent->getChild<LLPanel>("banlist_header", recurse);
mFooter = parent->getChild<LLPanel>("banlist_footer", recurse);
mHeader = parent->findChild<LLPanel>("banlist_header", recurse);
mFooter = parent->findChild<LLPanel>("banlist_footer", recurse);
mBanList = parent->getChild<LLNameListCtrl>("ban_list", recurse);
mCreateBanButton = parent->getChild<LLButton>("ban_create", recurse);

View File

@ -132,7 +132,7 @@ protected:
BOOL is_owner_role);
protected:
LLPanel* mHeader;
LLPanel* mHeader; // Might not be present in xui of derived class (NULL)
LLPanel* mFooter;
LLFilterEditor* mSearchEditor;
@ -182,6 +182,7 @@ public:
bool handleBanCallback(const LLSD& notification, const LLSD& response);
void confirmBanMembers();
void updateActionDescription();
void applyMemberChanges();
bool addOwnerCB(const LLSD& notification, const LLSD& response);
@ -222,6 +223,8 @@ protected:
BOOL mPendingMemberUpdate;
BOOL mHasMatch;
LLTextEditor* mActionDescription;
member_role_changes_map_t mMemberRoleChangeData;
U32 mNumOwnerAdditions;
@ -269,6 +272,8 @@ public:
static void onDeleteRole(void*);
void handleDeleteRole();
void updateActionDescription();
void saveRoleChanges(bool select_saved_role);
virtual void setGroupID(const LLUUID& id);
@ -282,6 +287,7 @@ protected:
LLScrollListCtrl* mRolesList;
LLNameListCtrl* mAssignedMembersList;
LLScrollListCtrl* mAllowedActionsList;
LLTextEditor* mActionDescription;
LLLineEditor* mRoleName;
LLLineEditor* mRoleTitle;

View File

@ -271,9 +271,6 @@ LLPanelLogin::LLPanelLogin(const LLRect &rect,
LLTextBox* forgot_password_text = getChild<LLTextBox>("forgot_password_text");
forgot_password_text->setClickedCallback(onClickForgotPassword, NULL);
LLTextBox* need_help_text = getChild<LLTextBox>("login_help");
need_help_text->setClickedCallback(onClickHelp, NULL);
// get the web browser control
LLMediaCtrl* web_browser = getChild<LLMediaCtrl>("login_html");
web_browser->addObserver(this);
@ -284,6 +281,7 @@ LLPanelLogin::LLPanelLogin(const LLRect &rect,
username_combo->setTextChangedCallback(boost::bind(&LLPanelLogin::addFavoritesToStartLocation, this));
// STEAM-14: When user presses Enter with this field in focus, initiate login
username_combo->setCommitCallback(boost::bind(&LLPanelLogin::onClickConnect, this));
username_combo->setKeystrokeOnEsc(TRUE);
}
void LLPanelLogin::addFavoritesToStartLocation()
@ -923,16 +921,6 @@ void LLPanelLogin::onClickForgotPassword(void*)
}
}
//static
void LLPanelLogin::onClickHelp(void*)
{
if (sInstance)
{
LLViewerHelp* vhelp = LLViewerHelp::getInstance();
vhelp->showTopic(vhelp->preLoginTopic());
}
}
// static
void LLPanelLogin::onPassKey(LLLineEditor* caller, void* user_data)
{

View File

@ -99,7 +99,6 @@ private:
static void onClickNewAccount(void*);
static void onClickVersion(void*);
static void onClickForgotPassword(void*);
static void onClickHelp(void*);
static void onPassKey(LLLineEditor* caller, void* user_data);
static void updateServerCombo();

View File

@ -448,20 +448,6 @@ void LLPanelObject::getState( )
S32 roots_selected = LLSelectMgr::getInstance()->getSelection()->getRootObjectCount();
BOOL editable = root_objectp->permModify();
// Select Single Message
getChildView("select_single")->setVisible( FALSE);
getChildView("edit_object")->setVisible( FALSE);
if (!editable || single_volume || selected_count <= 1)
{
getChildView("edit_object")->setVisible( TRUE);
getChildView("edit_object")->setEnabled(TRUE);
}
else
{
getChildView("select_single")->setVisible( TRUE);
getChildView("select_single")->setEnabled(TRUE);
}
BOOL is_flexible = volobjp && volobjp->isFlexible();
BOOL is_permanent = root_objectp->flagObjectPermanent();
BOOL is_permanent_enforced = root_objectp->isPermanentEnforced();
@ -1893,10 +1879,6 @@ void LLPanelObject::clearCtrls()
mLabelTaper ->setEnabled( FALSE );
mLabelRadiusOffset->setEnabled( FALSE );
mLabelRevolutions->setEnabled( FALSE );
getChildView("select_single")->setVisible( FALSE);
getChildView("edit_object")->setVisible( TRUE);
getChildView("edit_object")->setEnabled(FALSE);
getChildView("scale_hole")->setEnabled(FALSE);
getChildView("scale_taper")->setEnabled(FALSE);

View File

@ -101,9 +101,7 @@ public:
static LLTaskInvFVBridge* createObjectBridge(LLPanelObjectInventory* panel,
LLInventoryObject* object);
void showProperties();
void buyItem();
S32 getPrice();
static bool commitBuyItem(const LLSD& notification, const LLSD& response);
// LLFolderViewModelItemInventory functionality
virtual const std::string& getName() const;
@ -201,75 +199,6 @@ void LLTaskInvFVBridge::showProperties()
show_task_item_profile(mUUID, mPanel->getTaskUUID());
}
struct LLBuyInvItemData
{
LLUUID mTaskID;
LLUUID mItemID;
LLAssetType::EType mType;
LLBuyInvItemData(const LLUUID& task,
const LLUUID& item,
LLAssetType::EType type) :
mTaskID(task), mItemID(item), mType(type)
{}
};
void LLTaskInvFVBridge::buyItem()
{
LL_INFOS() << "LLTaskInvFVBridge::buyItem()" << LL_ENDL;
LLInventoryItem* item = findItem();
if(!item || !item->getSaleInfo().isForSale()) return;
LLBuyInvItemData* inv = new LLBuyInvItemData(mPanel->getTaskUUID(),
mUUID,
item->getType());
const LLSaleInfo& sale_info = item->getSaleInfo();
const LLPermissions& perm = item->getPermissions();
const std::string owner_name; // no owner name currently... FIXME?
LLViewerObject* obj;
if( ( obj = gObjectList.findObject( mPanel->getTaskUUID() ) ) && obj->isAttachment() )
{
LLNotificationsUtil::add("Cannot_Purchase_an_Attachment");
LL_INFOS() << "Attempt to purchase an attachment" << LL_ENDL;
delete inv;
}
else
{
LLSD args;
args["PRICE"] = llformat("%d",sale_info.getSalePrice());
args["OWNER"] = owner_name;
if (sale_info.getSaleType() != LLSaleInfo::FS_CONTENTS)
{
U32 next_owner_mask = perm.getMaskNextOwner();
args["MODIFYPERM"] = LLTrans::getString((next_owner_mask & PERM_MODIFY) ? "PermYes" : "PermNo");
args["COPYPERM"] = LLTrans::getString((next_owner_mask & PERM_COPY) ? "PermYes" : "PermNo");
args["RESELLPERM"] = LLTrans::getString((next_owner_mask & PERM_TRANSFER) ? "PermYes" : "PermNo");
}
std::string alertdesc;
switch(sale_info.getSaleType())
{
case LLSaleInfo::FS_ORIGINAL:
alertdesc = owner_name.empty() ? "BuyOriginalNoOwner" : "BuyOriginal";
break;
case LLSaleInfo::FS_CONTENTS:
alertdesc = owner_name.empty() ? "BuyContentsNoOwner" : "BuyContents";
break;
case LLSaleInfo::FS_COPY:
default:
alertdesc = owner_name.empty() ? "BuyCopyNoOwner" : "BuyCopy";
break;
}
LLSD payload;
payload["task_id"] = inv->mTaskID;
payload["item_id"] = inv->mItemID;
payload["type"] = inv->mType;
LLNotificationsUtil::add(alertdesc, args, payload, LLTaskInvFVBridge::commitBuyItem);
}
}
S32 LLTaskInvFVBridge::getPrice()
{
LLInventoryItem* item = findItem();
@ -283,31 +212,6 @@ S32 LLTaskInvFVBridge::getPrice()
}
}
// static
bool LLTaskInvFVBridge::commitBuyItem(const LLSD& notification, const LLSD& response)
{
S32 option = LLNotificationsUtil::getSelectedOption(notification, response);
if(0 == option)
{
LLViewerObject* object = gObjectList.findObject(notification["payload"]["task_id"].asUUID());
if(!object || !object->getRegion()) return false;
LLMessageSystem* msg = gMessageSystem;
msg->newMessageFast(_PREHASH_BuyObjectInventory);
msg->nextBlockFast(_PREHASH_AgentData);
msg->addUUIDFast(_PREHASH_AgentID, gAgent.getID());
msg->addUUIDFast(_PREHASH_SessionID, gAgent.getSessionID());
msg->nextBlockFast(_PREHASH_Data);
msg->addUUIDFast(_PREHASH_ObjectID, notification["payload"]["task_id"].asUUID());
msg->addUUIDFast(_PREHASH_ItemID, notification["payload"]["item_id"].asUUID());
msg->addUUIDFast(_PREHASH_FolderID,
gInventory.findCategoryUUIDForType((LLFolderType::EType)notification["payload"]["type"].asInteger()));
msg->sendReliable(object->getRegion()->getHost());
}
return false;
}
const std::string& LLTaskInvFVBridge::getName() const
{
return mName;
@ -616,29 +520,7 @@ BOOL LLTaskInvFVBridge::dragOrDrop(MASK mask, BOOL drop,
// virtual
void LLTaskInvFVBridge::performAction(LLInventoryModel* model, std::string action)
{
if (action == "task_buy")
{
// Check the price of the item.
S32 price = getPrice();
if (-1 == price)
{
LL_WARNS() << "label_buy_task_bridged_item: Invalid price" << LL_ENDL;
}
else
{
if (price > 0 && price > gStatusBar->getBalance())
{
LLStringUtil::format_map_t args;
args["AMOUNT"] = llformat("%d", price);
LLBuyCurrencyHTML::openCurrencyFloater( LLTrans::getString("this_costs", args), price );
}
else
{
buyItem();
}
}
}
else if (action == "task_open")
if (action == "task_open")
{
openItem();
}
@ -660,39 +542,7 @@ void LLTaskInvFVBridge::buildContextMenu(LLMenuGL& menu, U32 flags)
return;
}
if(!gAgent.allowOperation(PERM_OWNER, item->getPermissions(),
GP_OBJECT_MANIPULATE)
&& item->getSaleInfo().isForSale())
{
items.push_back(std::string("Task Buy"));
std::string label= LLTrans::getString("Buy");
// Check the price of the item.
S32 price = getPrice();
if (-1 == price)
{
LL_WARNS() << "label_buy_task_bridged_item: Invalid price" << LL_ENDL;
}
else
{
std::ostringstream info;
info << LLTrans::getString("BuyforL$") << price;
label.assign(info.str());
}
const LLView::child_list_t *list = menu.getChildList();
LLView::child_list_t::const_iterator itor;
for (itor = list->begin(); itor != list->end(); ++itor)
{
std::string name = (*itor)->getName();
LLMenuItemCallGL* menu_itemp = dynamic_cast<LLMenuItemCallGL*>(*itor);
if (name == "Task Buy" && menu_itemp)
{
menu_itemp->setLabel(label);
}
}
}
else if (canOpenItem())
if (canOpenItem())
{
items.push_back(std::string("Task Open"));
}
@ -980,42 +830,15 @@ void LLTaskSoundBridge::performAction(LLInventoryModel* model, std::string actio
void LLTaskSoundBridge::buildContextMenu(LLMenuGL& menu, U32 flags)
{
LLInventoryItem* item = findItem();
if(!item) return;
std::vector<std::string> items;
std::vector<std::string> disabled_items;
if(item->getPermissions().getOwner() != gAgent.getID()
&& item->getSaleInfo().isForSale())
if (!item)
{
items.push_back(std::string("Task Buy"));
std::string label= LLTrans::getString("Buy");
// Check the price of the item.
S32 price = getPrice();
if (-1 == price)
{
LL_WARNS() << "label_buy_task_bridged_item: Invalid price" << LL_ENDL;
}
else
{
std::ostringstream info;
info << LLTrans::getString("BuyforL$") << price;
label.assign(info.str());
}
const LLView::child_list_t *list = menu.getChildList();
LLView::child_list_t::const_iterator itor;
for (itor = list->begin(); itor != list->end(); ++itor)
{
std::string name = (*itor)->getName();
LLMenuItemCallGL* menu_itemp = dynamic_cast<LLMenuItemCallGL*>(*itor);
if (name == "Task Buy" && menu_itemp)
{
menu_itemp->setLabel(label);
}
}
hide_context_entries(menu, items, disabled_items);
return;
}
else if (canOpenItem())
if (canOpenItem())
{
if (!isItemCopyable())
{
@ -1354,49 +1177,20 @@ void LLTaskMeshBridge::performAction(LLInventoryModel* model, std::string action
void LLTaskMeshBridge::buildContextMenu(LLMenuGL& menu, U32 flags)
{
LLInventoryItem* item = findItem();
if(!item) return;
std::vector<std::string> items;
std::vector<std::string> disabled_items;
if(item->getPermissions().getOwner() != gAgent.getID()
&& item->getSaleInfo().isForSale())
if(!item)
{
items.push_back(std::string("Task Buy"));
std::string label= LLTrans::getString("Buy");
// Check the price of the item.
S32 price = getPrice();
if (-1 == price)
{
LL_WARNS() << "label_buy_task_bridged_item: Invalid price" << LL_ENDL;
}
else
{
std::ostringstream info;
info << LLTrans::getString("BuyforL$") << price;
label.assign(info.str());
}
const LLView::child_list_t *list = menu.getChildList();
LLView::child_list_t::const_iterator itor;
for (itor = list->begin(); itor != list->end(); ++itor)
{
std::string name = (*itor)->getName();
LLMenuItemCallGL* menu_itemp = dynamic_cast<LLMenuItemCallGL*>(*itor);
if (name == "Task Buy" && menu_itemp)
{
menu_itemp->setLabel(label);
}
}
hide_context_entries(menu, items, disabled_items);
return;
}
else
items.push_back(std::string("Task Open"));
if (!isItemCopyable())
{
items.push_back(std::string("Task Open"));
if (!isItemCopyable())
{
disabled_items.push_back(std::string("Task Open"));
}
disabled_items.push_back(std::string("Task Open"));
}
items.push_back(std::string("Task Properties"));
if ((flags & FIRST_SELECTED_ITEM) == 0)
{

View File

@ -531,11 +531,6 @@ BOOL LLPanelOutfitEdit::postBuild()
mPlusBtn = getChild<LLButton>("plus_btn");
mPlusBtn->setClickedCallback(boost::bind(&LLPanelOutfitEdit::onPlusBtnClicked, this));
mEditWearableBtn = getChild<LLButton>("edit_wearable_btn");
mEditWearableBtn->setEnabled(FALSE);
mEditWearableBtn->setVisible(FALSE);
mEditWearableBtn->setCommitCallback(boost::bind(&LLPanelOutfitEdit::onEditWearableClicked, this));
childSetAction(REVERT_BTN, boost::bind(&LLAppearanceMgr::wearBaseOutfit, LLAppearanceMgr::getInstance()));

View File

@ -214,7 +214,6 @@ private:
LLFilterEditor* mSearchFilter;
LLSaveFolderState* mSavedFolderState;
std::string mSearchString;
LLButton* mEditWearableBtn;
LLButton* mFolderViewBtn;
LLButton* mListViewBtn;
LLButton* mPlusBtn;

View File

@ -586,7 +586,6 @@ BOOL LLPanelPeople::postBuild()
getChild<LLFilterEditor>("friends_filter_input")->setCommitCallback(boost::bind(&LLPanelPeople::onFilterEdit, this, _2));
getChild<LLFilterEditor>("groups_filter_input")->setCommitCallback(boost::bind(&LLPanelPeople::onFilterEdit, this, _2));
getChild<LLFilterEditor>("recent_filter_input")->setCommitCallback(boost::bind(&LLPanelPeople::onFilterEdit, this, _2));
getChild<LLFilterEditor>("fbc_filter_input")->setCommitCallback(boost::bind(&LLPanelPeople::onFilterEdit, this, _2));
if(gMaxAgentGroups <= BASE_MAX_AGENT_GROUPS)
{

View File

@ -171,6 +171,8 @@ BOOL LLPanelPermissions::postBuild()
childSetCommitCallback("search_check",LLPanelPermissions::onCommitIncludeInSearch,this);
mLabelGroupName = getChild<LLNameBox>("Group Name Proxy");
mLabelOwnerName = getChild<LLTextBox>("Owner Name");
mLabelCreatorName = getChild<LLTextBox>("Creator Name");
return TRUE;
}
@ -178,6 +180,14 @@ BOOL LLPanelPermissions::postBuild()
LLPanelPermissions::~LLPanelPermissions()
{
if (mOwnerCacheConnection.connected())
{
mOwnerCacheConnection.disconnect();
}
if (mCreatorCacheConnection.connected())
{
mCreatorCacheConnection.disconnect();
}
// base class will take care of everything
}
@ -192,14 +202,14 @@ void LLPanelPermissions::disableAll()
getChildView("Creator:")->setEnabled(FALSE);
getChild<LLUICtrl>("Creator Icon")->setVisible(FALSE);
getChild<LLUICtrl>("Creator Name")->setValue(LLStringUtil::null);
getChildView("Creator Name")->setEnabled(FALSE);
mLabelCreatorName->setValue(LLStringUtil::null);
mLabelCreatorName->setEnabled(FALSE);
getChildView("Owner:")->setEnabled(FALSE);
getChild<LLUICtrl>("Owner Icon")->setVisible(FALSE);
getChild<LLUICtrl>("Owner Group Icon")->setVisible(FALSE);
getChild<LLUICtrl>("Owner Name")->setValue(LLStringUtil::null);
getChildView("Owner Name")->setEnabled(FALSE);
mLabelOwnerName->setValue(LLStringUtil::null);
mLabelOwnerName->setEnabled(FALSE);
getChildView("Group:")->setEnabled(FALSE);
getChild<LLUICtrl>("Group Name Proxy")->setValue(LLStringUtil::null);
@ -214,8 +224,6 @@ void LLPanelPermissions::disableAll()
getChildView("Description:")->setEnabled(FALSE);
getChild<LLUICtrl>("Object Description")->setValue(LLStringUtil::null);
getChildView("Object Description")->setEnabled(FALSE);
getChildView("Permissions:")->setEnabled(FALSE);
getChild<LLUICtrl>("checkbox share with group")->setValue(FALSE);
getChildView("checkbox share with group")->setEnabled(FALSE);
@ -369,8 +377,6 @@ void LLPanelPermissions::refresh()
getChildView("pathfinding_attributes_value")->setEnabled(TRUE);
getChild<LLUICtrl>("pathfinding_attributes_value")->setValue(LLTrans::getString(pfAttrName));
getChildView("Permissions:")->setEnabled(TRUE);
// Update creator text field
getChildView("Creator:")->setEnabled(TRUE);
@ -383,22 +389,29 @@ void LLPanelPermissions::refresh()
style_params.color = link_color;
style_params.readonly_color = link_color;
style_params.is_link = true; // link will be added later
const LLFontGL* fontp = getChild<LLTextBox>("Creator Name")->getFont();
const LLFontGL* fontp = mLabelCreatorName->getFont();
style_params.font.name = LLFontGL::nameFromFont(fontp);
style_params.font.size = LLFontGL::sizeFromFont(fontp);
style_params.font.style = "UNDERLINE";
LLAvatarName av_name;
style_params.link_href = creator_app_link;
if (LLAvatarNameCache::get(mCreatorID, &av_name))
{
// If name isn't present, this will 'request' it and trigger refresh() again
LLTextBox* text_box = getChild<LLTextBox>("Creator Name");
style_params.link_href = creator_app_link;
text_box->setText(av_name.getCompleteName(), style_params);
updateCreatorName(mCreatorID, av_name, style_params);
}
else
{
if (mCreatorCacheConnection.connected())
{
mCreatorCacheConnection.disconnect();
}
mLabelCreatorName->setText(LLTrans::getString("None"));
mCreatorCacheConnection = LLAvatarNameCache::get(mCreatorID, boost::bind(&LLPanelPermissions::updateCreatorName, this, _1, _2, style_params));
}
getChild<LLAvatarIconCtrl>("Creator Icon")->setValue(mCreatorID);
getChild<LLAvatarIconCtrl>("Creator Icon")->setVisible(TRUE);
getChildView("Creator Name")->setEnabled(TRUE);
mLabelCreatorName->setEnabled(TRUE);
// Update owner text field
getChildView("Owner:")->setEnabled(TRUE);
@ -413,9 +426,8 @@ void LLPanelPermissions::refresh()
LLGroupMgrGroupData* group_data = LLGroupMgr::getInstance()->getGroupData(mOwnerID);
if (group_data && group_data->isGroupPropertiesDataComplete())
{
LLTextBox* text_box = getChild<LLTextBox>("Owner Name");
style_params.link_href = owner_app_link;
text_box->setText(group_data->mName, style_params);
mLabelOwnerName->setText(group_data->mName, style_params);
getChild<LLGroupIconCtrl>("Owner Group Icon")->setIconId(group_data->mInsigniaID);
getChild<LLGroupIconCtrl>("Owner Group Icon")->setVisible(TRUE);
getChild<LLUICtrl>("Owner Icon")->setVisible(FALSE);
@ -444,18 +456,27 @@ void LLPanelPermissions::refresh()
}
owner_id = mLastOwnerID;
}
style_params.link_href = owner_app_link;
if (LLAvatarNameCache::get(owner_id, &av_name))
{
// If name isn't present, this will 'request' it and trigger refresh() again
LLTextBox* text_box = getChild<LLTextBox>("Owner Name");
style_params.link_href = owner_app_link;
text_box->setText(av_name.getCompleteName(), style_params);
updateOwnerName(owner_id, av_name, style_params);
}
else
{
if (mOwnerCacheConnection.connected())
{
mOwnerCacheConnection.disconnect();
}
mLabelOwnerName->setText(LLTrans::getString("None"));
mOwnerCacheConnection = LLAvatarNameCache::get(owner_id, boost::bind(&LLPanelPermissions::updateOwnerName, this, _1, _2, style_params));
}
getChild<LLAvatarIconCtrl>("Owner Icon")->setValue(owner_id);
getChild<LLAvatarIconCtrl>("Owner Icon")->setVisible(TRUE);
getChild<LLUICtrl>("Owner Group Icon")->setVisible(FALSE);
}
getChildView("Owner Name")->setEnabled(TRUE);
mLabelOwnerName->setEnabled(TRUE);
// update group text field
getChildView("Group:")->setEnabled(TRUE);
@ -785,7 +806,7 @@ void LLPanelPermissions::refresh()
else
{
getChild<LLUICtrl>("checkbox share with group")->setValue(TRUE);
getChild<LLUICtrl>("checkbox share with group")->setTentative( TRUE);
getChild<LLUICtrl>("checkbox share with group")->setTentative(!has_change_perm_ability);
getChildView("button deed")->setEnabled(gAgent.hasPowerInGroup(group_id, GP_OBJECT_DEED) && (group_mask_on & PERM_MOVE) && (owner_mask_on & PERM_TRANSFER) && !group_owned && can_transfer);
}
}
@ -944,6 +965,23 @@ void LLPanelPermissions::refresh()
getChildView("clickaction")->setEnabled(is_perm_modify && is_nonpermanent_enforced && all_volume);
}
void LLPanelPermissions::updateOwnerName(const LLUUID& owner_id, const LLAvatarName& owner_name, const LLStyle::Params& style_params)
{
if (mOwnerCacheConnection.connected())
{
mOwnerCacheConnection.disconnect();
}
mLabelOwnerName->setText(owner_name.getCompleteName(), style_params);
}
void LLPanelPermissions::updateCreatorName(const LLUUID& creator_id, const LLAvatarName& creator_name, const LLStyle::Params& style_params)
{
if (mCreatorCacheConnection.connected())
{
mCreatorCacheConnection.disconnect();
}
mLabelCreatorName->setText(creator_name.getCompleteName(), style_params);
}
// static
void LLPanelPermissions::onClickClaim(void*)

View File

@ -28,6 +28,7 @@
#define LL_LLPANELPERMISSIONS_H
#include "llpanel.h"
#include "llstyle.h"
#include "lluuid.h"
//~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
@ -36,6 +37,8 @@
// Panel for permissions of an object.
//~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
class LLAvatarName;
class LLTextBox;
class LLNameBox;
class LLViewerInventoryItem;
@ -46,7 +49,8 @@ public:
virtual ~LLPanelPermissions();
/*virtual*/ BOOL postBuild();
void updateOwnerName(const LLUUID& owner_id, const LLAvatarName& owner_name, const LLStyle::Params& style_params);
void updateCreatorName(const LLUUID& creator_id, const LLAvatarName& creator_name, const LLStyle::Params& style_params);
void refresh(); // refresh all labels as needed
protected:
@ -85,10 +89,14 @@ protected:
private:
LLNameBox* mLabelGroupName; // group name
LLTextBox* mLabelOwnerName;
LLTextBox* mLabelCreatorName;
LLUUID mCreatorID;
LLUUID mOwnerID;
LLUUID mLastOwnerID;
boost::signals2::connection mOwnerCacheConnection;
boost::signals2::connection mCreatorCacheConnection;
};

View File

@ -282,7 +282,6 @@ void LLPanelVolume::getState( )
if (is_light && editable && single_volume)
{
getChildView("label color")->setEnabled(true);
//mLabelColor ->setEnabled( TRUE );
LLColorSwatchCtrl* LightColorSwatch = getChild<LLColorSwatchCtrl>("colorswatch");
if(LightColorSwatch)
@ -325,7 +324,6 @@ void LLPanelVolume::getState( )
getChild<LLSpinCtrl>("Light Radius", true)->clear();
getChild<LLSpinCtrl>("Light Falloff", true)->clear();
getChildView("label color")->setEnabled(false);
LLColorSwatchCtrl* LightColorSwatch = getChild<LLColorSwatchCtrl>("colorswatch");
if(LightColorSwatch)
{
@ -526,7 +524,6 @@ void LLPanelVolume::refresh()
BOOL visible = LLViewerShaderMgr::instance()->getVertexShaderLevel(LLViewerShaderMgr::SHADER_DEFERRED) > 0 ? TRUE : FALSE;
getChildView("label texture")->setVisible( visible);
getChildView("Light FOV")->setVisible( visible);
getChildView("Light Focus")->setVisible( visible);
getChildView("Light Ambiance")->setVisible( visible);
@ -567,9 +564,7 @@ void LLPanelVolume::clearCtrls()
getChildView("select_single")->setVisible(true);
getChildView("edit_object")->setEnabled(false);
getChildView("edit_object")->setVisible(false);
getChildView("Light Checkbox Ctrl")->setEnabled(false);
getChildView("label color")->setEnabled(false);
getChildView("label color")->setEnabled(false);
getChildView("Light Checkbox Ctrl")->setEnabled(false);;
LLColorSwatchCtrl* LightColorSwatch = getChild<LLColorSwatchCtrl>("colorswatch");
if(LightColorSwatch)
{

View File

@ -35,6 +35,7 @@
// Linden libs
#include "llbutton.h"
#include "llcheckboxctrl.h"
#include "lltabcontainer.h"
#include "llfloaterreg.h"
#include "llfloaterpreference.h"
@ -52,17 +53,15 @@ LLPanelVolumePulldown::LLPanelVolumePulldown()
{
mHoverTimer.stop();
mCommitCallbackRegistrar.add("Vol.setControlFalse", boost::bind(&LLPanelVolumePulldown::setControlFalse, this, _2));
mCommitCallbackRegistrar.add("Vol.setControlFalse", boost::bind(&LLPanelVolumePulldown::setControlFalse, this, _2));
mCommitCallbackRegistrar.add("Vol.SetSounds", boost::bind(&LLPanelVolumePulldown::onClickSetSounds, this));
mCommitCallbackRegistrar.add("Vol.updateMediaAutoPlayCheckbox", boost::bind(&LLPanelVolumePulldown::updateMediaAutoPlayCheckbox, this, _1));
mCommitCallbackRegistrar.add("Vol.GoAudioPrefs", boost::bind(&LLPanelVolumePulldown::onAdvancedButtonClick, this, _2));
buildFromFile( "panel_volume_pulldown.xml");
}
BOOL LLPanelVolumePulldown::postBuild()
{
// set the initial volume-slider's position to reflect reality
LLSliderCtrl* volslider = getChild<LLSliderCtrl>( "mastervolume" );
volslider->setValue(gSavedSettings.getF32("AudioLevelMaster"));
return LLPanel::postBuild();
}
@ -130,6 +129,28 @@ void LLPanelVolumePulldown::setControlFalse(const LLSD& user_data)
control->set(LLSD(FALSE));
}
void LLPanelVolumePulldown::updateMediaAutoPlayCheckbox(LLUICtrl* ctrl)
{
std::string name = ctrl->getName();
// Disable "Allow Media to auto play" only when both
// "Streaming Music" and "Media" are unchecked. STORM-513.
if ((name == "enable_music") || (name == "enable_media"))
{
bool music_enabled = getChild<LLCheckBoxCtrl>("enable_music")->get();
bool media_enabled = getChild<LLCheckBoxCtrl>("enable_media")->get();
getChild<LLCheckBoxCtrl>("media_auto_play_btn")->setEnabled(music_enabled || media_enabled);
}
}
void LLPanelVolumePulldown::onClickSetSounds()
{
// Disable Enable gesture sounds checkbox if the master sound is disabled
// or if sound effects are disabled.
getChild<LLCheckBoxCtrl>("gesture_audio_play_btn")->setEnabled(!gSavedSettings.getBOOL("MuteSounds"));
}
//virtual
void LLPanelVolumePulldown::draw()
{

View File

@ -47,6 +47,10 @@ class LLPanelVolumePulldown : public LLPanel
private:
void setControlFalse(const LLSD& user_data);
void onClickSetSounds();
// Disables "Allow Media to auto play" check box only when both
// "Streaming Music" and "Media" are unchecked. Otherwise enables it.
void updateMediaAutoPlayCheckbox(LLUICtrl* ctrl);
void onAdvancedButtonClick(const LLSD& user_data);
LLFrameTimer mHoverTimer;

View File

@ -60,6 +60,7 @@
#include "llselectmgr.h"
#include "llviewerinventory.h"
#include "llviewermenu.h"
#include "llviewermenufile.h" // LLFilePickerReplyThread
#include "llviewerobject.h"
#include "llviewerobjectlist.h"
#include "llviewerregion.h"
@ -1201,17 +1202,12 @@ BOOL LLScriptEdCore::handleKeyHere(KEY key, MASK mask)
void LLScriptEdCore::onBtnLoadFromFile( void* data )
{
LLScriptEdCore* self = (LLScriptEdCore*) data;
(new LLFilePickerReplyThread(boost::bind(&LLScriptEdCore::loadScriptFromFile, _1, data), LLFilePicker::FFLOAD_SCRIPT, false))->getFile();
}
// TODO Maybe add a dialogue warning here if the current file has unsaved changes.
LLFilePicker& file_picker = LLFilePicker::instance();
if( !file_picker.getOpenFile( LLFilePicker::FFLOAD_SCRIPT ) )
{
//File picking cancelled by user, so nothing to do.
return;
}
std::string filename = file_picker.getFirstFile();
void LLScriptEdCore::loadScriptFromFile(const std::vector<std::string>& filenames, void* data)
{
std::string filename = filenames[0];
llifstream fin(filename.c_str());
@ -1219,8 +1215,8 @@ void LLScriptEdCore::onBtnLoadFromFile( void* data )
std::string text;
std::string linetotal;
while (!fin.eof())
{
getline(fin,line);
{
getline(fin, line);
text += line;
if (!fin.eof())
{
@ -1230,7 +1226,8 @@ void LLScriptEdCore::onBtnLoadFromFile( void* data )
fin.close();
// Only replace the script if there is something to replace with.
if (text.length() > 0)
LLScriptEdCore* self = (LLScriptEdCore*)data;
if (self && (text.length() > 0))
{
self->mEditor->selectAll();
LLWString script(utf8str_to_wstring(text));
@ -1246,16 +1243,21 @@ void LLScriptEdCore::onBtnSaveToFile( void* userdata )
if( self->mSaveCallback )
{
LLFilePicker& file_picker = LLFilePicker::instance();
if( file_picker.getSaveFile( LLFilePicker::FFSAVE_SCRIPT, self->mScriptName ) )
{
std::string filename = file_picker.getFirstFile();
std::string scriptText=self->mEditor->getText();
llofstream fout(filename.c_str());
fout<<(scriptText);
fout.close();
self->mSaveCallback( self->mUserdata, FALSE );
}
(new LLFilePickerReplyThread(boost::bind(&LLScriptEdCore::saveScriptToFile, _1, userdata), LLFilePicker::FFSAVE_SCRIPT, self->mScriptName))->getFile();
}
}
void LLScriptEdCore::saveScriptToFile(const std::vector<std::string>& filenames, void* data)
{
LLScriptEdCore* self = (LLScriptEdCore*)data;
if (self)
{
std::string filename = filenames[0];
std::string scriptText = self->mEditor->getText();
llofstream fout(filename.c_str());
fout << (scriptText);
fout.close();
self->mSaveCallback(self->mUserdata, FALSE);
}
}

Some files were not shown because too many files have changed in this diff Show More