Bug 1137009 part 1 - Always save dirty window attributes but do not persist them in nsXULWindow::SavePersistentAttributes() directly. r=enndeakin

The attributes should eventually be saved via the AttributeChanged callback in
XULDocument if one is specified in the "persist" attribute.
This commit is contained in:
Xidorn Quan 2015-09-24 11:39:22 +10:00
parent d937c3176e
commit 0f79e48404
3 changed files with 44 additions and 76 deletions

View File

@ -419,8 +419,8 @@ nsWebShellWindow::WindowActivated()
fm->WindowRaised(window);
if (mChromeLoaded) {
PersistentAttributesDirty(PAD_POSITION | PAD_SIZE | PAD_MISC);
SavePersistentAttributes();
SetAttributesDirty(PAD_POSITION | PAD_SIZE | PAD_MISC);
SaveAttributes();
}
}
@ -512,14 +512,14 @@ nsWebShellWindow::SetPersistenceTimer(uint32_t aDirtyFlags)
mSPTimer->InitWithCallback(callback, SIZE_PERSISTENCE_TIMEOUT,
nsITimer::TYPE_ONE_SHOT);
PersistentAttributesDirty(aDirtyFlags);
SetAttributesDirty(aDirtyFlags);
}
void
nsWebShellWindow::FirePersistenceTimer()
{
MutexAutoLock lock(mSPTimerLock);
SavePersistentAttributes();
SaveAttributes();
}
@ -772,7 +772,7 @@ NS_IMETHODIMP nsWebShellWindow::Destroy()
MutexAutoLock lock(mSPTimerLock);
if (mSPTimer) {
mSPTimer->Cancel();
SavePersistentAttributes();
SaveAttributes();
mSPTimer = nullptr;
}
}

View File

