FIRE-6094 Import 'script recovery' (through changeset 26dd79c2b49d)
parent
ff18e33738
commit
f168b2db27
|
|
@ -295,6 +295,7 @@ set(viewer_SOURCE_FILES
|
|||
llfloaterreporter.cpp
|
||||
llfloaterscriptdebug.cpp
|
||||
llfloaterscriptlimits.cpp
|
||||
llfloaterscriptrecover.cpp
|
||||
llfloatersearch.cpp
|
||||
llfloatersearchreplace.cpp
|
||||
llfloatersellland.cpp
|
||||
|
|
@ -946,6 +947,7 @@ set(viewer_HEADER_FILES
|
|||
llfloaterreporter.h
|
||||
llfloaterscriptdebug.h
|
||||
llfloaterscriptlimits.h
|
||||
llfloaterscriptrecover.h
|
||||
llfloatersearch.h
|
||||
llfloatersearchreplace.h
|
||||
llfloatersellland.h
|
||||
|
|
|
|||
|
|
@ -95,6 +95,9 @@
|
|||
#include "llupdaterservice.h"
|
||||
#include "llcallfloater.h"
|
||||
#include "llfloatertexturefetchdebugger.h"
|
||||
// [SL:KB] - Patch: Build-ScriptRecover | Checked: 2011-11-24 (Catznip-3.2.0)
|
||||
#include "llfloaterscriptrecover.h"
|
||||
// [/SL:KB]
|
||||
#include "llspellcheck.h"
|
||||
|
||||
// Linden library includes
|
||||
|
|
@ -5486,6 +5489,10 @@ void LLAppViewer::handleLoginComplete()
|
|||
}
|
||||
// </FS:TT>
|
||||
|
||||
// [SL:KB] - Patch: Build-ScriptRecover | Checked: 2011-11-24 (Catznip-3.2.0) | Added: Catznip-3.2.0
|
||||
LLScriptRecoverQueue::recoverIfNeeded();
|
||||
// [/SL:KB]
|
||||
|
||||
writeDebugInfo();
|
||||
|
||||
// <FS:AO> Warn users cache purge will affect usability
|
||||
|
|
|
|||
|
|
@ -516,6 +516,18 @@ LLUpdateAgentInventoryResponder::LLUpdateAgentInventoryResponder(
|
|||
{
|
||||
}
|
||||
|
||||
// [SL:KB] - Patch: Build-ScriptRecover | Checked: 2012-04-29 (Catznip-3.3.0) | Modified: Catznip-3.3.0
|
||||
LLUpdateAgentInventoryResponder::LLUpdateAgentInventoryResponder(
|
||||
const LLSD& post_data,
|
||||
const std::string& file_name,
|
||||
LLAssetType::EType asset_type,
|
||||
upload_callback_t upload_cb,
|
||||
error_callback_t error_cb)
|
||||
: LLAssetUploadResponder(post_data, file_name, asset_type), mUploadCallback(upload_cb), mErrorCallback(error_cb)
|
||||
{
|
||||
}
|
||||
// [/SL:KB]
|
||||
|
||||
//virtual
|
||||
void LLUpdateAgentInventoryResponder::uploadComplete(const LLSD& content)
|
||||
{
|
||||
|
|
@ -527,6 +539,12 @@ void LLUpdateAgentInventoryResponder::uploadComplete(const LLSD& content)
|
|||
{
|
||||
llwarns << "Inventory item for " << mVFileID
|
||||
<< " is no longer in agent inventory." << llendl;
|
||||
// [SL:KB] - Patch: Build-ScriptRecover | Checked: 2012-02-06 (Catznip-3.2.1) | Added: Catznip-3.2.1
|
||||
if (!mUploadCallback.empty())
|
||||
{
|
||||
mUploadCallback(item_id, content, false /*failure*/);
|
||||
}
|
||||
// [/SL:KB]
|
||||
return;
|
||||
}
|
||||
|
||||
|
|
@ -539,6 +557,14 @@ void LLUpdateAgentInventoryResponder::uploadComplete(const LLSD& content)
|
|||
llinfos << "Inventory item " << item->getName() << " saved into "
|
||||
<< content["new_asset"].asString() << llendl;
|
||||
|
||||
// [SL:KB] - Patch: Build-ScriptRecover | Checked: 2011-11-24 (Catznip-3.2.0) | Added: Catznip-3.2.0
|
||||
if (!mUploadCallback.empty())
|
||||
{
|
||||
mUploadCallback(item_id, content, true /*success*/);
|
||||
return;
|
||||
}
|
||||
// [/SL:KB]
|
||||
|
||||
LLInventoryType::EType inventory_type = new_item->getInventoryType();
|
||||
switch(inventory_type)
|
||||
{
|
||||
|
|
@ -611,6 +637,26 @@ void LLUpdateAgentInventoryResponder::uploadComplete(const LLSD& content)
|
|||
}
|
||||
}
|
||||
|
||||
// [SL:KB] - Patch: Build-ScriptRecover | Checked: 2011-11-24 (Catznip-3.2.0) | Added: Catznip-3.2.0
|
||||
void LLUpdateAgentInventoryResponder::uploadFailure(const LLSD& content)
|
||||
{
|
||||
if (!mUploadCallback.empty())
|
||||
mUploadCallback(mPostData["item_id"].asUUID(), content, false /*failure*/);
|
||||
else
|
||||
LLAssetUploadResponder::uploadFailure(content);
|
||||
}
|
||||
|
||||
void LLUpdateAgentInventoryResponder::error(U32 statusNum, const std::string& reason)
|
||||
{
|
||||
LLAssetUploadResponder::error(statusNum, reason);
|
||||
if (!mErrorCallback.empty())
|
||||
{
|
||||
// Clear the filename if the error callback returns false (prevents parent's destructor from deleting the file)
|
||||
if (!mErrorCallback(mFileName, statusNum, reason))
|
||||
mFileName.clear();
|
||||
}
|
||||
}
|
||||
// [/SL:KB]
|
||||
|
||||
LLUpdateTaskInventoryResponder::LLUpdateTaskInventoryResponder(const LLSD& post_data,
|
||||
const LLUUID& vfile_id,
|
||||
|
|
|
|||
|
|
@ -136,7 +136,26 @@ public:
|
|||
LLUpdateAgentInventoryResponder(const LLSD& post_data,
|
||||
const std::string& file_name,
|
||||
LLAssetType::EType asset_type);
|
||||
// [SL:KB] - Patch: Build-ScriptRecover | Checked: 2012-04-29 (Catznip-3.3.0) | Modified: Catznip-3.3.0
|
||||
typedef boost::function<void(const LLUUID&, const LLSD&, bool)> upload_callback_t;
|
||||
typedef boost::function<bool(const std::string& filename, U32 statusNum, const std::string reason)> error_callback_t;
|
||||
LLUpdateAgentInventoryResponder(const LLSD& post_data,
|
||||
const std::string& file_name,
|
||||
LLAssetType::EType asset_type,
|
||||
upload_callback_t upload_cb,
|
||||
error_callback_t error_cb = error_callback_t());
|
||||
// [/SL:KB]
|
||||
|
||||
virtual void uploadComplete(const LLSD& content);
|
||||
// [SL:KB] - Patch: Build-ScriptRecover | Checked: 2012-04-29 (Catznip-3.3.0) | Modified: Catznip-3.3.0
|
||||
virtual void uploadFailure(const LLSD& content);
|
||||
virtual void error(U32 statusNum, const std::string& reason);
|
||||
// [/SL:KB]
|
||||
|
||||
// [SL:KB] - Patch: Build-ScriptRecover | Checked: 2012-04-29 (Catznip-3.3.0) | Modified: Catznip-3.3.0
|
||||
upload_callback_t mUploadCallback;
|
||||
error_callback_t mErrorCallback;
|
||||
// [/SL:KB]
|
||||
};
|
||||
|
||||
class LLUpdateTaskInventoryResponder : public LLAssetUploadResponder
|
||||
|
|
|
|||
|
|
@ -0,0 +1,278 @@
|
|||
/**
|
||||
*
|
||||
* Copyright (c) 2011-2012, Kitty Barnett
|
||||
*
|
||||
* The source code in this file is provided to you under the terms of the
|
||||
* GNU Lesser General Public License, version 2.1, but WITHOUT ANY WARRANTY;
|
||||
* without even the implied warranty of MERCHANTABILITY or FITNESS FOR A
|
||||
* PARTICULAR PURPOSE. Terms of the LGPL can be found in doc/LGPL-licence.txt
|
||||
* in this distribution, or online at http://www.gnu.org/licenses/lgpl-2.1.txt
|
||||
*
|
||||
* By copying, modifying or distributing this software, you acknowledge that
|
||||
* you have read and understood your obligations described above, and agree to
|
||||
* abide by those obligations.
|
||||
*
|
||||
*/
|
||||
|
||||
#include "llviewerprecompiledheaders.h"
|
||||
|
||||
#include "llagent.h"
|
||||
#include "llassetuploadresponders.h"
|
||||
#include "llcheckboxctrl.h"
|
||||
#include "lldiriterator.h"
|
||||
#include "llfloaterreg.h"
|
||||
#include "llfolderview.h"
|
||||
#include "llinventoryfunctions.h"
|
||||
#include "llinventorymodel.h"
|
||||
#include "llinventorypanel.h"
|
||||
#include "llscrolllistctrl.h"
|
||||
#include "llviewerassettype.h"
|
||||
#include "llviewerinventory.h"
|
||||
#include "llviewerregion.h"
|
||||
|
||||
#include "llfloaterscriptrecover.h"
|
||||
|
||||
// ============================================================================
|
||||
// LLFloaterScriptRecover
|
||||
//
|
||||
|
||||
LLFloaterScriptRecover::LLFloaterScriptRecover(const LLSD& sdKey)
|
||||
: LLFloater(sdKey)
|
||||
{
|
||||
}
|
||||
|
||||
void LLFloaterScriptRecover::onOpen(const LLSD& sdKey)
|
||||
{
|
||||
LLScrollListCtrl* pListCtrl = findChild<LLScrollListCtrl>("script_list");
|
||||
|
||||
LLSD sdBhvrRow; LLSD& sdBhvrColumns = sdBhvrRow["columns"];
|
||||
sdBhvrColumns[0] = LLSD().with("column", "script_check").with("type", "checkbox");
|
||||
sdBhvrColumns[1] = LLSD().with("column", "script_name").with("type", "text");
|
||||
|
||||
pListCtrl->clearRows();
|
||||
for (LLSD::array_const_iterator itFile = sdKey["files"].beginArray(), endFile = sdKey["files"].endArray();
|
||||
itFile != endFile; ++itFile)
|
||||
{
|
||||
const LLSD& sdFile = *itFile;
|
||||
|
||||
sdBhvrRow["value"] = sdFile;
|
||||
sdBhvrColumns[0]["value"] = true;
|
||||
sdBhvrColumns[1]["value"] = sdFile["name"];
|
||||
|
||||
pListCtrl->addElement(sdBhvrRow, ADD_BOTTOM);
|
||||
}
|
||||
}
|
||||
|
||||
BOOL LLFloaterScriptRecover::postBuild()
|
||||
{
|
||||
findChild<LLUICtrl>("recover_btn")->setCommitCallback(boost::bind(&LLFloaterScriptRecover::onBtnRecover, this));
|
||||
findChild<LLUICtrl>("cancel_btn")->setCommitCallback(boost::bind(&LLFloaterScriptRecover::onBtnCancel, this));
|
||||
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
void LLFloaterScriptRecover::onBtnCancel()
|
||||
{
|
||||
LLScrollListCtrl* pListCtrl = findChild<LLScrollListCtrl>("script_list");
|
||||
|
||||
// Delete all listed files
|
||||
std::vector<LLScrollListItem*> items = pListCtrl->getAllData();
|
||||
for (std::vector<LLScrollListItem*>::const_iterator itItem = items.begin(); itItem != items.end(); ++itItem)
|
||||
{
|
||||
LLFile::remove((*itItem)->getValue().asString());
|
||||
}
|
||||
|
||||
closeFloater();
|
||||
}
|
||||
|
||||
void LLFloaterScriptRecover::onBtnRecover()
|
||||
{
|
||||
LLScrollListCtrl* pListCtrl = findChild<LLScrollListCtrl>("script_list");
|
||||
|
||||
// Recover all selected, delete any unselected
|
||||
std::vector<LLScrollListItem*> items = pListCtrl->getAllData(); LLSD sdFiles;
|
||||
for (std::vector<LLScrollListItem*>::const_iterator itItem = items.begin(); itItem != items.end(); ++itItem)
|
||||
{
|
||||
LLScrollListCheck* pCheckColumn = dynamic_cast<LLScrollListCheck*>((*itItem)->getColumn(0));
|
||||
if (!pCheckColumn)
|
||||
continue;
|
||||
|
||||
const LLSD sdFile = (*itItem)->getValue();
|
||||
if (pCheckColumn->getCheckBox()->getValue().asBoolean())
|
||||
sdFiles.append(sdFile);
|
||||
else
|
||||
LLFile::remove(sdFile["path"]);
|
||||
}
|
||||
|
||||
if (!sdFiles.emptyArray())
|
||||
new LLScriptRecoverQueue(sdFiles);
|
||||
|
||||
closeFloater();
|
||||
}
|
||||
|
||||
// ============================================================================
|
||||
// LLCreateRecoverScriptCallback
|
||||
//
|
||||
|
||||
class LLCreateRecoverScriptCallback : public LLInventoryCallback
|
||||
{
|
||||
public:
|
||||
LLCreateRecoverScriptCallback(LLScriptRecoverQueue* pRecoverQueue)
|
||||
: LLInventoryCallback(), mRecoverQueue(pRecoverQueue)
|
||||
{
|
||||
}
|
||||
|
||||
void fire(const LLUUID& idItem)
|
||||
{
|
||||
mRecoverQueue->onCreateScript(idItem);
|
||||
}
|
||||
|
||||
protected:
|
||||
LLScriptRecoverQueue* mRecoverQueue;
|
||||
};
|
||||
|
||||
// ============================================================================
|
||||
// LLScriptRecoverQueue
|
||||
//
|
||||
|
||||
// static
|
||||
void LLScriptRecoverQueue::recoverIfNeeded()
|
||||
{
|
||||
const std::string strTempPath = LLFile::tmpdir();
|
||||
LLSD sdData, &sdFiles = sdData["files"];
|
||||
|
||||
LLDirIterator itFiles(strTempPath, "*.lslbackup"); std::string strFilename;
|
||||
while (itFiles.next(strFilename))
|
||||
{
|
||||
// Build a friendly name for the file
|
||||
std::string strName = gDirUtilp->getBaseFileName(strFilename, true);
|
||||
std::string::size_type offset = strName.find_last_of("-");
|
||||
if ( (std::string::npos != offset) && (offset != 0) && (offset == strName.length() - 9))
|
||||
strName.erase(strName.length() - 9);
|
||||
|
||||
LLStringUtil::trim(strName);
|
||||
if (0 == strName.length())
|
||||
strName = "(Unknown script)";
|
||||
|
||||
sdFiles.append(LLSD().with("path", strTempPath + strFilename).with("name", strName));
|
||||
}
|
||||
|
||||
if (sdFiles.size())
|
||||
LLFloaterReg::showInstance("script_recover", sdData);
|
||||
}
|
||||
|
||||
LLScriptRecoverQueue::LLScriptRecoverQueue(const LLSD& sdFiles)
|
||||
{
|
||||
for (LLSD::array_const_iterator itFile = sdFiles.beginArray(), endFile = sdFiles.endArray(); itFile != endFile; ++itFile)
|
||||
{
|
||||
const LLSD& sdFile = *itFile;
|
||||
if (LLFile::isfile(sdFile["path"]))
|
||||
m_FileQueue.insert(std::pair<std::string, LLSD>(sdFile["path"], sdFile));
|
||||
}
|
||||
recoverNext();
|
||||
}
|
||||
|
||||
bool LLScriptRecoverQueue::recoverNext()
|
||||
{
|
||||
/**
|
||||
* Steps:
|
||||
* (1) create a script inventory item under Lost and Found
|
||||
* (2) once we have the item's UUID we can upload the script
|
||||
* (3) once the script is uploaded we move on to the next item
|
||||
*/
|
||||
const LLUUID idFNF = gInventory.findCategoryUUIDForType(LLFolderType::FT_LOST_AND_FOUND);
|
||||
|
||||
// Sanity check - if the associated UUID is non-null then this file is already being processed
|
||||
filename_queue_t::const_iterator itFile = m_FileQueue.begin();
|
||||
while ( (itFile != m_FileQueue.end()) && (itFile->second.has("item")) && (itFile->second["item"].asUUID().notNull()) )
|
||||
++itFile;
|
||||
|
||||
if (m_FileQueue.end() == itFile)
|
||||
{
|
||||
LLInventoryPanel* pInvPanel = LLInventoryPanel::getActiveInventoryPanel(TRUE);
|
||||
if (pInvPanel)
|
||||
{
|
||||
LLFolderViewFolder* pFVF = dynamic_cast<LLFolderViewFolder*>(pInvPanel->getRootFolder()->getItemByID(idFNF));
|
||||
if (pFVF)
|
||||
{
|
||||
pFVF->setOpenArrangeRecursively(TRUE, LLFolderViewFolder::RECURSE_UP);
|
||||
pInvPanel->setSelection(idFNF, TRUE);
|
||||
}
|
||||
}
|
||||
|
||||
delete this;
|
||||
return false;
|
||||
}
|
||||
|
||||
std::string strItemDescr;
|
||||
LLViewerAssetType::generateDescriptionFor(LLAssetType::AT_LSL_TEXT, strItemDescr);
|
||||
|
||||
create_inventory_item(gAgent.getID(), gAgent.getSessionID(), idFNF, LLTransactionID::tnull,
|
||||
itFile->second["name"].asString(), strItemDescr, LLAssetType::AT_LSL_TEXT, LLInventoryType::IT_LSL,
|
||||
NOT_WEARABLE, PERM_MOVE | PERM_TRANSFER, new LLCreateRecoverScriptCallback(this));
|
||||
return true;
|
||||
}
|
||||
|
||||
void LLScriptRecoverQueue::onCreateScript(const LLUUID& idItem)
|
||||
{
|
||||
const LLViewerInventoryItem* pItem = gInventory.getItem(idItem);
|
||||
if (!pItem)
|
||||
{
|
||||
// TODO: error handling
|
||||
return;
|
||||
}
|
||||
|
||||
std::string strFileName;
|
||||
for (filename_queue_t::iterator itFile = m_FileQueue.begin(); itFile != m_FileQueue.end(); ++itFile)
|
||||
{
|
||||
if (itFile->second["name"].asString() != pItem->getName())
|
||||
continue;
|
||||
strFileName = itFile->second["path"];
|
||||
itFile->second["item"] = idItem;
|
||||
break;
|
||||
}
|
||||
|
||||
LLSD sdBody;
|
||||
sdBody["item_id"] = idItem;
|
||||
sdBody["target"] = "lsl2";
|
||||
|
||||
std::string strCapsUrl = gAgent.getRegion()->getCapability("UpdateScriptAgent");
|
||||
LLHTTPClient::post(strCapsUrl, sdBody,
|
||||
new LLUpdateAgentInventoryResponder(sdBody, strFileName, LLAssetType::AT_LSL_TEXT,
|
||||
boost::bind(&LLScriptRecoverQueue::onSavedScript, this, _1, _2, _3),
|
||||
boost::bind(&LLScriptRecoverQueue::onUploadError, this, _1)));
|
||||
}
|
||||
|
||||
void LLScriptRecoverQueue::onSavedScript(const LLUUID& idItem, const LLSD&, bool fSuccess)
|
||||
{
|
||||
const LLViewerInventoryItem* pItem = gInventory.getItem(idItem);
|
||||
if (pItem)
|
||||
{
|
||||
filename_queue_t::iterator itFile = m_FileQueue.begin();
|
||||
while ( (itFile != m_FileQueue.end()) && ((!itFile->second.has("item")) || (itFile->second["item"].asUUID() != idItem)) )
|
||||
++itFile;
|
||||
if (itFile != m_FileQueue.end())
|
||||
{
|
||||
LLFile::remove(itFile->first);
|
||||
m_FileQueue.erase(itFile);
|
||||
}
|
||||
}
|
||||
recoverNext();
|
||||
}
|
||||
|
||||
bool LLScriptRecoverQueue::onUploadError(const std::string& strFilename)
|
||||
{
|
||||
// Skip over the file when there's an error, we can try again on the next relog
|
||||
filename_queue_t::iterator itFile = m_FileQueue.find(strFilename);
|
||||
if (itFile != m_FileQueue.end())
|
||||
{
|
||||
LLViewerInventoryItem* pItem = gInventory.getItem(itFile->second["item"]);
|
||||
if (pItem)
|
||||
gInventory.changeItemParent(pItem, gInventory.findCategoryUUIDForType(LLFolderType::FT_TRASH), FALSE);
|
||||
m_FileQueue.erase(itFile);
|
||||
}
|
||||
recoverNext();
|
||||
return false;
|
||||
}
|
||||
|
||||
// ============================================================================
|
||||
|
|
@ -0,0 +1,75 @@
|
|||
/**
|
||||
*
|
||||
* Copyright (c) 2011-2012, Kitty Barnett
|
||||
*
|
||||
* The source code in this file is provided to you under the terms of the
|
||||
* GNU Lesser General Public License, version 2.1, but WITHOUT ANY WARRANTY;
|
||||
* without even the implied warranty of MERCHANTABILITY or FITNESS FOR A
|
||||
* PARTICULAR PURPOSE. Terms of the LGPL can be found in doc/LGPL-licence.txt
|
||||
* in this distribution, or online at http://www.gnu.org/licenses/lgpl-2.1.txt
|
||||
*
|
||||
* By copying, modifying or distributing this software, you acknowledge that
|
||||
* you have read and understood your obligations described above, and agree to
|
||||
* abide by those obligations.
|
||||
*
|
||||
*/
|
||||
|
||||
#ifndef LL_FLOATERSCRIPTRECOVER_H
|
||||
#define LL_FLOATERSCRIPTRECOVER_H
|
||||
|
||||
#include "llfloater.h"
|
||||
|
||||
// ============================================================================
|
||||
// LLFloaterScriptRecover
|
||||
//
|
||||
|
||||
class LLFloaterScriptRecover : public LLFloater
|
||||
{
|
||||
friend class LLFloaterReg;
|
||||
private:
|
||||
LLFloaterScriptRecover(const LLSD& sdKey);
|
||||
|
||||
/*
|
||||
* LLFloater overrides
|
||||
*/
|
||||
public:
|
||||
/*virtual*/ void onOpen(const LLSD& sdKey);
|
||||
/*virtual*/ BOOL postBuild();
|
||||
|
||||
/*
|
||||
* Member functions
|
||||
*/
|
||||
protected:
|
||||
void onBtnCancel();
|
||||
void onBtnRecover();
|
||||
};
|
||||
|
||||
// ============================================================================
|
||||
// LLScriptRecoverQueue
|
||||
//
|
||||
|
||||
class LLScriptRecoverQueue
|
||||
{
|
||||
friend class LLCreateRecoverScriptCallback;
|
||||
friend class LLFloaterScriptRecover;
|
||||
protected:
|
||||
LLScriptRecoverQueue(const LLSD& sdFiles);
|
||||
|
||||
public:
|
||||
static void recoverIfNeeded();
|
||||
|
||||
protected:
|
||||
bool recoverNext();
|
||||
|
||||
void onCreateScript(const LLUUID& idItem);
|
||||
void onSavedScript(const LLUUID& idItem, const LLSD& sdContent, bool fSuccess);
|
||||
bool onUploadError(const std::string& strFilename);
|
||||
|
||||
protected:
|
||||
typedef std::map<std::string, LLSD> filename_queue_t;
|
||||
filename_queue_t m_FileQueue;
|
||||
};
|
||||
|
||||
// ============================================================================
|
||||
|
||||
#endif // LL_FLOATERSCRIPTRECOVER_H
|
||||
|
|
@ -104,7 +104,10 @@ public:
|
|||
|
||||
// llview
|
||||
/*virtual*/ void draw();
|
||||
void refreshFromItem();
|
||||
// void refreshFromItem();
|
||||
// [SL:KB] - Patch: Build-ScriptRecover | Checked: 2012-02-06 (Catznip-3.2.1) | Added: Catznip-3.2.1
|
||||
virtual void refreshFromItem();
|
||||
// [/SL:KB]
|
||||
|
||||
protected:
|
||||
virtual void onCommit();
|
||||
|
|
|
|||
|
|
@ -127,6 +127,29 @@ static bool have_script_upload_cap(LLUUID& object_id)
|
|||
return object && (! object->getRegion()->getCapability("UpdateScriptTask").empty());
|
||||
}
|
||||
|
||||
// [SL:KB] - Patch: Build-ScriptRecover | Checked: 2011-11-23 (Catznip-3.2.0) | Added: Catznip-3.2.0
|
||||
#include "lleventtimer.h"
|
||||
|
||||
/// ---------------------------------------------------------------------------
|
||||
/// Timer helper class
|
||||
/// ---------------------------------------------------------------------------
|
||||
class LLCallbackTimer : public LLEventTimer
|
||||
{
|
||||
public:
|
||||
typedef boost::function<bool()> bool_func_t;
|
||||
public:
|
||||
LLCallbackTimer(F32 nPeriod, bool_func_t cb) : LLEventTimer(nPeriod), m_Callback(cb) {}
|
||||
/*virtual*/ BOOL tick() { return m_Callback(); }
|
||||
protected:
|
||||
bool_func_t m_Callback;
|
||||
};
|
||||
|
||||
inline LLEventTimer* setupCallbackTimer(F32 nPeriod, LLCallbackTimer::bool_func_t cb)
|
||||
{
|
||||
return new LLCallbackTimer(nPeriod, cb);
|
||||
}
|
||||
// [/SL:KB]
|
||||
|
||||
/// ---------------------------------------------------------------------------
|
||||
/// LLLiveLSLFile
|
||||
/// ---------------------------------------------------------------------------
|
||||
|
|
@ -1252,9 +1275,71 @@ bool LLScriptEdCore::enableLoadFromFileMenu(void* userdata)
|
|||
LLScriptEdContainer::LLScriptEdContainer(const LLSD& key)
|
||||
: LLPreview(key)
|
||||
, mScriptEd(NULL)
|
||||
// [SL:KB] - Patch: Build-ScriptRecover | Checked: 2011-11-23 (Catznip-3.2.0) | Added: Catznip-3.2.0
|
||||
, mBackupTimer(NULL)
|
||||
// [/SL:KB]
|
||||
{
|
||||
}
|
||||
|
||||
// [SL:KB] - Patch: Build-ScriptRecover | Checked: 2011-11-23 (Catznip-3.2.0) | Added: Catznip-3.2.0
|
||||
LLScriptEdContainer::~LLScriptEdContainer()
|
||||
{
|
||||
// Clean up the backup file (unless we've gotten disconnected)
|
||||
if ( (!mBackupFilename.empty()) && (gAgent.getRegion()) )
|
||||
LLFile::remove(mBackupFilename);
|
||||
delete mBackupTimer;
|
||||
}
|
||||
|
||||
void LLScriptEdContainer::refreshFromItem()
|
||||
{
|
||||
LLPreview::refreshFromItem();
|
||||
|
||||
if (!mBackupFilename.empty())
|
||||
{
|
||||
const std::string strFilename = getBackupFileName();
|
||||
if (strFilename != mBackupFilename)
|
||||
{
|
||||
LLFile::rename(mBackupFilename, strFilename);
|
||||
mBackupFilename = strFilename;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
bool LLScriptEdContainer::onBackupTimer()
|
||||
{
|
||||
if ( (mScriptEd) && (mScriptEd->hasChanged()) )
|
||||
{
|
||||
if (mBackupFilename.empty())
|
||||
mBackupFilename = getBackupFileName();
|
||||
mScriptEd->writeToFile(mBackupFilename);
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
std::string LLScriptEdContainer::getBackupFileName() const
|
||||
{
|
||||
// NOTE: this function is not guaranteed to return the same filename every time (i.e. the item name may have changed)
|
||||
std::string strFile = LLFile::tmpdir();
|
||||
|
||||
// Find the inventory item for this script
|
||||
const LLInventoryItem* pItem = getItem();
|
||||
if (pItem)
|
||||
{
|
||||
strFile += gDirUtilp->getScrubbedFileName(pItem->getName().substr(0, 32));
|
||||
strFile += "-";
|
||||
}
|
||||
|
||||
// Append a CRC of the item UUID to make the filename (hopefully) unique
|
||||
LLCRC crcUUID;
|
||||
crcUUID.update((U8*)(&mItemUUID.mData), UUID_BYTES);
|
||||
strFile += llformat("%X", crcUUID.getCRC());
|
||||
|
||||
strFile += ".lslbackup";
|
||||
|
||||
return strFile;
|
||||
}
|
||||
// [/SL:KB]
|
||||
|
||||
std::string LLScriptEdContainer::getTmpFileName()
|
||||
{
|
||||
// Take script inventory item id (within the object inventory)
|
||||
|
|
@ -1350,6 +1435,16 @@ void LLPreviewLSL::callbackLSLCompileSucceeded()
|
|||
// successful message here, since it's meaningless anyway.
|
||||
// mScriptEd->mErrorList->setCommentText(LLTrans::getString("CompileSuccessful"));
|
||||
mScriptEd->mErrorList->setCommentText(LLTrans::getString("SaveComplete"));
|
||||
|
||||
// [SL:KB] - Patch: Build-ScriptRecover | Checked: 2011-11-23 (Catznip-3.2.0) | Added: Catznip-3.2.0
|
||||
// Script was successfully saved so delete our backup copy if we have one and the editor is still pristine
|
||||
if ( (!mBackupFilename.empty()) && (!mScriptEd->hasChanged()) )
|
||||
{
|
||||
LLFile::remove(mBackupFilename);
|
||||
mBackupFilename.clear();
|
||||
}
|
||||
// [/SL:KB]
|
||||
|
||||
closeIfNeeded();
|
||||
}
|
||||
|
||||
|
|
@ -1370,6 +1465,16 @@ void LLPreviewLSL::callbackLSLCompileFailed(const LLSD& compile_errors)
|
|||
mScriptEd->mErrorList->addElement(row);
|
||||
}
|
||||
mScriptEd->selectFirstError();
|
||||
|
||||
// [SL:KB] - Patch: Build-ScriptRecover | Checked: 2011-11-23 (Catznip-3.2.0) | Added: Catznip-3.2.0
|
||||
// Script was successfully saved so delete our backup copy if we have one and the editor is still pristine
|
||||
if ( (!mBackupFilename.empty()) && (!mScriptEd->hasChanged()) )
|
||||
{
|
||||
LLFile::remove(mBackupFilename);
|
||||
mBackupFilename.clear();
|
||||
}
|
||||
// [/SL:KB]
|
||||
|
||||
closeIfNeeded();
|
||||
}
|
||||
|
||||
|
|
@ -1475,7 +1580,10 @@ void LLPreviewLSL::onSave(void* userdata, BOOL close_after_save)
|
|||
void LLPreviewLSL::saveIfNeeded(bool sync /*= true*/)
|
||||
{
|
||||
// llinfos << "LLPreviewLSL::saveIfNeeded()" << llendl;
|
||||
if(!mScriptEd->hasChanged())
|
||||
// if(!mScriptEd->hasChanged())
|
||||
// [SL:KB] - Patch: Build-ScriptRecover | Checked: 2012-02-10 (Catznip-3.2.1) | Added: Catznip-3.2.1
|
||||
if ( (!mScriptEd->hasChanged()) || (!gAgent.getRegion()) )
|
||||
// [/SL:KB]
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
|
@ -1764,6 +1872,11 @@ void LLPreviewLSL::onLoadComplete( LLVFS *vfs, const LLUUID& asset_uuid, LLAsset
|
|||
}
|
||||
preview->mScriptEd->setEnableEditing(is_modifiable);
|
||||
preview->mAssetStatus = PREVIEW_ASSET_LOADED;
|
||||
|
||||
// [SL:KB] - Patch: Build-ScriptRecover | Checked: 2011-11-23 (Catznip-3.2.0) | Added: Catznip-3.2.0
|
||||
// Start the timer which will perform regular backup saves
|
||||
preview->mBackupTimer = setupCallbackTimer(60.0f, boost::bind(&LLPreviewLSL::onBackupTimer, preview));
|
||||
// [/SL:KB]
|
||||
}
|
||||
else
|
||||
{
|
||||
|
|
@ -1854,6 +1967,16 @@ void LLLiveLSLEditor::callbackLSLCompileSucceeded(const LLUUID& task_id,
|
|||
lldebugs << "LSL Bytecode saved" << llendl;
|
||||
mScriptEd->mErrorList->setCommentText(LLTrans::getString("CompileSuccessful"));
|
||||
mScriptEd->mErrorList->setCommentText(LLTrans::getString("SaveComplete"));
|
||||
|
||||
// [SL:KB] - Patch: Build-ScriptRecover | Checked: 2011-11-23 (Catznip-3.2.0) | Added: Catznip-3.2.0
|
||||
// Script was successfully saved so delete our backup copy if we have one and the editor is still pristine
|
||||
if ( (!mBackupFilename.empty()) && (!mScriptEd->hasChanged()) )
|
||||
{
|
||||
LLFile::remove(mBackupFilename);
|
||||
mBackupFilename.clear();
|
||||
}
|
||||
// [/SL:KB]
|
||||
|
||||
closeIfNeeded();
|
||||
}
|
||||
|
||||
|
|
@ -1874,6 +1997,16 @@ void LLLiveLSLEditor::callbackLSLCompileFailed(const LLSD& compile_errors)
|
|||
mScriptEd->mErrorList->addElement(row);
|
||||
}
|
||||
mScriptEd->selectFirstError();
|
||||
|
||||
// [SL:KB] - Patch: Build-ScriptRecover | Checked: 2011-11-23 (Catznip-3.2.0) | Added: Catznip-3.2.0
|
||||
// Script was successfully saved so delete our backup copy if we have one and the editor is still pristine
|
||||
if ( (!mBackupFilename.empty()) && (!mScriptEd->hasChanged()) )
|
||||
{
|
||||
LLFile::remove(mBackupFilename);
|
||||
mBackupFilename.clear();
|
||||
}
|
||||
// [/SL:KB]
|
||||
|
||||
closeIfNeeded();
|
||||
}
|
||||
|
||||
|
|
@ -1996,6 +2129,11 @@ void LLLiveLSLEditor::onLoadComplete(LLVFS *vfs, const LLUUID& asset_id,
|
|||
instance->loadScriptText(vfs, asset_id, type);
|
||||
instance->mScriptEd->setEnableEditing(TRUE);
|
||||
instance->mAssetStatus = PREVIEW_ASSET_LOADED;
|
||||
|
||||
// [SL:KB] - Patch: Build-ScriptRecover | Checked: 2011-11-23 (Catznip-3.2.0) | Added: Catznip-3.2.0
|
||||
// Start the timer which will perform regular backup saves
|
||||
instance->mBackupTimer = setupCallbackTimer(60.0f, boost::bind(&LLLiveLSLEditor::onBackupTimer, instance));
|
||||
// [/SL:KB]
|
||||
}
|
||||
else
|
||||
{
|
||||
|
|
|
|||
|
|
@ -49,6 +49,9 @@ class LLKeywordToken;
|
|||
class LLVFS;
|
||||
class LLViewerInventoryItem;
|
||||
class LLScriptEdContainer;
|
||||
// [SL:KB] - Patch: Build-ScriptRecover | Checked: 2011-11-23 (Catznip-3.2.0)
|
||||
class LLEventTimer;
|
||||
// [/SL:KB]
|
||||
// NaCl - LSL Preprocessor
|
||||
class FSLSLPreprocessor;
|
||||
// NaCl End
|
||||
|
|
@ -176,13 +179,27 @@ class LLScriptEdContainer : public LLPreview
|
|||
|
||||
public:
|
||||
LLScriptEdContainer(const LLSD& key);
|
||||
// [SL:KB] - Patch: Build-ScriptRecover | Checked: 2011-11-23 (Catznip-3.2.0) | Added: Catznip-3.2.0
|
||||
/*virtual*/ ~LLScriptEdContainer();
|
||||
|
||||
/*virtual*/ void refreshFromItem();
|
||||
// [/SL:KB]
|
||||
|
||||
protected:
|
||||
std::string getTmpFileName();
|
||||
// [SL:KB] - Patch: Build-ScriptRecover | Checked: 2011-11-23 (Catznip-3.2.0) | Added: Catznip-3.2.0
|
||||
virtual std::string getBackupFileName() const;
|
||||
bool onBackupTimer();
|
||||
// [/SL:KB]
|
||||
|
||||
bool onExternalChange(const std::string& filename);
|
||||
virtual void saveIfNeeded(bool sync = true) = 0;
|
||||
|
||||
LLScriptEdCore* mScriptEd;
|
||||
// [SL:KB] - Patch: Build-ScriptRecover | Checked: 2011-11-23 (Catznip-3.2.0) | Added: Catznip-3.2.0
|
||||
std::string mBackupFilename;
|
||||
LLEventTimer* mBackupTimer;
|
||||
// [/SL:KB]
|
||||
};
|
||||
|
||||
// Used to view and edit a LSL from your inventory.
|
||||
|
|
|
|||
|
|
@ -96,6 +96,9 @@
|
|||
#include "llfloaterreporter.h"
|
||||
#include "llfloaterscriptdebug.h"
|
||||
#include "llfloaterscriptlimits.h"
|
||||
// [SL:KB] - Patch: Build-ScriptRecover | Checked: 2011-11-24 (Catznip-3.2.0)
|
||||
#include "llfloaterscriptrecover.h"
|
||||
// [/SL:KB]
|
||||
#include "llfloatersearch.h"
|
||||
#include "llfloatersellland.h"
|
||||
#include "llfloatersettingsdebug.h"
|
||||
|
|
@ -345,6 +348,9 @@ void LLViewerFloaterReg::registerFloaters()
|
|||
LLFloaterReg::add("script_debug_output", "floater_script_debug_panel.xml", (LLFloaterBuildFunc)&LLFloaterReg::build<LLFloaterScriptDebugOutput>);
|
||||
LLFloaterReg::add("script_floater", "floater_script.xml", (LLFloaterBuildFunc)&LLFloaterReg::build<LLScriptFloater>);
|
||||
LLFloaterReg::add("script_limits", "floater_script_limits.xml", (LLFloaterBuildFunc)&LLFloaterReg::build<LLFloaterScriptLimits>);
|
||||
// [SL:KB] - Patch: Build-ScriptRecover | Checked: 2011-11-24 (Catznip-3.2.0) | Added: Catznip-3.2.0
|
||||
LLFloaterReg::add("script_recover", "floater_script_recover.xml", (LLFloaterBuildFunc)&LLFloaterReg::build<LLFloaterScriptRecover>);
|
||||
// [/SL:KB]
|
||||
LLFloaterReg::add("sell_land", "floater_sell_land.xml", &LLFloaterSellLand::buildFloater);
|
||||
LLFloaterReg::add("settings_debug", "floater_settings_debug.xml", (LLFloaterBuildFunc)&LLFloaterReg::build<LLFloaterSettingsDebug>);
|
||||
LLFloaterReg::add("sound_devices", "floater_sound_devices.xml", (LLFloaterBuildFunc)&LLFloaterReg::build<LLFloaterSoundDevices>);
|
||||
|
|
|
|||
|
|
@ -0,0 +1,67 @@
|
|||
<?xml version="1.0" encoding="utf-8" standalone="yes" ?>
|
||||
<floater
|
||||
can_close="false"
|
||||
can_minimize="false"
|
||||
can_resize="false"
|
||||
height="275"
|
||||
open_positioning="centered"
|
||||
name="script_recover"
|
||||
single_instance="true"
|
||||
title="Script Recovery"
|
||||
width="350">
|
||||
|
||||
<text
|
||||
follows="top|left|right"
|
||||
height="48"
|
||||
layout="topleft"
|
||||
left="15"
|
||||
length="1"
|
||||
name="txt2"
|
||||
top="10"
|
||||
type="string"
|
||||
word_wrap="true"
|
||||
width="330">
|
||||
[APP_NAME] has detected recoverable scripts that may have been left over from a recent viewer crash.
|
||||
|
||||
If you choose to recover these scripts they will be placed in the 'Lost and Found' folder of your inventory.
|
||||
</text>
|
||||
|
||||
<scroll_list
|
||||
draw_border="false"
|
||||
draw_heading="true"
|
||||
draw_stripes="true"
|
||||
follows="all"
|
||||
height="150"
|
||||
layout="topleft"
|
||||
left="10"
|
||||
multi_select="false"
|
||||
name="script_list"
|
||||
top_pad="20"
|
||||
width="330">
|
||||
<scroll_list.columns
|
||||
label=""
|
||||
name="script_check"
|
||||
width="20" />
|
||||
<scroll_list.columns
|
||||
label="Script Name"
|
||||
name="script_name"
|
||||
width="170" />
|
||||
</scroll_list>
|
||||
|
||||
<button
|
||||
follows="bottom|left"
|
||||
height="25"
|
||||
label="Recover"
|
||||
left="65"
|
||||
name="recover_btn"
|
||||
top_pad="10"
|
||||
width="100" />
|
||||
<button
|
||||
follows="bottom|left"
|
||||
height="25"
|
||||
label="Cancel"
|
||||
left_pad="20"
|
||||
name="cancel_btn"
|
||||
width="100" />
|
||||
|
||||
</floater>
|
||||
Loading…
Reference in New Issue