зеркало из https://github.com/mozilla/pjs.git
fix for #67088. sr=bienvenu.
1) on batch deletes, we quickly bail out of ThreadPaneSelectionChange() 2) we only call document.commandDispatcher.updateCommands('threadTree-select'); once per delete, next, move, selection, folder loading. 3) general cleanup
This commit is contained in:
Родитель
1e8b232691
Коммит
6909a8b42a
|
@ -30,7 +30,7 @@ var gBeforeFolderLoadTime;
|
|||
var gRDFNamespace = "http://www.w3.org/1999/02/22-rdf-syntax-ns#";
|
||||
function OpenURL(url)
|
||||
{
|
||||
dump("\n\nOpenURL from XUL\n\n\n");
|
||||
//dump("\n\nOpenURL from XUL\n\n\n");
|
||||
messenger.SetWindow(window, msgWindow);
|
||||
messenger.OpenURL(url);
|
||||
}
|
||||
|
@ -61,10 +61,7 @@ function GetMsgFolderFromURI(folderURI)
|
|||
function LoadMessage(messageNode)
|
||||
{
|
||||
var uri = messageNode.getAttribute('id');
|
||||
dump(uri + "\n");
|
||||
|
||||
LoadMessageByUri(uri);
|
||||
|
||||
}
|
||||
|
||||
function LoadMessageByUri(uri)
|
||||
|
@ -759,8 +756,9 @@ function LoadSelectionIntoMessagePane()
|
|||
var tree = GetThreadTree();
|
||||
|
||||
var selArray = tree.selectedItems;
|
||||
if (!gNextMessageAfterDelete && selArray && (selArray.length == 1) )
|
||||
if (!gNextMessageAfterDelete && selArray && (selArray.length == 1) ) {
|
||||
LoadMessage(selArray[0]);
|
||||
}
|
||||
else
|
||||
{
|
||||
// don't necessarily clear the message pane...if you uncomment this,
|
||||
|
@ -957,7 +955,6 @@ function SelectNextMessage(nextMessage)
|
|||
{
|
||||
var tree = GetThreadTree();
|
||||
ChangeSelection(tree, nextMessage);
|
||||
|
||||
}
|
||||
|
||||
function GetSelectTrashUri(folder)
|
||||
|
|
|
@ -309,7 +309,7 @@ function MsgDeleteMessage(reallyDelete, fromToolbar)
|
|||
var compositeDataSource = GetCompositeDataSource("DeleteMessages");
|
||||
var messages = GetSelectedMessages();
|
||||
|
||||
SetNextMessageAfterDelete(null, true);
|
||||
SetNextMessageAfterDelete();
|
||||
DeleteMessages(compositeDataSource, srcFolder, messages, reallyDelete);
|
||||
}
|
||||
|
||||
|
@ -351,8 +351,7 @@ function MsgMoveMessage(destFolder)
|
|||
}
|
||||
else
|
||||
{
|
||||
SetNextMessageAfterDelete(null, true);
|
||||
|
||||
SetNextMessageAfterDelete();
|
||||
CopyMessages(compositeDataSource, srcFolder, destMsgFolder, messages, true);
|
||||
}
|
||||
}
|
||||
|
|
|
@ -324,10 +324,7 @@ function GetCompositeDataSource(command)
|
|||
return gCompositeDataSource;
|
||||
}
|
||||
|
||||
//Sets the next message after a delete. If useSelection is true then use the
|
||||
//current selection to determine this. Otherwise use messagesToCheck which will
|
||||
//be an array of nsIMessage's.
|
||||
function SetNextMessageAfterDelete(messagesToCheck, useSelection)
|
||||
function SetNextMessageAfterDelete()
|
||||
{
|
||||
gCurrentMessageIsDeleted = true;
|
||||
}
|
||||
|
|
|
@ -291,7 +291,7 @@ function DropOnFolderTree(event)
|
|||
messageTree = GetThreadTree();
|
||||
nextMessage = GetNextMessageAfterDelete(messageTree.selectedItems);
|
||||
if(nextMessage)
|
||||
gNextMessageAfterDelete = nextMessage.getAttribute('id');
|
||||
gNextMessageAfterDelete = nextMessage.getAttribute('id');
|
||||
else
|
||||
gNextMessageAfterDelete = null;
|
||||
}
|
||||
|
|
|
@ -49,6 +49,8 @@ var gStartFolderUri = null;
|
|||
//If we've loaded a message, set to true. Helps us keep the start page around.
|
||||
var gHaveLoadedMessage;
|
||||
|
||||
var gBatching = false;
|
||||
|
||||
// the folderListener object
|
||||
var folderListener = {
|
||||
OnItemAdded: function(parentItem, item, view) {},
|
||||
|
@ -95,7 +97,9 @@ var folderListener = {
|
|||
OnItemPropertyFlagChanged: function(item, property, oldFlag, newFlag) {},
|
||||
|
||||
OnItemEvent: function(folder, event) {
|
||||
if (event.GetUnicode() == "FolderLoaded") {
|
||||
var eventType = event.GetUnicode();
|
||||
|
||||
if (eventType == "FolderLoaded") {
|
||||
|
||||
if(folder)
|
||||
{
|
||||
|
@ -155,10 +159,10 @@ var folderListener = {
|
|||
}
|
||||
|
||||
}
|
||||
} else if (event.GetUnicode() == "DeleteOrMoveMsgCompleted") {
|
||||
} else if (eventType == "DeleteOrMoveMsgCompleted") {
|
||||
HandleDeleteOrMoveMsgCompleted(folder);
|
||||
}
|
||||
else if (event.GetUnicode() == "DeleteOrMoveMsgFailed") {
|
||||
else if (eventType == "DeleteOrMoveMsgFailed") {
|
||||
HandleDeleteOrMoveMsgFailed(folder);
|
||||
}
|
||||
|
||||
|
@ -167,30 +171,35 @@ var folderListener = {
|
|||
|
||||
function HandleDeleteOrMoveMsgFailed(folder)
|
||||
{
|
||||
if(IsCurrentLoadedFolder(folder)) {
|
||||
if(gNextMessageAfterDelete) {
|
||||
gNextMessageAfterDelete = null;
|
||||
}
|
||||
}
|
||||
|
||||
if(IsCurrentLoadedFolder(folder))
|
||||
{
|
||||
if(gNextMessageAfterDelete)
|
||||
{
|
||||
gNextMessageAfterDelete = null;
|
||||
}
|
||||
}
|
||||
if (gBatching) {
|
||||
gBatching = false;
|
||||
var threadTree = GetThreadTree();
|
||||
//threadTree.treeBoxObject.endBatch();
|
||||
dump("XXX end tree batch (delete or move failed)\n");
|
||||
}
|
||||
|
||||
ThreadPaneSelectionChange(true);
|
||||
}
|
||||
|
||||
|
||||
function HandleDeleteOrMoveMsgCompleted(folder)
|
||||
{
|
||||
var threadTree = GetThreadTree();
|
||||
|
||||
if(IsCurrentLoadedFolder(folder))
|
||||
{
|
||||
msgNavigationService.EnsureDocumentIsLoaded(document);
|
||||
if(gNextMessageAfterDelete)
|
||||
{
|
||||
var nextMessage = document.getElementById(gNextMessageAfterDelete);
|
||||
var nextMessage = document.getElementById(gNextMessageAfterDelete);
|
||||
gNextMessageAfterDelete = null;
|
||||
SelectNextMessage(nextMessage);
|
||||
var threadTree = GetThreadTree();
|
||||
if(threadTree)
|
||||
threadTree.ensureElementIsVisible(nextMessage);
|
||||
}
|
||||
|
@ -205,6 +214,13 @@ function HandleDeleteOrMoveMsgCompleted(folder)
|
|||
}
|
||||
}
|
||||
|
||||
if (gBatching) {
|
||||
gBatching = false;
|
||||
//threadTree.treeBoxObject.endBatch();
|
||||
dump("XXX end tree batch (delete or move succeeded)\n");
|
||||
}
|
||||
|
||||
ThreadPaneSelectionChange(true);
|
||||
}
|
||||
|
||||
|
||||
|
@ -229,6 +245,7 @@ function IsCurrentLoadedFolder(folder)
|
|||
/* Functions related to startup */
|
||||
function OnLoadMessenger()
|
||||
{
|
||||
showPerformance = pref.GetBoolPref('mail.showMessengerPerformance');
|
||||
var beforeLoadMessenger;
|
||||
if(showPerformance) {
|
||||
beforeLoadMessenger = new Date();
|
||||
|
@ -324,11 +341,8 @@ function OnUnloadMessenger()
|
|||
|
||||
function Create3PaneGlobals()
|
||||
{
|
||||
showPerformance = pref.GetBoolPref('mail.showMessengerPerformance');
|
||||
|
||||
msgNavigationService = Components.classes['@mozilla.org/messenger/msgviewnavigationservice;1'].getService();
|
||||
msgNavigationService= msgNavigationService.QueryInterface(Components.interfaces.nsIMsgViewNavigationService);
|
||||
|
||||
}
|
||||
|
||||
|
||||
|
@ -938,20 +952,22 @@ function GetCompositeDataSource(command)
|
|||
|
||||
}
|
||||
|
||||
//Sets the next message after a delete. If useSelection is true then use the
|
||||
//current selection to determine this. Otherwise use messagesToCheck which will
|
||||
//be an array of nsIMessage's.
|
||||
function SetNextMessageAfterDelete(messagesToCheck, useSelection)
|
||||
function SetNextMessageAfterDelete()
|
||||
{
|
||||
if(useSelection)
|
||||
{
|
||||
var tree = GetThreadTree();
|
||||
var nextMessage = GetNextMessageAfterDelete(tree.selectedItems);
|
||||
if(nextMessage)
|
||||
gNextMessageAfterDelete = nextMessage.getAttribute('id');
|
||||
else
|
||||
gNextMessageAfterDelete = null;
|
||||
}
|
||||
var tree = GetThreadTree();
|
||||
|
||||
var nextMessage = GetNextMessageAfterDelete(tree.selectedItems);
|
||||
if(nextMessage)
|
||||
gNextMessageAfterDelete = nextMessage.getAttribute('id');
|
||||
else
|
||||
gNextMessageAfterDelete = null;
|
||||
|
||||
// use the magic number of 3 to determine if we want to batch or not.
|
||||
if (!gBatching && (GetNumSelectedMessages() > 3)) {
|
||||
gBatching = true;
|
||||
//tree.treeBoxObject.beginBatch();
|
||||
dump("XXX begin tree batch\n");
|
||||
}
|
||||
}
|
||||
|
||||
function SelectFolder(folderUri)
|
||||
|
@ -964,7 +980,6 @@ function SelectFolder(folderUri)
|
|||
|
||||
function SelectMessage(messageUri)
|
||||
{
|
||||
dump("SelectMessage: " + messageUri + "\n");
|
||||
var tree = GetThreadTree();
|
||||
var treeitem = document.getElementById(messageUri);
|
||||
if(tree && treeitem)
|
||||
|
|
|
@ -197,7 +197,6 @@ function GoPreviousMessage(type, startFromEnd)
|
|||
// gotoNextInThread is true if once we find an unrad thread we should select the first message in that thread that fits criteria
|
||||
function GoNextThread(type, startFromBeginning, gotoNextInThread)
|
||||
{
|
||||
|
||||
if(messageView.showThreads)
|
||||
{
|
||||
var tree = GetThreadTree();
|
||||
|
|
|
@ -18,7 +18,8 @@
|
|||
* Rights Reserved.
|
||||
*/
|
||||
|
||||
var gOldNumSelected = 0;
|
||||
var gLastMessageUriToLoad = null;
|
||||
|
||||
function ThreadPaneOnClick(event)
|
||||
{
|
||||
var t = event.originalTarget;
|
||||
|
@ -223,29 +224,51 @@ function IsSpecialFolderSelected(folderName)
|
|||
}
|
||||
|
||||
//Called when selection changes in the thread pane.
|
||||
function ThreadPaneSelectionChange()
|
||||
function ThreadPaneSelectionChange(fromDeleteOrMoveHandler)
|
||||
{
|
||||
// we are batching. bail out, we'll be back when the batch is over
|
||||
if (gBatching) return;
|
||||
|
||||
var collapsed = IsThreadAndMessagePaneSplitterCollapsed();
|
||||
|
||||
if(!collapsed)
|
||||
{
|
||||
LoadSelectionIntoMessagePane();
|
||||
|
||||
}
|
||||
|
||||
var tree = GetThreadTree();
|
||||
var tree = GetThreadTree();
|
||||
var selectedMessages = tree.selectedItems;
|
||||
var numSelected = selectedMessages.length;
|
||||
//If the current selected is 1 or 0 then we know that a change has taken place that might
|
||||
//cause us to send out threadTree update notifications. We also care about this if the previous
|
||||
//numSelected was 0 or 1 because we might be involved in something like a SelectAll where we won't
|
||||
//get notified about the change from 0 to 1.
|
||||
if(numSelected == 0 || numSelected == 1 || gOldNumSelected == 0 || gOldNumSelected == 1)
|
||||
{
|
||||
document.commandDispatcher.updateCommands('threadTree-select');
|
||||
var messageUriToLoad = null;
|
||||
|
||||
if (!gNextMessageAfterDelete && selectedMessages && (numSelected == 1) ) {
|
||||
messageUriToLoad = selectedMessages[0].getAttribute('id');
|
||||
}
|
||||
|
||||
// if the message pane isn't collapsed, and we have a message to load
|
||||
// go ahead and load the message
|
||||
if (!collapsed && messageUriToLoad) {
|
||||
LoadMessageByUri(messageUriToLoad);
|
||||
}
|
||||
//Store the current number selected.
|
||||
gOldNumSelected = numSelected;
|
||||
|
||||
// if gNextMessageAfterDelete is true, we can skip updating the commands because
|
||||
// we'll be coming back to load that message, and we'll update the commands then
|
||||
//
|
||||
// if fromDeleteOrMoveHandler is true, we are calling ThreadPaneSelectionChange after handling
|
||||
// a message delete or message move, so we might need to update the commands. (see below)
|
||||
//
|
||||
// if gCurrentLoadingFolderURI is non null, we are loading a folder, so we need to update the commands
|
||||
//
|
||||
// if messageUriToLoad is non null, we are loading a message, so we might need to update commmands. (see below)
|
||||
if (!gNextMessageAfterDelete && (gCurrentLoadingFolderURI || fromDeleteOrMoveHandler || messageUriToLoad)) {
|
||||
// if we are moving or deleting, we'll come in here twice. once to load the message and once when
|
||||
// we are done moving or deleting. when we loaded the message the first time, we called updateCommands().
|
||||
// there is no need to do it again.
|
||||
if (fromDeleteOrMoveHandler && messageUriToLoad && (messageUriToLoad == gLastMessageUriToLoad)) {
|
||||
// skip the call to updateCommands()
|
||||
}
|
||||
else {
|
||||
document.commandDispatcher.updateCommands('threadTree-select');
|
||||
}
|
||||
}
|
||||
|
||||
//remember the last message we loaded
|
||||
gLastMessageUriToLoad = messageUriToLoad;
|
||||
}
|
||||
|
||||
function GetThreadTree()
|
||||
|
|
|
@ -36,7 +36,7 @@ Rights Reserved.
|
|||
onclick="ThreadPaneOnClick(event);"
|
||||
ondraggesture="return BeginDragThreadTree(event);"
|
||||
ondragdrop="return DropOnThreadTree(event);"
|
||||
onselect="top.ThreadPaneSelectionChange();"
|
||||
onselect="top.ThreadPaneSelectionChange(false);"
|
||||
onkeypress="ThreadPaneKeyPress(event);"
|
||||
onblur="goOnEvent(this,'blur')"
|
||||
containment="http://home.netscape.com/NC-rdf#MessageChild"
|
||||
|
|
Загрузка…
Ссылка в новой задаче