@ -222,8 +222,8 @@ NS_IMETHODIMP nsXULWindow::SetZLevel(uint32_t aLevel)
// do it
mediator->SetZLevel(this, aLevel);
PersistentAttributesDirty(PAD_MISC);
SavePersistentAttributes();
SetAttributesDirty(PAD_MISC);
SaveAttributes();
nsCOMPtr<nsIContentViewer> cv;
mDocShell->GetContentViewer(getter_AddRefs(cv));
@ -546,8 +546,8 @@ NS_IMETHODIMP nsXULWindow::SetPosition(int32_t aX, int32_t aY)
mIgnoreXULPosition = true;
return NS_OK;
}
PersistentAttributesDirty(PAD_POSITION);
SavePersistentAttributes();
SetAttributesDirty(PAD_POSITION);
SaveAttributes();
return NS_OK;
}
@ -578,8 +578,8 @@ NS_IMETHODIMP nsXULWindow::SetSize(int32_t aCX, int32_t aCY, bool aRepaint)
mIgnoreXULSizeMode = true;
return NS_OK;
}
PersistentAttributesDirty(PAD_SIZE);
SavePersistentAttributes();
SetAttributesDirty(PAD_SIZE);
SaveAttributes();
return NS_OK;
}
@ -612,8 +612,8 @@ NS_IMETHODIMP nsXULWindow::SetPositionAndSize(int32_t aX, int32_t aY,
mIgnoreXULSizeMode = true;
return NS_OK;
}
PersistentAttributesDirty(PAD_POSITION | PAD_SIZE);
SavePersistentAttributes();
SetAttributesDirty(PAD_POSITION | PAD_SIZE);
SaveAttributes();
return NS_OK;
}
@ -1429,22 +1429,17 @@ void nsXULWindow::SyncAttributesToWidget()
}
}
NS_IMETHODIMP nsXULWindow::SavePersistentAttributes()
void nsXULWindow::SaveAttributes()
{
// can happen when the persistence timer fires at an inopportune time
// during window shutdown
if (!mDocShell)
return NS_ERROR_FAILURE;
if (!mDocShell) {
return;
}
nsCOMPtr<dom::Element> docShellElement = GetWindowDOMElement();
if (!docShellElement)
return NS_ERROR_FAILURE;
nsAutoString persistString;
docShellElement->GetAttribute(PERSIST_ATTRIBUTE, persistString);
if (persistString.IsEmpty()) { // quick check which sometimes helps
mPersistentAttributesDirty = 0;
return NS_OK;
if (!docShellElement) {
return;
}
// get our size, position and mode to persist
@ -1465,49 +1460,27 @@ NS_IMETHODIMP nsXULWindow::SavePersistentAttributes()
char sizeBuf[10];
nsAutoString sizeString;
nsAutoString windowElementId;
nsCOMPtr<nsIDOMXULDocument> ownerXULDoc;
// fetch docShellElement's ID and XUL owner document
ownerXULDoc = do_QueryInterface(docShellElement->OwnerDoc());
if (docShellElement->IsXULElement()) {
docShellElement->GetId(windowElementId);
}
ErrorResult rv;
// (only for size elements which are persisted)
if ((mPersistentAttributesDirty & PAD_POSITION) && gotRestoredBounds) {
if (persistString.Find("screenX") >= 0) {
PR_snprintf(sizeBuf, sizeof(sizeBuf), "%d", NSToIntRound(rect.x / scale.scale));
sizeString.AssignWithConversion(sizeBuf);
docShellElement->SetAttribute(SCREENX_ATTRIBUTE, sizeString, rv);
if (ownerXULDoc) // force persistence in case the value didn't change
ownerXULDoc->Persist(windowElementId, SCREENX_ATTRIBUTE);
}
if (persistString.Find("screenY") >= 0) {
PR_snprintf(sizeBuf, sizeof(sizeBuf), "%d", NSToIntRound(rect.y / scale.scale));
sizeString.AssignWithConversion(sizeBuf);
docShellElement->SetAttribute(SCREENY_ATTRIBUTE, sizeString, rv);
if (ownerXULDoc)
ownerXULDoc->Persist(windowElementId, SCREENY_ATTRIBUTE);
}
PR_snprintf(sizeBuf, sizeof(sizeBuf), "%d", NSToIntRound(rect.x / scale.scale));
sizeString.AssignWithConversion(sizeBuf);
docShellElement->SetAttribute(SCREENX_ATTRIBUTE, sizeString, rv);
PR_snprintf(sizeBuf, sizeof(sizeBuf), "%d", NSToIntRound(rect.y / scale.scale));
sizeString.AssignWithConversion(sizeBuf);
docShellElement->SetAttribute(SCREENY_ATTRIBUTE, sizeString, rv);
}
if ((mPersistentAttributesDirty & PAD_SIZE) && gotRestoredBounds) {
if (persistString.Find("width") >= 0) {
PR_snprintf(sizeBuf, sizeof(sizeBuf), "%d", NSToIntRound(rect.width / scale.scale));
sizeString.AssignWithConversion(sizeBuf);
docShellElement->SetAttribute(WIDTH_ATTRIBUTE, sizeString, rv);
if (ownerXULDoc)
ownerXULDoc->Persist(windowElementId, WIDTH_ATTRIBUTE);
}
if (persistString.Find("height") >= 0) {
PR_snprintf(sizeBuf, sizeof(sizeBuf), "%d", NSToIntRound(rect.height / scale.scale));
sizeString.AssignWithConversion(sizeBuf);
docShellElement->SetAttribute(HEIGHT_ATTRIBUTE, sizeString, rv);
if (ownerXULDoc)
ownerXULDoc->Persist(windowElementId, HEIGHT_ATTRIBUTE);
}
PR_snprintf(sizeBuf, sizeof(sizeBuf), "%d", NSToIntRound(rect.width / scale.scale));
sizeString.AssignWithConversion(sizeBuf);
docShellElement->SetAttribute(WIDTH_ATTRIBUTE, sizeString, rv);
PR_snprintf(sizeBuf, sizeof(sizeBuf), "%d", NSToIntRound(rect.height / scale.scale));
sizeString.AssignWithConversion(sizeBuf);
docShellElement->SetAttribute(HEIGHT_ATTRIBUTE, sizeString, rv);
}
if (mPersistentAttributesDirty & PAD_MISC) {
@ -1521,24 +1494,19 @@ NS_IMETHODIMP nsXULWindow::SavePersistentAttributes()
else
sizeString.Assign(SIZEMODE_NORMAL);
docShellElement->SetAttribute(MODE_ATTRIBUTE, sizeString, rv);
if (ownerXULDoc && persistString.Find("sizemode") >= 0)
ownerXULDoc->Persist(windowElementId, MODE_ATTRIBUTE);
}
if (persistString.Find("zlevel") >= 0) {
uint32_t zLevel;
nsCOMPtr<nsIWindowMediator> mediator(do_GetService(NS_WINDOWMEDIATOR_CONTRACTID));
if (mediator) {
mediator->GetZLevel(this, &zLevel);
PR_snprintf(sizeBuf, sizeof(sizeBuf), "%lu", (unsigned long)zLevel);
sizeString.AssignWithConversion(sizeBuf);
docShellElement->SetAttribute(ZLEVEL_ATTRIBUTE, sizeString, rv);
ownerXULDoc->Persist(windowElementId, ZLEVEL_ATTRIBUTE);
}
uint32_t zLevel;
nsCOMPtr<nsIWindowMediator> mediator(do_GetService(NS_WINDOWMEDIATOR_CONTRACTID));
if (mediator) {
mediator->GetZLevel(this, &zLevel);
PR_snprintf(sizeBuf, sizeof(sizeBuf), "%lu", (unsigned long)zLevel);
sizeString.AssignWithConversion(sizeBuf);
docShellElement->SetAttribute(ZLEVEL_ATTRIBUTE, sizeString, rv);
}
}
mPersistentAttributesDirty = 0;
return NS_OK;
}
NS_IMETHODIMP nsXULWindow::GetWindowDOMWindow(nsIDOMWindow** aDOMWindow)
@ -2008,7 +1976,7 @@ bool nsXULWindow::GetContentScrollbarVisibility()
}
// during spinup, attributes that haven't been loaded yet can't be dirty
void nsXULWindow::PersistentAttributesDirty(uint32_t aDirtyFlags)
void nsXULWindow::SetAttributesDirty(uint32_t aDirtyFlags)
{
mPersistentAttributesDirty |= aDirtyFlags & mPersistentAttributesMask;
}

View File

@ -96,7 +96,7 @@ protected:
bool LoadSizeFromXUL();
bool LoadMiscPersistentAttributesFromXUL();
void SyncAttributesToWidget();
NS_IMETHOD SavePersistentAttributes();
void SaveAttributes();
NS_IMETHOD GetWindowDOMWindow(nsIDOMWindow** aDOMWindow);
mozilla::dom::Element* GetWindowDOMElement() const;
@ -119,7 +119,7 @@ protected:
nsIXULWindow *aBehind);
void SetContentScrollbarVisibility(bool aVisible);
bool GetContentScrollbarVisibility();
void PersistentAttributesDirty(uint32_t aDirtyFlags);
void SetAttributesDirty(uint32_t aDirtyFlags);
nsChromeTreeOwner* mChromeTreeOwner;
nsContentTreeOwner* mContentTreeOwner;