From 198bc4292115918fe76c76f20a6804d5370b68c6 Mon Sep 17 00:00:00 2001 From: "jst%netscape.com" Date: Thu, 4 Apr 2002 22:42:19 +0000 Subject: [PATCH] Checking in the fix for bug 52334 again now that the linux crash and the scrollwheel crash has been fixed. Making iframe's load their document even if they are not displayed. r=jkeiser@netscae.com, sr=rpotts@netscape.com, a=asa@mozilla.org git-svn-id: svn://10.0.0.236/trunk@118156 18797224-902f-48f8-a5cc-f745e15eee43 --- .../src/base/nsAccessibilityService.cpp | 79 +- mozilla/content/base/public/MANIFEST | 1 + mozilla/content/base/public/Makefile.in | 1 + mozilla/content/base/public/makefile.win | 1 + mozilla/content/base/public/nsIDocument.h | 37 +- mozilla/content/base/public/nsIFrameLoader.h | 33 +- mozilla/content/base/src/Makefile.in | 8 +- mozilla/content/base/src/makefile.win | 24 +- mozilla/content/base/src/nsDocument.cpp | 227 ++- mozilla/content/base/src/nsDocument.h | 42 +- mozilla/content/base/src/nsDocumentViewer.cpp | 1439 ++++++++++------- mozilla/content/base/src/nsFrameLoader.cpp | 428 +++-- mozilla/content/base/src/nsGenericElement.cpp | 4 +- mozilla/content/base/src/nsGenericElement.h | 9 +- mozilla/content/build/nsContentDLF.cpp | 5 + mozilla/content/build/nsContentModule.cpp | 8 + .../events/src/nsEventStateManager.cpp | 131 +- mozilla/content/html/content/src/makefile.win | 2 +- .../html/content/src/nsGenericHTMLElement.cpp | 32 +- .../html/content/src/nsGenericHTMLElement.h | 2 - .../html/content/src/nsHTMLFrameElement.cpp | 44 +- .../html/content/src/nsHTMLIFrameElement.cpp | 157 +- .../html/content/src/nsHTMLObjectElement.cpp | 30 +- .../content/src/nsHTMLSharedObjectElement.cpp | 30 +- .../html/document/src/nsHTMLContentSink.cpp | 130 +- .../html/document/src/nsHTMLDocument.cpp | 35 +- .../html/style/src/nsCSSStyleSheet.cpp | 2 +- mozilla/content/macbuild/content.xml | 30 + .../xul/document/src/nsXULDocument.cpp | 186 ++- .../content/xul/document/src/nsXULDocument.h | 12 +- mozilla/docshell/base/nsDocShell.cpp | 23 +- mozilla/docshell/base/nsWebShell.cpp | 2 +- mozilla/dom/public/base/nsPIDOMWindow.h | 9 +- .../public/idl/base/nsIDOMWindowInternal.idl | 2 + mozilla/dom/src/base/nsGlobalWindow.cpp | 83 +- mozilla/dom/src/base/nsGlobalWindow.h | 5 + mozilla/dom/src/events/nsJSEventListener.cpp | 6 +- mozilla/editor/libeditor/base/nsEditor.cpp | 3 +- .../inspector/base/src/inLayoutUtils.cpp | 39 +- mozilla/layout/base/nsDocumentViewer.cpp | 1439 ++++++++++------- mozilla/layout/base/nsIPresShell.h | 22 - mozilla/layout/base/nsPresShell.cpp | 115 -- mozilla/layout/base/public/nsIPresShell.h | 22 - mozilla/layout/build/nsContentDLF.cpp | 5 + mozilla/layout/generic/nsFrameFrame.cpp | 752 ++++----- mozilla/layout/generic/nsFrameSetFrame.cpp | 8 +- mozilla/layout/generic/nsFrameSetFrame.h | 7 +- mozilla/layout/html/base/src/nsPresShell.cpp | 115 -- .../layout/html/document/src/nsFrameFrame.cpp | 752 ++++----- .../html/document/src/nsFrameSetFrame.cpp | 8 +- .../html/document/src/nsFrameSetFrame.h | 7 +- mozilla/layout/style/nsCSSStyleSheet.cpp | 2 +- .../xul/base/src/nsBrowserBoxObject.cpp | 24 +- .../layout/xul/base/src/nsEditorBoxObject.cpp | 24 +- .../layout/xul/base/src/nsIFrameBoxObject.cpp | 23 +- mozilla/uriloader/base/nsDocLoader.cpp | 4 +- 56 files changed, 3636 insertions(+), 3034 deletions(-) diff --git a/mozilla/accessible/src/base/nsAccessibilityService.cpp b/mozilla/accessible/src/base/nsAccessibilityService.cpp index eb673e8ce1c..1bbe4288f95 100644 --- a/mozilla/accessible/src/base/nsAccessibilityService.cpp +++ b/mozilla/accessible/src/base/nsAccessibilityService.cpp @@ -130,17 +130,28 @@ nsAccessibilityService::GetInfo(nsISupports* aFrame, nsIFrame** aRealFrame, nsIW return NS_OK; } -void nsAccessibilityService::GetOwnerFor(nsIPresShell *aPresShell, nsIPresShell **aOwnerShell, nsIContent **aOwnerContent) +void nsAccessibilityService::GetOwnerFor(nsIPresShell *aPresShell, + nsIPresShell **aOwnerShell, + nsIContent **aOwnerContent) { + *aOwnerShell = nsnull; + *aOwnerContent = nsnull; + nsCOMPtr presContext; aPresShell->GetPresContext(getter_AddRefs(presContext)); if (!presContext) return; + + nsCOMPtr doc; + aPresShell->GetDocument(getter_AddRefs(doc)); + + if (!doc) + return; + nsCOMPtr pcContainer; presContext->GetContainer(getter_AddRefs(pcContainer)); if (!pcContainer) return; - nsCOMPtr docShellSupports(do_QueryInterface(pcContainer)); nsCOMPtr treeItem(do_QueryInterface(pcContainer)); if (!treeItem) @@ -166,17 +177,11 @@ void nsAccessibilityService::GetOwnerFor(nsIPresShell *aPresShell, nsIPresShell if (!parentDoc) return; - nsCOMPtr rootContent; - parentDoc->GetRootContent(getter_AddRefs(rootContent)); + parentDoc->FindContentForSubDocument(doc, aOwnerContent); - nsCOMPtr tempContent; - parentPresShell->FindContentForShell(docShellSupports, getter_AddRefs(tempContent)); - - if (tempContent) { - *aOwnerContent = tempContent; + if (*aOwnerContent) { *aOwnerShell = parentPresShell; NS_ADDREF(*aOwnerShell); - NS_ADDREF(*aOwnerContent); } } @@ -250,46 +255,46 @@ nsAccessibilityService::CreateIFrameAccessible(nsIDOMNode* aDOMNode, nsIAccessib NS_WARNING("No outer pres shell in CreateHTMLIFrameAccessible!"); return NS_ERROR_FAILURE; } - + nsCOMPtr outerPresContext; outerPresShell->GetPresContext(getter_AddRefs(outerPresContext)); if (!outerPresContext) { NS_WARNING("No outer pres context in CreateHTMLIFrameAccessible!"); return NS_ERROR_FAILURE; } - + nsCOMPtr doc; if (NS_SUCCEEDED(content->GetDocument(*getter_AddRefs(doc))) && doc) { - if (outerPresShell) { - nsCOMPtr supps; - outerPresShell->GetSubShellFor(content, getter_AddRefs(supps)); - if (supps) { - nsCOMPtr docShell(do_QueryInterface(supps)); - if (docShell) { - nsCOMPtr innerPresShell; - docShell->GetPresShell(getter_AddRefs(innerPresShell)); - if (innerPresShell) { - nsCOMPtr innerWeakShell(do_GetWeakReference(innerPresShell)); - nsCOMPtr innerDoc; - innerPresShell->GetDocument(getter_AddRefs(innerDoc)); - if (innerDoc) { - nsCOMPtr innerRootAccessible(new nsHTMLIFrameRootAccessible(aDOMNode, innerWeakShell)); - if (innerRootAccessible) { - nsHTMLIFrameAccessible* outerRootAccessible = new nsHTMLIFrameAccessible(aDOMNode, innerRootAccessible, outerWeakShell, innerDoc); - if (outerRootAccessible) { - *_retval = NS_STATIC_CAST(nsIAccessible*, outerRootAccessible); - if (*_retval) { - NS_ADDREF(*_retval); - return NS_OK; - } - } - } - } + nsCOMPtr sub_doc; + doc->GetSubDocumentFor(content, getter_AddRefs(sub_doc)); + + if (sub_doc) { + nsCOMPtr innerPresShell; + sub_doc->GetShellAt(0, getter_AddRefs(innerPresShell)); + + if (innerPresShell) { + nsCOMPtr innerWeakShell = + do_GetWeakReference(innerPresShell); + + nsCOMPtr innerRootAccessible = + new nsHTMLIFrameRootAccessible(aDOMNode, innerWeakShell); + + if (innerRootAccessible) { + nsHTMLIFrameAccessible* outerRootAccessible = + new nsHTMLIFrameAccessible(aDOMNode, innerRootAccessible, + outerWeakShell, sub_doc); + + if (outerRootAccessible) { + *_retval = outerRootAccessible; + NS_ADDREF(*_retval); + + return NS_OK; } } } } } + return NS_ERROR_FAILURE; } diff --git a/mozilla/content/base/public/MANIFEST b/mozilla/content/base/public/MANIFEST index 805b3c61427..53d8bd75617 100644 --- a/mozilla/content/base/public/MANIFEST +++ b/mozilla/content/base/public/MANIFEST @@ -27,3 +27,4 @@ nsIStyleSheet.h nsIStyleSheetLinkingElement.h nsITextContent.h nsIContentList.h +nsIFrameLoader.h diff --git a/mozilla/content/base/public/Makefile.in b/mozilla/content/base/public/Makefile.in index 3179cbb90aa..497ce3c81b1 100644 --- a/mozilla/content/base/public/Makefile.in +++ b/mozilla/content/base/public/Makefile.in @@ -56,6 +56,7 @@ nsIPrivateDOMImplementation.h \ nsIContentSerializer.h \ nsIHTMLToTextSink.h \ nsIContentList.h \ +nsIFrameLoader.h \ $(NULL) XPIDLSRCS = \ diff --git a/mozilla/content/base/public/makefile.win b/mozilla/content/base/public/makefile.win index 74d364afd98..f690b86a59f 100644 --- a/mozilla/content/base/public/makefile.win +++ b/mozilla/content/base/public/makefile.win @@ -48,6 +48,7 @@ EXPORTS = \ nsIContentSerializer.h \ nsIHTMLToTextSink.h \ nsIContentList.h \ + nsIFrameLoader.h \ $(NULL) MODULE=content diff --git a/mozilla/content/base/public/nsIDocument.h b/mozilla/content/base/public/nsIDocument.h index cfb53010ba8..37c50e58724 100644 --- a/mozilla/content/base/public/nsIDocument.h +++ b/mozilla/content/base/public/nsIDocument.h @@ -227,13 +227,32 @@ public: /** * Return the parent document of this document. Will return null - * unless this document is within a compound document and has a parent. + * unless this document is within a compound document and has a + * parent. Note that this parent chain may cross chrome boundaries. */ NS_IMETHOD GetParentDocument(nsIDocument** aParent) = 0; + + /** + * Set the parent document of this document. + */ NS_IMETHOD SetParentDocument(nsIDocument* aParent) = 0; - NS_IMETHOD AddSubDocument(nsIDocument* aSubDoc) = 0; - NS_IMETHOD GetNumberOfSubDocuments(PRInt32* aCount) = 0; - NS_IMETHOD GetSubDocumentAt(PRInt32 aIndex, nsIDocument** aSubDoc) = 0; + + /** + * Set the sub document for aContent to aSubDoc. + */ + NS_IMETHOD SetSubDocumentFor(nsIContent *aContent, nsIDocument* aSubDoc) = 0; + + /** + * Get the sub document for aContent + */ + NS_IMETHOD GetSubDocumentFor(nsIContent *aContent, + nsIDocument** aSubDoc) = 0; + + /** + * Find the content node for which aDocument is a sub document. + */ + NS_IMETHOD FindContentForSubDocument(nsIDocument *aDocument, + nsIContent **aContent) = 0; /** * Return the root content object for this document. @@ -373,6 +392,16 @@ public: NS_IMETHOD AddReference(void *aKey, nsISupports *aReference) = 0; NS_IMETHOD RemoveReference(void *aKey, nsISupports **aOldReference) = 0; + + /** + * Set the container (docshell) for this document. + */ + NS_IMETHOD SetContainer(nsISupports *aContainer) = 0; + + /** + * Get the container (docshell) for this document. + */ + NS_IMETHOD GetContainer(nsISupports **aContainer) = 0; }; diff --git a/mozilla/content/base/public/nsIFrameLoader.h b/mozilla/content/base/public/nsIFrameLoader.h index 1fcfcc4b1d4..5f6e99f3651 100644 --- a/mozilla/content/base/public/nsIFrameLoader.h +++ b/mozilla/content/base/public/nsIFrameLoader.h @@ -43,7 +43,7 @@ #include "nsAString.h" // Forward declarations -class nsIDOMElement; +class nsIContent; class nsIDocShell; class nsIURI; @@ -57,18 +57,42 @@ class nsIURI; { 0x0080d493, 0x96b4, 0x4606, \ {0xa7, 0x43, 0x0f, 0x47, 0xee, 0x87, 0x14, 0xd1} } +// CID for the nsIFrameLoader implementation +#define NS_FRAMELOADER_CID \ +{ 0x712603da, 0xf245, 0x4503, \ + {0xa5, 0x41, 0xb0, 0x49, 0xcb, 0x06, 0x81, 0xae} } + +#define NS_FRAMELOADER_CONTRACTID "@mozilla.org/content/frameloader" class nsIFrameLoader : public nsISupports { public: NS_DEFINE_STATIC_IID_ACCESSOR(NS_IFRAMELOADER_IID) - NS_IMETHOD Init(nsIDOMElement *aOwner) = 0; + /** + * Initialize the frame loader, hand it the owner content. Note that + * the owner content reference is a weak reference, if the owner + * content is destroyed before the frame loader goes away the owner + * content must call the Destroy() method to clear the owner content + * reference. + */ + NS_IMETHOD Init(nsIContent *aOwner) = 0; - NS_IMETHOD LoadURI(nsIURI *aURI) = 0; + /** + * Start loading the frame. This method figures out what to load + * from the owner content in the frame loader. + */ + NS_IMETHOD LoadFrame() = 0; + /** + * Get the docshell from the frame loader. + */ NS_IMETHOD GetDocShell(nsIDocShell **aDocShell) = 0; + /** + * Destroy the frame loader and everything inside it. This will + * clear the weak owner content reference. + */ NS_IMETHOD Destroy() = 0; }; @@ -78,6 +102,9 @@ class nsIFrameLoaderOwner : public nsISupports public: NS_DEFINE_STATIC_IID_ACCESSOR(NS_IFRAMELOADEROWNER_IID) + /** + * Get the frame loader from the frame loader owner. + */ NS_IMETHOD GetFrameLoader(nsIFrameLoader **aFrameLoader) = 0; }; diff --git a/mozilla/content/base/src/Makefile.in b/mozilla/content/base/src/Makefile.in index b2ab0306987..1571feae676 100644 --- a/mozilla/content/base/src/Makefile.in +++ b/mozilla/content/base/src/Makefile.in @@ -55,8 +55,8 @@ REQUIRES = xpcom \ imglib2 \ gfx2 \ uriloader \ - webbrwsr \ - webBrowser_core \ + webbrwsr \ + webBrowser_core \ $(NULL) CPPSRCS = \ @@ -97,9 +97,11 @@ CPPSRCS = \ nsScriptLoader.cpp \ nsStyleLinkElement.cpp \ nsContentAreaDragDrop.cpp \ + nsFrameLoader.cpp \ $(NULL) -# we don't want the shared lib, but we want to force the creation of a static lib. +# we don't want the shared lib, but we want to force the creation of a +# static lib. FORCE_STATIC_LIB = 1 include $(topsrcdir)/config/rules.mk diff --git a/mozilla/content/base/src/makefile.win b/mozilla/content/base/src/makefile.win index ebda5b315a3..32f25e5a8de 100644 --- a/mozilla/content/base/src/makefile.win +++ b/mozilla/content/base/src/makefile.win @@ -43,6 +43,7 @@ REQUIRES = xpcom \ uconv \ chrome \ docshell \ + uriloader \ pref \ xpconnect \ util \ @@ -68,10 +69,10 @@ CPP_OBJS= \ .\$(OBJDIR)\nsCommentNode.obj \ .\$(OBJDIR)\nsGenericDOMDataNode.obj \ .\$(OBJDIR)\nsGenericDOMNodeList.obj \ - .\$(OBJDIR)\nsGenericElement.obj \ - .\$(OBJDIR)\nsContentList.obj \ - .\$(OBJDIR)\nsContentIterator.obj \ - .\$(OBJDIR)\nsContentPolicy.obj \ + .\$(OBJDIR)\nsGenericElement.obj \ + .\$(OBJDIR)\nsContentList.obj \ + .\$(OBJDIR)\nsContentIterator.obj \ + .\$(OBJDIR)\nsContentPolicy.obj \ .\$(OBJDIR)\nsDocument.obj \ .\$(OBJDIR)\nsDocumentEncoder.obj \ .\$(OBJDIR)\nsDocumentFragment.obj \ @@ -79,7 +80,7 @@ CPP_OBJS= \ .\$(OBJDIR)\nsDOMAttribute.obj \ .\$(OBJDIR)\nsDOMAttributeMap.obj \ .\$(OBJDIR)\nsDOMDocumentType.obj \ - .\$(OBJDIR)\nsGeneratedIterator.obj \ + .\$(OBJDIR)\nsGeneratedIterator.obj \ .\$(OBJDIR)\nsNameSpaceManager.obj \ .\$(OBJDIR)\nsNodeInfo.obj \ .\$(OBJDIR)\nsNodeInfoManager.obj \ @@ -91,12 +92,13 @@ CPP_OBJS= \ .\$(OBJDIR)\nsTreeWalker.obj \ .\$(OBJDIR)\nsXMLContentSerializer.obj \ .\$(OBJDIR)\nsHTMLContentSerializer.obj \ - .\$(OBJDIR)\nsParserUtils.obj \ - .\$(OBJDIR)\nsPlainTextSerializer.obj \ - .\$(OBJDIR)\nsContentUtils.obj \ - .\$(OBJDIR)\nsScriptLoader.obj \ - .\$(OBJDIR)\nsStyleLinkElement.obj \ - .\$(OBJDIR)\nsContentAreaDragDrop.obj \ + .\$(OBJDIR)\nsParserUtils.obj \ + .\$(OBJDIR)\nsPlainTextSerializer.obj \ + .\$(OBJDIR)\nsContentUtils.obj \ + .\$(OBJDIR)\nsScriptLoader.obj \ + .\$(OBJDIR)\nsStyleLinkElement.obj \ + .\$(OBJDIR)\nsContentAreaDragDrop.obj \ + .\$(OBJDIR)\nsFrameLoader.obj \ $(NULL) LINCS=-I..\..\html\base\src -I..\..\html\style\src \ diff --git a/mozilla/content/base/src/nsDocument.cpp b/mozilla/content/base/src/nsDocument.cpp index d3149226a01..b5cfc0ed3a8 100644 --- a/mozilla/content/base/src/nsDocument.cpp +++ b/mozilla/content/base/src/nsDocument.cpp @@ -445,7 +445,7 @@ nsDocumentChildNodes::DropReference() // ================================================================== nsDocument::nsDocument() : mIsGoingAway(PR_FALSE), - mCSSLoader(nsnull) + mCSSLoader(nsnull), mSubDocuments(nsnull) { NS_INIT_REFCNT(); @@ -476,6 +476,7 @@ nsDocument::nsDocument() : mIsGoingAway(PR_FALSE), mObservers.InsertElementAt(observer, 0); } + nsDocument::~nsDocument() { // XXX Inform any remaining observers that we are going away. @@ -501,11 +502,12 @@ nsDocument::~nsDocument() mParentDocument = nsnull; - // Delete references to sub-documents - indx = mSubDocuments.Count(); - while (--indx >= 0) { - nsIDocument* subdoc = (nsIDocument*) mSubDocuments.ElementAt(indx); - NS_RELEASE(subdoc); + // Kill the subdocument map, doing this will release its strong + // references, if any. + if (mSubDocuments) { + PL_DHashTableDestroy(mSubDocuments); + + mSubDocuments = nsnull; } if (mRootContent) { @@ -671,25 +673,28 @@ nsDocument::ResetToURI(nsIURI *aURI, nsILoadGroup *aLoadGroup) NS_IF_RELEASE(mPrincipal); mDocumentLoadGroup = nsnull; - // Delete references to sub-documents - PRInt32 indx = mSubDocuments.Count(); - while (--indx >= 0) { - nsIDocument* subdoc = (nsIDocument*) mSubDocuments.ElementAt(indx); - NS_RELEASE(subdoc); + // Delete references to sub-documents and kill the subdocument map, + // if any. It holds strong references + if (mSubDocuments) { + PL_DHashTableDestroy(mSubDocuments); + + mSubDocuments = nsnull; } mRootContent = nsnull; PRUint32 count, i; mChildren->Count(&count); for (i = 0; i < count; i++) { - nsCOMPtr content(dont_AddRef(NS_STATIC_CAST(nsIContent*,mChildren->ElementAt(i)))); + nsCOMPtr content = + dont_AddRef(NS_STATIC_CAST(nsIContent *, mChildren->ElementAt(i))); + content->SetDocument(nsnull, PR_TRUE, PR_TRUE); - ContentRemoved(nsnull, content, indx); + ContentRemoved(nsnull, content, i); } mChildren->Clear(); // Delete references to style sheets - indx = mStyleSheets.Count(); + PRInt32 indx = mStyleSheets.Count(); while (--indx >= 0) { nsIStyleSheet* sheet = (nsIStyleSheet*) mStyleSheets.ElementAt(indx); sheet->SetOwningDocument(nsnull); @@ -723,8 +728,9 @@ nsDocument::ResetToURI(nsIURI *aURI, nsILoadGroup *aLoadGroup) if (aLoadGroup) { mDocumentLoadGroup = getter_AddRefs(NS_GetWeakReference(aLoadGroup)); - // there was an assertion here that aLoadGroup was not null. This is no longer valid - // nsWebShell::SetDocument does not create a load group, and it works just fine. + // there was an assertion here that aLoadGroup was not null. This + // is no longer valid nsWebShell::SetDocument does not create a + // load group, and it works just fine. } if (NS_OK == rv) @@ -1159,26 +1165,151 @@ nsDocument::SetParentDocument(nsIDocument* aParent) return NS_OK; } -NS_IMETHODIMP -nsDocument::AddSubDocument(nsIDocument* aSubDoc) +PR_STATIC_CALLBACK(void) +SubDocClearEntry(PLDHashTable *table, PLDHashEntryHdr *entry) { - NS_ADDREF(aSubDoc); - mSubDocuments.AppendElement(aSubDoc); + SubDocMapEntry *e = NS_STATIC_CAST(SubDocMapEntry *, entry); + + NS_RELEASE(e->mKey); + NS_IF_RELEASE(e->mSubDocument); +} + +PR_STATIC_CALLBACK(void) +SubDocInitEntry(PLDHashTable *table, PLDHashEntryHdr *entry, const void *key) +{ + SubDocMapEntry *e = + NS_CONST_CAST(SubDocMapEntry *, + NS_STATIC_CAST(const SubDocMapEntry *, entry)); + + e->mKey = NS_CONST_CAST(nsIContent *, + NS_STATIC_CAST(const nsIContent *, key)); + NS_ADDREF(e->mKey); + + e->mSubDocument = nsnull; +} + +NS_IMETHODIMP +nsDocument::SetSubDocumentFor(nsIContent *aContent, nsIDocument* aSubDoc) +{ + NS_ENSURE_TRUE(aContent, NS_ERROR_UNEXPECTED); + + if (!aSubDoc) { + // aSubDoc is nsnull, remove the mapping + + if (mSubDocuments) { + SubDocMapEntry *entry = + NS_STATIC_CAST(SubDocMapEntry*, + PL_DHashTableOperate(mSubDocuments, aContent, + PL_DHASH_LOOKUP)); + + if (PL_DHASH_ENTRY_IS_LIVE(entry)) { + entry->mSubDocument->SetParentDocument(nsnull); + + PL_DHashTableRawRemove(mSubDocuments, entry); + } + } + } else { + if (!mSubDocuments) { + // Create a new hashtable + + static PLDHashTableOps hash_table_ops = + { + PL_DHashAllocTable, + PL_DHashFreeTable, + PL_DHashGetKeyStub, + PL_DHashVoidPtrKeyStub, + PL_DHashMatchEntryStub, + PL_DHashMoveEntryStub, + SubDocClearEntry, + PL_DHashFinalizeStub, + SubDocInitEntry + }; + + mSubDocuments = PL_NewDHashTable(&hash_table_ops, nsnull, + sizeof(SubDocMapEntry), 16); + if (!mSubDocuments) { + return NS_ERROR_OUT_OF_MEMORY; + } + } + + // Add a mapping to the hash table + SubDocMapEntry *entry = + NS_STATIC_CAST(SubDocMapEntry*, + PL_DHashTableOperate(mSubDocuments, aContent, + PL_DHASH_ADD)); + + if (!entry) { + return NS_ERROR_OUT_OF_MEMORY; + } + + if (entry->mSubDocument) { + entry->mSubDocument->SetParentDocument(nsnull); + + // Release the old sub document + NS_RELEASE(entry->mSubDocument); + } + + entry->mSubDocument = aSubDoc; + NS_ADDREF(entry->mSubDocument); + + aSubDoc->SetParentDocument(this); + } + return NS_OK; } NS_IMETHODIMP -nsDocument::GetNumberOfSubDocuments(PRInt32* aCount) +nsDocument::GetSubDocumentFor(nsIContent *aContent, nsIDocument** aSubDoc) { - *aCount = mSubDocuments.Count(); + *aSubDoc = nsnull; + + if (mSubDocuments) { + SubDocMapEntry *entry = + NS_STATIC_CAST(SubDocMapEntry*, + PL_DHashTableOperate(mSubDocuments, aContent, + PL_DHASH_LOOKUP)); + + if (PL_DHASH_ENTRY_IS_LIVE(entry)) { + *aSubDoc = entry->mSubDocument; + NS_ADDREF(*aSubDoc); + } + } + return NS_OK; } -NS_IMETHODIMP -nsDocument::GetSubDocumentAt(PRInt32 aIndex, nsIDocument** aSubDoc) +PR_STATIC_CALLBACK(PLDHashOperator) +FindContentEnumerator(PLDHashTable *table, PLDHashEntryHdr *hdr, + PRUint32 number, void *arg) { - *aSubDoc = (nsIDocument*) mSubDocuments.SafeElementAt(aIndex); - NS_IF_ADDREF(*aSubDoc); + SubDocMapEntry *entry = NS_STATIC_CAST(SubDocMapEntry*, hdr); + FindContentData *data = NS_STATIC_CAST(FindContentData*, arg); + + if (entry->mSubDocument == data->mSubDocument) { + data->mResult = entry->mKey; + + return PL_DHASH_STOP; + } + + return PL_DHASH_NEXT; +} + +NS_IMETHODIMP +nsDocument::FindContentForSubDocument(nsIDocument *aDocument, + nsIContent **aContent) +{ + NS_ENSURE_ARG_POINTER(aDocument); + + if (!mSubDocuments) { + *aContent = nsnull; + return NS_OK; + } + + FindContentData data(aDocument); + PL_DHashTableEnumerate(mSubDocuments, FindContentEnumerator, &data); + + *aContent = data.mResult; + NS_IF_ADDREF(*aContent); return NS_OK; } @@ -1740,23 +1871,18 @@ nsDocument::EndLoad() if (docShellAsItem) { docShellAsItem->GetSameTypeParent(getter_AddRefs(docShellParent)); - nsCOMPtr doc; + nsCOMPtr parent_doc; - GetDocumentFromDocShellTreeItem(docShellParent, getter_AddRefs(doc)); + GetDocumentFromDocShellTreeItem(docShellParent, + getter_AddRefs(parent_doc)); - if (doc) { - nsCOMPtr shell; - doc->GetShellAt(0, getter_AddRefs(shell)); + if (parent_doc) { + nsCOMPtr target_content; - if (shell) { - nsCOMPtr target_content; + parent_doc->FindContentForSubDocument(this, + getter_AddRefs(target_content)); - nsCOMPtr docshell_identity(docShell); - shell->FindContentForShell(docshell_identity, - getter_AddRefs(target_content)); - - target_frame = do_QueryInterface(target_content); - } + target_frame = do_QueryInterface(target_content); } } } @@ -2145,8 +2271,8 @@ nsDocument::GetDocumentElement(nsIDOMElement** aDocumentElement) nsresult res = NS_OK; - if (nsnull != mRootContent) { - res = mRootContent->QueryInterface(NS_GET_IID(nsIDOMElement), (void**)aDocumentElement); + if (mRootContent) { + res = CallQueryInterface(mRootContent, aDocumentElement); NS_ASSERTION(NS_OK == res, "Must be a DOM Element"); } else { *aDocumentElement = nsnull; @@ -3471,6 +3597,25 @@ nsDocument::RemoveReference(void *aKey, nsISupports **aOldReference) return NS_OK; } +NS_IMETHODIMP +nsDocument::SetContainer(nsISupports *aContainer) +{ + mDocumentContainer = dont_AddRef(NS_GetWeakReference(aContainer)); + + return NS_OK; +} + +NS_IMETHODIMP +nsDocument::GetContainer(nsISupports **aContainer) +{ + nsCOMPtr container = do_QueryReferent(mDocumentContainer); + + *aContainer = container; + NS_IF_ADDREF(*aContainer); + + return NS_OK; +} + #ifdef IBMBIDI /** * Check if bidi enabled (set depending on the presence of RTL diff --git a/mozilla/content/base/src/nsDocument.h b/mozilla/content/base/src/nsDocument.h index 22b2e9d1b42..9fb44599c6f 100644 --- a/mozilla/content/base/src/nsDocument.h +++ b/mozilla/content/base/src/nsDocument.h @@ -69,6 +69,8 @@ #include "nsScriptLoader.h" #include "nsICSSLoader.h" +#include "pldhash.h" + class nsIEventListenerManager; class nsDOMStyleSheetList; class nsIOutputStream; @@ -212,6 +214,29 @@ protected: void* mScriptObject; }; + +// Helper structs for the content->subdoc map + +class SubDocMapEntry : public PLDHashEntryHdr +{ +public: + // Both of these are strong references + nsIContent *mKey; // must be first, to look like PLDHashEntryStub + nsIDocument *mSubDocument; +}; + +struct FindContentData +{ + FindContentData(nsIDocument *aSubDoc) + : mSubDocument(aSubDoc), mResult(nsnull) + { + } + + nsISupports *mSubDocument; + nsIContent *mResult; +}; + + // Base class for our document implementations. // // Note that this class *implements* nsIDOMXMLDocument, but it's not @@ -367,9 +392,11 @@ public: */ NS_IMETHOD GetParentDocument(nsIDocument** aParent); NS_IMETHOD SetParentDocument(nsIDocument* aParent); - NS_IMETHOD AddSubDocument(nsIDocument* aSubDoc); - NS_IMETHOD GetNumberOfSubDocuments(PRInt32* aCount); - NS_IMETHOD GetSubDocumentAt(PRInt32 aIndex, nsIDocument** aSubDoc); + + NS_IMETHOD SetSubDocumentFor(nsIContent *aContent, nsIDocument* aSubDoc); + NS_IMETHOD GetSubDocumentFor(nsIContent *aContent, nsIDocument** aSubDoc); + NS_IMETHOD FindContentForSubDocument(nsIDocument *aDocument, + nsIContent **aContent); /** * Return the root content object for this document. @@ -492,6 +519,8 @@ public: NS_IMETHOD GetNodeInfoManager(nsINodeInfoManager*& aNodeInfoManager); NS_IMETHOD AddReference(void *aKey, nsISupports *aReference); NS_IMETHOD RemoveReference(void *aKey, nsISupports **aOldReference); + NS_IMETHOD SetContainer(nsISupports *aContainer); + NS_IMETHOD GetContainer(nsISupports **aContainer); // nsIDOMNode NS_DECL_NSIDOMNODE @@ -573,13 +602,16 @@ protected: nsCOMPtr mDocumentBaseURL; nsIPrincipal* mPrincipal; nsWeakPtr mDocumentLoadGroup; - + nsWeakPtr mDocumentContainer; + nsString mCharacterSet; PRInt32 mCharacterSetSource; nsVoidArray mCharSetObservers; nsIDocument* mParentDocument; - nsVoidArray mSubDocuments; + + PLDHashTable *mSubDocuments; + nsVoidArray mPresShells; nsCOMPtr mChildren; // contains owning references nsIContent* mRootContent; // a weak reference to the only element in diff --git a/mozilla/content/base/src/nsDocumentViewer.cpp b/mozilla/content/base/src/nsDocumentViewer.cpp index 92f9c14d123..0ca981ca4ea 100644 --- a/mozilla/content/base/src/nsDocumentViewer.cpp +++ b/mozilla/content/base/src/nsDocumentViewer.cpp @@ -93,6 +93,7 @@ #include "nsIDocShellTreeNode.h" #include "nsIDocShellTreeOwner.h" #include "nsIDocShell.h" +#include "nsIBaseWindow.h" #include "nsIFrameDebug.h" #include "nsILayoutHistoryState.h" #include "nsLayoutAtoms.h" @@ -145,7 +146,7 @@ static NS_DEFINE_IID(kPrinterEnumeratorCID, NS_PRINTER_ENUMERATOR_CID); // Print Preview #include "nsIPrintPreviewContext.h" #include "imgIContainer.h" // image animation mode constants -#include "nsIScrollableView.h" +#include "nsIScrollableView.h" #include "nsIWebBrowserPrint.h" // needed for PrintPreview Navigation constants // Print Progress @@ -169,7 +170,7 @@ static NS_DEFINE_IID(kPrinterEnumeratorCID, NS_PRINTER_ENUMERATOR_CID); #include "nsIWebShell.h" //focus -#include "nsIDOMEventReceiver.h" +#include "nsIDOMEventReceiver.h" #include "nsIDOMFocusListener.h" #include "nsISelectionController.h" @@ -198,7 +199,7 @@ static NS_DEFINE_CID(kStyleSetCID, NS_STYLESET_CID); #ifdef DEBUG_PRINTING // XXX NOTE: I am including a header from the layout directory // merely to set up a file pointer for debug logging. This is -// fragile and may break in the future, which means it can be +// fragile and may break in the future, which means it can be // removed if necessary #if defined(XP_PC) #include "../../../layout/html/base/src/nsSimplePageSequence.h" @@ -212,20 +213,20 @@ static const char * gPrintRangeStr[] = {"kRangeAllPages", "kRangeSpecified static PRUint32 gDumpFileNameCnt = 0; static PRUint32 gDumpLOFileNameCnt = 0; -#define PRINT_DEBUG_MSG1(_msg1) fprintf(mPrt->mDebugFD, (_msg1)); -#define PRINT_DEBUG_MSG2(_msg1, _msg2) fprintf(mPrt->mDebugFD, (_msg1), (_msg2)); -#define PRINT_DEBUG_MSG3(_msg1, _msg2, _msg3) fprintf(mPrt->mDebugFD, (_msg1), (_msg2), (_msg3)); -#define PRINT_DEBUG_MSG4(_msg1, _msg2, _msg3, _msg4) fprintf(mPrt->mDebugFD, (_msg1), (_msg2), (_msg3), (_msg4)); -#define PRINT_DEBUG_MSG5(_msg1, _msg2, _msg3, _msg4, _msg5) fprintf(mPrt->mDebugFD, (_msg1), (_msg2), (_msg3), (_msg4), (_msg5)); +#define PRINT_DEBUG_MSG1(_msg1) fprintf(mPrt->mDebugFD, (_msg1)); +#define PRINT_DEBUG_MSG2(_msg1, _msg2) fprintf(mPrt->mDebugFD, (_msg1), (_msg2)); +#define PRINT_DEBUG_MSG3(_msg1, _msg2, _msg3) fprintf(mPrt->mDebugFD, (_msg1), (_msg2), (_msg3)); +#define PRINT_DEBUG_MSG4(_msg1, _msg2, _msg3, _msg4) fprintf(mPrt->mDebugFD, (_msg1), (_msg2), (_msg3), (_msg4)); +#define PRINT_DEBUG_MSG5(_msg1, _msg2, _msg3, _msg4, _msg5) fprintf(mPrt->mDebugFD, (_msg1), (_msg2), (_msg3), (_msg4), (_msg5)); #define PRINT_DEBUG_FLUSH fflush(mPrt->mDebugFD); #else //-------------- -#define PRT_YESNO(_p) -#define PRINT_DEBUG_MSG1(_msg) -#define PRINT_DEBUG_MSG2(_msg1, _msg2) -#define PRINT_DEBUG_MSG3(_msg1, _msg2, _msg3) -#define PRINT_DEBUG_MSG4(_msg1, _msg2, _msg3, _msg4) -#define PRINT_DEBUG_MSG5(_msg1, _msg2, _msg3, _msg4, _msg5) -#define PRINT_DEBUG_FLUSH +#define PRT_YESNO(_p) +#define PRINT_DEBUG_MSG1(_msg) +#define PRINT_DEBUG_MSG2(_msg1, _msg2) +#define PRINT_DEBUG_MSG3(_msg1, _msg2, _msg3) +#define PRINT_DEBUG_MSG4(_msg1, _msg2, _msg3, _msg4) +#define PRINT_DEBUG_MSG5(_msg1, _msg2, _msg3, _msg4, _msg5) +#define PRINT_DEBUG_FLUSH #endif @@ -251,7 +252,7 @@ public: NS_DECL_ISUPPORTS // nsISelectionListerner interface - NS_DECL_NSISELECTIONLISTENER + NS_DECL_NSISELECTIONLISTENER nsDocViewerSelectionListener() : mDocViewer(NULL) @@ -260,9 +261,9 @@ public: { NS_INIT_REFCNT(); } - + virtual ~nsDocViewerSelectionListener() {} - + nsresult Init(DocumentViewerImpl *aDocViewer); protected: @@ -270,13 +271,13 @@ protected: DocumentViewerImpl* mDocViewer; PRPackedBool mGotSelectionState; PRPackedBool mSelectionWasCollapsed; - + }; /** editor Implementation of the FocusListener interface */ -class nsDocViewerFocusListener : public nsIDOMFocusListener +class nsDocViewerFocusListener : public nsIDOMFocusListener { public: /** default constructor @@ -398,8 +399,8 @@ public: // Listener Helper Methods void OnEndPrinting(); void OnStartPrinting(); - static void DoOnProgressChange(nsVoidArray& aListeners, - PRInt32 aProgess, + static void DoOnProgressChange(nsVoidArray& aListeners, + PRInt32 aProgess, PRInt32 aMaxProgress, PRBool aDoStartStop = PR_FALSE, PRInt32 aFlag = 0); @@ -416,7 +417,7 @@ public: nsCOMPtr mPrintProgress; nsCOMPtr mPrintProgressParams; PRBool mShowProgressDialog; - + nsCOMPtr mCurrentFocusWin; // cache a pointer to the currently focused window nsVoidArray* mPrintDocList; @@ -472,11 +473,11 @@ class DocumentViewerImpl : public nsIDocumentViewer, friend class nsDocViewerSelectionListener; friend class nsPagePrintTimer; friend class PrintData; - + public: DocumentViewerImpl(); DocumentViewerImpl(nsIPresContext* aPresContext); - + NS_DECL_AND_IMPL_ZEROING_OPERATOR_NEW // nsISupports interface... @@ -511,15 +512,24 @@ public: nsresult CallChildren(CallChildFunc aFunc, void* aClosure); // Printing Methods - PRBool PrintPage(nsIPresContext* aPresContext,nsIPrintSettings* aPrintSettings,PrintObject* aPOect, PRBool& aInRange); + PRBool PrintPage(nsIPresContext* aPresContext, + nsIPrintSettings* aPrintSettings, + PrintObject* aPOect, PRBool& aInRange); PRBool DonePrintingPages(PrintObject* aPO); - + // helper method - static void GetWebShellTitleAndURL(nsIWebShell * aWebShell, PRUnichar** aTitle, PRUnichar** aURLStr); + static void GetWebShellTitleAndURL(nsIWebShell* aWebShell, + PRUnichar** aTitle, PRUnichar** aURLStr); // This enum tells indicates what the default should be for the title // if the title from the document is null - enum eDocTitleDefault {eDocTitleDefNone, eDocTitleDefBlank, eDocTitleDefDocument, eDocTitleDefURLDoc}; + enum eDocTitleDefault { + eDocTitleDefNone, + eDocTitleDefBlank, + eDocTitleDefDocument, + eDocTitleDefURLDoc + }; + static void GetDisplayTitleAndURL(PrintObject* aPO, nsIPrintSettings* aPrintSettings, const PRUnichar* aBrandName, @@ -539,12 +549,15 @@ private: nsIDeviceContext* aDeviceContext, const nsRect& aBounds, PRBool aDoCreation); - nsresult GetDocumentSelection(nsISelection **aSelection, nsIPresShell * aPresShell = nsnull); + nsresult InitPresentationStuff(PRBool aDoInitialReflow); + + nsresult GetDocumentSelection(nsISelection **aSelection, + nsIPresShell * aPresShell = nsnull); nsresult FindFrameSetWithIID(nsIContent * aParentContent, const nsIID& aIID); PRBool IsThereARangeSelection(nsIDOMWindowInternal * aDOMWin); PRBool IsParentAFrameSet(nsIWebShell * aParent); PRBool IsWebShellAFrameSet(nsIWebShell * aParent); - + PRBool IsThereAnIFrameSelected(nsIWebShell* aWebShell, nsIDOMWindowInternal * aDOMWin, PRPackedBool& aDoesContainFrameset); @@ -556,11 +569,12 @@ private: nsresult GetPopupImageNode(nsIDOMNode** aNode); //--------------------------------------------------------------------- - void BuildDocTree(nsIDocShellTreeNode * aParentNode, - nsVoidArray * aDocList, + void BuildDocTree(nsIDocShellTreeNode * aParentNode, + nsVoidArray * aDocList, PrintObject * aPO); - nsresult ReflowDocList(PrintObject * aPO, PRBool aSetPixelScale, PRBool aDoCalcShrink); - void SetClipRect(PrintObject* aPO, + nsresult ReflowDocList(PrintObject * aPO, PRBool aSetPixelScale, + PRBool aDoCalcShrink); + void SetClipRect(PrintObject* aPO, const nsRect& aClipRect, nscoord aOffsetX, nscoord aOffsetY, @@ -575,14 +589,18 @@ private: nsIContent* aContent); void MapContentToWebShells(PrintObject* aRootPO, PrintObject* aPO); nsresult MapSubDocFrameLocations(PrintObject* aPO); - PrintObject* FindPrintObjectByDOMWin(PrintObject* aParentObject, nsIDOMWindowInternal * aDOMWin); - void GetPresShellAndRootContent(nsIWebShell * aWebShell, nsIPresShell** aPresShell, nsIContent** aContent); + PrintObject* FindPrintObjectByDOMWin(PrintObject* aParentObject, + nsIDOMWindowInternal * aDOMWin); + void GetPresShellAndRootContent(nsIWebShell * aWebShell, + nsIPresShell** aPresShell, + nsIContent** aContent); void CalcNumPrintableDocsAndPages(PRInt32& aNumDocs, PRInt32& aNumPages); void DoProgressForAsIsFrames(); void DoProgressForSeparateFrames(); void DoPrintProgress(PRBool aIsForPrinting); - void SetDocAndURLIntoProgress(PrintObject* aPO, nsIPrintProgressParams* aParams); + void SetDocAndURLIntoProgress(PrintObject* aPO, + nsIPrintProgressParams* aParams); nsresult CheckForPrinters(nsIPrintOptions* aPrintOptions, nsIPrintSettings* aPrintSettings, PRUint32 aErrorCode, @@ -600,7 +618,8 @@ private: // nsresult DocumentReadyForPrinting(); //nsresult PrintSelection(nsIDeviceContextSpec * aDevSpec); - nsresult GetSelectionDocument(nsIDeviceContextSpec * aDevSpec, nsIDocument ** aNewDoc); + nsresult GetSelectionDocument(nsIDeviceContextSpec * aDevSpec, + nsIDocument ** aNewDoc); static void PR_CALLBACK HandlePLEvent(PLEvent* aEvent); static void PR_CALLBACK DestroyPLEvent(PLEvent* aEvent); @@ -610,12 +629,17 @@ private: nsIDOMWindowInternal* aCurrentFocusedDOMWin); nsresult EnablePOsForPrinting(); PrintObject* FindXMostPO(); - void FindXMostFrameSize(nsIPresContext* aPresContext, nsIRenderingContext* aRC, nsIFrame* aFrame, nscoord aX, nscoord aY, PRInt32& aMaxWidth); - void FindXMostFrameInList(nsIPresContext* aPresContext, nsIRenderingContext* aRC, nsIAtom* aList, nsIFrame* aFrame, - nscoord aX, nscoord aY, PRInt32& aMaxWidth); + void FindXMostFrameSize(nsIPresContext* aPresContext, + nsIRenderingContext* aRC, nsIFrame* aFrame, + nscoord aX, nscoord aY, PRInt32& aMaxWidth); + void FindXMostFrameInList(nsIPresContext* aPresContext, + nsIRenderingContext* aRC, nsIAtom* aList, + nsIFrame* aFrame, nscoord aX, nscoord aY, + PRInt32& aMaxWidth); PRBool PrintDocContent(PrintObject* aPO, nsresult& aStatus); - nsresult DoPrint(PrintObject * aPO, PRBool aDoSyncPrinting, PRBool& aDonePrinting); + nsresult DoPrint(PrintObject * aPO, PRBool aDoSyncPrinting, + PRBool& aDonePrinting); void SetPrintAsIs(PrintObject* aPO, PRBool aAsIs = PR_TRUE); void SetPrintPO(PrintObject* aPO, PRBool aPrint); @@ -630,15 +654,18 @@ private: // Timer Methods - nsresult StartPagePrintTimer(nsIPresContext * aPresContext, + nsresult StartPagePrintTimer(nsIPresContext * aPresContext, nsIPrintSettings* aPrintSettings, PrintObject* aPO, PRUint32 aDelay); void PrepareToStartLoad(void); - + + nsresult SyncParentSubDocMap(); + // Misc - static void ShowPrintErrorDialog(nsresult printerror, PRBool aIsPrinting = PR_TRUE); + static void ShowPrintErrorDialog(nsresult printerror, + PRBool aIsPrinting = PR_TRUE); protected: // IMPORTANT: The ownership implicit in the following member @@ -646,7 +673,7 @@ protected: // for owning pointers and raw COM interface pointers for weak // (ie, non owning) references. If you add any members to this // class, please make the ownership explicit (pinkerton, scc). - + nsISupports* mContainer; // [WEAK] it owns me! nsCOMPtr mDeviceContext; // ??? can't hurt, but... nsIView* mView; // [WEAK] cleaned up by view mgr @@ -664,7 +691,7 @@ protected: nsCOMPtr mSelectionListener; nsCOMPtr mFocusListener; - + nsCOMPtr mPreviousViewer; PRBool mEnableRendering; @@ -739,7 +766,7 @@ public: NS_WARNING("unable to start the timer"); } else { mTimer->Init(this, aUseDelay?mDelay:0, NS_PRIORITY_NORMAL, NS_TYPE_ONE_SHOT); - } + } return result; } @@ -760,7 +787,7 @@ public: if (mDocViewer->DonePrintingPages(mPrintObj)) { initNewTimer = PR_FALSE; } - } + } Stop(); if (initNewTimer) { @@ -773,15 +800,15 @@ public: } } - void Init(DocumentViewerImpl* aDocViewerImpl, + void Init(DocumentViewerImpl* aDocViewerImpl, nsIPresContext* aPresContext, nsIPrintSettings* aPrintSettings, PrintObject* aPO, - PRUint32 aDelay) + PRUint32 aDelay) { NS_IF_RELEASE(mDocViewer); mDocViewer = aDocViewerImpl; - NS_ADDREF(mDocViewer); + NS_ADDREF(mDocViewer); mPresContext = aPresContext; mPrintSettings = aPrintSettings; @@ -789,11 +816,11 @@ public: mDelay = aDelay; } - nsresult Start(DocumentViewerImpl* aDocViewerImpl, + nsresult Start(DocumentViewerImpl* aDocViewerImpl, nsIPresContext* aPresContext, nsIPrintSettings* aPrintSettings, PrintObject* aPO, - PRUint32 aDelay) + PRUint32 aDelay) { Init(aDocViewerImpl, aPresContext, aPrintSettings, aPO, aDelay); return StartTimer(PR_FALSE); @@ -843,7 +870,7 @@ static nsresult NS_NewUpdateTimer(nsPagePrintTimer **aResult) PrintData::PrintData() : mPrintView(nsnull), mDebugFilePtr(nsnull), mPrintObject(nsnull), mSelectedPO(nsnull), mShowProgressDialog(PR_TRUE), mPrintDocList(nsnull), mIsIFrameSelected(PR_FALSE), - mIsParentAFrameSet(PR_FALSE), mPrintingAsIsSubDoc(PR_FALSE), mOnStartSent(PR_FALSE), + mIsParentAFrameSet(PR_FALSE), mPrintingAsIsSubDoc(PR_FALSE), mOnStartSent(PR_FALSE), mIsAborted(PR_FALSE), mPreparingForPrint(PR_FALSE), mDocWasToBeDestroyed(PR_FALSE), mShrinkToFit(PR_FALSE), mPrintFrameType(nsIPrintSettings::kFramesAsIs), mNumPrintableDocs(0), mNumDocsPrinted(0), mNumPrintablePages(0), mNumPagesPrinted(0), @@ -869,7 +896,7 @@ PrintData::PrintData() : } -PrintData::~PrintData() +PrintData::~PrintData() { // removed any cached if (mCachedPresObj) { @@ -898,7 +925,7 @@ PrintData::~PrintData() if (!isCancelled && !mIsAborted) { rv = mPrintDC->EndDocument(); } else { - rv = mPrintDC->AbortDocument(); + rv = mPrintDC->AbortDocument(); } if (NS_FAILED(rv)) { DocumentViewerImpl::ShowPrintErrorDialog(rv); @@ -947,8 +974,8 @@ void PrintData::OnEndPrinting() } void -PrintData::DoOnProgressChange(nsVoidArray& aListeners, - PRInt32 aProgess, +PrintData::DoOnProgressChange(nsVoidArray& aListeners, + PRInt32 aProgess, PRInt32 aMaxProgress, PRBool aDoStartStop, PRInt32 aFlag) @@ -958,7 +985,7 @@ PrintData::DoOnProgressChange(nsVoidArray& aListeners, for (PRInt32 i=0;iOnProgressChange(nsnull, nsnull, aProgess, aMaxProgress, aProgess, aMaxProgress); + wpl->OnProgressChange(nsnull, nsnull, aProgess, aMaxProgress, aProgess, aMaxProgress); if (aDoStartStop) { wpl->OnStateChange(nsnull, nsnull, aFlag, 0); } @@ -969,10 +996,10 @@ PrintData::DoOnProgressChange(nsVoidArray& aListeners, //--------------------------------------------------- //-- PrintObject Class Impl //--------------------------------------------------- -PrintObject::PrintObject() : +PrintObject::PrintObject() : mFrameType(eFrame), mRootView(nsnull), mContent(nsnull), - mSeqFrame(nsnull), mPageFrame(nsnull), mPageNum(-1), + mSeqFrame(nsnull), mPageFrame(nsnull), mPageNum(-1), mRect(0,0,0,0), mReflowRect(0,0,0,0), mParent(nsnull), mHasBeenPrinted(PR_FALSE), mDontPrint(PR_TRUE), mPrintAsIs(PR_FALSE), mSkippedPageEject(PR_FALSE), mSharedPresShell(PR_FALSE), @@ -992,7 +1019,7 @@ PrintObject::~PrintObject() PrintObject* po = (PrintObject*)mKids[i]; NS_ASSERTION(po, "PrintObject can't be null!"); delete po; - } + } if (mPresShell && !mSharedPresShell) { mPresShell->Destroy(); @@ -1031,16 +1058,14 @@ PRBool DocumentViewerImpl::mIsDoingPrinting = PR_FALSE; nsresult NS_NewDocumentViewer(nsIDocumentViewer** aResult) { - NS_PRECONDITION(aResult, "null OUT ptr"); - if (!aResult) { - return NS_ERROR_NULL_POINTER; - } - DocumentViewerImpl* it = new DocumentViewerImpl(); - if (nsnull == it) { - *aResult = nsnull; + *aResult = new DocumentViewerImpl(); + if (!*aResult) { return NS_ERROR_OUT_OF_MEMORY; } - return CallQueryInterface(it, aResult); + + NS_ADDREF(*aResult); + + return NS_OK; } // Note: operator new zeros our memory @@ -1054,7 +1079,8 @@ DocumentViewerImpl::DocumentViewerImpl() #endif } -void DocumentViewerImpl::PrepareToStartLoad() { +void DocumentViewerImpl::PrepareToStartLoad() +{ mEnableRendering = PR_TRUE; mStopped = PR_FALSE; mLoaded = PR_FALSE; @@ -1092,12 +1118,14 @@ NS_IMPL_ISUPPORTS6(DocumentViewerImpl, DocumentViewerImpl::~DocumentViewerImpl() { NS_ASSERTION(!mDocument, "User did not call nsIContentViewer::Close"); - if (mDocument) + if (mDocument) { Close(); + } NS_ASSERTION(!mPresShell, "User did not call nsIContentViewer::Destroy"); - if (mPresShell) + if (mPresShell) { Destroy(); + } // XXX(?) Revoke pending invalidate events @@ -1125,10 +1153,10 @@ DocumentViewerImpl::LoadStart(nsISupports *aDoc) nsresult rv; if (!mDocument) { - mDocument = do_QueryInterface(aDoc,&rv); + mDocument = do_QueryInterface(aDoc, &rv); } else if (mDocument == aDoc) { - // Reset the document viewer's state back to what it was + // Reset the document viewer's state back to what it was // when the document load started. PrepareToStartLoad(); } @@ -1136,6 +1164,42 @@ DocumentViewerImpl::LoadStart(nsISupports *aDoc) return rv; } +nsresult +DocumentViewerImpl::SyncParentSubDocMap() +{ + nsCOMPtr item(do_QueryInterface(mContainer)); + nsCOMPtr win(do_GetInterface(item)); + nsCOMPtr pwin(do_QueryInterface(win)); + nsCOMPtr content; + + if (mDocument && pwin) { + nsCOMPtr frame_element; + pwin->GetFrameElementInternal(getter_AddRefs(frame_element)); + + content = do_QueryInterface(frame_element); + } + + if (content) { + nsCOMPtr parent; + item->GetParent(getter_AddRefs(parent)); + + nsCOMPtr parent_win(do_GetInterface(parent)); + + if (parent_win) { + nsCOMPtr dom_doc; + parent_win->GetDocument(getter_AddRefs(dom_doc)); + + nsCOMPtr parent_doc(do_QueryInterface(dom_doc)); + + if (parent_doc) { + return parent_doc->SetSubDocumentFor(content, mDocument); + } + } + } + + return NS_OK; +} + NS_IMETHODIMP DocumentViewerImpl::SetContainer(nsISupports* aContainer) { @@ -1143,7 +1207,12 @@ DocumentViewerImpl::SetContainer(nsISupports* aContainer) if (mPresContext) { mPresContext->SetContainer(aContainer); } - return NS_OK; + + // We're loading a new document into the window where this document + // viewer lives, sync the parent document's frame element -> sub + // document map + + return SyncParentSubDocMap(); } NS_IMETHODIMP @@ -1165,6 +1234,99 @@ DocumentViewerImpl::Init(nsIWidget* aParentWidget, return InitInternal(aParentWidget, aDeviceContext, aBounds, PR_TRUE); } +nsresult +DocumentViewerImpl::InitPresentationStuff(PRBool aDoInitialReflow) +{ + // Create the style set... + nsCOMPtr styleSet; + nsresult rv = CreateStyleSet(mDocument, getter_AddRefs(styleSet)); + NS_ENSURE_SUCCESS(rv, rv); + + // Now make the shell for the document + rv = mDocument->CreateShell(mPresContext, mViewManager, styleSet, + getter_AddRefs(mPresShell)); + NS_ENSURE_SUCCESS(rv, rv); + + mPresShell->BeginObservingDocument(); + + // Initialize our view manager + nsRect bounds; + mWindow->GetBounds(bounds); + + float p2t; + + mPresContext->GetPixelsToTwips(&p2t); + + nscoord width = NSIntPixelsToTwips(bounds.width, p2t); + nscoord height = NSIntPixelsToTwips(bounds.height, p2t); + + mViewManager->DisableRefresh(); + mViewManager->SetWindowDimensions(width, height); + + // Setup default view manager background color + + // This may be overridden by the docshell with the background color + // for the last document loaded into the docshell + nscolor bgcolor = NS_RGB(0, 0, 0); + mPresContext->GetDefaultBackgroundColor(&bgcolor); + mViewManager->SetDefaultBackgroundColor(bgcolor); + + if (aDoInitialReflow) { + // Initial refllow + mPresShell->InitialReflow(width, height); + + // Now trigger a refresh + if (mEnableRendering) { + mViewManager->EnableRefresh(NS_VMREFRESH_IMMEDIATE); + } + } + + // now register ourselves as a selection listener, so that we get + // called when the selection changes in the window + nsDocViewerSelectionListener *selectionListener = + new nsDocViewerSelectionListener(); + NS_ENSURE_TRUE(selectionListener, NS_ERROR_OUT_OF_MEMORY); + + selectionListener->Init(this); + + // mSelectionListener is a owning reference + mSelectionListener = selectionListener; + + nsCOMPtr selection; + rv = GetDocumentSelection(getter_AddRefs(selection)); + NS_ENSURE_SUCCESS(rv, rv); + + nsCOMPtr selPrivate(do_QueryInterface(selection)); + rv = selPrivate->AddSelectionListener(mSelectionListener); + if (NS_FAILED(rv)) + return rv; + + // focus listener + // + // now register ourselves as a focus listener, so that we get called + // when the focus changes in the window + nsDocViewerFocusListener *focusListener; + NS_NEWXPCOM(focusListener, nsDocViewerFocusListener); + NS_ENSURE_TRUE(focusListener, NS_ERROR_OUT_OF_MEMORY); + + focusListener->Init(this); + + // mFocusListener is a strong reference + mFocusListener = focusListener; + + // get the DOM event receiver + nsCOMPtr erP(do_QueryInterface(mDocument)); + NS_WARN_IF_FALSE(erP, "No event receiver in document!"); + + if (erP) { + rv = erP->AddEventListenerByIID(mFocusListener, + NS_GET_IID(nsIDOMFocusListener)); + NS_ASSERTION(NS_SUCCEEDED(rv), "failed to register focus listener"); + } + + return NS_OK; +} + //----------------------------------------------- // This method can be used to initial the "presentation" // The aDoCreation indicates whether it should create @@ -1175,16 +1337,16 @@ DocumentViewerImpl::InitInternal(nsIWidget* aParentWidget, const nsRect& aBounds, PRBool aDoCreation) { - NS_ASSERTION(aParentWidget != nsnull, "Null aParentWidget"); + nsresult rv = NS_OK; #ifdef NS_PRINT_PREVIEW mParentWidget = aParentWidget; // not ref counted #endif - nsresult rv; NS_ENSURE_TRUE(mDocument, NS_ERROR_NULL_POINTER); mDeviceContext = dont_QueryInterface(aDeviceContext); + #ifdef NS_PRINT_PREVIEW // Clear PrintPreview Alternate Device if (mDeviceContext) { @@ -1195,16 +1357,18 @@ DocumentViewerImpl::InitInternal(nsIWidget* aParentWidget, PRBool makeCX = PR_FALSE; if (aDoCreation) { - if (!mPresContext) { + if (aParentWidget && !mPresContext) { // Create presentation context if (mIsCreatingPrintPreview) { - mPresContext = do_CreateInstance(kPrintPreviewContextCID,&rv); + mPresContext = do_CreateInstance(kPrintPreviewContextCID, &rv); } else { - mPresContext = do_CreateInstance(kGalleyContextCID,&rv); + mPresContext = do_CreateInstance(kGalleyContextCID, &rv); } - if (NS_FAILED(rv)) return rv; + if (NS_FAILED(rv)) + return rv; mPresContext->Init(aDeviceContext); + #ifdef NS_PRINT_PREVIEW makeCX = !mIsDoingPrintPreview; // needs to be true except when we are already in PP #else @@ -1213,142 +1377,52 @@ DocumentViewerImpl::InitInternal(nsIWidget* aParentWidget, } } + if (aDoCreation && mPresContext) { + // Create the ViewManager and Root View... + + // We must do this before we tell the script global object about + // this new document since doing that will cause us to re-enter + // into nsHTMLFrameInnerFrame code through reflows caused by + // FlushPendingNotifications() calls down the road... + + rv = MakeWindow(aParentWidget, aBounds); + NS_ENSURE_SUCCESS(rv, rv); + Hide(); + } + nsCOMPtr requestor(do_QueryInterface(mContainer)); if (requestor) { - nsCOMPtr linkHandler; - requestor->GetInterface(NS_GET_IID(nsILinkHandler), - getter_AddRefs(linkHandler)); - mPresContext->SetContainer(mContainer); - mPresContext->SetLinkHandler(linkHandler); + if (mPresContext) { + nsCOMPtr linkHandler; + requestor->GetInterface(NS_GET_IID(nsILinkHandler), + getter_AddRefs(linkHandler)); + mPresContext->SetContainer(mContainer); + mPresContext->SetLinkHandler(linkHandler); + } if (!mIsDoingPrintPreview) { // Set script-context-owner in the document - nsCOMPtr owner; - requestor->GetInterface(NS_GET_IID(nsIScriptGlobalObjectOwner), - getter_AddRefs(owner)); - if (owner) { - nsCOMPtr global; - owner->GetScriptGlobalObject(getter_AddRefs(global)); + nsCOMPtr global; + requestor->GetInterface(NS_GET_IID(nsIScriptGlobalObject), + getter_AddRefs(global)); - if (global) { - mDocument->SetScriptGlobalObject(global); - nsCOMPtr domdoc(do_QueryInterface(mDocument)); + if (global) { + mDocument->SetScriptGlobalObject(global); + nsCOMPtr domdoc(do_QueryInterface(mDocument)); - if (domdoc) { - global->SetNewDocument(domdoc, PR_TRUE); - } + if (domdoc) { + global->SetNewDocument(domdoc, PR_TRUE); } } } } - if (aDoCreation) { - // Create the ViewManager and Root View... - rv = MakeWindow(aParentWidget, aBounds); - Hide(); + if (aDoCreation && mPresContext) { + // The ViewManager and Root View was created above (in + // MakeWindow())... - if (NS_FAILED(rv)) return rv; - - // Create the style set... - nsIStyleSet* styleSet; - rv = CreateStyleSet(mDocument, &styleSet); - if (NS_FAILED(rv)) return rv; - - // Now make the shell for the document - rv = mDocument->CreateShell(mPresContext, mViewManager, styleSet, - getter_AddRefs(mPresShell)); - NS_RELEASE(styleSet); - if (NS_FAILED(rv)) return rv; - - mPresShell->BeginObservingDocument(); - - // Initialize our view manager - nsRect bounds; - mWindow->GetBounds(bounds); - nscoord width = bounds.width; - nscoord height = bounds.height; - float p2t; - mPresContext->GetPixelsToTwips(&p2t); - width = NSIntPixelsToTwips(width, p2t); - height = NSIntPixelsToTwips(height, p2t); - mViewManager->DisableRefresh(); - mViewManager->SetWindowDimensions(width, height); - - /* Setup default view manager background color */ - /* This may be overridden by the docshell with the background color for the - last document loaded into the docshell */ - nscolor bgcolor = NS_RGB(0, 0, 0); - mPresContext->GetDefaultBackgroundColor(&bgcolor); - mViewManager->SetDefaultBackgroundColor(bgcolor); - - if (!makeCX) { - // Make shell an observer for next time - // XXX - we observe the docuement always, see above after preshell is created - // mPresShell->BeginObservingDocument(); - - //XXX I don't think this should be done *here*; and why paint nothing - //(which turns out to cause black flashes!)??? - // Resize-reflow this time - mPresShell->InitialReflow(width, height); - - // Now trigger a refresh - if (mEnableRendering) { - mViewManager->EnableRefresh(NS_VMREFRESH_IMMEDIATE); - } - } - } else { - mPresShell->BeginObservingDocument(); - } - // now register ourselves as a selection listener, so that we get called - // when the selection changes in the window - nsDocViewerSelectionListener *selectionListener; - NS_NEWXPCOM(selectionListener, nsDocViewerSelectionListener); - if (!selectionListener) return NS_ERROR_OUT_OF_MEMORY; - selectionListener->Init(this); - - // this is the owning reference. The nsCOMPtr will take care of releasing - // our ref to the listener on destruction. - NS_ADDREF(selectionListener); - mSelectionListener = do_QueryInterface(selectionListener); - NS_RELEASE(selectionListener); - if (NS_FAILED(rv)) return rv; - - nsCOMPtr selection; - rv = GetDocumentSelection(getter_AddRefs(selection)); - if (NS_FAILED(rv)) return rv; - - nsCOMPtr selPrivate(do_QueryInterface(selection)); - rv = selPrivate->AddSelectionListener(mSelectionListener); - if (NS_FAILED(rv)) return rv; - - //focus listener - // now register ourselves as a focus listener, so that we get called - // when the focus changes in the window - nsDocViewerFocusListener *focusListener; - NS_NEWXPCOM(focusListener, nsDocViewerFocusListener); - if (!focusListener) return NS_ERROR_OUT_OF_MEMORY; - focusListener->Init(this); - - // this is the owning reference. The nsCOMPtr will take care of releasing - // our ref to the listener on destruction. - NS_ADDREF(focusListener); - mFocusListener = do_QueryInterface(focusListener); - NS_RELEASE(focusListener); - if (NS_FAILED(rv)) - return rv; - - if(mDocument) - { - // get the DOM event receiver - nsCOMPtr erP (do_QueryInterface(mDocument, &rv)); - if(NS_FAILED(rv)) - return rv; - if(!erP) - return NS_ERROR_FAILURE; - - rv = erP->AddEventListenerByIID(mFocusListener, NS_GET_IID(nsIDOMFocusListener)); - NS_ASSERTION(NS_SUCCEEDED(rv), "failed to register focus listener"); + rv = InitPresentationStuff(!makeCX); } return rv; @@ -1374,14 +1448,14 @@ DocumentViewerImpl::LoadComplete(nsresult aStatus) rv = mDocument->GetScriptGlobalObject(getter_AddRefs(global)); // Fail if no ScriptGlobalObject is available... - NS_ASSERTION(global, "nsIScriptGlobalObject not set for document!"); - if (!global) return NS_ERROR_NULL_POINTER; + NS_ENSURE_TRUE(global, NS_ERROR_NULL_POINTER); mLoaded = PR_TRUE; - /* We need to protect ourself against auto-destruction in case the window is closed - while processing the OnLoad event. - See bug http://bugzilla.mozilla.org/show_bug.cgi?id=78445 for more explanation. + /* We need to protect ourself against auto-destruction in case the + window is closed while processing the OnLoad event. See bug + http://bugzilla.mozilla.org/show_bug.cgi?id=78445 for more + explanation. */ NS_ADDREF_THIS(); @@ -1397,11 +1471,14 @@ DocumentViewerImpl::LoadComplete(nsresult aStatus) #ifdef MOZ_TIMELINE // if navigator.xul's load is complete, the main nav window is visible // mark that point. + if (mDocument) { //printf("DEBUG: getting uri from document (%p)\n", mDocument.get()); + nsCOMPtr uri; mDocument->GetDocumentURL(getter_AddRefs(uri)); - if (uri.get() != nsnull) { + + if (uri) { //printf("DEBUG: getting spec fro uri (%p)\n", uri.get()); nsCAutoString spec; uri->GetSpec(spec); @@ -1414,11 +1491,12 @@ DocumentViewerImpl::LoadComplete(nsresult aStatus) } else { // XXX: Should fire error event to the document... } - + // Now that the document has loaded, we can tell the presshell // to unsuppress painting. - if (mPresShell && !mStopped) + if (mPresShell && !mStopped) { mPresShell->UnsuppressPainting(); + } NS_RELEASE_THIS(); @@ -1470,11 +1548,9 @@ DocumentViewerImpl::Close() // for an object that can be switched in and out so that we don't need // to disable scripts during paint suppression. - nsresult rv; - if (mDocument) { #ifdef NS_PRINT_PREVIEW - // Turn scripting back on + // Turn scripting back on // after PrintPreview had turned it off if (mPrtPreview) { TurnScriptingOn(PR_TRUE); @@ -1485,20 +1561,28 @@ DocumentViewerImpl::Close() // in the DocViewer Init nsCOMPtr globalObject; mDocument->GetScriptGlobalObject(getter_AddRefs(globalObject)); + if (globalObject) { globalObject->SetNewDocument(nsnull, PR_TRUE); } + // out of band cleanup of webshell mDocument->SetScriptGlobalObject(nsnull); + if (mFocusListener) { // get the DOM event receiver - nsCOMPtr erP( do_QueryInterface(mDocument, &rv) ); - if(NS_SUCCEEDED(rv) && erP) - erP->RemoveEventListenerByIID(mFocusListener, NS_GET_IID(nsIDOMFocusListener)); + nsCOMPtr erP(do_QueryInterface(mDocument)); + NS_WARN_IF_FALSE(erP, "No event receiver in document!"); + + if (erP) { + erP->RemoveEventListenerByIID(mFocusListener, + NS_GET_IID(nsIDOMFocusListener)); + } } - } + } mDocument = nsnull; + return NS_OK; } @@ -1558,15 +1642,19 @@ DocumentViewerImpl::Destroy() if (mPresShell) { // Break circular reference (or something) mPresShell->EndObservingDocument(); + nsCOMPtr selection; - nsresult rv = GetDocumentSelection(getter_AddRefs(selection)); + GetDocumentSelection(getter_AddRefs(selection)); + nsCOMPtr selPrivate(do_QueryInterface(selection)); - if (NS_SUCCEEDED(rv) && selPrivate && mSelectionListener) + + if (selPrivate && mSelectionListener) selPrivate->RemoveSelectionListener(mSelectionListener); + mPresShell->Destroy(); mPresShell = nsnull; } - + return NS_OK; } @@ -1601,15 +1689,17 @@ DocumentViewerImpl::SetDOMDocument(nsIDOMDocument *aDocument) // Assumptions: // // 1) this document viewer has been initialized with a call to Init(). - // 2) the stylesheets associated with the document have been added to the document. + // 2) the stylesheets associated with the document have been added + // to the document. - // XXX Right now, this method assumes that the layout of the current document - // hasn't started yet. More cleanup will probably be necessary to make this - // method work for the case when layout *has* occurred for the current document. + // XXX Right now, this method assumes that the layout of the current + // document hasn't started yet. More cleanup will probably be + // necessary to make this method work for the case when layout *has* + // occurred for the current document. // That work can happen when and if it is needed. - + nsresult rv; - if (nsnull == aDocument) + if (!aDocument) return NS_ERROR_NULL_POINTER; nsCOMPtr newDoc = do_QueryInterface(aDocument, &rv); @@ -1619,46 +1709,50 @@ DocumentViewerImpl::SetDOMDocument(nsIDOMDocument *aDocument) mDocument = newDoc; // 1) Set the script global object on the new document - nsCOMPtr requestor(do_QueryInterface(mContainer)); - if (requestor) { - nsCOMPtr owner; - requestor->GetInterface(NS_GET_IID(nsIScriptGlobalObjectOwner), - getter_AddRefs(owner)); - if (nsnull != owner) { - nsCOMPtr global; - rv = owner->GetScriptGlobalObject(getter_AddRefs(global)); - if (NS_SUCCEEDED(rv) && (nsnull != global)) { - mDocument->SetScriptGlobalObject(global); - global->SetNewDocument(aDocument, PR_TRUE); - } - } - } + nsCOMPtr global(do_GetInterface(mContainer)); - // 2) Create a new style set for the document - nsCOMPtr styleSet; - rv = CreateStyleSet(mDocument, getter_AddRefs(styleSet)); - if (NS_FAILED(rv)) return rv; + if (global) { + mDocument->SetScriptGlobalObject(global); + global->SetNewDocument(aDocument, PR_TRUE); - // 3) Replace the current pres shell with a new shell for the new document - mPresShell->EndObservingDocument(); - mPresShell->Destroy(); + rv = SyncParentSubDocMap(); + NS_ENSURE_SUCCESS(rv, rv); + } - mPresShell = nsnull; - rv = newDoc->CreateShell(mPresContext, mViewManager, styleSet, - getter_AddRefs(mPresShell)); - if (NS_FAILED(rv)) return rv; + // 2) Replace the current pres shell with a new shell for the new document - mPresShell->BeginObservingDocument(); + if (mPresShell) { + mPresShell->EndObservingDocument(); + mPresShell->Destroy(); + + mPresShell = nsnull; + } + + // And if we're already given a prescontext... + if (mPresContext) { + // 3) Create a new style set for the document + + nsCOMPtr styleSet; + rv = CreateStyleSet(mDocument, getter_AddRefs(styleSet)); + if (NS_FAILED(rv)) + return rv; + + rv = newDoc->CreateShell(mPresContext, mViewManager, styleSet, + getter_AddRefs(mPresShell)); + if (NS_FAILED(rv)) return rv; + + mPresShell->BeginObservingDocument(); + + // 4) Register the focus listener on the new document - // 4) Register the focus listener on the new document - if(mDocument) - { nsCOMPtr erP = do_QueryInterface(mDocument, &rv); - if(NS_FAILED(rv) || !erP) - return rv ? rv : NS_ERROR_FAILURE; + NS_WARN_IF_FALSE(erP, "No event receiver in document!"); - rv = erP->AddEventListenerByIID(mFocusListener, NS_GET_IID(nsIDOMFocusListener)); - NS_ASSERTION(NS_SUCCEEDED(rv), "failed to register focus listener"); + if (erP) { + rv = erP->AddEventListenerByIID(mFocusListener, + NS_GET_IID(nsIDOMFocusListener)); + NS_ASSERTION(NS_SUCCEEDED(rv), "failed to register focus listener"); + } } return rv; @@ -1675,7 +1769,7 @@ DocumentViewerImpl::SetUAStyleSheet(nsIStyleSheet* aUAStyleSheet) } return NS_OK; } - + NS_IMETHODIMP DocumentViewerImpl::GetDocument(nsIDocument*& aResult) { @@ -1683,7 +1777,7 @@ DocumentViewerImpl::GetDocument(nsIDocument*& aResult) NS_IF_ADDREF(aResult); return NS_OK; } - + NS_IMETHODIMP DocumentViewerImpl::GetPresShell(nsIPresShell*& aResult) { @@ -1691,7 +1785,7 @@ DocumentViewerImpl::GetPresShell(nsIPresShell*& aResult) NS_IF_ADDREF(aResult); return NS_OK; } - + NS_IMETHODIMP DocumentViewerImpl::GetPresContext(nsIPresContext*& aResult) { @@ -1733,7 +1827,7 @@ DocumentViewerImpl::SetPreviousViewer(nsIContentViewer* aViewer) "can't set previous viewer when there already is one"); // In a multiple chaining situation (which occurs when running a thrashing - // test like i-bench or jrgm's tests with no delay), we can build up a + // test like i-bench or jrgm's tests with no delay), we can build up a // whole chain of viewers. In order to avoid this, we always set our previous // viewer to the MOST previous viewer in the chain, and then dump the intermediate // link from the chain. This ensures that at most only 2 documents are alive @@ -1756,7 +1850,7 @@ NS_IMETHODIMP DocumentViewerImpl::SetBounds(const nsRect& aBounds) { NS_ENSURE_TRUE(mDocument, NS_ERROR_NOT_AVAILABLE); - NS_PRECONDITION(mWindow, "null window"); + if (mWindow) { // Don't have the widget repaint. Layout will generate repaint requests // during reflow @@ -1781,7 +1875,6 @@ NS_IMETHODIMP DocumentViewerImpl::Show(void) { NS_ENSURE_TRUE(mDocument, NS_ERROR_NOT_AVAILABLE); - NS_PRECONDITION(mWindow, "null window"); // We don't need the previous viewer anymore since we're not // displaying it. @@ -1796,6 +1889,114 @@ DocumentViewerImpl::Show(void) if (mWindow) { mWindow->Show(PR_TRUE); } + + if (mDocument && !mPresShell && !mWindow && !mDeviceContext) { + nsresult rv; + + nsCOMPtr base_win(do_QueryInterface(mContainer)); + NS_ENSURE_TRUE(base_win, NS_ERROR_UNEXPECTED); + + base_win->GetParentWidget(&mParentWidget); + NS_ENSURE_TRUE(mParentWidget, NS_ERROR_UNEXPECTED); + + if (!mDeviceContext) { + mDeviceContext = dont_AddRef(mParentWidget->GetDeviceContext()); + } + +#ifdef NS_PRINT_PREVIEW + // Clear PrintPreview Alternate Device + if (mDeviceContext) { + mDeviceContext->SetAltDevice(nsnull); + } +#endif + + PRBool makeCX = PR_FALSE; + + // Create presentation context + if (mIsCreatingPrintPreview) { + NS_ERROR("Whoa, we should not get here!"); + + return NS_ERROR_UNEXPECTED; + } + + mPresContext = do_CreateInstance(kGalleyContextCID, &rv); + NS_ENSURE_SUCCESS(rv, rv); + + mPresContext->Init(mDeviceContext); + + nsRect tbounds; + mParentWidget->GetBounds(tbounds); + + float p2t; + mPresContext->GetPixelsToTwips(&p2t); + tbounds *= p2t; + + // Create the view manager + mViewManager = do_CreateInstance(kViewManagerCID); + NS_ENSURE_TRUE(mViewManager, NS_ERROR_NOT_AVAILABLE); + + // Initialize the view manager with an offset. This allows the + // viewmanager to manage a coordinate space offset from (0,0) + rv = mViewManager->Init(mDeviceContext); + if (NS_FAILED(rv)) + return rv; + + rv = mViewManager->SetWindowOffset(tbounds.x, tbounds.y); + if (NS_FAILED(rv)) + return rv; + + // Reset the bounds offset so the root view is set to 0,0. The + // offset is specified in nsIViewManager::Init above. + // Besides, layout will reset the root view to (0,0) during reflow, + // so changing it to 0,0 eliminates placing the root view in the + // wrong place initially. + tbounds.x = 0; + tbounds.y = 0; + + // Create a child window of the parent that is our "root + // view/window" Create a view + rv = CallCreateInstance(kViewCID, &mView); + if (NS_FAILED(rv)) + return rv; + rv = mView->Init(mViewManager, tbounds, nsnull); + if (NS_FAILED(rv)) + return rv; + + rv = mView->CreateWidget(kWidgetCID, nsnull, + mParentWidget->GetNativeData(NS_NATIVE_WIDGET), + PR_TRUE, PR_FALSE); + + if (NS_FAILED(rv)) + return rv; + + // Setup hierarchical relationship in view manager + mViewManager->SetRootView(mView); + + mView->GetWidget(*getter_AddRefs(mWindow)); + + if (mPresContext && mContainer) { + nsCOMPtr linkHandler(do_GetInterface(mContainer)); + + if (linkHandler) { + mPresContext->SetLinkHandler(linkHandler); + } + + mPresContext->SetContainer(mContainer); + } + + if (mPresContext) { + Hide(); + + rv = InitPresentationStuff(PR_TRUE); + } + + // If we get here the document load has already started and the + // window is shown because some JS on the page caused it to be + // shown... + + mPresShell->UnsuppressPainting(); + } + return NS_OK; } @@ -1807,6 +2008,48 @@ DocumentViewerImpl::Hide(void) if (mWindow) { mWindow->Show(PR_FALSE); } + + if (!mPresShell) { + return NS_OK; + } + + // Avoid leaking the old viewer. + if (mPreviousViewer) { + mPreviousViewer->Destroy(); + mPreviousViewer = nsnull; + } + + if (mDeviceContext) + mDeviceContext->FlushFontCache(); + + // Break circular reference (or something) + mPresShell->EndObservingDocument(); + nsCOMPtr selection; + + GetDocumentSelection(getter_AddRefs(selection)); + + nsCOMPtr selPrivate(do_QueryInterface(selection)); + + if (selPrivate && mSelectionListener) + selPrivate->RemoveSelectionListener(mSelectionListener); + + mPresShell->Destroy(); + + mPresShell = nsnull; + mPresContext = nsnull; + mViewManager = nsnull; + mView = nsnull; + mWindow = nsnull; + mDeviceContext = nsnull; + mView = nsnull; + mParentWidget = nsnull; + + nsCOMPtr base_win(do_QueryInterface(mContainer)); + + if (base_win) { + base_win->SetParentWidget(nsnull); + } + return NS_OK; } @@ -1832,7 +2075,7 @@ DocumentViewerImpl::FindFrameSetWithIID(nsIContent * aParentContent, const nsIID } /** --------------------------------------------------- - * Helper function + * Helper function */ static nsIPresShell* GetPresShellFor(nsIDocShell* aDocShell) @@ -1859,10 +2102,10 @@ GetPresShellFor(nsIDocShell* aDocShell) #include "process.h" #include "direct.h" -#define MY_FINDFIRST(a,b) FindFirstFile(a,b) -#define MY_FINDNEXT(a,b) FindNextFile(a,b) -#define ISDIR(a) (a.dwFileAttributes & FILE_ATTRIBUTE_DIRECTORY) -#define MY_FINDCLOSE(a) FindClose(a) +#define MY_FINDFIRST(a,b) FindFirstFile(a,b) +#define MY_FINDNEXT(a,b) FindNextFile(a,b) +#define ISDIR(a) (a.dwFileAttributes & FILE_ATTRIBUTE_DIRECTORY) +#define MY_FINDCLOSE(a) FindClose(a) #define MY_FILENAME(a) a.cFileName #define MY_FILESIZE(a) (a.nFileSizeHigh * MAXDWORD) + a.nFileSizeLow @@ -1937,10 +2180,10 @@ static void RootFrameList(nsIPresContext* aPresContext, FILE* out, PRInt32 aInde /** --------------------------------------------------- * Dumps Frames for Printing */ -static void DumpFrames(FILE* out, - nsIPresContext* aPresContext, - nsIRenderingContext * aRendContext, - nsIFrame * aFrame, +static void DumpFrames(FILE* out, + nsIPresContext* aPresContext, + nsIRenderingContext * aRendContext, + nsIFrame * aFrame, PRInt32 aLevel) { NS_ASSERTION(out, "Pointer is null!"); @@ -2108,16 +2351,16 @@ static void DumpPrintObjectsList(nsVoidArray * aDocList, FILE* aFD = nsnull) } } - fprintf(fd, "%s %d %d %d %p %p %p %p %p %d %d,%d,%d,%d\n", types[po->mFrameType], + fprintf(fd, "%s %d %d %d %p %p %p %p %p %d %d,%d,%d,%d\n", types[po->mFrameType], po->IsPrintable(), po->mPrintAsIs, po->mHasBeenPrinted, po, po->mWebShell, po->mSeqFrame, - po->mPageFrame, rootFrame, po->mPageNum, po->mRect.x, po->mRect.y, po->mRect.width, po->mRect.height); + po->mPageFrame, rootFrame, po->mPageNum, po->mRect.x, po->mRect.y, po->mRect.width, po->mRect.height); if (fd != nsnull && fd != stdout) { - fprintf(stdout, "%s %d %d %d %p %p %p %p %p %d %d,%d,%d,%d\n", types[po->mFrameType], + fprintf(stdout, "%s %d %d %d %p %p %p %p %p %d %d,%d,%d,%d\n", types[po->mFrameType], po->IsPrintable(), po->mPrintAsIs, po->mHasBeenPrinted, po, po->mWebShell, po->mSeqFrame, - po->mPageFrame, rootFrame, po->mPageNum, po->mRect.x, po->mRect.y, po->mRect.width, po->mRect.height); + po->mPageFrame, rootFrame, po->mPageNum, po->mRect.x, po->mRect.y, po->mRect.width, po->mRect.height); } - } -} + } +} static void DumpPrintObjectsTree(PrintObject * aPO, int aLevel= 0, FILE* aFD = nsnull) { NS_ASSERTION(aPO, "Pointer is null!"); @@ -2134,11 +2377,12 @@ static void DumpPrintObjectsTree(PrintObject * aPO, int aLevel= 0, FILE* aFD = n NS_ASSERTION(po, "PrintObject can't be null!"); for (PRInt32 k=0;kmFrameType], po, po->mWebShell, po->mSeqFrame, - po->mPageFrame, po->mPageNum, po->mRect.x, po->mRect.y, po->mRect.width, po->mRect.height); - } + po->mPageFrame, po->mPageNum, po->mRect.x, po->mRect.y, po->mRect.width, po->mRect.height); + } } - -static void GetDocTitleAndURL(PrintObject* aPO, char *& aDocStr, char *& aURLStr) + +static void GetDocTitleAndURL(PrintObject* aPO, char *& aDocStr, + char *& aURLStr) { aDocStr = nsnull; aURLStr = nsnull; @@ -2146,7 +2390,9 @@ static void GetDocTitleAndURL(PrintObject* aPO, char *& aDocStr, char *& aURLStr PRUnichar * mozillaDoc = ToNewUnicode(NS_LITERAL_STRING("Mozilla Document")); PRUnichar * docTitleStr; PRUnichar * docURLStr; - DocumentViewerImpl::GetDisplayTitleAndURL(aPO, nsnull, mozillaDoc, &docTitleStr, &docURLStr, DocumentViewerImpl::eDocTitleDefURLDoc); + DocumentViewerImpl::GetDisplayTitleAndURL(aPO, nsnull, mozillaDoc, + &docTitleStr, &docURLStr, + DocumentViewerImpl::eDocTitleDefURLDoc); if (docTitleStr) { nsAutoString strDocTitle(docTitleStr); @@ -2165,7 +2411,7 @@ static void GetDocTitleAndURL(PrintObject* aPO, char *& aDocStr, char *& aURLStr } } -static void DumpPrintObjectsTreeLayout(PrintObject * aPO, +static void DumpPrintObjectsTreeLayout(PrintObject * aPO, nsIDeviceContext * aDC, int aLevel= 0, FILE * aFD = nsnull) { @@ -2189,7 +2435,7 @@ static void DumpPrintObjectsTreeLayout(PrintObject * aPO, } for (PRInt32 k=0;kmFrameType], aPO, aPO->mWebShell, aPO->mSeqFrame, - aPO->mPageFrame, aPO->mPageNum, aPO->mRect.x, aPO->mRect.y, aPO->mRect.width, aPO->mRect.height); + aPO->mPageFrame, aPO->mPageNum, aPO->mRect.x, aPO->mRect.y, aPO->mRect.width, aPO->mRect.height); if (aPO->IsPrintable()) { char * docStr; char * urlStr; @@ -2210,7 +2456,7 @@ static void DumpPrintObjectsTreeLayout(PrintObject * aPO, if (aLevel == 0 && fd) { fclose(fd); } -} +} static void DumpPrintObjectsListStart(char * aStr, nsVoidArray * aDocList, FILE* aFD = nsnull) { @@ -2228,7 +2474,7 @@ static void DumpPrintObjectsListStart(char * aStr, nsVoidArray * aDocList, FILE* #else #define DUMP_DOC_LIST(_title) #define DUMP_DOC_TREE -#define DUMP_DOC_TREELAYOUT +#define DUMP_DOC_TREELAYOUT #endif //--------------------------------------------------------------- @@ -2238,7 +2484,7 @@ static void DumpPrintObjectsListStart(char * aStr, nsVoidArray * aDocList, FILE* //--------------------------------------------------------------- /** --------------------------------------------------- - * Giving a child frame it searches "up" the tree until it + * Giving a child frame it searches "up" the tree until it * finds a "Page" frame. */ static nsIFrame * GetPageFrame(nsIFrame * aFrame) @@ -2263,7 +2509,7 @@ static nsIFrame * FindFrameByType(nsIPresContext* aPresContext, nsIFrame * aParentFrame, nsIAtom * aType, nsRect& aRect, - nsRect& aChildRect) + nsRect& aChildRect) { NS_ASSERTION(aPresContext, "Pointer is null!"); NS_ASSERTION(aParentFrame, "Pointer is null!"); @@ -2390,7 +2636,7 @@ static nsresult GetPageRangeForSelection(nsIPresShell * aPresShell, seqFrame->GetRect(rect); // start out with the sequence frame and search the entire frame tree - // capturing the the starting and ending child frames of the selection + // capturing the the starting and ending child frames of the selection // and their rects FindSelectionBounds(aPresContext, aRC, seqFrame, rect, startFrame, aStartRect, endFrame, aEndRect); @@ -2399,7 +2645,7 @@ static nsresult GetPageRangeForSelection(nsIPresShell * aPresShell, printf("End Frame: %p\n", endFrame); #endif - // initial the page numbers here + // initial the page numbers here // in case we don't find and frames aStartPageNum = -1; aEndPageNum = -1; @@ -2415,7 +2661,7 @@ static nsresult GetPageRangeForSelection(nsIPresShell * aPresShell, // Check to see if start should be same as end if // the end frame comes back null if (endFrame == nsnull) { - // XXX the "GetPageFrame" step could be integrated into + // XXX the "GetPageFrame" step could be integrated into // the FindSelectionBounds step, but walking up to find // the parent of a child frame isn't expensive and it makes // FindSelectionBounds a little easier to understand @@ -2455,7 +2701,7 @@ static nsresult GetPageRangeForSelection(nsIPresShell * aPresShell, while (page != nsnull) { if (page == startPageFrame) { aStartPageNum = pageNum; - } + } if (page == endPageFrame) { aEndPageNum = pageNum; } @@ -2475,7 +2721,7 @@ static nsresult GetPageRangeForSelection(nsIPresShell * aPresShell, } //------------------------------------------------------- -PRBool +PRBool DocumentViewerImpl::IsParentAFrameSet(nsIWebShell * aParent) { NS_ASSERTION(aParent, "Pointer is null!"); @@ -2484,8 +2730,8 @@ DocumentViewerImpl::IsParentAFrameSet(nsIWebShell * aParent) nsCOMPtr parentAsItem(do_QueryInterface(aParent)); if (!parentAsItem) return PR_FALSE; - // When it is the top level document we need to check - // to see if it contains a frameset. If it does, then + // When it is the top level document we need to check + // to see if it contains a frameset. If it does, then // we only want to print the doc's children and not the document itself // For anything else we always print all the children and the document // for example, if the doc contains an IFRAME we eant to print the child @@ -2494,10 +2740,10 @@ DocumentViewerImpl::IsParentAFrameSet(nsIWebShell * aParent) // XXX we really need to search the frame tree, and not the content // but there is no way to distinguish between IFRAMEs and FRAMEs // with the GetFrameType call. - // Bug 53459 has been files so we can eventually distinguish + // Bug 53459 has been files so we can eventually distinguish // between IFRAME frames and FRAME frames PRBool isFrameSet = PR_FALSE; - // only check to see if there is a frameset if there is + // only check to see if there is a frameset if there is // NO parent doc for this doc. meaning this parent is the root doc nsCOMPtr shell; mPresContext->GetShell(getter_AddRefs(shell)); @@ -2518,7 +2764,7 @@ DocumentViewerImpl::IsParentAFrameSet(nsIWebShell * aParent) } //------------------------------------------------------- -PRBool +PRBool DocumentViewerImpl::IsWebShellAFrameSet(nsIWebShell * aWebShell) { NS_ASSERTION(aWebShell, "Pointer is null!"); @@ -2537,8 +2783,8 @@ DocumentViewerImpl::IsWebShellAFrameSet(nsIWebShell * aWebShell) //------------------------------------------------------- void -DocumentViewerImpl::GetWebShellTitleAndURL(nsIWebShell * aWebShell, - PRUnichar** aTitle, +DocumentViewerImpl::GetWebShellTitleAndURL(nsIWebShell * aWebShell, + PRUnichar** aTitle, PRUnichar** aURLStr) { NS_ASSERTION(aWebShell, "Pointer is null!"); @@ -2634,7 +2880,7 @@ DocumentViewerImpl::GetDisplayTitleAndURL(PrintObject* aPO, case eDocTitleDefDocument: if (aBrandName) *aTitle = nsCRT::strdup(aBrandName); break; - case eDocTitleDefURLDoc: + case eDocTitleDefURLDoc: if (*aURLStr) { *aTitle = nsCRT::strdup(*aURLStr); } else { @@ -2770,12 +3016,12 @@ DocumentViewerImpl::PrintPage(nsIPresContext* aPresContext, if (mPrt->mPrintFrameType == nsIPrintSettings::kEachFrameSep) { DoProgressForSeparateFrames(); - } else if (mPrt->mPrintFrameType != nsIPrintSettings::kFramesAsIs || + } else if (mPrt->mPrintFrameType != nsIPrintSettings::kFramesAsIs || mPrt->mPrintObject->mFrameType == eDoc && aPO == mPrt->mPrintObject) { PrintData::DoOnProgressChange(mPrt->mPrintProgressListeners, curPage, endPage); } - // Set Clip when Printing "AsIs" or + // Set Clip when Printing "AsIs" or // when printing an IFrame for SelectedFrame or EachFrame PRBool setClip = PR_FALSE; switch (mPrt->mPrintFrameType) { @@ -2800,7 +3046,7 @@ DocumentViewerImpl::PrintPage(nsIPresContext* aPresContext, } break; - } //switch + } //switch if (setClip) { // Always set the clip x,y to zero because it isn't going to have any margins @@ -2814,7 +3060,7 @@ DocumentViewerImpl::PrintPage(nsIPresContext* aPresContext, // fail and the failure is passed back here. // Returning PR_TRUE means we are done printing. // - // When rv == NS_ERROR_ABORT, it means we want out of the + // When rv == NS_ERROR_ABORT, it means we want out of the // print job without displaying any error messages nsresult rv = mPageSeqFrame->PrintNextPage(aPresContext); if (NS_FAILED(rv)) { @@ -2823,7 +3069,7 @@ DocumentViewerImpl::PrintPage(nsIPresContext* aPresContext, mPrt->mIsAborted = PR_TRUE; } return PR_TRUE; - } + } // Now see if any of the SubDocs are on this page if (aPO->mPrintAsIs) { @@ -2889,9 +3135,9 @@ PrintObject * DocumentViewerImpl::FindPrintObjectByWS(PrintObject* aPO, nsIWebSh //------------------------------------------------------- // Recursively build a list of of sub documents to be printed // that mirrors the document tree -void -DocumentViewerImpl::BuildDocTree(nsIDocShellTreeNode * aParentNode, - nsVoidArray * aDocList, +void +DocumentViewerImpl::BuildDocTree(nsIDocShellTreeNode * aParentNode, + nsVoidArray * aDocList, PrintObject * aPO) { NS_ASSERTION(aParentNode, "Pointer is null!"); @@ -2899,7 +3145,7 @@ DocumentViewerImpl::BuildDocTree(nsIDocShellTreeNode * aParentNode, NS_ASSERTION(aPO, "Pointer is null!"); // Get the Doc and Title String - GetWebShellTitleAndURL(aPO->mWebShell, &aPO->mDocTitle, &aPO->mDocURL); + GetWebShellTitleAndURL(aPO->mWebShell, &aPO->mDocTitle, &aPO->mDocURL); PRInt32 childWebshellCount; aParentNode->GetChildCount(&childWebshellCount); @@ -2908,6 +3154,14 @@ DocumentViewerImpl::BuildDocTree(nsIDocShellTreeNode * aParentNode, nsCOMPtr child; aParentNode->GetChildAt(i, getter_AddRefs(child)); nsCOMPtr childAsShell(do_QueryInterface(child)); + + nsCOMPtr presShell; + childAsShell->GetPresShell(getter_AddRefs(presShell)); + + if (!presShell) { + continue; + } + nsCOMPtr viewer; childAsShell->GetContentViewer(getter_AddRefs(viewer)); if (viewer) { @@ -2938,7 +3192,7 @@ DocumentViewerImpl::SetPrintAsIs(PrintObject* aPO, PRBool aAsIs) aPO->mPrintAsIs = aAsIs; for (PRInt32 i=0;imKids.Count();i++) { SetPrintAsIs((PrintObject*)aPO->mKids[i], aAsIs); - } + } } //------------------------------------------------------- @@ -2952,7 +3206,7 @@ DocumentViewerImpl::SetPrintPO(PrintObject* aPO, PRBool aPrint) aPO->mDontPrint = !aPrint; for (PRInt32 i=0;imKids.Count();i++) { SetPrintPO((PrintObject*)aPO->mKids[i], aPrint); - } + } } //------------------------------------------------------- @@ -2962,7 +3216,7 @@ DocumentViewerImpl::SetPrintPO(PrintObject* aPO, PRBool aPrint) // NOTE: This MUST be done after the sub-doc has been laid out // This is called by "MapSubDocFrameLocations" // -nsresult +nsresult DocumentViewerImpl::CalcPageFrameLocation(nsIPresShell * aPresShell, PrintObject* aPO) { @@ -2973,7 +3227,7 @@ DocumentViewerImpl::CalcPageFrameLocation(nsIPresShell * aPresShell, // Find that frame for the sub-doc's content element // in the parent document - // if it comes back null it probably has the style + // if it comes back null it probably has the style // set to "display:none" nsIFrame * frame; aPresShell->GetPrimaryFrameFor(aPO->mContent, &frame); @@ -3003,9 +3257,9 @@ DocumentViewerImpl::CalcPageFrameLocation(nsIPresShell * aPresShell, rect.y += rr.y; nsIFrame * temp = parent; temp->GetParent(&parent); - // Keep a pointer to the Seq and Page frames + // Keep a pointer to the Seq and Page frames nsIPageSequenceFrame * sqf = nsnull; - if (parent != nsnull && + if (parent != nsnull && NS_SUCCEEDED(CallQueryInterface(parent, &sqf)) && sqf) { pageFrame = temp; seqFrame = parent; @@ -3069,17 +3323,17 @@ DocumentViewerImpl::MapSubDocFrameLocations(PrintObject* aPO) // // This "maps" or figures out which sub-doc represents a // given Frame or IFrame in it's parent sub-doc. -// +// // So the Mcontent pointer in the child sub-doc points to the // content in the it's parent document, that caused it to be printed. // This is used later to (after reflow) to find the absolute location -// of the sub-doc on it's parent's page frame so it can be +// of the sub-doc on it's parent's page frame so it can be // printed in the correct location. // // This method recursvely "walks" the content for a document finding // all the Frames and IFrames, then sets the "mFrameType" data member // which tells us what type of PO we have -void +void DocumentViewerImpl::MapContentForPO(PrintObject* aRootObject, nsIPresShell* aPresShell, nsIContent* aContent) @@ -3088,19 +3342,38 @@ DocumentViewerImpl::MapContentForPO(PrintObject* aRootObject, NS_ASSERTION(aPresShell, "Pointer is null!"); NS_ASSERTION(aContent, "Pointer is null!"); - nsCOMPtr supps; - aPresShell->GetSubShellFor(aContent, getter_AddRefs(supps)); - if (supps) { - nsCOMPtr webShell(do_QueryInterface(supps)); - if (webShell) { + nsCOMPtr doc; + aContent->GetDocument(*getter_AddRefs(doc)); + + if (!doc) { + NS_ERROR("No document!"); + + return; + } + + nsCOMPtr subDoc; + doc->GetSubDocumentFor(aContent, getter_AddRefs(subDoc)); + + if (subDoc) { + nsCOMPtr container; + subDoc->GetContainer(getter_AddRefs(container)); + + nsCOMPtr presShell; + subDoc->GetShellAt(0, getter_AddRefs(presShell)); + + nsCOMPtr webShell(do_QueryInterface(container)); + + if (presShell && webShell) { PrintObject * po = FindPrintObjectByWS(aRootObject, webShell); NS_ASSERTION(po, "PO can't be null!"); - if (po != nsnull) { + if (po) { po->mContent = aContent; - // Now, "type" the PO - nsCOMPtr frameSet(do_QueryInterface(aContent)); + // Now, "type" the PO + nsCOMPtr frameSet = + do_QueryInterface(aContent); + if (frameSet) { po->mFrameType = eFrameSet; } else { @@ -3108,8 +3381,11 @@ DocumentViewerImpl::MapContentForPO(PrintObject* aRootObject, if (frame) { po->mFrameType = eFrame; } else { - nsCOMPtr objElement(do_QueryInterface(aContent)); - nsCOMPtr iFrame(do_QueryInterface(aContent)); + nsCOMPtr objElement = + do_QueryInterface(aContent); + nsCOMPtr iFrame = + do_QueryInterface(aContent); + if (iFrame || objElement) { po->mFrameType = eIFrame; po->mPrintAsIs = PR_TRUE; @@ -3135,11 +3411,11 @@ DocumentViewerImpl::MapContentForPO(PrintObject* aRootObject, //------------------------------------------------------- // The walks the PO tree and for each document it walks the content -// tree looking for any content that are sub-shells +// tree looking for any content that are sub-shells // -// It then sets the mContent pointer in the "found" PO object back to the +// It then sets the mContent pointer in the "found" PO object back to the // the document that contained it. -void +void DocumentViewerImpl::MapContentToWebShells(PrintObject* aRootPO, PrintObject* aPO) { @@ -3157,16 +3433,16 @@ DocumentViewerImpl::MapContentToWebShells(PrintObject* aRootPO, // Continue recursively walking the chilren of this PO for (PRInt32 i=0;imKids.Count();i++) { MapContentToWebShells(aRootPO, (PrintObject*)aPO->mKids[i]); - } + } } //------------------------------------------------------- // This gets ref counted copies of the PresShell and Root Content // for a given nsIWebShell -void -DocumentViewerImpl::GetPresShellAndRootContent(nsIWebShell * aWebShell, - nsIPresShell** aPresShell, +void +DocumentViewerImpl::GetPresShellAndRootContent(nsIWebShell * aWebShell, + nsIPresShell** aPresShell, nsIContent** aContent) { NS_ASSERTION(aWebShell, "Pointer is null!"); @@ -3192,8 +3468,8 @@ DocumentViewerImpl::GetPresShellAndRootContent(nsIWebShell * aWebShell, //------------------------------------------------------- // Recursively sets the clip rect on all thchildren -void -DocumentViewerImpl::SetClipRect(PrintObject* aPO, +void +DocumentViewerImpl::SetClipRect(PrintObject* aPO, const nsRect& aClipRect, nscoord aOffsetX, nscoord aOffsetY, @@ -3207,8 +3483,8 @@ DocumentViewerImpl::SetClipRect(PrintObject* aPO, nscoord height = (aPO->mRect.y+aPO->mRect.height) > aClipRect.height?aClipRect.height-aPO->mRect.y:aPO->mRect.height; aPO->mClipRect.SetRect(aPO->mRect.x, aPO->mRect.y, width, height); - } - + } + PRBool doClip = aDoingSetClip; if (aPO->mFrameType == eFrame) { @@ -3249,7 +3525,7 @@ DocumentViewerImpl::SetClipRect(PrintObject* aPO, PRInt32 cnt = aPO->mKids.Count(); for (PRInt32 i=0;imKids[i], clipRect, + SetClipRect((PrintObject *)aPO->mKids[i], clipRect, aOffsetX+aPO->mRect.x, aOffsetY+aPO->mRect.y, doClip); } } @@ -3257,12 +3533,12 @@ DocumentViewerImpl::SetClipRect(PrintObject* aPO, //------------------------------------------------------- // Recursively reflow each sub-doc and then calc // all the frame locations of the sub-docs -nsresult +nsresult DocumentViewerImpl::ReflowDocList(PrintObject* aPO, PRBool aSetPixelScale, PRBool aDoCalcShrink) { NS_ASSERTION(aPO, "Pointer is null!"); - // Here is where we set the shrinkage value into the DC + // Here is where we set the shrinkage value into the DC // and this is what actually makes it shrink if (aSetPixelScale && aPO->mFrameType != eIFrame) { float ratio; @@ -3274,7 +3550,7 @@ DocumentViewerImpl::ReflowDocList(PrintObject* aPO, PRBool aSetPixelScale, PRBoo mPrt->mPrintDC->SetCanonicalPixelScale(ratio*mPrt->mOrigDCScale); } - // Reflow the PO + // Reflow the PO if (NS_FAILED(ReflowPrintObject(aPO, aDoCalcShrink))) { return NS_ERROR_FAILURE; } @@ -3354,7 +3630,8 @@ DocumentViewerImpl::ReflowPrintObject(PrintObject * aPO, PRBool aDoCalcShrink) return rv; } - rv = document->CreateShell(aPO->mPresContext, aPO->mViewManager, aPO->mStyleSet, getter_AddRefs(aPO->mPresShell)); + rv = document->CreateShell(aPO->mPresContext, aPO->mViewManager, + aPO->mStyleSet, getter_AddRefs(aPO->mPresShell)); if (NS_FAILED(rv)) { return rv; } @@ -3364,7 +3641,7 @@ DocumentViewerImpl::ReflowPrintObject(PrintObject * aPO, PRBool aDoCalcShrink) PRInt32 width, height; if (aPO->mContent == nsnull || !aPO->mPrintAsIs || - (aPO->mPrintAsIs && aPO->mParent != nsnull && !aPO->mParent->mPrintAsIs) || + (aPO->mPrintAsIs && aPO->mParent && !aPO->mParent->mPrintAsIs) || (aPO->mFrameType == eIFrame && aPO == mPrt->mSelectedPO)) { width = pageWidth; height = pageHeight; @@ -3375,22 +3652,25 @@ DocumentViewerImpl::ReflowPrintObject(PrintObject * aPO, PRBool aDoCalcShrink) PRINT_DEBUG_MSG5("In DV::ReflowPrintObject PO: %p (%9s) Setting w,h to %d,%d\n", aPO, gFrameTypesStr[aPO->mFrameType], width, height); - nsCOMPtr domWinIntl(do_QueryInterface(mPrt->mPrintDocDW)); + nsCOMPtr domWinIntl = + do_QueryInterface(mPrt->mPrintDocDW); // XXX - Hack Alert - // OK, so ther eis a selection, we will print the entire selection + // OK, so ther eis a selection, we will print the entire selection // on one page and then crop the page. - // This means you can never print any selection that is longer than one page - // put it keeps it from page breaking in the middle of your print of the selection - // (see also nsSimplePageSequence.cpp) + // This means you can never print any selection that is longer than + // one page put it keeps it from page breaking in the middle of your + // print of the selection (see also nsSimplePageSequence.cpp) PRInt16 printRangeType = nsIPrintSettings::kRangeAllPages; if (mPrt->mPrintSettings != nsnull) { mPrt->mPrintSettings->GetPrintRange(&printRangeType); } - if (printRangeType == nsIPrintSettings::kRangeSelection && IsThereARangeSelection(domWinIntl)) { + if (printRangeType == nsIPrintSettings::kRangeSelection && + IsThereARangeSelection(domWinIntl)) { height = NS_UNCONSTRAINEDSIZE; } + nsRect tbounds = nsRect(0, 0, width, height); // Create a child window of the parent that is our "root view/window" @@ -3404,7 +3684,7 @@ DocumentViewerImpl::ReflowPrintObject(PrintObject * aPO, PRBool aDoCalcShrink) } #ifdef NS_PRINT_PREVIEW - // Here we decide whether we need scrollbars and + // Here we decide whether we need scrollbars and // what the parent will be of the widget if (mIsCreatingPrintPreview) { PRBool canCreateScrollbars = PR_FALSE; @@ -3416,16 +3696,17 @@ DocumentViewerImpl::ReflowPrintObject(PrintObject * aPO, PRBool aDoCalcShrink) NS_ASSERTION(frameMan, "No Frame manager!"); nsIFrame* frame; frameMan->GetPrimaryFrameFor(aPO->mContent, &frame); - if (frame != nsnull && (aPO->mFrameType == eIFrame || aPO->mFrameType == eFrame)) { + if (frame && (aPO->mFrameType == eIFrame || aPO->mFrameType == eFrame)) { frame->FirstChild(aPO->mParent->mPresContext, nsnull, &frame); } - if (frame != nsnull) { + + if (frame) { nsIView* view = nsnull; frame->GetView(aPO->mParent->mPresContext, &view); - if (view != nsnull) { + if (view) { nsCOMPtr w2; view->GetWidget(*getter_AddRefs(w2)); - if (nsnull != w2) { + if (w2) { widget = w2; } canCreateScrollbars = PR_FALSE; @@ -3476,9 +3757,9 @@ DocumentViewerImpl::ReflowPrintObject(PrintObject * aPO, PRBool aDoCalcShrink) // initialize it with the default/generic case nsRect adjRect(aPO->mRect.x != 0?margin.left:0, aPO->mRect.y != 0?margin.top:0, width, height); - // XXX This is an arbitray height, + // XXX This is an arbitray height, // but reflow somethimes gets upset when using max int - // basically, we want to reflow a single page that is large + // basically, we want to reflow a single page that is large // enough to fit any atomic object like an IFrame const PRInt32 kFivePagesHigh = 5; @@ -3570,7 +3851,7 @@ DocumentViewerImpl::ReflowPrintObject(PrintObject * aPO, PRBool aDoCalcShrink) nsRect rect; child->GetRect(rect); - // Create a RenderingContext and set the PresContext + // Create a RenderingContext and set the PresContext // appropriately if we are printing selection nsCOMPtr rc; if (nsIPrintSettings::kRangeSelection == printRangeType) { @@ -3653,7 +3934,7 @@ DocumentViewerImpl::ReflowPrintObject(PrintObject * aPO, PRBool aDoCalcShrink) //------------------------------------------------------- // Given a DOMWindow it recursively finds the PO object that matches -PrintObject* +PrintObject* DocumentViewerImpl::FindPrintObjectByDOMWin(PrintObject* aPO, nsIDOMWindowInternal * aDOMWin) { NS_ASSERTION(aPO, "Pointer is null!"); @@ -3687,12 +3968,11 @@ DocumentViewerImpl::GetDOMWinForWebShell(nsIWebShell* aWebShell) NS_ASSERTION(aWebShell, "Pointer is null!"); nsCOMPtr domWin = do_GetInterface(aWebShell); - if (!domWin) return nsnull; nsCOMPtr domWinInt(do_QueryInterface(domWin)); if (!domWinInt) return nsnull; - nsIDOMWindowInternal * dw = NS_STATIC_CAST(nsIDOMWindowInternal *, domWinInt.get()); + nsIDOMWindowInternal * dw = domWinInt.get(); NS_ADDREF(dw); return dw; @@ -3710,10 +3990,10 @@ DocumentViewerImpl::EnablePOsForPrinting() return NS_ERROR_FAILURE; } - mPrt->mPrintFrameType = nsIPrintSettings::kNoFrames; + mPrt->mPrintFrameType = nsIPrintSettings::kNoFrames; mPrt->mPrintSettings->GetPrintFrameType(&mPrt->mPrintFrameType); - PRInt16 printHowEnable = nsIPrintSettings::kFrameEnableNone; + PRInt16 printHowEnable = nsIPrintSettings::kFrameEnableNone; mPrt->mPrintSettings->GetHowToEnableFrameUI(&printHowEnable); PRInt16 printRangeType = nsIPrintSettings::kRangeAllPages; @@ -3731,13 +4011,13 @@ DocumentViewerImpl::EnablePOsForPrinting() // then set the mPrintFrameType as if it were the selected frame if (printRangeType == nsIPrintSettings::kRangeSelection) { mPrt->mPrintFrameType = nsIPrintSettings::kSelectedFrame; - printHowEnable = nsIPrintSettings::kFrameEnableNone; + printHowEnable = nsIPrintSettings::kFrameEnableNone; } // This tells us that the "Frame" UI has turned off, // so therefore there are no FrameSets/Frames/IFrames to be printed // - // This means there are not FrameSets, + // This means there are not FrameSets, // but the document could contain an IFrame if (printHowEnable == nsIPrintSettings::kFrameEnableNone) { @@ -3763,7 +4043,7 @@ DocumentViewerImpl::EnablePOsForPrinting() PRINT_DEBUG_MSG2("PrintRange: %s \n", gPrintRangeStr[printRangeType]); return NS_OK; } - + // This means we are either printed a selected IFrame or // we are printing the current selection if (printRangeType == nsIPrintSettings::kRangeSelection) { @@ -3780,12 +4060,12 @@ DocumentViewerImpl::EnablePOsForPrinting() // Now, only enable this POs (the selected PO) and all of its children SetPrintPO(po, PR_TRUE); - // check to see if we have a range selection, + // check to see if we have a range selection, // as oppose to a insert selection - // this means if the user just clicked on the IFrame then + // this means if the user just clicked on the IFrame then // there will not be a selection so we want the entire page to print // - // XXX this is sort of a hack right here to make the page + // XXX this is sort of a hack right here to make the page // not try to reposition itself when printing selection nsCOMPtr domWin = getter_AddRefs(GetDOMWinForWebShell(po->mWebShell)); if (!IsThereARangeSelection(domWin)) { @@ -3827,12 +4107,12 @@ DocumentViewerImpl::EnablePOsForPrinting() // Now, only enable this POs (the selected PO) and all of its children SetPrintPO(po, PR_TRUE); - // check to see if we have a range selection, + // check to see if we have a range selection, // as oppose to a insert selection - // this means if the user just clicked on the IFrame then + // this means if the user just clicked on the IFrame then // there will not be a selection so we want the entire page to print // - // XXX this is sort of a hack right here to make the page + // XXX this is sort of a hack right here to make the page // not try to reposition itself when printing selection nsCOMPtr domWin = getter_AddRefs(GetDOMWinForWebShell(po->mWebShell)); if (!IsThereARangeSelection(domWin)) { @@ -3863,9 +4143,9 @@ DocumentViewerImpl::EnablePOsForPrinting() PrintObject * po = FindPrintObjectByDOMWin(mPrt->mPrintObject, mPrt->mCurrentFocusWin); if (po != nsnull) { mPrt->mSelectedPO = po; - // NOTE: Calling this sets the "po" and + // NOTE: Calling this sets the "po" and // we don't want to do this for documents that have no children, - // because then the "DoEndPage" gets called and it shouldn't + // because then the "DoEndPage" gets called and it shouldn't if (po->mKids.Count() > 0) { // Makes sure that itself, and all of its children are printed "AsIs" SetPrintAsIs(po); @@ -3876,10 +4156,10 @@ DocumentViewerImpl::EnablePOsForPrinting() } } return NS_OK; - } - - // If we are print each subdoc separately, - // then don't print any of the FraneSet Docs + } + + // If we are print each subdoc separately, + // then don't print any of the FraneSet Docs if (mPrt->mPrintFrameType == nsIPrintSettings::kEachFrameSep) { SetPrintPO(mPrt->mPrintObject, PR_TRUE); PRInt32 cnt = mPrt->mPrintDocList->Count(); @@ -3897,11 +4177,11 @@ DocumentViewerImpl::EnablePOsForPrinting() //--------------------------------------------------- // Find the Frame in a Frame List that is XMost -void -DocumentViewerImpl::FindXMostFrameInList(nsIPresContext* aPresContext, +void +DocumentViewerImpl::FindXMostFrameInList(nsIPresContext* aPresContext, nsIRenderingContext* aRC, nsIAtom* aList, - nsIFrame* aFrame, + nsIFrame* aFrame, nscoord aX, nscoord aY, PRInt32& aMaxWidth) @@ -3910,7 +4190,7 @@ DocumentViewerImpl::FindXMostFrameInList(nsIPresContext* aPresContext, aFrame->FirstChild(aPresContext, aList, &child); while (child) { PRBool isVisible = PR_TRUE; - // If the aRC is nsnull, then we skip the more expensive check and + // If the aRC is nsnull, then we skip the more expensive check and // just check visibility if (aRC) { child->IsVisibleForPainting(aPresContext, *aRC, PR_TRUE, &isVisible); @@ -3963,10 +4243,10 @@ DocumentViewerImpl::FindXMostFrameInList(nsIPresContext* aPresContext, //--------------------------------------------------- // Find the Frame that is XMost -void -DocumentViewerImpl::FindXMostFrameSize(nsIPresContext* aPresContext, +void +DocumentViewerImpl::FindXMostFrameSize(nsIPresContext* aPresContext, nsIRenderingContext* aRC, - nsIFrame* aFrame, + nsIFrame* aFrame, nscoord aX, nscoord aY, PRInt32& aMaxWidth) @@ -3981,15 +4261,15 @@ DocumentViewerImpl::FindXMostFrameSize(nsIPresContext* aPresContext, FindXMostFrameInList(aPresContext, aRC, childListName, aFrame, aX, aY, aMaxWidth); NS_IF_RELEASE(childListName); aFrame->GetAdditionalChildListName(childListIndex++, &childListName); - } while (childListName); + } while (childListName); } //------------------------------------------------------- -// Return the PrintObject with that is XMost (The widest frameset frame) AND -// contains the XMost (widest) layout frame -PrintObject* +// Return the PrintObject with that is XMost (The widest frameset frame) AND +// contains the XMost (widest) layout frame +PrintObject* DocumentViewerImpl::FindXMostPO() { nscoord xMostForPO = 0; @@ -4097,7 +4377,7 @@ DocumentViewerImpl::SetupToPrintContent(nsIWebShell* aParent, PRINT_DEBUG_MSG1("\n-------------------------------------------------------\n\n"); // Set up the clipping rectangle for all documents - // When frames are being printed as part of a frame set and also IFrames, + // When frames are being printed as part of a frame set and also IFrames, // they are reflowed with a very large page height. We need to setup the // clipping so they do not rpint over top of anything else PRINT_DEBUG_MSG1("SetClipRect-------------------------------------------------------\n"); @@ -4132,7 +4412,7 @@ DocumentViewerImpl::SetupToPrintContent(nsIWebShell* aParent, // This will print the webshell document // when it completes asynchronously in the DonePrintingPages method - // it will check to see if there are more webshells to be printed and + // it will check to see if there are more webshells to be printed and // then PrintDocContent will be called again. nsresult rv = NS_OK; @@ -4189,7 +4469,7 @@ DocumentViewerImpl::DoPrint(PrintObject * aPO, PRBool aDoSyncPrinting, PRBool& a if (aPO->mFrameType == eFrame) { switch (mPrt->mPrintFrameType) { - case nsIPrintSettings::kFramesAsIs: + case nsIPrintSettings::kFramesAsIs: skipAllPageAdjustments = PR_TRUE; doOffsetting = PR_TRUE; break; @@ -4238,7 +4518,7 @@ DocumentViewerImpl::DoPrint(PrintObject * aPO, PRBool aDoSyncPrinting, PRBool& a skipPageEjectOnly = aPO->mPrintAsIs; } - // That we are all configured, + // That we are all configured, // let's set everything up to print if (skipPageEjectOnly) { pageSequence->SkipPageEnd(); @@ -4272,8 +4552,8 @@ DocumentViewerImpl::DoPrint(PrintObject * aPO, PRBool aDoSyncPrinting, PRBool& a } } - PRINT_DEBUG_MSG5("*** skipPageEjectOnly: %s skipAllPageAdjustments: %s doOffsetting: %s doAddInParentsOffset: %s\n", - PRT_YESNO(skipPageEjectOnly), PRT_YESNO(skipAllPageAdjustments), + PRINT_DEBUG_MSG5("*** skipPageEjectOnly: %s skipAllPageAdjustments: %s doOffsetting: %s doAddInParentsOffset: %s\n", + PRT_YESNO(skipPageEjectOnly), PRT_YESNO(skipAllPageAdjustments), PRT_YESNO(doOffsetting), PRT_YESNO(doAddInParentsOffset)); // We are done preparing for printing, so we can turn this off @@ -4290,7 +4570,7 @@ DocumentViewerImpl::DoPrint(PrintObject * aPO, PRBool aDoSyncPrinting, PRBool& a if (NS_SUCCEEDED(CallQueryInterface(root, &fdbg))) { fdbg->DumpRegressionData(poPresContext, mPrt->mDebugFilePtr, 0, PR_TRUE); } - fclose(mPrt->mDebugFilePtr); + fclose(mPrt->mDebugFilePtr); #endif } else { nsIFrame* rootFrame; @@ -4311,9 +4591,10 @@ DocumentViewerImpl::DoPrint(PrintObject * aPO, PRBool aDoSyncPrinting, PRBool& a if (!skipSetTitle) { PRUnichar * docTitleStr; PRUnichar * docURLStr; - GetDisplayTitleAndURL(aPO, mPrt->mPrintSettings, mPrt->mBrandName, &docTitleStr, &docURLStr, eDocTitleDefBlank); + GetDisplayTitleAndURL(aPO, mPrt->mPrintSettings, mPrt->mBrandName, + &docTitleStr, &docURLStr, eDocTitleDefBlank); - // Set them down into the PrintOptions so + // Set them down into the PrintOptions so // they can used by the DeviceContext if (docTitleStr) { mPrt->mPrintOptions->SetTitle(docTitleStr); @@ -4347,8 +4628,8 @@ DocumentViewerImpl::DoPrint(PrintObject * aPO, PRBool aDoSyncPrinting, PRBool& a if (NS_SUCCEEDED(rvv) && selectionPS) { } - rv = GetPageRangeForSelection(poPresShell, poPresContext, *rc, selectionPS, pageSequence, - &startFrame, startPageNum, startRect, + rv = GetPageRangeForSelection(poPresShell, poPresContext, *rc, selectionPS, pageSequence, + &startFrame, startPageNum, startRect, &endFrame, endPageNum, endRect); if (NS_SUCCEEDED(rv)) { mPrt->mPrintSettings->SetStartPageRange(startPageNum); @@ -4516,7 +4797,7 @@ DocumentViewerImpl::PrintDocContent(PrintObject* aPO, nsresult& aStatus) if (!aPO->mHasBeenPrinted && aPO->IsPrintable()) { PRBool donePrinting; // donePrinting is only valid when when doing synchronous printing - aStatus = DoPrint(aPO, PR_FALSE, donePrinting); + aStatus = DoPrint(aPO, PR_FALSE, donePrinting); if (donePrinting) { return PR_TRUE; } @@ -4528,8 +4809,8 @@ DocumentViewerImpl::PrintDocContent(PrintObject* aPO, nsresult& aStatus) if (printed || NS_FAILED(aStatus)) { return PR_TRUE; } - } - return PR_FALSE; + } + return PR_FALSE; } NS_IMETHODIMP @@ -4540,11 +4821,11 @@ DocumentViewerImpl::SetEnableRendering(PRBool aOn) if (mViewManager) { if (aOn) { mViewManager->EnableRefresh(NS_VMREFRESH_IMMEDIATE); - nsIView* view; - mViewManager->GetRootView(view); // views are not refCounted - if (view) { + nsIView* view; + mViewManager->GetRootView(view); // views are not refCounted + if (view) { mViewManager->UpdateView(view, NS_VMREFRESH_IMMEDIATE); - } + } } else { mViewManager->DisableRefresh(); @@ -4604,7 +4885,7 @@ DocumentViewerImpl::CreateStyleSet(nsIDocument* aDocument, } } - nsCOMPtr chromeRegistry = + nsCOMPtr chromeRegistry = do_GetService("@mozilla.org/chrome/chrome-registry;1", &rv); if (NS_SUCCEEDED(rv) && chromeRegistry) { nsCOMPtr sheets; @@ -4660,7 +4941,7 @@ DocumentViewerImpl::MakeWindow(nsIWidget* aParentWidget, nsCOMPtr dx; mPresContext->GetDeviceContext(getter_AddRefs(dx)); - + nsRect tbounds = aBounds; float p2t; mPresContext->GetPixelsToTwips(&p2t); @@ -4675,11 +4956,11 @@ DocumentViewerImpl::MakeWindow(nsIWidget* aParentWidget, if (NS_FAILED(rv)) return rv; - // Reset the bounds offset so the root view is set to 0,0. The offset is - // specified in nsIViewManager::Init above. - // Besides, layout will reset the root view to (0,0) during reflow, - // so changing it to 0,0 eliminates placing - // the root view in the wrong place initially. + // Reset the bounds offset so the root view is set to 0,0. The + // offset is specified in nsIViewManager::Init above. + // Besides, layout will reset the root view to (0,0) during reflow, + // so changing it to 0,0 eliminates placing the root view in the + // wrong place initially. tbounds.x = 0; tbounds.y = 0; @@ -4694,7 +4975,7 @@ DocumentViewerImpl::MakeWindow(nsIWidget* aParentWidget, nsIView* containerView = nsnull; if (NS_SUCCEEDED(aParentWidget->GetClientData(clientData))) { nsISupports* data = (nsISupports*)clientData; - + if (nsnull != data) { data->QueryInterface(NS_GET_IID(nsIView), (void **)&containerView); } @@ -4718,7 +4999,7 @@ DocumentViewerImpl::MakeWindow(nsIWidget* aParentWidget, // // If the parent container is a chrome shell, or a frameset, then we won't hook into its view // tree. This will improve performance a little bit (especially given scrolling/painting perf bugs) - // but is really just for peace of mind. This check can be removed if we want to support fancy + // but is really just for peace of mind. This check can be removed if we want to support fancy // chrome effects like transparent controls floating over content, transparent Web browsers, and // things like that, and the perf bugs are fixed. nsCOMPtr container(do_QueryInterface(mContainer)); @@ -4775,8 +5056,8 @@ nsresult DocumentViewerImpl::GetDocumentSelection(nsISelection **aSelection, nsI nsCOMPtr selcon; selcon = do_QueryInterface(aPresShell); - if (selcon) - return selcon->GetSelection(nsISelectionController::SELECTION_NORMAL, aSelection); + if (selcon) + return selcon->GetSelection(nsISelectionController::SELECTION_NORMAL, aSelection); return NS_ERROR_FAILURE; } @@ -4788,13 +5069,13 @@ DocumentViewerImpl::CreateDocumentViewerUsing(nsIPresContext* aPresContext, // XXX better error return NS_ERROR_NULL_POINTER; } - if (nsnull == aPresContext) { + if (!aPresContext) { return NS_ERROR_NULL_POINTER; } // Create new viewer DocumentViewerImpl* viewer = new DocumentViewerImpl(aPresContext); - if (nsnull == viewer) { + if (!viewer) { return NS_ERROR_OUT_OF_MEMORY; } NS_ADDREF(viewer); @@ -4805,7 +5086,7 @@ DocumentViewerImpl::CreateDocumentViewerUsing(nsIPresContext* aPresContext, // Bind the new viewer to the old document nsresult rv = viewer->LoadStart(mDocument); - + aResult = viewer; return rv; @@ -4854,7 +5135,7 @@ nsresult DocumentViewerImpl::DocumentReadyForPrinting() return rv; } -NS_IMETHODIMP +NS_IMETHODIMP DocumentViewerImpl::SetTransformMediator(nsITransformMediator* aMediator) { NS_ASSERTION(nsnull == mTransformMediator, "nsXMLDocument::SetTransformMediator(): \ @@ -4906,7 +5187,7 @@ NS_IMETHODIMP DocumentViewerImpl::SelectAll() nsCOMPtr htmldoc = do_QueryInterface(mDocument); nsCOMPtr bodyNode; - + if (htmldoc) { nsCOMPtrbodyElement; @@ -4921,8 +5202,8 @@ NS_IMETHODIMP DocumentViewerImpl::SelectAll() mDocument->GetRootContent(getter_AddRefs(rootContent)); bodyNode = do_QueryInterface(rootContent); } - if (!bodyNode) return NS_ERROR_FAILURE; - + if (!bodyNode) return NS_ERROR_FAILURE; + rv = selection->RemoveAllRanges(); if (NS_FAILED(rv)) return rv; @@ -4975,10 +5256,10 @@ NS_IMETHODIMP DocumentViewerImpl::GetCopyable(PRBool *aCopyable) nsresult rv; rv = GetDocumentSelection(getter_AddRefs(selection)); if (NS_FAILED(rv)) return rv; - + PRBool isCollapsed; selection->GetIsCollapsed(&isCollapsed); - + *aCopyable = !isCollapsed; return NS_OK; } @@ -5063,7 +5344,7 @@ nsresult DocumentViewerImpl::GetSelectionDocument(nsIDeviceContextSpec * aDevSpe if (NS_FAILED(rv)) { return rv; } rv = htmlElement->AppendChildTo(bodyElement, PR_FALSE, PR_FALSE); if (NS_FAILED(rv)) { return rv; } - + // load the document into the docshell nsCOMPtr domDoc = do_QueryInterface(doc); if (!domDoc) { return NS_ERROR_NULL_POINTER; } @@ -5081,8 +5362,8 @@ nsresult DocumentViewerImpl::GetSelectionDocument(nsIDeviceContextSpec * aDevSpe } //------------------------------------------------------ -PRBool -DocumentViewerImpl::IsThereAnIFrameSelected(nsIWebShell* aWebShell, +PRBool +DocumentViewerImpl::IsThereAnIFrameSelected(nsIWebShell* aWebShell, nsIDOMWindowInternal * aDOMWin, PRPackedBool& aIsParentFrameSet) { @@ -5098,7 +5379,7 @@ DocumentViewerImpl::IsThereAnIFrameSelected(nsIWebShell* aWebShell, // if so, it means the selected frame is either the main webshell // or an IFRAME if (aDOMWin != nsnull) { - // Get the main webshell's DOMWin to see if it matches + // Get the main webshell's DOMWin to see if it matches // the frame that is selected nsCOMPtr domWin = getter_AddRefs(GetDOMWinForWebShell(aWebShell)); if (aDOMWin != nsnull && domWin != aDOMWin) { @@ -5112,7 +5393,7 @@ DocumentViewerImpl::IsThereAnIFrameSelected(nsIWebShell* aWebShell, //------------------------------------------------------ -PRBool +PRBool DocumentViewerImpl::IsThereARangeSelection(nsIDOMWindowInternal * aDOMWin) { nsCOMPtr presShell; @@ -5147,7 +5428,7 @@ DocumentViewerImpl::IsThereARangeSelection(nsIDOMWindowInternal * aDOMWin) //------------------------------------------------------- // Recursively walks the PrintObject tree and installs the DocViewer // as an event processor and it shows the window -nsresult +nsresult DocumentViewerImpl::ShowDocList(PrintObject* aPO, PRBool aShow) { NS_ASSERTION(aPO, "Pointer is null!"); @@ -5206,7 +5487,7 @@ DocumentViewerImpl::InstallPrintPreviewListener() //---------------------------------------------------------------------- static nsresult GetSeqFrameAndCountPages(PrintObject* aPO, - nsIFrame*& aSeqFrame, + nsIFrame*& aSeqFrame, PRInt32& aCount) { NS_ENSURE_ARG_POINTER(aPO); @@ -5353,7 +5634,7 @@ DocumentViewerImpl::PrintPreviewNavigate(PRInt16 aType, PRInt32 aPageNum) } /* readonly attribute boolean isFramesetDocument; */ -NS_IMETHODIMP +NS_IMETHODIMP DocumentViewerImpl::GetIsFramesetDocument(PRBool *aIsFramesetDocument) { nsCOMPtr webContainer(do_QueryInterface(mContainer)); @@ -5402,7 +5683,7 @@ DocumentViewerImpl::GetIsFramesetFrameSelected(PRBool *aIsFramesetFrameSelected) } /* readonly attribute long printPreviewNumPages; */ -NS_IMETHODIMP +NS_IMETHODIMP DocumentViewerImpl::GetPrintPreviewNumPages(PRInt32 *aPrintPreviewNumPages) { NS_ENSURE_ARG_POINTER(aPrintPreviewNumPages); @@ -5419,7 +5700,7 @@ DocumentViewerImpl::GetPrintPreviewNumPages(PRInt32 *aPrintPreviewNumPages) } /* void exitPrintPreview (); */ -NS_IMETHODIMP +NS_IMETHODIMP DocumentViewerImpl::ExitPrintPreview() { if (mIsDoingPrintPreview) { @@ -5465,7 +5746,7 @@ DocumentViewerImpl::InstallNewPresentation() nsCOMPtr selection; nsresult rv = GetDocumentSelection(getter_AddRefs(selection)); nsCOMPtr selPrivate(do_QueryInterface(selection)); - if (NS_SUCCEEDED(rv) && selPrivate && mSelectionListener) + if (NS_SUCCEEDED(rv) && selPrivate && mSelectionListener) selPrivate->RemoveSelectionListener(mSelectionListener); // We need to destroy the PreShell if there is an existing PP @@ -5501,7 +5782,7 @@ DocumentViewerImpl::InstallNewPresentation() // This is the new code for selecting the appropriate Frame of a Frameset // for Print Preview. But it can't be turned on yet -#if 0 +#if 0 // If it is a Frameset then choose the selected one // or select the one with the largest area if (mPrt->mPrintObject->mFrameType == eFrameSet) { @@ -5619,7 +5900,7 @@ DocumentViewerImpl::ReturnToGalleyPresentation() nsCOMPtr selection; nsresult rv = GetDocumentSelection(getter_AddRefs(selection)); nsCOMPtr selPrivate(do_QueryInterface(selection)); - if (NS_SUCCEEDED(rv) && selPrivate && mSelectionListener) + if (NS_SUCCEEDED(rv) && selPrivate && mSelectionListener) selPrivate->RemoveSelectionListener(mSelectionListener); mPresShell->Destroy(); } @@ -5680,7 +5961,7 @@ DocumentViewerImpl::ReturnToGalleyPresentation() // This method checks to see if there is at least one printer defined // and if so, it sets the first printer in the list as the default name // in the PrintSettings which is then used for Printer Preview -nsresult +nsresult DocumentViewerImpl::CheckForPrinters(nsIPrintOptions* aPrintOptions, nsIPrintSettings* aPrintSettings, PRUint32 aErrorCode, @@ -5698,7 +5979,7 @@ DocumentViewerImpl::CheckForPrinters(nsIPrintOptions* aPrintOptions, simpEnum->HasMoreElements(&fndPrinter); if (fndPrinter) { // For now, it assumes the first item in the list - // is the default printer, but only set the + // is the default printer, but only set the // printer name if there isn't one nsCOMPtr supps; simpEnum->GetNext(getter_AddRefs(supps)); @@ -5825,23 +6106,36 @@ DocumentViewerImpl::CheckDocumentForPPCaching() * See documentation above in the nsIContentViewerfile class definition * @update 11/01/01 rods * - * For a full and detailed understanding of the issues with - * PrintPreview: See the design spec that is attached to Bug 107562 + * For a full and detailed understanding of the issues with + * PrintPreview: See the design spec that is attached to Bug 107562 */ NS_IMETHODIMP DocumentViewerImpl::PrintPreview(nsIPrintSettings* aPrintSettings) { - // Get the webshell for this documentviewer - nsCOMPtr webContainer(do_QueryInterface(mContainer)); - // Get the DocShell and see if it is busy - // We can't Print or Print Preview this document if it is still busy - nsCOMPtr docShell(do_QueryInterface(webContainer)); - NS_ASSERTION(docShell.get(), "This has to be a docshell"); + nsCOMPtr docShell(do_QueryInterface(mContainer)); + NS_ASSERTION(docShell, "This has to be a docshell"); + + nsCOMPtr presShell; + docShell->GetPresShell(getter_AddRefs(presShell)); + + if (!presShell) { + // A frame that's not displayed can't be printed! + + return NS_OK; + } + + PRUint32 busyFlags = nsIDocShell::BUSY_FLAGS_NONE; - if (NS_FAILED(docShell->GetBusyFlags(&busyFlags)) || busyFlags != nsIDocShell::BUSY_FLAGS_NONE) { + + if (NS_FAILED(docShell->GetBusyFlags(&busyFlags)) || + busyFlags != nsIDocShell::BUSY_FLAGS_NONE) { ShowPrintErrorDialog(NS_ERROR_GFX_PRINTER_DOC_IS_BUSY_PP, PR_FALSE); return NS_ERROR_FAILURE; } + + // Get the webshell for this documentviewer + nsCOMPtr webContainer(do_QueryInterface(mContainer)); + nsresult rv = NS_OK; #if defined(XP_PC) && defined(DEBUG_rods) && defined(DEBUG_PRINTING) @@ -5872,12 +6166,13 @@ DocumentViewerImpl::PrintPreview(nsIPrintSettings* aPrintSettings) mOldPrtPreview->mCachedPresObj = nsnull; } - // You have to have both a PrintOptions and a PrintSetting to call CheckForPrinters. - // The user can pass in a null PrintSettings, - // but you can only create one if you have a PrintOptions. - // So we we might as check to if we have a PrintOptions first, - // because we can't do anything below without it - // then inside we check to se if the printSettings is null to know if we need to create on. + // You have to have both a PrintOptions and a PrintSetting to call + // CheckForPrinters. + // The user can pass in a null PrintSettings, but you can only + // create one if you have a PrintOptions. So we we might as check + // to if we have a PrintOptions first, because we can't do anything + // below without it then inside we check to se if the printSettings + // is null to know if we need to create on. mPrt->mPrintSettings = aPrintSettings; mPrt->mPrintOptions = do_GetService(kPrintOptionsCID, &rv); if (NS_SUCCEEDED(rv) && mPrt->mPrintOptions) { @@ -5894,7 +6189,7 @@ DocumentViewerImpl::PrintPreview(nsIPrintSettings* aPrintSettings) return NS_ERROR_FAILURE; } } - + // Let's print ... mIsCreatingPrintPreview = PR_TRUE; mIsDoingPrintPreview = PR_TRUE; @@ -5931,7 +6226,7 @@ DocumentViewerImpl::PrintPreview(nsIPrintSettings* aPrintSettings) mPrt->mPrintDocList->AppendElement(mPrt->mPrintObject); mPrt->mIsParentAFrameSet = IsParentAFrameSet(webContainer); - mPrt->mPrintObject->mFrameType = mPrt->mIsParentAFrameSet?eFrameSet:eDoc; + mPrt->mPrintObject->mFrameType = mPrt->mIsParentAFrameSet ? eFrameSet : eDoc; // Build the "tree" of PrintObjects nsCOMPtr parentAsNode(do_QueryInterface(webContainer)); @@ -5941,8 +6236,8 @@ DocumentViewerImpl::PrintPreview(nsIPrintSettings* aPrintSettings) // in the parent document MapContentToWebShells(mPrt->mPrintObject, mPrt->mPrintObject); - // Get whether the doc contains a frameset - // Also, check to see if the currently focus webshell + // Get whether the doc contains a frameset + // Also, check to see if the currently focus webshell // is a child of this webshell mPrt->mIsIFrameSelected = IsThereAnIFrameSelected(webContainer, mPrt->mCurrentFocusWin, mPrt->mIsParentAFrameSet); @@ -5969,7 +6264,7 @@ DocumentViewerImpl::PrintPreview(nsIPrintSettings* aPrintSettings) #ifdef DEBUG_PRINTING if (mPrt->mPrintSettings) { - PRInt16 printHowEnable = nsIPrintSettings::kFrameEnableNone; + PRInt16 printHowEnable = nsIPrintSettings::kFrameEnableNone; mPrt->mPrintSettings->GetHowToEnableFrameUI(&printHowEnable); PRBool val; mPrt->mPrintSettings->GetPrintOptions(nsIPrintSettings::kEnableSelectionRB, &val); @@ -5997,7 +6292,7 @@ DocumentViewerImpl::PrintPreview(nsIPrintSettings* aPrintSettings) nsCOMPtr dx; nsresult rv = factory->CreateDeviceContextSpec(mWindow, aPrintSettings, *getter_AddRefs(devspec), doSilent); if (NS_SUCCEEDED(rv)) { - rv = mDeviceContext->GetDeviceContextFor(devspec, *getter_AddRefs(ppDC)); + rv = mDeviceContext->GetDeviceContextFor(devspec, *getter_AddRefs(ppDC)); if (NS_SUCCEEDED(rv)) { mDeviceContext->SetAltDevice(ppDC); if (mPrt->mPrintSettings != nsnull) { @@ -6024,7 +6319,7 @@ DocumentViewerImpl::PrintPreview(nsIPrintSettings* aPrintSettings) mPrt->mPrintSettings->SetPrintRange(nsIPrintSettings::kRangeAllPages); } - mPrt->mPrintDC = mDeviceContext; + mPrt->mPrintDC = mDeviceContext; // Get the Original PixelScale incase we need to start changing it mPrt->mPrintDC->GetCanonicalPixelScale(mPrt->mOrigDCScale); @@ -6054,8 +6349,8 @@ DocumentViewerImpl::PrintPreview(nsIPrintSettings* aPrintSettings) } /* cleanup done, let's fire-up an error dialog to notify the user - * what went wrong... - */ + * what went wrong... + */ ShowPrintErrorDialog(rv, PR_FALSE); TurnScriptingOn(PR_TRUE); mIsCreatingPrintPreview = PR_FALSE; @@ -6064,7 +6359,7 @@ DocumentViewerImpl::PrintPreview(nsIPrintSettings* aPrintSettings) } - // At this point we are done preparing everything + // At this point we are done preparing everything // before it is to be created // Noew create the new Presentation and display it @@ -6161,7 +6456,7 @@ DocumentViewerImpl::DoPrintProgress(PRBool aIsForPrinting) */ NS_IMETHODIMP DocumentViewerImpl::Print(PRBool aSilent, - FILE * aDebugFile, + FILE * aDebugFile, nsIPrintSettings* aPrintSettings) { nsCOMPtr printSettings; @@ -6185,7 +6480,7 @@ DocumentViewerImpl::Print(PRBool aSilent, return Print(printSettings, nsnull); - + } /** --------------------------------------------------- @@ -6204,6 +6499,17 @@ DocumentViewerImpl::Print(nsIPrintSettings* aPrintSettings, nsresult rv = NS_ERROR_FAILURE; + nsCOMPtr docShell(do_QueryInterface(mContainer)); + NS_ASSERTION(docShell, "This has to be a docshell"); + + nsCOMPtr presShell; + docShell->GetPresShell(getter_AddRefs(presShell)); + + if (!presShell) { + // A frame that's not displayed can't be printed! + + return NS_OK; + } if (mIsDoingPrintPreview) { PRBool okToPrint = PR_FALSE; @@ -6218,7 +6524,7 @@ DocumentViewerImpl::Print(nsIPrintSettings* aPrintSettings, } // if we are printing another URL, then exit - // the reason we check here is because this method can be called while + // the reason we check here is because this method can be called while // another is still in here (the printing dialog is a good example). // the only time we can print more than one job at a time is the regression tests if (mIsDoingPrinting) { @@ -6227,7 +6533,7 @@ DocumentViewerImpl::Print(nsIPrintSettings* aPrintSettings, ShowPrintErrorDialog(rv); return rv; } - + mPrt = new PrintData(); if (mPrt == nsnull) { return NS_ERROR_OUT_OF_MEMORY; @@ -6266,7 +6572,7 @@ DocumentViewerImpl::Print(nsIPrintSettings* aPrintSettings, mPrt->mPrintProgressListeners.AppendElement((void*)aWebProgressListener); NS_ADDREF(aWebProgressListener); } - + // Get the currently focused window and cache it // because the Print Dialog will "steal" focus and later when you try // to get the currently focused windows it will be NULL @@ -6308,8 +6614,8 @@ DocumentViewerImpl::Print(nsIPrintSettings* aPrintSettings, MapContentToWebShells(mPrt->mPrintObject, mPrt->mPrintObject); - // Get whether the doc contains a frameset - // Also, check to see if the currently focus webshell + // Get whether the doc contains a frameset + // Also, check to see if the currently focus webshell // is a child of this webshell mPrt->mIsIFrameSelected = IsThereAnIFrameSelected(webContainer, mPrt->mCurrentFocusWin, mPrt->mIsParentAFrameSet); @@ -6331,7 +6637,7 @@ DocumentViewerImpl::Print(nsIPrintSettings* aPrintSettings, #ifdef DEBUG_PRINTING if (mPrt->mPrintSettings) { - PRInt16 printHowEnable = nsIPrintSettings::kFrameEnableNone; + PRInt16 printHowEnable = nsIPrintSettings::kFrameEnableNone; mPrt->mPrintSettings->GetHowToEnableFrameUI(&printHowEnable); PRBool val; mPrt->mPrintSettings->GetPrintOptions(nsIPrintSettings::kEnableSelectionRB, &val); @@ -6350,7 +6656,7 @@ DocumentViewerImpl::Print(nsIPrintSettings* aPrintSettings, /* create factory (incl. create print dialog) */ nsCOMPtr factory = do_CreateInstance(kDeviceContextSpecFactoryCID, &rv); - + if (NS_SUCCEEDED(rv)) { #ifdef DEBUG_dcone printf("PRINT JOB STARTING\n"); @@ -6472,7 +6778,7 @@ DocumentViewerImpl::Print(nsIPrintSettings* aPrintSettings, mPrt->mPrintFrameType = nsIPrintSettings::kEachFrameSep; mPrt->mPrintSettings->SetPrintFrameType(mPrt->mPrintFrameType); } else { - // First find out from the PrinService what options are available + // First find out from the PrinService what options are available // to us for Printing FrameSets PRInt16 howToEnableFrameUI; mPrt->mPrintSettings->GetHowToEnableFrameUI(&howToEnableFrameUI); @@ -6517,12 +6823,14 @@ DocumentViewerImpl::Print(nsIPrintSettings* aPrintSettings, PRUnichar * docTitleStr; PRUnichar * docURLStr; - GetDisplayTitleAndURL(mPrt->mPrintObject, mPrt->mPrintSettings, mPrt->mBrandName, &docTitleStr, &docURLStr, eDocTitleDefURLDoc); + GetDisplayTitleAndURL(mPrt->mPrintObject, mPrt->mPrintSettings, + mPrt->mBrandName, &docTitleStr, &docURLStr, + eDocTitleDefURLDoc); // BeginDocument may pass back a FAILURE code - // i.e. On Windows, if you are printing to a file and hit "Cancel" + // i.e. On Windows, if you are printing to a file and hit "Cancel" // to the "File Name" dialog, this comes back as an error - // Don't start printing when regression test are executed + // Don't start printing when regression test are executed rv = mPrt->mDebugFilePtr ? NS_OK: mPrt->mPrintDC->BeginDocument(docTitleStr); PRINT_DEBUG_MSG1("****************** Begin Document ************************\n"); @@ -6535,12 +6843,12 @@ DocumentViewerImpl::Print(nsIPrintSettings* aPrintSettings, // Print listener setup... if (mPrt != nsnull) { - mPrt->OnStartPrinting(); + mPrt->OnStartPrinting(); } // // The mIsPrinting flag is set when the ImageGroup observer is - // notified that images must be loaded as a result of the + // notified that images must be loaded as a result of the // InitialReflow... // if(!mIsPrinting || mPrt->mDebugFilePtr) { @@ -6553,20 +6861,18 @@ DocumentViewerImpl::Print(nsIPrintSettings* aPrintSettings, } } } - } + } } else { mPrt->mPrintSettings->SetIsCancelled(PR_TRUE); mPrt->mPrintOptions->SetIsCancelled(PR_TRUE); } - - // Set that we are once again in print preview + + // Set that we are once again in print preview if ( mIsDoingPrintPreview == PR_TRUE) { aPrintSettings->SetIsPrintPreview(PR_TRUE); } } - - /* cleaup on failure + notify user */ if (NS_FAILED(rv)) { /* cleanup... */ @@ -6574,7 +6880,7 @@ DocumentViewerImpl::Print(nsIPrintSettings* aPrintSettings, mPagePrintTimer->Stop(); NS_RELEASE(mPagePrintTimer); } - + if (mPrt) { delete mPrt; mPrt = nsnull; @@ -6582,16 +6888,16 @@ DocumentViewerImpl::Print(nsIPrintSettings* aPrintSettings, mIsDoingPrinting = PR_FALSE; /* cleanup done, let's fire-up an error dialog to notify the user - * what went wrong... - * - * When rv == NS_ERROR_ABORT, it means we want out of the + * what went wrong... + * + * When rv == NS_ERROR_ABORT, it means we want out of the * print job without displaying any error messages */ if (rv != NS_ERROR_ABORT) { ShowPrintErrorDialog(rv); } } - + return rv; } @@ -6600,19 +6906,19 @@ void DocumentViewerImpl::ShowPrintErrorDialog(nsresult aPrintError, PRBool aIsPrinting) { nsresult rv; - + static NS_DEFINE_CID(kCStringBundleServiceCID, NS_STRINGBUNDLESERVICE_CID); nsCOMPtr stringBundleService = do_GetService(kCStringBundleServiceCID); - - if (!stringBundleService) { + + if (!stringBundleService) { NS_WARNING("ERROR: Failed to get StringBundle Service instance.\n"); return; } nsCOMPtr myStringBundle; - rv = stringBundleService->CreateBundle(NS_ERROR_GFX_PRINTER_BUNDLE_URL, getter_AddRefs(myStringBundle)); - if (NS_FAILED(rv)) + rv = stringBundleService->CreateBundle(NS_ERROR_GFX_PRINTER_BUNDLE_URL, getter_AddRefs(myStringBundle)); + if (NS_FAILED(rv)) return; - + nsXPIDLString msg, title; nsAutoString stringName; @@ -6653,7 +6959,7 @@ DocumentViewerImpl::ShowPrintErrorDialog(nsresult aPrintError, PRBool aIsPrintin default: NS_ERROR_TO_LOCALIZED_PRINT_ERROR_MSG(NS_ERROR_FAILURE) -#undef NS_ERROR_TO_LOCALIZED_PRINT_ERROR_MSG +#undef NS_ERROR_TO_LOCALIZED_PRINT_ERROR_MSG } myStringBundle->GetStringFromName(stringName.get(), getter_Copies(msg)); @@ -6665,7 +6971,7 @@ DocumentViewerImpl::ShowPrintErrorDialog(nsresult aPrintError, PRBool aIsPrintin if (!msg) return; - + nsCOMPtr wwatch = do_GetService("@mozilla.org/embedcomp/window-watcher;1", &rv); if (NS_FAILED(rv)) return; @@ -6676,27 +6982,22 @@ DocumentViewerImpl::ShowPrintErrorDialog(nsresult aPrintError, PRBool aIsPrintin nsCOMPtr parent = do_QueryInterface(active, &rv); if (NS_FAILED(rv)) return; - - nsCOMPtr dialog; - parent->GetPrompter(getter_AddRefs(dialog)); + + nsCOMPtr dialog; + parent->GetPrompter(getter_AddRefs(dialog)); if (!dialog) return; - + dialog->Alert(title, msg); } // nsIContentViewerFile interface NS_IMETHODIMP -DocumentViewerImpl::GetPrintable(PRBool *aPrintable) +DocumentViewerImpl::GetPrintable(PRBool *aPrintable) { NS_ENSURE_ARG_POINTER(aPrintable); - - if(mIsDoingPrinting==PR_TRUE){ - *aPrintable = PR_FALSE; - } else { - *aPrintable = PR_TRUE; - } + *aPrintable = !mIsDoingPrinting; return NS_OK; } @@ -6707,7 +7008,7 @@ DocumentViewerImpl::GetPrintable(PRBool *aPrintable) //***************************************************************************** // nsIMarkupDocumentViewer -//***************************************************************************** +//***************************************************************************** NS_IMETHODIMP DocumentViewerImpl::ScrollToNode(nsIDOMNode* aNode) { @@ -6716,25 +7017,25 @@ NS_IMETHODIMP DocumentViewerImpl::ScrollToNode(nsIDOMNode* aNode) nsCOMPtr presShell; NS_ENSURE_SUCCESS(GetPresShell(*(getter_AddRefs(presShell))), NS_ERROR_FAILURE); - // Get the nsIContent interface, because that's what we need to + // Get the nsIContent interface, because that's what we need to // get the primary frame - + nsCOMPtr content(do_QueryInterface(aNode)); NS_ENSURE_TRUE(content, NS_ERROR_FAILURE); // Get the primary frame - nsIFrame* frame; // Remember Frames aren't ref-counted. They are in their + nsIFrame* frame; // Remember Frames aren't ref-counted. They are in their // own special little world. NS_ENSURE_SUCCESS(presShell->GetPrimaryFrameFor(content, &frame), NS_ERROR_FAILURE); // tell the pres shell to scroll to the frame - NS_ENSURE_SUCCESS(presShell->ScrollFrameIntoView(frame, - NS_PRESSHELL_SCROLL_TOP, - NS_PRESSHELL_SCROLL_ANYWHERE), - NS_ERROR_FAILURE); - return NS_OK; + NS_ENSURE_SUCCESS(presShell->ScrollFrameIntoView(frame, + NS_PRESSHELL_SCROLL_TOP, + NS_PRESSHELL_SCROLL_ANYWHERE), + NS_ERROR_FAILURE); + return NS_OK; } NS_IMETHODIMP DocumentViewerImpl::GetAllowPlugins(PRBool* aAllowPlugins) @@ -6760,17 +7061,17 @@ DocumentViewerImpl::CallChildren(CallChildFunc aFunc, void* aClosure) PRInt32 i; PRInt32 n; docShellNode->GetChildCount(&n); - for (i=0; i < n; i++) + for (i=0; i < n; i++) { nsCOMPtr child; docShellNode->GetChildAt(i, getter_AddRefs(child)); nsCOMPtr childAsShell(do_QueryInterface(child)); NS_ASSERTION(childAsShell, "null child in docshell"); - if (childAsShell) + if (childAsShell) { nsCOMPtr childCV; childAsShell->GetContentViewer(getter_AddRefs(childCV)); - if (childCV) + if (childCV) { nsCOMPtr markupCV = do_QueryInterface(childCV); if (markupCV) { @@ -6821,7 +7122,7 @@ NS_IMETHODIMP DocumentViewerImpl::GetTextZoom(float* aTextZoom) return NS_OK; } -// XXX: SEMANTIC CHANGE! +// XXX: SEMANTIC CHANGE! // returns a copy of the string. Caller is responsible for freeing result // using Recycle(aDefaultCharacterSet) NS_IMETHODIMP DocumentViewerImpl::GetDefaultCharacterSet(PRUnichar** aDefaultCharacterSet) @@ -6829,18 +7130,18 @@ NS_IMETHODIMP DocumentViewerImpl::GetDefaultCharacterSet(PRUnichar** aDefaultCha NS_ENSURE_ARG_POINTER(aDefaultCharacterSet); NS_ENSURE_STATE(mContainer); - if (mDefaultCharacterSet.IsEmpty()) + if (mDefaultCharacterSet.IsEmpty()) { nsXPIDLString defCharset; nsCOMPtr webShell; webShell = do_QueryInterface(mContainer); if (webShell) - { + { nsCOMPtr prefs(do_GetService(NS_PREF_CONTRACTID)); if (prefs) prefs->GetLocalizedUnicharPref("intl.charset.default", getter_Copies(defCharset)); - } + } if (!defCharset.IsEmpty()) mDefaultCharacterSet.Assign(defCharset.get()); @@ -6865,7 +7166,7 @@ NS_IMETHODIMP DocumentViewerImpl::SetDefaultCharacterSet(const PRUnichar* aDefau (void*) aDefaultCharacterSet); } -// XXX: SEMANTIC CHANGE! +// XXX: SEMANTIC CHANGE! // returns a copy of the string. Caller is responsible for freeing result // using Recycle(aForceCharacterSet) NS_IMETHODIMP DocumentViewerImpl::GetForceCharacterSet(PRUnichar** aForceCharacterSet) @@ -6895,7 +7196,7 @@ NS_IMETHODIMP DocumentViewerImpl::SetForceCharacterSet(const PRUnichar* aForceCh return CallChildren(SetChildForceCharacterSet, (void*) aForceCharacterSet); } -// XXX: SEMANTIC CHANGE! +// XXX: SEMANTIC CHANGE! // returns a copy of the string. Caller is responsible for freeing result // using Recycle(aHintCharacterSet) NS_IMETHODIMP DocumentViewerImpl::GetHintCharacterSet(PRUnichar * *aHintCharacterSet) @@ -6980,7 +7281,7 @@ NS_IMETHODIMP DocumentViewerImpl::GetBidiTextDirection(PRUint8* aTextDirection) #endif return NS_OK; } - + NS_IMETHODIMP DocumentViewerImpl::SetBidiTextType(PRUint8 aTextType) { #ifdef IBMBIDI @@ -7136,9 +7437,9 @@ NS_IMETHODIMP DocumentViewerImpl::SetBidiOptions(PRUint32 aBidiOptions) #ifdef IBMBIDI if (mPresContext) { #if 1 - // forcing reflow will cause bug 80352. Temp turn off force reflow and + // forcing reflow will cause bug 80352. Temp turn off force reflow and // wait for simon@softel.co.il to find the real solution - mPresContext->SetBidi(aBidiOptions, PR_FALSE); + mPresContext->SetBidi(aBidiOptions, PR_FALSE); #else mPresContext->SetBidi(aBidiOptions, PR_TRUE); // force reflow #endif @@ -7173,7 +7474,7 @@ NS_IMETHODIMP DocumentViewerImpl::SizeToContent() nsCOMPtr docShellParent; docShellAsItem->GetSameTypeParent(getter_AddRefs(docShellParent)); - // It's only valid to access this from a top frame. Doesn't work from + // It's only valid to access this from a top frame. Doesn't work from // sub-frames. NS_ENSURE_TRUE(!docShellParent, NS_ERROR_FAILURE); @@ -7262,7 +7563,7 @@ DocumentViewerImpl::GetPopupNode(nsIDOMNode** aNode) // get the internal dom window nsCOMPtr internalWin(do_QueryInterface(global, &rv)); NS_ENSURE_SUCCESS(rv, rv); - NS_ENSURE_TRUE(internalWin, NS_ERROR_FAILURE); + NS_ENSURE_TRUE(internalWin, NS_ERROR_FAILURE); // get the private dom window nsCOMPtr privateWin(do_QueryInterface(internalWin, &rv)); @@ -7434,20 +7735,20 @@ NS_IMETHODIMP nsDocViewerSelectionListener::NotifySelectionChanged(nsIDOMDocumen if (!mGotSelectionState || mSelectionWasCollapsed != selectionCollapsed) { nsCOMPtr theDoc; - mDocViewer->GetDocument(*getter_AddRefs(theDoc)); + mDocViewer->GetDocument(*getter_AddRefs(theDoc)); if (!theDoc) return NS_ERROR_FAILURE; - + nsCOMPtr scriptGlobalObject; theDoc->GetScriptGlobalObject(getter_AddRefs(scriptGlobalObject)); nsCOMPtr domWindow = do_QueryInterface(scriptGlobalObject); if (!domWindow) return NS_ERROR_FAILURE; - + domWindow->UpdateCommands(NS_LITERAL_STRING("select")); mGotSelectionState = PR_TRUE; mSelectionWasCollapsed = selectionCollapsed; - } - + } + return NS_OK; } @@ -7484,7 +7785,7 @@ nsDocViewerFocusListener::Focus(nsIDOMEvent* aEvent) selCon->GetDisplaySelection( &selectionStatus); //if selection was nsISelectionController::SELECTION_OFF, do nothing - //otherwise re-enable it. + //otherwise re-enable it. if(selectionStatus == nsISelectionController::SELECTION_DISABLED || selectionStatus == nsISelectionController::SELECTION_HIDDEN) { @@ -7498,7 +7799,7 @@ NS_IMETHODIMP nsDocViewerFocusListener::Blur(nsIDOMEvent* aEvent) { nsCOMPtr shell; - if(!mDocViewer) + if(!mDocViewer) return NS_ERROR_FAILURE; nsresult result = mDocViewer->GetPresShell(*getter_AddRefs(shell));//deref once cause it take a ptr ref @@ -7508,7 +7809,7 @@ nsDocViewerFocusListener::Blur(nsIDOMEvent* aEvent) selCon = do_QueryInterface(shell); PRInt16 selectionStatus; selCon->GetDisplaySelection(&selectionStatus); - + //if selection was nsISelectionController::SELECTION_OFF, do nothing //otherwise re-enable it. if(selectionStatus == nsISelectionController::SELECTION_ON) @@ -7528,7 +7829,7 @@ nsDocViewerFocusListener::Init(DocumentViewerImpl *aDocViewer) } -PRBool +PRBool DocumentViewerImpl::IsWindowsInOurSubTree(nsIDOMWindowInternal * aDOMWindow) { PRBool found = PR_FALSE; @@ -7569,7 +7870,7 @@ DocumentViewerImpl::IsWindowsInOurSubTree(nsIDOMWindowInternal * aDOMWindow) //---------------------------------------------------------------------------------- -void +void DocumentViewerImpl::CleanupDocTitleArray(PRUnichar**& aArray, PRInt32& aCount) { for (PRInt32 i = aCount - 1; i >= 0; i--) { @@ -7582,8 +7883,8 @@ DocumentViewerImpl::CleanupDocTitleArray(PRUnichar**& aArray, PRInt32& aCount) //---------------------------------------------------------------------------------- // Enumerate all the documents for their titles -NS_IMETHODIMP -DocumentViewerImpl::EnumerateDocumentNames(PRUint32* aCount, +NS_IMETHODIMP +DocumentViewerImpl::EnumerateDocumentNames(PRUint32* aCount, PRUnichar*** aResult) { NS_ENSURE_ARG(aCount); @@ -7591,12 +7892,12 @@ DocumentViewerImpl::EnumerateDocumentNames(PRUint32* aCount, *aCount = 0; *aResult = nsnull; - + PRInt32 numDocs = mPrt->mPrintDocList->Count(); PRUnichar** array = (PRUnichar**) nsMemory::Alloc(numDocs * sizeof(PRUnichar*)); - if (!array) + if (!array) return NS_ERROR_OUT_OF_MEMORY; - + for (PRInt32 i=0;imPrintDocList->ElementAt(i); NS_ASSERTION(po, "PrintObject can't be null!"); @@ -7629,7 +7930,7 @@ DocumentViewerImpl::EnumerateDocumentNames(PRUint32* aCount, } /* readonly attribute nsIPrintSettings newPrintSettings; */ -NS_IMETHODIMP +NS_IMETHODIMP DocumentViewerImpl::GetNewPrintSettings(nsIPrintSettings * *aNewPrintSettings) { NS_ENSURE_ARG_POINTER(aNewPrintSettings); @@ -7644,7 +7945,7 @@ DocumentViewerImpl::GetNewPrintSettings(nsIPrintSettings * *aNewPrintSettings) } /* readonly attribute wstring defaultPrinterName; */ -NS_IMETHODIMP +NS_IMETHODIMP DocumentViewerImpl::GetDefaultPrinterName(PRUnichar * *aDefaultPrinterName) { NS_ENSURE_ARG_POINTER(aDefaultPrinterName); @@ -7658,7 +7959,7 @@ DocumentViewerImpl::GetDefaultPrinterName(PRUnichar * *aDefaultPrinterName) } /* void initPrintSettingsFromPrinter (in wstring aPrinterName, in nsIPrintSettings aPrintSettings); */ -NS_IMETHODIMP +NS_IMETHODIMP DocumentViewerImpl::InitPrintSettingsFromPrinter(const PRUnichar *aPrinterName, nsIPrintSettings *aPrintSettings) { NS_ENSURE_ARG_POINTER(aPrintSettings); @@ -7680,7 +7981,7 @@ DocumentViewerImpl::InitPrintSettingsFromPrinter(const PRUnichar *aPrinterName, } /* readonly attribute nsIPrintSettings globalPrintSettings; */ -NS_IMETHODIMP +NS_IMETHODIMP DocumentViewerImpl::GetGlobalPrintSettings(nsIPrintSettings * *aGlobalPrintSettings) { NS_ENSURE_ARG_POINTER(aGlobalPrintSettings); @@ -7703,7 +8004,7 @@ DocumentViewerImpl::GetDoingPrintPreview(PRBool *aDoingPrintPreview) } /* readonly attribute nsIPrintSettings currentPrintSettings; */ -NS_IMETHODIMP +NS_IMETHODIMP DocumentViewerImpl::GetCurrentPrintSettings(nsIPrintSettings * *aCurrentPrintSettings) { NS_ENSURE_ARG_POINTER(aCurrentPrintSettings); @@ -7722,7 +8023,7 @@ DocumentViewerImpl::GetCurrentPrintSettings(nsIPrintSettings * *aCurrentPrintSet } /* void cancel (); */ -NS_IMETHODIMP +NS_IMETHODIMP DocumentViewerImpl::Cancel() { nsresult rv; @@ -7734,7 +8035,7 @@ DocumentViewerImpl::Cancel() } /* void initPrintSettingsFromPrefs (in nsIPrintSettings aPrintSettings, in boolean aUsePrinterNamePrefix, in unsigned long aFlags); */ -NS_IMETHODIMP +NS_IMETHODIMP DocumentViewerImpl::InitPrintSettingsFromPrefs(nsIPrintSettings *aPrintSettings, PRBool aUsePrinterNamePrefix, PRUint32 aFlags) { nsresult rv; @@ -7746,7 +8047,7 @@ DocumentViewerImpl::InitPrintSettingsFromPrefs(nsIPrintSettings *aPrintSettings, } /* void savePrintSettingsToPrefs (in nsIPrintSettings aPrintSettings, in boolean aUsePrinterNamePrefix, in unsigned long aFlags); */ -NS_IMETHODIMP +NS_IMETHODIMP DocumentViewerImpl::SavePrintSettingsToPrefs(nsIPrintSettings *aPrintSettings, PRBool aUsePrinterNamePrefix, PRUint32 aFlags) { nsresult rv; @@ -7759,7 +8060,7 @@ DocumentViewerImpl::SavePrintSettingsToPrefs(nsIPrintSettings *aPrintSettings, P /** --------------------------------------------------- * Get the Focused Frame for a documentviewer - * + * */ nsIDOMWindowInternal* DocumentViewerImpl::FindFocusedDOMWindowInternal() @@ -7770,7 +8071,7 @@ DocumentViewerImpl::FindFocusedDOMWindowInternal() nsCOMPtr focusController; nsIDOMWindowInternal * domWin = nsnull; - this->GetDocument(*getter_AddRefs(theDoc)); + this->GetDocument(*getter_AddRefs(theDoc)); if(theDoc){ theDoc->GetScriptGlobalObject(getter_AddRefs(theSGO)); if(theSGO){ @@ -7796,7 +8097,7 @@ DocumentViewerImpl::FindFocusedDOMWindowInternal() /*=============== Timer Related Code ======================*/ nsresult -DocumentViewerImpl::StartPagePrintTimer(nsIPresContext * aPresContext, +DocumentViewerImpl::StartPagePrintTimer(nsIPresContext * aPresContext, nsIPrintSettings* aPrintSettings, PrintObject* aPOect, PRUint32 aDelay) diff --git a/mozilla/content/base/src/nsFrameLoader.cpp b/mozilla/content/base/src/nsFrameLoader.cpp index 1a4e5c9f97d..fc75c957693 100644 --- a/mozilla/content/base/src/nsFrameLoader.cpp +++ b/mozilla/content/base/src/nsFrameLoader.cpp @@ -40,13 +40,14 @@ #include "nsIFrameLoader.h" #include "nsIDOMHTMLIFrameElement.h" #include "nsIDOMHTMLFrameElement.h" -#include "nsIDOMEventListener.h" -#include "nsIDOMEventTarget.h" #include "nsIDOMWindow.h" #include "nsIPresContext.h" #include "nsIPresShell.h" +#include "nsIContent.h" #include "nsIDocument.h" #include "nsIDOMDocument.h" +#include "nsIDOMWindow.h" +#include "nsPIDOMWindow.h" #include "nsIWebNavigation.h" #include "nsIChromeEventHandler.h" #include "nsIDocShell.h" @@ -56,9 +57,6 @@ #include "nsIDocShellLoadInfo.h" #include "nsIBaseWindow.h" #include "nsIWebShell.h" -#include "nsIWebProgressListener.h" -#include "nsIWebProgress.h" -#include "nsWeakReference.h" #include "nsIScriptSecurityManager.h" #include "nsICodebasePrincipal.h" @@ -66,10 +64,17 @@ #include "nsIURI.h" #include "nsNetUtil.h" -class nsFrameLoader : public nsIFrameLoader, - public nsIDOMEventListener, - public nsIWebProgressListener, - public nsSupportsWeakReference +#include "nsHTMLAtoms.h" +#include "nsINameSpaceManager.h" + + +// Bug 8065: Limit content frame depth to some reasonable level. This +// does not count chrome frames when determining depth, nor does it +// prevent chrome recursion. +#define MAX_DEPTH_CONTENT_FRAMES 25 + + +class nsFrameLoader : public nsIFrameLoader { public: nsFrameLoader(); @@ -79,26 +84,19 @@ public: NS_DECL_ISUPPORTS // nsIFrameLoader - NS_IMETHOD Init(nsIDOMElement *aOwner); - NS_IMETHOD LoadURI(nsIURI *aURI); + NS_IMETHOD Init(nsIContent *aOwner); + NS_IMETHOD LoadFrame(); NS_IMETHOD GetDocShell(nsIDocShell **aDocShell); NS_IMETHOD Destroy(); - // nsIDOMEventListener - NS_DECL_NSIDOMEVENTLISTENER - - // nsIWebProgressListener - NS_DECL_NSIWEBPROGRESSLISTENER - protected: nsresult GetPresContext(nsIPresContext **aPresContext); nsresult EnsureDocShell(); + void GetURL(nsAString& aURL); nsCOMPtr mDocShell; - nsCOMPtr mOwnerElement; - - nsCOMPtr mURI; + nsIContent *mOwnerContent; // WEAK }; nsresult @@ -112,26 +110,22 @@ NS_NewFrameLoader(nsIFrameLoader **aFrameLoader) return NS_OK; } - nsFrameLoader::nsFrameLoader() + : mOwnerContent(nsnull) { NS_INIT_ISUPPORTS(); } nsFrameLoader::~nsFrameLoader() { - nsCOMPtr treeOwnerAsWin(do_QueryInterface(mDocShell)); - - if (treeOwnerAsWin) { - treeOwnerAsWin->Destroy(); - } + Destroy(); } // QueryInterface implementation for nsFrameLoader NS_INTERFACE_MAP_BEGIN(nsFrameLoader) - NS_INTERFACE_MAP_ENTRY(nsISupportsWeakReference) NS_INTERFACE_MAP_ENTRY(nsIFrameLoader) + NS_INTERFACE_MAP_ENTRY(nsISupports) NS_INTERFACE_MAP_END @@ -139,27 +133,49 @@ NS_IMPL_ADDREF(nsFrameLoader); NS_IMPL_RELEASE(nsFrameLoader); NS_IMETHODIMP -nsFrameLoader::Init(nsIDOMElement *aOwner) +nsFrameLoader::Init(nsIContent *aOwner) { - mOwnerElement = aOwner; + mOwnerContent = aOwner; // WEAK return NS_OK; } NS_IMETHODIMP -nsFrameLoader::LoadURI(nsIURI *aURI) +nsFrameLoader::LoadFrame() { - mURI = aURI; + NS_ENSURE_TRUE(mOwnerContent, NS_ERROR_NOT_INITIALIZED); nsresult rv = EnsureDocShell(); + NS_ENSURE_SUCCESS(rv, rv); + nsCOMPtr doc; + mOwnerContent->GetDocument(*getter_AddRefs(doc)); + NS_ENSURE_TRUE(doc, NS_ERROR_UNEXPECTED); - // Prevent recursion + nsAutoString src; + GetURL(src); + src.Trim(" \t\n\r"); + if (src.IsEmpty()) { + // about:blank will be synthesized into a frame if not URL is + // loaded into it (bug 35986) - // mCreatingViewer=PR_TRUE; + return NS_OK; + } + // Make an absolute URI + nsCOMPtr base_uri; + doc->GetBaseURL(*getter_AddRefs(base_uri)); + + nsAutoString doc_charset; + doc->GetDocumentCharacterSet(doc_charset); + + nsCOMPtr uri; + rv = NS_NewURI(getter_AddRefs(uri), src, + doc_charset.IsEmpty() ? nsnull : + NS_ConvertUCS2toUTF8(doc_charset).get(), base_uri); + NS_ENSURE_SUCCESS(rv, rv); // Check for security nsCOMPtr secMan = @@ -197,31 +213,21 @@ nsFrameLoader::LoadURI(nsIURI *aURI) loadInfo->SetInheritOwner(PR_TRUE); - nsCOMPtr dom_doc; - mOwnerElement->GetOwnerDocument(getter_AddRefs(dom_doc)); - nsCOMPtr doc(do_QueryInterface(dom_doc)); - - if (doc) { - doc->GetBaseURL(*getter_AddRefs(referrer)); - } + referrer = base_uri; } loadInfo->SetReferrer(referrer); // Check if we are allowed to load absURL - rv = secMan->CheckLoadURI(referrer, mURI, + rv = secMan->CheckLoadURI(referrer, uri, nsIScriptSecurityManager::STANDARD); if (NS_FAILED(rv)) { return rv; // We're not } - nsCOMPtr webProgress(do_GetInterface(mDocShell)); - - if (webProgress) { - webProgress->AddProgressListener(this); - } - - rv = mDocShell->LoadURI(mURI, loadInfo, nsIWebNavigation::LOAD_FLAGS_NONE); + // Kick off the load... + rv = mDocShell->LoadURI(uri, loadInfo, nsIWebNavigation::LOAD_FLAGS_NONE, + PR_FALSE); NS_ASSERTION(NS_SUCCEEDED(rv), "failed to load URL"); return rv; @@ -241,12 +247,25 @@ nsFrameLoader::GetDocShell(nsIDocShell **aDocShell) NS_IMETHODIMP nsFrameLoader::Destroy() { - return NS_OK; -} + if (mOwnerContent) { + nsCOMPtr doc; -NS_IMETHODIMP -nsFrameLoader::HandleEvent(nsIDOMEvent *aEvent) -{ + mOwnerContent->GetDocument(*getter_AddRefs(doc)); + + if (doc) { + doc->SetSubDocumentFor(mOwnerContent, nsnull); + } + + mOwnerContent = nsnull; + } + + nsCOMPtr base_win(do_QueryInterface(mDocShell)); + + if (base_win) { + base_win->Destroy(); + } + + mDocShell = nsnull; return NS_OK; } @@ -256,10 +275,8 @@ nsFrameLoader::GetPresContext(nsIPresContext **aPresContext) { *aPresContext = nsnull; - nsCOMPtr dom_doc; - mOwnerElement->GetOwnerDocument(getter_AddRefs(dom_doc)); - - nsCOMPtr doc(do_QueryInterface(dom_doc)); + nsCOMPtr doc; + mOwnerContent->GetDocument(*getter_AddRefs(doc)); while (doc) { nsCOMPtr presShell; @@ -287,16 +304,15 @@ nsFrameLoader::EnsureDocShell() return NS_OK; } -#if 0 - - - + nsCOMPtr presContext; + GetPresContext(getter_AddRefs(presContext)); + NS_ENSURE_TRUE(presContext, NS_ERROR_UNEXPECTED); // Bug 8065: Don't exceed some maximum depth in content frames // (MAX_DEPTH_CONTENT_FRAMES) PRInt32 depth = 0; nsCOMPtr parentAsSupports; - aPresContext->GetContainer(getter_AddRefs(parentAsSupports)); + presContext->GetContainer(getter_AddRefs(parentAsSupports)); if (parentAsSupports) { nsCOMPtr parentAsItem = @@ -321,32 +337,16 @@ nsFrameLoader::EnsureDocShell() } } } -#endif + // Create the docshell... mDocShell = do_CreateInstance("@mozilla.org/webshell;1"); NS_ENSURE_TRUE(mDocShell, NS_ERROR_FAILURE); -#if 0 - // notify the pres shell that a docshell has been created - nsCOMPtr presShell; - aPresContext->GetShell(getter_AddRefs(presShell)); - - if (presShell) { - nsCOMPtr subShellAsSupports(do_QueryInterface(mDocShell)); - NS_ENSURE_TRUE(subShellAsSupports, NS_ERROR_FAILURE); - - presShell->SetSubShellFor(mContent, subShellAsSupports); - - // We need to be able to get back to the presShell to unset the - // subshell at destruction - mPresShellWeak = getter_AddRefs(NS_GetWeakReference(presShell)); - } -#endif - + // Get the frame name and tell the docshell about it. nsCOMPtr docShellAsItem(do_QueryInterface(mDocShell)); NS_ENSURE_TRUE(docShellAsItem, NS_ERROR_FAILURE); nsAutoString frameName; - mOwnerElement->GetAttribute(NS_LITERAL_STRING("name"), frameName); + mOwnerContent->GetAttr(kNameSpaceID_None, nsHTMLAtoms::name, frameName); if (!frameName.IsEmpty()) { docShellAsItem->SetName(frameName.get()); @@ -356,178 +356,148 @@ nsFrameLoader::EnsureDocShell() // child. If it's not a web-shell then some things will not operate // properly. - - nsCOMPtr presContext; - GetPresContext(getter_AddRefs(presContext)); - - - - - - - - - - - - // what if !presContext ? - - - - - - - - - nsCOMPtr container; presContext->GetContainer(getter_AddRefs(container)); - if (container) { - nsCOMPtr parentAsNode(do_QueryInterface(container)); - if (parentAsNode) { - nsCOMPtr parentAsItem = - do_QueryInterface(parentAsNode); + nsCOMPtr parentAsNode(do_QueryInterface(container)); + if (parentAsNode) { + nsCOMPtr parentAsItem = + do_QueryInterface(parentAsNode); - PRInt32 parentType; - parentAsItem->GetItemType(&parentType); + PRInt32 parentType; + parentAsItem->GetItemType(&parentType); - nsAutoString value, valuePiece; - PRBool isContent; + nsAutoString value; + PRBool isContent; - isContent = PR_FALSE; - mOwnerElement->GetAttribute(NS_LITERAL_STRING("type"), value); + isContent = PR_FALSE; - if (!value.IsEmpty()) { - // we accept "content" and "content-xxx" values. - // at time of writing, we expect "xxx" to be "primary", but - // someday it might be an integer expressing priority + if (mOwnerContent->IsContentOfType(nsIContent::eXUL)) { + mOwnerContent->GetAttr(kNameSpaceID_None, nsHTMLAtoms::type, value); + } + if (!value.IsEmpty()) { + // we accept "content" and "content-xxx" values. + // at time of writing, we expect "xxx" to be "primary", but + // someday it might be an integer expressing priority + if (value.Length() >= 7) { + ToLowerCase(value); + nsAutoString::const_iterator start, end; + value.BeginReading(start); + value.EndReading(end); - // string iterators! + nsAutoString::const_iterator iter(start); + iter.advance(7); + const nsAString& valuePiece = Substring(start, iter); - value.Left(valuePiece, 7); - if (valuePiece.EqualsIgnoreCase("content") && - (value.Length() == 7 || - value.Mid(valuePiece, 7, 1) == 1 && - valuePiece.EqualsWithConversion("-"))) { + if (valuePiece.Equals(NS_LITERAL_STRING("content")) && + (iter == end || *iter == '-')) { isContent = PR_TRUE; } } - - if (isContent) { - // The web shell's type is content. - docShellAsItem->SetItemType(nsIDocShellTreeItem::typeContent); - } else { - // Inherit our type from our parent webshell. If it is - // chrome, we'll be chrome. If it is content, we'll be - // content. - docShellAsItem->SetItemType(parentType); - } - - parentAsNode->AddChild(docShellAsItem); - - if (isContent) { - nsCOMPtr parentTreeOwner; - parentAsItem->GetTreeOwner(getter_AddRefs(parentTreeOwner)); - if(parentTreeOwner) { - PRBool is_primary = value.EqualsIgnoreCase("content-primary"); - - parentTreeOwner->ContentShellAdded(docShellAsItem, is_primary, - value.get()); - } - } - - // connect the container... - nsCOMPtr webShell(do_QueryInterface(mDocShell)); - nsCOMPtr outerContainer = - do_QueryInterface(container); - - if (outerContainer) { - webShell->SetContainer(outerContainer); - } - - // Make sure all shells have links back to the content element - // in the nearest enclosing chrome shell. - nsCOMPtr chromeEventHandler; - - if (parentType == nsIDocShellTreeItem::typeChrome) { - // Our parent shell is a chrome shell. It is therefore our nearest - // enclosing chrome shell. - chromeEventHandler = do_QueryInterface(mOwnerElement); - NS_WARN_IF_FALSE(chromeEventHandler, - "This mContent should implement this."); - } else { - nsCOMPtr parentShell(do_QueryInterface(parentAsNode)); - - // Our parent shell is a content shell. Get the chrome info from - // it and use that for our shell as well. - parentShell->GetChromeEventHandler(getter_AddRefs(chromeEventHandler)); - } - - - - // Should this be in the layout code? - - mDocShell->SetChromeEventHandler(chromeEventHandler); } + + if (isContent) { + // The web shell's type is content. + + docShellAsItem->SetItemType(nsIDocShellTreeItem::typeContent); + } else { + // Inherit our type from our parent webshell. If it is + // chrome, we'll be chrome. If it is content, we'll be + // content. + + docShellAsItem->SetItemType(parentType); + } + + parentAsNode->AddChild(docShellAsItem); + + if (isContent) { + nsCOMPtr parentTreeOwner; + parentAsItem->GetTreeOwner(getter_AddRefs(parentTreeOwner)); + + if(parentTreeOwner) { + // value is lowercased above. + PRBool is_primary = value.Equals(NS_LITERAL_STRING("content-primary")); + + parentTreeOwner->ContentShellAdded(docShellAsItem, is_primary, + value.get()); + } + } + + // connect the container... + nsCOMPtr webShell(do_QueryInterface(mDocShell)); + nsCOMPtr outerContainer = + do_QueryInterface(container); + + if (outerContainer) { + webShell->SetContainer(outerContainer); + } + + // Make sure all shells have links back to the content element + // in the nearest enclosing chrome shell. + nsCOMPtr chromeEventHandler; + + if (parentType == nsIDocShellTreeItem::typeChrome) { + // Our parent shell is a chrome shell. It is therefore our nearest + // enclosing chrome shell. + + chromeEventHandler = do_QueryInterface(mOwnerContent); + NS_WARN_IF_FALSE(chromeEventHandler, + "This mContent should implement this."); + } else { + nsCOMPtr parentShell(do_QueryInterface(parentAsNode)); + + // Our parent shell is a content shell. Get the chrome event + // handler from it and use that for our shell as well. + + parentShell->GetChromeEventHandler(getter_AddRefs(chromeEventHandler)); + } + + mDocShell->SetChromeEventHandler(chromeEventHandler); } + // This is nasty, this code (the do_GetInterface(mDocShell) below) + // *must* come *after* the above call to + // mDocShell->SetChromeEventHandler() for the global window to get + // the right chrome event handler. + + // Tell the window about the frame that hosts it. + nsCOMPtr frame_element(do_QueryInterface(mOwnerContent)); + NS_ASSERTION(frame_element, "frame loader owner element not a DOM element!"); + + nsCOMPtr win(do_GetInterface(mDocShell)); + nsCOMPtr win_private(do_QueryInterface(win)); + NS_ENSURE_TRUE(win_private, NS_ERROR_UNEXPECTED); + + win_private->SetFrameElementInternal(frame_element); + + nsCOMPtr base_win(do_QueryInterface(mDocShell)); + NS_ENSURE_TRUE(base_win, NS_ERROR_UNEXPECTED); + + // This is kinda whacky, this call doesn't really create anything, + // but it must be called to make sure things are properly + // initialized + + base_win->Create(); + return NS_OK; } -NS_IMETHODIMP -nsFrameLoader::OnStateChange(nsIWebProgress *aWebProgress, - nsIRequest *aRequest, - PRInt32 aStateFlags, PRUint32 aStatus) +void +nsFrameLoader::GetURL(nsAString& aURI) { - if (!((~aStateFlags) & (nsIWebProgressListener::STATE_IS_DOCUMENT | - nsIWebProgressListener::STATE_TRANSFERRING))) { - nsCOMPtr win(do_GetInterface(mDocShell)); - nsCOMPtr eventTarget(do_QueryInterface(win)); + aURI.Truncate(); - if (eventTarget) { - eventTarget->AddEventListener(NS_LITERAL_STRING("load"), this, - PR_FALSE); - } + nsCOMPtr type; + mOwnerContent->GetTag(*getter_AddRefs(type)); + + if (type == nsHTMLAtoms::object) { + mOwnerContent->GetAttr(kNameSpaceID_None, nsHTMLAtoms::data, aURI); + } else { + mOwnerContent->GetAttr(kNameSpaceID_None, nsHTMLAtoms::src, aURI); } - - return NS_OK; -} - -NS_IMETHODIMP -nsFrameLoader::OnProgressChange(nsIWebProgress *aWebProgress, - nsIRequest *aRequest, - PRInt32 aCurSelfProgress, - PRInt32 aMaxSelfProgress, - PRInt32 aCurTotalProgress, - PRInt32 aMaxTotalProgress) -{ - return NS_OK; -} - -NS_IMETHODIMP -nsFrameLoader::OnLocationChange(nsIWebProgress *aWebProgress, - nsIRequest *aRequest, nsIURI *location) -{ - return NS_OK; -} - -NS_IMETHODIMP -nsFrameLoader::OnStatusChange(nsIWebProgress *aWebProgress, - nsIRequest *aRequest, nsresult aStatus, - const PRUnichar *aMessage) -{ - return NS_OK; -} - -NS_IMETHODIMP -nsFrameLoader::OnSecurityChange(nsIWebProgress *aWebProgress, - nsIRequest *aRequest, PRInt32 state) -{ - return NS_OK; } diff --git a/mozilla/content/base/src/nsGenericElement.cpp b/mozilla/content/base/src/nsGenericElement.cpp index 89d652f6549..5d3758df8f0 100644 --- a/mozilla/content/base/src/nsGenericElement.cpp +++ b/mozilla/content/base/src/nsGenericElement.cpp @@ -1620,8 +1620,8 @@ nsGenericElement::HandleDOMEvent(nsIPresContext* aPresContext, PRBool intermediateCapture = PR_FALSE; //Capturing stage evaluation - if (NS_EVENT_FLAG_BUBBLE != aFlags && aEvent->message != NS_PAGE_LOAD - && aEvent->message != NS_SCRIPT_LOAD && + if (NS_EVENT_FLAG_BUBBLE != aFlags && aEvent->message != NS_PAGE_LOAD && + aEvent->message != NS_SCRIPT_LOAD && aEvent->message != NS_IMAGE_ERROR && aEvent->message != NS_IMAGE_LOAD) { //Initiate capturing phase. Special case first call to document if (parent) { diff --git a/mozilla/content/base/src/nsGenericElement.h b/mozilla/content/base/src/nsGenericElement.h index e5b9a3b83ab..c015fb4d281 100644 --- a/mozilla/content/base/src/nsGenericElement.h +++ b/mozilla/content/base/src/nsGenericElement.h @@ -91,15 +91,16 @@ private: // objects for each of these instance variables, we put them off // in a side structure that's only allocated when the content is // accessed through the DOM. -typedef struct { +struct nsDOMSlots +{ nsChildContentList *mChildNodes; nsDOMCSSDeclaration *mStyle; nsDOMAttributeMap* mAttributeMap; nsVoidArray *mRangeList; nsIEventListenerManager* mListenerManager; - nsIContent* mBindingParent; // The nearest enclosing content node with a binding - // that created us. [Weak] -} nsDOMSlots; + nsIContent* mBindingParent; // The nearest enclosing content node with a + // binding that created us. [Weak] +}; class nsNode3Tearoff : public nsIDOM3Node diff --git a/mozilla/content/build/nsContentDLF.cpp b/mozilla/content/build/nsContentDLF.cpp index 5dbb7e3668c..98026f58e1d 100644 --- a/mozilla/content/build/nsContentDLF.cpp +++ b/mozilla/content/build/nsContentDLF.cpp @@ -416,6 +416,8 @@ nsContentDLF::CreateDocument(const char* aCommand, break; docv->SetUAStyleSheet(gUAStyleSheet); + doc->SetContainer(aContainer); + // Initialize the document to begin loading the data. An // nsIStreamListener connected to the parser is returned in // aDocListener. @@ -512,6 +514,9 @@ nsContentDLF::CreateRDFDocument(const char* aCommand, * An nsIStreamListener connected to the parser is returned in * aDocListener. */ + + doc->SetContainer(aContainer); + rv = doc->StartDocumentLoad(aCommand, aChannel, aLoadGroup, aContainer, aDocListener, PR_TRUE); if (NS_SUCCEEDED(rv)) { /* diff --git a/mozilla/content/build/nsContentModule.cpp b/mozilla/content/build/nsContentModule.cpp index 84f8f367766..4c494695b2b 100644 --- a/mozilla/content/build/nsContentModule.cpp +++ b/mozilla/content/build/nsContentModule.cpp @@ -97,6 +97,7 @@ #include "nsISelection.h" #include "nsITextContent.h" #include "nsIXBLService.h" +#include "nsIFrameLoader.h" #include "nsLayoutAtoms.h" #include "nsPlainTextSerializer.h" #include "nsRange.h" @@ -275,6 +276,7 @@ extern nsresult NS_NewXBLService(nsIXBLService** aResult); extern nsresult NS_NewBindingManager(nsIBindingManager** aResult); extern nsresult NS_NewNodeInfoManager(nsINodeInfoManager** aResult); extern nsresult NS_NewContentPolicy(nsIContentPolicy** aResult); +extern nsresult NS_NewFrameLoader(nsIFrameLoader** aResult); #ifdef MOZ_XUL extern nsresult NS_NewXULElementFactory(nsIElementFactory** aResult); @@ -346,6 +348,7 @@ MAKE_CTOR(CreatePlainTextSerializer, nsIContentSerializer, NS_NewPla MAKE_CTOR(CreateXBLService, nsIXBLService, NS_NewXBLService) MAKE_CTOR(CreateBindingManager, nsIBindingManager, NS_NewBindingManager) MAKE_CTOR(CreateContentPolicy, nsIContentPolicy, NS_NewContentPolicy) +MAKE_CTOR(CreateFrameLoader, nsIFrameLoader, NS_NewFrameLoader) MAKE_CTOR(CreateNodeInfoManager, nsINodeInfoManager, NS_NewNodeInfoManager) MAKE_CTOR(CreateComputedDOMStyle, nsIComputedDOMStyle, NS_NewComputedDOMStyle) #ifdef MOZ_XUL @@ -735,6 +738,11 @@ static const nsModuleComponentInfo gComponents[] = { NS_CONTENTPOLICY_CONTRACTID, CreateContentPolicy }, + { "Frame Loader", + NS_FRAMELOADER_CID, + NS_FRAMELOADER_CONTRACTID, + CreateFrameLoader }, + { "NodeInfoManager", NS_NODEINFOMANAGER_CID, NS_NODEINFOMANAGER_CONTRACTID, diff --git a/mozilla/content/events/src/nsEventStateManager.cpp b/mozilla/content/events/src/nsEventStateManager.cpp index 552e27b4605..2ddb50ad003 100644 --- a/mozilla/content/events/src/nsEventStateManager.cpp +++ b/mozilla/content/events/src/nsEventStateManager.cpp @@ -1513,7 +1513,7 @@ nsEventStateManager::DoWheelScroll(nsIPresContext* aPresContext, rv = GetParentScrollingView(msEvent, aPresContext, newFrame, *getter_AddRefs(newPresContext)); - if (NS_SUCCEEDED(rv)) + if (NS_SUCCEEDED(rv) && newFrame) return DoWheelScroll(newPresContext, newFrame, msEvent, numLines, scrollPage, PR_TRUE); else @@ -1529,41 +1529,40 @@ nsEventStateManager::GetParentScrollingView(nsMouseScrollEvent *aEvent, nsIFrame* &targetOuterFrame, nsIPresContext* &presCtxOuter) { + targetOuterFrame = nsnull; + if (!aEvent) return NS_ERROR_FAILURE; if (!aPresContext) return NS_ERROR_FAILURE; - - nsCOMPtr shell; - aPresContext->GetContainer(getter_AddRefs(shell)); - if (!shell) return NS_ERROR_FAILURE; - - nsCOMPtr treeItem = do_QueryInterface(shell); - if (!treeItem) return NS_ERROR_FAILURE; - /* get our docshell's parent */ - nsCOMPtr parent; - treeItem->GetParent(getter_AddRefs(parent)); - if (!parent) return NS_ERROR_FAILURE; - - nsCOMPtr pDocShell = do_QueryInterface(parent); - if (!pDocShell) return NS_ERROR_FAILURE; + nsCOMPtr doc; - nsCOMPtr pPresShell; - pDocShell->GetPresShell(getter_AddRefs(pPresShell)); - if (!pPresShell) return NS_ERROR_FAILURE; + { + nsCOMPtr presShell; + aPresContext->GetShell(getter_AddRefs(presShell)); + NS_ASSERTION(presShell, "No presshell in prescontext!"); + + presShell->GetDocument(getter_AddRefs(doc)); + } + + NS_ASSERTION(doc, "No document in prescontext!"); nsCOMPtr parentDoc; - pPresShell->GetDocument(getter_AddRefs(parentDoc)); + doc->GetParentDocument(getter_AddRefs(parentDoc)); - nsCOMPtr rootContent; - parentDoc->GetRootContent(getter_AddRefs(rootContent)); + if (!parentDoc) { + return NS_OK; + } - nsCOMPtr ourDS = do_QueryInterface(shell); + nsCOMPtr pPresShell; + parentDoc->GetShellAt(0, getter_AddRefs(pPresShell)); + NS_ENSURE_TRUE(pPresShell, NS_ERROR_FAILURE); - /* now find the content node in our parent docshell's document that corresponds - to our docshell */ + /* now find the content node in our parent docshell's document that + corresponds to our docshell */ nsCOMPtr frameContent; - pPresShell->FindContentForShell(ourDS, getter_AddRefs(frameContent)); - if (!frameContent) return NS_ERROR_FAILURE; + + parentDoc->FindContentForSubDocument(doc, getter_AddRefs(frameContent)); + NS_ENSURE_TRUE(frameContent, NS_ERROR_FAILURE); /* get this content node's frame, and use it as the new event target, @@ -1571,6 +1570,7 @@ nsEventStateManager::GetParentScrollingView(nsMouseScrollEvent *aEvent, Note that we don't actually need to translate the event coordinates because they are not used by DoWheelScroll(). */ + nsIFrame* frameFrame = nsnull; pPresShell->GetPrimaryFrameFor(frameContent, &frameFrame); if (!frameFrame) return NS_ERROR_FAILURE; @@ -2745,7 +2745,7 @@ nsEventStateManager::ShiftFocusInternal(PRBool aForward, nsIContent* aStart) nsCOMPtr pcContainer; mPresContext->GetContainer(getter_AddRefs(pcContainer)); NS_ASSERTION(pcContainer, "no container for presContext"); - + nsCOMPtr docShell(do_QueryInterface(pcContainer)); PRBool docHasFocus = PR_FALSE; @@ -2838,19 +2838,32 @@ nsEventStateManager::ShiftFocusInternal(PRBool aForward, nsIContent* aStart) // Check to see if the next focused element has a subshell. // This is the case for an IFRAME or FRAME element. If it // does, we send focus into the subshell. - nsCOMPtr shellObject; - presShell->GetSubShellFor(nextFocus, getter_AddRefs(shellObject)); - if (shellObject) { - nsCOMPtr subShell = do_QueryInterface(shellObject); - if (subShell) { - SetContentState(nsnull, NS_EVENT_STATE_FOCUS); - nsIFrame* nextFocusFrame = nsnull; - presShell->GetPrimaryFrameFor(nextFocus, &nextFocusFrame); - presShell->ScrollFrameIntoView(nextFocusFrame, NS_PRESSHELL_SCROLL_ANYWHERE, - NS_PRESSHELL_SCROLL_ANYWHERE); - TabIntoDocument(subShell, aForward); + nsCOMPtr sub_shell; + + nsCOMPtr doc, sub_doc; + nextFocus->GetDocument(*getter_AddRefs(doc)); + + if (doc) { + doc->GetSubDocumentFor(nextFocus, getter_AddRefs(sub_doc)); + + if (sub_doc) { + nsCOMPtr container; + sub_doc->GetContainer(getter_AddRefs(container)); + + sub_shell = do_QueryInterface(container); } + } + + if (sub_shell) { + SetContentState(nsnull, NS_EVENT_STATE_FOCUS); + + nsIFrame* nextFocusFrame = nsnull; + presShell->GetPrimaryFrameFor(nextFocus, &nextFocusFrame); + presShell->ScrollFrameIntoView(nextFocusFrame, + NS_PRESSHELL_SCROLL_ANYWHERE, + NS_PRESSHELL_SCROLL_ANYWHERE); + TabIntoDocument(sub_shell, aForward); } else { // there is no subshell, so just focus nextFocus #ifdef DEBUG_DOCSHELL_FOCUS @@ -2927,23 +2940,28 @@ nsEventStateManager::ShiftFocusInternal(PRBool aForward, nsIContent* aStart) if (parentDS) { nsCOMPtr parentShell; parentDS->GetPresShell(getter_AddRefs(parentShell)); - - nsCOMPtr shellContent; - parentShell->FindContentForShell(docShell, getter_AddRefs(shellContent)); - + + nsCOMPtr docContent; + nsCOMPtr parent_doc; + + parentShell->GetDocument(getter_AddRefs(parent_doc)); + + parent_doc->FindContentForSubDocument(mDocument, + getter_AddRefs(docContent)); + nsCOMPtr parentPC; parentShell->GetPresContext(getter_AddRefs(parentPC)); - + nsCOMPtr parentESM; parentPC->GetEventStateManager(getter_AddRefs(parentESM)); - + SetContentState(nsnull, NS_EVENT_STATE_FOCUS); #ifdef DEBUG_DOCSHELL_FOCUS printf("popping out focus to parent docshell\n"); #endif parentESM->MoveCaretToFocus(); - parentESM->ShiftFocus(aForward, shellContent); + parentESM->ShiftFocus(aForward, docContent); } } else { PRBool tookFocus = PR_FALSE; @@ -4647,6 +4665,14 @@ PRBool nsEventStateManager::IsIFrameDoc(nsIDocShell* aDocShell) { NS_ASSERTION(aDocShell, "docshell is null"); + + nsCOMPtr presShell; + aDocShell->GetPresShell(getter_AddRefs(presShell)); + + nsCOMPtr doc; + presShell->GetDocument(getter_AddRefs(doc)); + NS_ASSERTION(doc, "No document in presshell!"); + nsCOMPtr treeItem = do_QueryInterface(aDocShell); nsCOMPtr parentItem; treeItem->GetParent(getter_AddRefs(parentItem)); @@ -4654,12 +4680,17 @@ nsEventStateManager::IsIFrameDoc(nsIDocShell* aDocShell) return PR_FALSE; nsCOMPtr parentDS = do_QueryInterface(parentItem); - nsCOMPtr parentShell; - parentDS->GetPresShell(getter_AddRefs(parentShell)); - NS_ASSERTION(parentShell, "presshell is null"); - + nsCOMPtr parentPresShell; + parentDS->GetPresShell(getter_AddRefs(parentPresShell)); + NS_ASSERTION(parentPresShell, "presshell is null"); + + nsCOMPtr parentDoc; + parentPresShell->GetDocument(getter_AddRefs(parentDoc)); + nsCOMPtr docContent; - parentShell->FindContentForShell(aDocShell, getter_AddRefs(docContent)); + + parentDoc->FindContentForSubDocument(doc, getter_AddRefs(docContent)); + if (!docContent) return PR_FALSE; diff --git a/mozilla/content/html/content/src/makefile.win b/mozilla/content/html/content/src/makefile.win index 48fe2267239..5d4fe888565 100644 --- a/mozilla/content/html/content/src/makefile.win +++ b/mozilla/content/html/content/src/makefile.win @@ -32,10 +32,10 @@ REQUIRES = xpcom \ webshell \ htmlparser \ necko \ - uriloader \ view \ pref \ docshell \ + uriloader \ xpconnect \ caps \ editor \ diff --git a/mozilla/content/html/content/src/nsGenericHTMLElement.cpp b/mozilla/content/html/content/src/nsGenericHTMLElement.cpp index edc648048d5..cc27d46dd8c 100644 --- a/mozilla/content/html/content/src/nsGenericHTMLElement.cpp +++ b/mozilla/content/html/content/src/nsGenericHTMLElement.cpp @@ -2331,12 +2331,12 @@ nsGenericHTMLElement::GetBaseURL(const nsHTMLValue& aBaseHref, baseHref.Trim(" \t\n\r"); nsIURI* url = nsnull; - { - result = NS_NewURI(&url, baseHref, nsnull, docBaseURL); - } + result = NS_NewURI(&url, baseHref, nsnull, docBaseURL); + NS_IF_RELEASE(docBaseURL); *aBaseURL = url; } + return result; } @@ -4571,32 +4571,6 @@ nsGenericHTMLElement::SetElementFocus(PRBool aDoFocus) return RemoveFocus(presContext); } -nsresult -nsGenericHTMLElement::HandleFrameOnloadEvent(nsIDOMEvent* aEvent) -{ - NS_ENSURE_TRUE(aEvent, NS_OK); - - nsAutoString type; - aEvent->GetType(type); - - if (!type.EqualsIgnoreCase("load")) { - return NS_OK; - } - - nsCOMPtr ctx; - - GetPresContext(this, getter_AddRefs(ctx)); - NS_ENSURE_TRUE(ctx, NS_OK); - - nsEventStatus status = nsEventStatus_eIgnore; - nsEvent event; - - event.eventStructType = NS_EVENT; - event.message = NS_PAGE_LOAD; - - return HandleDOMEvent(ctx, &event, nsnull, NS_EVENT_FLAG_INIT, &status); -} - // static nsresult nsGenericHTMLElement::SetProtocolInHrefString(const nsAString &aHref, diff --git a/mozilla/content/html/content/src/nsGenericHTMLElement.h b/mozilla/content/html/content/src/nsGenericHTMLElement.h index f9bd9042635..204ebf84274 100644 --- a/mozilla/content/html/content/src/nsGenericHTMLElement.h +++ b/mozilla/content/html/content/src/nsGenericHTMLElement.h @@ -465,8 +465,6 @@ public: protected: nsresult SetElementFocus(PRBool aDoFocus); - nsresult HandleFrameOnloadEvent(nsIDOMEvent* aEvent); - PRBool IsEventName(nsIAtom* aName); }; diff --git a/mozilla/content/html/content/src/nsHTMLFrameElement.cpp b/mozilla/content/html/content/src/nsHTMLFrameElement.cpp index 53af3188dc0..f517094295c 100644 --- a/mozilla/content/html/content/src/nsHTMLFrameElement.cpp +++ b/mozilla/content/html/content/src/nsHTMLFrameElement.cpp @@ -37,7 +37,6 @@ * ***** END LICENSE BLOCK ***** */ #include "nsIDOMHTMLFrameElement.h" #include "nsIDOMNSHTMLFrameElement.h" -#include "nsIDOMEventListener.h" #include "nsIDOMEventReceiver.h" #include "nsIDOMWindow.h" #include "nsIScriptGlobalObject.h" @@ -49,14 +48,14 @@ #include "nsIDOMDocument.h" #include "nsIWebNavigation.h" #include "nsIChromeEventHandler.h" +#include "nsIDocShell.h" #include "nsDOMError.h" class nsHTMLFrameElement : public nsGenericHTMLLeafElement, public nsIDOMHTMLFrameElement, public nsIDOMNSHTMLFrameElement, - public nsIChromeEventHandler, - public nsIDOMEventListener + public nsIChromeEventHandler { public: nsHTMLFrameElement(); @@ -83,9 +82,6 @@ public: // nsIChromeEventHandler NS_DECL_NSICHROMEEVENTHANDLER - // nsIDOMEventListener - NS_DECL_NSIDOMEVENTLISTENER - NS_IMETHOD StringToAttribute(nsIAtom* aAttribute, const nsAString& aValue, nsHTMLValue& aResult); @@ -143,7 +139,6 @@ NS_HTML_CONTENT_INTERFACE_MAP_BEGIN(nsHTMLFrameElement, NS_INTERFACE_MAP_ENTRY(nsIDOMHTMLFrameElement) NS_INTERFACE_MAP_ENTRY(nsIDOMNSHTMLFrameElement) NS_INTERFACE_MAP_ENTRY(nsIChromeEventHandler) - NS_INTERFACE_MAP_ENTRY(nsIDOMEventListener) NS_INTERFACE_MAP_ENTRY_CONTENT_CLASSINFO(HTMLFrameElement) NS_HTML_CONTENT_INTERFACE_MAP_END @@ -191,33 +186,21 @@ NS_IMETHODIMP nsHTMLFrameElement::GetContentDocument(nsIDOMDocument** aContentDocument) { NS_ENSURE_ARG_POINTER(aContentDocument); - *aContentDocument = nsnull; - NS_ENSURE_TRUE(mDocument, NS_OK); + if (!mDocument) { + return NS_OK; + } - nsCOMPtr presShell; + nsCOMPtr content_document; - mDocument->GetShellAt(0, getter_AddRefs(presShell)); - NS_ENSURE_TRUE(presShell, NS_OK); + mDocument->GetSubDocumentFor(this, getter_AddRefs(content_document)); - nsCOMPtr tmp; + if (!content_document) { + return NS_OK; + } - presShell->GetSubShellFor(this, getter_AddRefs(tmp)); - NS_ENSURE_TRUE(tmp, NS_OK); - - nsCOMPtr webNav = do_QueryInterface(tmp); - NS_ENSURE_TRUE(webNav, NS_OK); - - nsCOMPtr domDoc; - - webNav->GetDocument(getter_AddRefs(domDoc)); - - *aContentDocument = domDoc; - - NS_IF_ADDREF(*aContentDocument); - - return NS_OK; + return CallQueryInterface(content_document, aContentDocument); } NS_IMETHODIMP @@ -329,8 +312,3 @@ nsHTMLFrameElement::HandleChromeEvent(nsIPresContext* aPresContext, return HandleDOMEvent(aPresContext, aEvent, aDOMEvent, aFlags,aEventStatus); } -nsresult -nsHTMLFrameElement::HandleEvent(nsIDOMEvent *aEvent) -{ - return HandleFrameOnloadEvent(aEvent); -} diff --git a/mozilla/content/html/content/src/nsHTMLIFrameElement.cpp b/mozilla/content/html/content/src/nsHTMLIFrameElement.cpp index 161391af067..7fb5d1daa2f 100644 --- a/mozilla/content/html/content/src/nsHTMLIFrameElement.cpp +++ b/mozilla/content/html/content/src/nsHTMLIFrameElement.cpp @@ -37,11 +37,10 @@ * ***** END LICENSE BLOCK ***** */ #include "nsIDOMHTMLIFrameElement.h" #include "nsIDOMNSHTMLFrameElement.h" -#include "nsIDOMEventListener.h" #include "nsIDOMEventReceiver.h" #include "nsIDOMWindow.h" #include "nsIScriptGlobalObject.h" -#include "nsIHTMLContent.h" +#include "nsIFrameLoader.h" #include "nsGenericHTMLElement.h" #include "nsHTMLAtoms.h" #include "nsIStyleContext.h" @@ -54,12 +53,14 @@ #include "nsIChromeEventHandler.h" #include "nsDOMError.h" #include "nsRuleNode.h" +#include "nsIDocShell.h" +#include "nsIInterfaceRequestorUtils.h" class nsHTMLIFrameElement : public nsGenericHTMLContainerElement, public nsIDOMHTMLIFrameElement, public nsIDOMNSHTMLFrameElement, public nsIChromeEventHandler, - public nsIDOMEventListener + public nsIFrameLoaderOwner { public: nsHTMLIFrameElement(); @@ -86,8 +87,11 @@ public: // nsIChromeEventHandler NS_DECL_NSICHROMEEVENTHANDLER - // nsIDOMEventListener - NS_DECL_NSIDOMEVENTLISTENER + // nsIFrameLoaderOwner + NS_IMETHOD GetFrameLoader(nsIFrameLoader **aFrameLoader); + + // nsIContent + NS_IMETHOD SetParent(nsIContent *aParent); NS_IMETHOD StringToAttribute(nsIAtom* aAttribute, const nsAString& aValue, @@ -101,6 +105,14 @@ public: #ifdef DEBUG NS_IMETHOD SizeOf(nsISizeOfHandler* aSizer, PRUint32* aResult) const; #endif + +protected: + // This doesn't really ensure a frame loade in all cases, only when + // it makes sense. + nsresult EnsureFrameLoader(); + nsresult LoadSrc(); + + nsCOMPtr mFrameLoader; }; nsresult @@ -136,6 +148,9 @@ nsHTMLIFrameElement::nsHTMLIFrameElement() nsHTMLIFrameElement::~nsHTMLIFrameElement() { + if (mFrameLoader) { + mFrameLoader->Destroy(); + } } @@ -148,7 +163,7 @@ NS_HTML_CONTENT_INTERFACE_MAP_BEGIN(nsHTMLIFrameElement, NS_INTERFACE_MAP_ENTRY(nsIDOMHTMLIFrameElement) NS_INTERFACE_MAP_ENTRY(nsIDOMNSHTMLFrameElement) NS_INTERFACE_MAP_ENTRY(nsIChromeEventHandler) - NS_INTERFACE_MAP_ENTRY(nsIDOMEventListener) + NS_INTERFACE_MAP_ENTRY(nsIFrameLoaderOwner) NS_INTERFACE_MAP_ENTRY_CONTENT_CLASSINFO(HTMLIFrameElement) NS_HTML_CONTENT_INTERFACE_MAP_END @@ -189,71 +204,123 @@ NS_IMPL_STRING_ATTR(nsHTMLIFrameElement, MarginHeight, marginheight) NS_IMPL_STRING_ATTR(nsHTMLIFrameElement, MarginWidth, marginwidth) NS_IMPL_STRING_ATTR(nsHTMLIFrameElement, Name, name) NS_IMPL_STRING_ATTR(nsHTMLIFrameElement, Scrolling, scrolling) -NS_IMPL_STRING_ATTR(nsHTMLIFrameElement, Src, src) NS_IMPL_STRING_ATTR(nsHTMLIFrameElement, Width, width) +NS_IMETHODIMP +nsHTMLIFrameElement::GetSrc(nsAString& aSrc) +{ + nsGenericHTMLContainerElement::GetAttr(kNameSpaceID_None, nsHTMLAtoms::src, + aSrc); + + return NS_OK; +} + +NS_IMETHODIMP +nsHTMLIFrameElement::SetSrc(const nsAString& aSrc) +{ + SetAttribute(NS_LITERAL_STRING("src"), aSrc); + + return LoadSrc(); +} NS_IMETHODIMP nsHTMLIFrameElement::GetContentDocument(nsIDOMDocument** aContentDocument) { NS_ENSURE_ARG_POINTER(aContentDocument); - *aContentDocument = nsnull; - NS_ENSURE_TRUE(mDocument, NS_OK); + nsresult rv = EnsureFrameLoader(); + NS_ENSURE_SUCCESS(rv, rv); - nsCOMPtr presShell; + if (!mFrameLoader) { + return NS_OK; + } - mDocument->GetShellAt(0, getter_AddRefs(presShell)); - NS_ENSURE_TRUE(presShell, NS_OK); + nsCOMPtr doc_shell; + mFrameLoader->GetDocShell(getter_AddRefs(doc_shell)); - nsCOMPtr tmp; + nsCOMPtr win(do_GetInterface(doc_shell)); - presShell->GetSubShellFor(this, getter_AddRefs(tmp)); - NS_ENSURE_TRUE(tmp, NS_OK); + if (!win) { + return NS_OK; + } - nsCOMPtr webNav = do_QueryInterface(tmp); - NS_ENSURE_TRUE(webNav, NS_OK); - - nsCOMPtr domDoc; - - webNav->GetDocument(getter_AddRefs(domDoc)); - - *aContentDocument = domDoc; - - NS_IF_ADDREF(*aContentDocument); - - return NS_OK; + return win->GetDocument(aContentDocument); } NS_IMETHODIMP nsHTMLIFrameElement::GetContentWindow(nsIDOMWindow** aContentWindow) { NS_ENSURE_ARG_POINTER(aContentWindow); - *aContentWindow = nsnull; - nsCOMPtr content_doc; - - nsresult rv = GetContentDocument(getter_AddRefs(content_doc)); + nsresult rv = EnsureFrameLoader(); NS_ENSURE_SUCCESS(rv, rv); - nsCOMPtr doc(do_QueryInterface(content_doc)); - - if (!doc) { + if (!mFrameLoader) { return NS_OK; } - nsCOMPtr globalObj; - doc->GetScriptGlobalObject(getter_AddRefs(globalObj)); + nsCOMPtr doc_shell; + mFrameLoader->GetDocShell(getter_AddRefs(doc_shell)); - nsCOMPtr window (do_QueryInterface(globalObj)); + nsCOMPtr win(do_GetInterface(doc_shell)); - *aContentWindow = window; + *aContentWindow = win; NS_IF_ADDREF(*aContentWindow); return NS_OK; } +nsresult +nsHTMLIFrameElement::EnsureFrameLoader() +{ + if (mFrameLoader || !mParent) { + return NS_OK; + } + + nsresult rv = NS_NewFrameLoader(getter_AddRefs(mFrameLoader)); + NS_ENSURE_SUCCESS(rv, rv); + + mFrameLoader->Init(this); + + return NS_OK; +} + +NS_IMETHODIMP +nsHTMLIFrameElement::GetFrameLoader(nsIFrameLoader **aFrameLoader) +{ + *aFrameLoader = mFrameLoader; + NS_IF_ADDREF(*aFrameLoader); + + return NS_OK; +} + +nsresult +nsHTMLIFrameElement::LoadSrc() +{ + nsresult rv = EnsureFrameLoader(); + NS_ENSURE_SUCCESS(rv, rv); + + if (!mFrameLoader) { + return NS_OK; + } + + rv = mFrameLoader->LoadFrame(); + NS_ASSERTION(NS_SUCCEEDED(rv), "failed to load URL"); + + return rv; +} + + +NS_IMETHODIMP +nsHTMLIFrameElement::SetParent(nsIContent *aParent) +{ + nsresult rv = nsGenericHTMLContainerElement::SetParent(aParent); + NS_ENSURE_SUCCESS(rv, rv); + + return LoadSrc(); +} + NS_IMETHODIMP nsHTMLIFrameElement::StringToAttribute(nsIAtom* aAttribute, const nsAString& aValue, @@ -366,7 +433,7 @@ MapAttributesIntoRule(const nsIHTMLMappedAttributes* aAttributes, if (aData->mPositionData->mHeight.GetUnit() == eCSSUnit_Null) { aAttributes->GetAttribute(nsHTMLAtoms::height, value); if (value.GetUnit() == eHTMLUnit_Pixel) - aData->mPositionData->mHeight.SetFloatValue((float)value.GetPixelValue(), eCSSUnit_Pixel); + aData->mPositionData->mHeight.SetFloatValue((float)value.GetPixelValue(), eCSSUnit_Pixel); else if (value.GetUnit() == eHTMLUnit_Percent) aData->mPositionData->mHeight.SetPercentValue(value.GetPercentValue()); } @@ -377,7 +444,8 @@ MapAttributesIntoRule(const nsIHTMLMappedAttributes* aAttributes, } NS_IMETHODIMP -nsHTMLIFrameElement::GetMappedAttributeImpact(const nsIAtom* aAttribute, PRInt32 aModType, +nsHTMLIFrameElement::GetMappedAttributeImpact(const nsIAtom* aAttribute, + PRInt32 aModType, PRInt32& aHint) const { if ((aAttribute == nsHTMLAtoms::width) || @@ -419,20 +487,15 @@ nsHTMLIFrameElement::SizeOf(nsISizeOfHandler* aSizer, PRUint32* aResult) const //***************************************************************************** // nsHTMLIFrameElement::nsIChromeEventHandler -//***************************************************************************** +//***************************************************************************** NS_IMETHODIMP nsHTMLIFrameElement::HandleChromeEvent(nsIPresContext* aPresContext, nsEvent* aEvent, nsIDOMEvent** aDOMEvent, - PRUint32 aFlags, + PRUint32 aFlags, nsEventStatus* aEventStatus) { return HandleDOMEvent(aPresContext, aEvent, aDOMEvent, aFlags,aEventStatus); } -nsresult -nsHTMLIFrameElement::HandleEvent(nsIDOMEvent *aEvent) -{ - return HandleFrameOnloadEvent(aEvent); -} diff --git a/mozilla/content/html/content/src/nsHTMLObjectElement.cpp b/mozilla/content/html/content/src/nsHTMLObjectElement.cpp index 27aa9de2798..898df0ab117 100644 --- a/mozilla/content/html/content/src/nsHTMLObjectElement.cpp +++ b/mozilla/content/html/content/src/nsHTMLObjectElement.cpp @@ -190,30 +190,18 @@ nsHTMLObjectElement::GetContentDocument(nsIDOMDocument** aContentDocument) *aContentDocument = nsnull; - NS_ENSURE_TRUE(mDocument, NS_OK); + if (!mDocument) { + return NS_OK; + } - nsCOMPtr presShell; + nsCOMPtr sub_doc; + mDocument->GetSubDocumentFor(this, getter_AddRefs(sub_doc)); - mDocument->GetShellAt(0, getter_AddRefs(presShell)); - NS_ENSURE_TRUE(presShell, NS_OK); + if (!sub_doc) { + return NS_OK; + } - nsCOMPtr tmp; - - presShell->GetSubShellFor(this, getter_AddRefs(tmp)); - if (!tmp) return NS_OK; - - nsCOMPtr webNav = do_QueryInterface(tmp); - NS_ENSURE_TRUE(webNav, NS_OK); - - nsCOMPtr domDoc; - - webNav->GetDocument(getter_AddRefs(domDoc)); - - *aContentDocument = domDoc; - - NS_IF_ADDREF(*aContentDocument); - - return NS_OK; + return CallQueryInterface(sub_doc, aContentDocument); } NS_IMETHODIMP diff --git a/mozilla/content/html/content/src/nsHTMLSharedObjectElement.cpp b/mozilla/content/html/content/src/nsHTMLSharedObjectElement.cpp index 27aa9de2798..898df0ab117 100644 --- a/mozilla/content/html/content/src/nsHTMLSharedObjectElement.cpp +++ b/mozilla/content/html/content/src/nsHTMLSharedObjectElement.cpp @@ -190,30 +190,18 @@ nsHTMLObjectElement::GetContentDocument(nsIDOMDocument** aContentDocument) *aContentDocument = nsnull; - NS_ENSURE_TRUE(mDocument, NS_OK); + if (!mDocument) { + return NS_OK; + } - nsCOMPtr presShell; + nsCOMPtr sub_doc; + mDocument->GetSubDocumentFor(this, getter_AddRefs(sub_doc)); - mDocument->GetShellAt(0, getter_AddRefs(presShell)); - NS_ENSURE_TRUE(presShell, NS_OK); + if (!sub_doc) { + return NS_OK; + } - nsCOMPtr tmp; - - presShell->GetSubShellFor(this, getter_AddRefs(tmp)); - if (!tmp) return NS_OK; - - nsCOMPtr webNav = do_QueryInterface(tmp); - NS_ENSURE_TRUE(webNav, NS_OK); - - nsCOMPtr domDoc; - - webNav->GetDocument(getter_AddRefs(domDoc)); - - *aContentDocument = domDoc; - - NS_IF_ADDREF(*aContentDocument); - - return NS_OK; + return CallQueryInterface(sub_doc, aContentDocument); } NS_IMETHODIMP diff --git a/mozilla/content/html/document/src/nsHTMLContentSink.cpp b/mozilla/content/html/document/src/nsHTMLContentSink.cpp index 770ccf3310c..aca715068a5 100644 --- a/mozilla/content/html/document/src/nsHTMLContentSink.cpp +++ b/mozilla/content/html/document/src/nsHTMLContentSink.cpp @@ -1503,7 +1503,7 @@ SinkContext::CloseContainer(const nsIParserNode& aNode) // Flush any collected text content. Release the last text // node to indicate that no more should be added to it. FlushTextAndRelease(); - + SINK_TRACE_NODE(SINK_TRACE_CALLS, "SinkContext::CloseContainer", aNode, mStackPos-1, mSink); @@ -1604,7 +1604,8 @@ SinkContext::CloseContainer(const nsIParserNode& aNode) case eHTMLTag_select: { - nsCOMPtr select = do_QueryInterface(content, &result); + nsCOMPtr select = do_QueryInterface(content); + if (select) { result = select->DoneAddingChildren(); } @@ -3824,43 +3825,57 @@ HTMLContentSink::DidProcessAToken(void) PRInt32 oldMaxTokenProcessingTime = GetMaxTokenProcessingTime(); #endif - // There is both a high frequency interrupt mode and a low frequency - // interupt mode controlled by the flag NS_SINK_FLAG_DYNAMIC_LOWER_VALUE - // The high frequency mode interupts the parser frequently to provide - // UI responsiveness at the expense of page load time. The low frequency mode - // interrupts the parser and samples the system clock infrequently to provide fast - // page load time. When the user moves the mouse, clicks or types the mode switches - // to the high frequency interrupt mode. If the user stops moving the mouse or typing - // for a duration of time (mDynamicIntervalSwitchThreshold) it switches to low - // frequency interrupt mode. + // There is both a high frequency interrupt mode and a low + // frequency interupt mode controlled by the flag + // NS_SINK_FLAG_DYNAMIC_LOWER_VALUE The high frequency mode + // interupts the parser frequently to provide UI responsiveness at + // the expense of page load time. The low frequency mode + // interrupts the parser and samples the system clock infrequently + // to provide fast page load time. When the user moves the mouse, + // clicks or types the mode switches to the high frequency + // interrupt mode. If the user stops moving the mouse or typing + // for a duration of time (mDynamicIntervalSwitchThreshold) it + // switches to low frequency interrupt mode. // Get the current user event time nsCOMPtr shell; mDocument->GetShellAt(0, getter_AddRefs(shell)); - NS_ENSURE_TRUE(shell, NS_ERROR_FAILURE); + + if (!shell) { + // If there's no pres shell in the document, return early since + // we're not laying anything out here. + + return NS_OK; + } + nsCOMPtr vm; shell->GetViewManager(getter_AddRefs(vm)); NS_ENSURE_TRUE(vm, NS_ERROR_FAILURE); PRUint32 eventTime; nsresult rv = vm->GetLastUserEventTime(eventTime); NS_ENSURE_TRUE(NS_SUCCEEDED(rv), NS_ERROR_FAILURE); - if ((!(mFlags & NS_SINK_FLAG_DYNAMIC_LOWER_VALUE)) && (mLastSampledUserEventTime == eventTime)) { - // The magic value of NS_MAX_TOKENS_DEFLECTED_IN_LOW_FREQ_MODE was selected by - // empirical testing. It provides reasonable - // user response and prevents us from sampling the clock too frequently. + // The magic value of NS_MAX_TOKENS_DEFLECTED_IN_LOW_FREQ_MODE + // was selected by empirical testing. It provides reasonable + // user response and prevents us from sampling the clock too + // frequently. if (mDeflectedCount < NS_MAX_TOKENS_DEFLECTED_IN_LOW_FREQ_MODE) { mDeflectedCount++; - return NS_OK; // return early to prevent sampling the clock. Note: This prevents - // us from switching to higher frequency (better UI responsive) mode, so - // limit ourselves to doing for no more than - // NS_MAX_TOKENS_DEFLECTED_IN_LOW_FREQ_MODE tokens. + + // return early to prevent sampling the clock. Note: This + // prevents us from switching to higher frequency (better UI + // responsive) mode, so limit ourselves to doing for no more + // than NS_MAX_TOKENS_DEFLECTED_IN_LOW_FREQ_MODE tokens. + + return NS_OK; } else { - mDeflectedCount = 0; // reset count and drop through to the code which samples the clock and - // does the dynamic switch between the high frequency and low frequency - // interruption of the parser. + // reset count and drop through to the code which samples the + // clock and does the dynamic switch between the high + // frequency and low frequency interruption of the parser. + + mDeflectedCount = 0; } } @@ -3868,48 +3883,49 @@ PRInt32 oldMaxTokenProcessingTime = GetMaxTokenProcessingTime(); PRUint32 currentTime = PR_IntervalToMicroseconds(PR_IntervalNow()); - // Get the last user event time and compare it with - // the current time to determine if the lower value - // for content notification and max token processing - // should be used. But only consider using the lower - // value if the document has already been loading - // for 2 seconds. 2 seconds was chosen because it is - // greater than the default 3/4 of second that is used - // to determine when to switch between the modes and it - // gives the document a little time to create windows. - // This is important because on some systems (Windows, - // for example) when a window is created and the mouse - // is over it, a mouse move event is sent, which will kick - // us into interactive mode otherwise. It also supresses - // reaction to pressing the ENTER key in the URL bar... + // Get the last user event time and compare it with the current + // time to determine if the lower value for content notification + // and max token processing should be used. But only consider + // using the lower value if the document has already been loading + // for 2 seconds. 2 seconds was chosen because it is greater than + // the default 3/4 of second that is used to determine when to + // switch between the modes and it gives the document a little + // time to create windows. This is important because on some + // systems (Windows, for example) when a window is created and the + // mouse is over it, a mouse move event is sent, which will kick + // us into interactive mode otherwise. It also supresses reaction + // to pressing the ENTER key in the URL bar... PRUint32 delayBeforeLoweringThreshold = NS_STATIC_CAST(PRUint32, ((2 * mDynamicIntervalSwitchThreshold) + NS_DELAY_FOR_WINDOW_CREATION)); - if (((currentTime - mBeginLoadTime) > delayBeforeLoweringThreshold) && mDocument) { - if ((currentTime - eventTime) < NS_STATIC_CAST(PRUint32, mDynamicIntervalSwitchThreshold)) { - // lower the dynamic values to favor - // application responsiveness over page load - // time. - mFlags |= NS_SINK_FLAG_DYNAMIC_LOWER_VALUE; - } - else { - // raise the content notification and - // MaxTokenProcessing time to favor overall - // page load speed over responsiveness - mFlags &= ~NS_SINK_FLAG_DYNAMIC_LOWER_VALUE; + + if ((currentTime - mBeginLoadTime) > delayBeforeLoweringThreshold) { + if ((currentTime - eventTime) < + NS_STATIC_CAST(PRUint32, mDynamicIntervalSwitchThreshold)) { + // lower the dynamic values to favor application + // responsiveness over page load time. + + mFlags |= NS_SINK_FLAG_DYNAMIC_LOWER_VALUE; + } else { + // raise the content notification and MaxTokenProcessing time + // to favor overall page load speed over responsiveness + + mFlags &= ~NS_SINK_FLAG_DYNAMIC_LOWER_VALUE; } } #ifdef NS_DEBUG -PRInt32 newMaxTokenProcessingTime = GetMaxTokenProcessingTime(); + PRInt32 newMaxTokenProcessingTime = GetMaxTokenProcessingTime(); - if (newMaxTokenProcessingTime != oldMaxTokenProcessingTime) { -// printf("Changed dynamic interval : MaxTokenProcessingTime %d\n", GetMaxTokenProcessingTime()); - } + if (newMaxTokenProcessingTime != oldMaxTokenProcessingTime) { +// printf("Changed dynamic interval : MaxTokenProcessingTime %d\n", +// GetMaxTokenProcessingTime()); + } #endif - if ((currentTime - mDelayTimerStart) > NS_STATIC_CAST(PRUint32, GetMaxTokenProcessingTime())) { - return NS_ERROR_HTMLPARSER_INTERRUPTED; - } + if ((currentTime - mDelayTimerStart) > + NS_STATIC_CAST(PRUint32, GetMaxTokenProcessingTime())) { + return NS_ERROR_HTMLPARSER_INTERRUPTED; + } } return NS_OK; @@ -4156,7 +4172,7 @@ nsresult HTMLContentSink::ProcessAREATag(const nsIParserNode& aNode) { nsresult rv = NS_OK; - if (nsnull != mCurrentMap) { + if (mCurrentMap) { nsHTMLTag nodeType = nsHTMLTag(aNode.GetNodeType()); nsIHTMLContent* area; rv = CreateContentObject(aNode, nodeType, nsnull, nsnull, &area); diff --git a/mozilla/content/html/document/src/nsHTMLDocument.cpp b/mozilla/content/html/document/src/nsHTMLDocument.cpp index 5351bc9e9f8..e7c9c1682c1 100644 --- a/mozilla/content/html/document/src/nsHTMLDocument.cpp +++ b/mozilla/content/html/document/src/nsHTMLDocument.cpp @@ -1477,7 +1477,7 @@ nsHTMLDocument::FlushPendingNotifications(PRBool aFlushReflows, } } - if ((isSafeToFlush) && (mParser)) { + if (isSafeToFlush && mParser) { nsCOMPtr sink; // XXX Ack! Parser doesn't addref sink before passing it back @@ -3750,34 +3750,33 @@ nsHTMLDocument::ResolveName(const nsAString& aName, PRBool nsHTMLDocument::GetBodyContent() { - nsCOMPtr root; + nsCOMPtr root; - GetDocumentElement(getter_AddRefs(root)); + GetRootContent(getter_AddRefs(root)); if (!root) { return PR_FALSE; } - NS_NAMED_LITERAL_STRING(bodyStr, "BODY"); - nsCOMPtr child; - root->GetFirstChild(getter_AddRefs(child)); + PRInt32 i, child_count; + root->ChildCount(child_count); - while (child) { - nsCOMPtr domElement(do_QueryInterface(child)); + for (i = 0; i < child_count; i++) { + nsCOMPtr child; - if (domElement) { - nsAutoString tagName; - domElement->GetTagName(tagName); + root->ChildAt(i, *getter_AddRefs(child)); + NS_ENSURE_TRUE(child, NS_ERROR_UNEXPECTED); - ToUpperCase(tagName); - if (bodyStr.Equals(tagName)) { - mBodyContent = child; + nsCOMPtr ni; + child->GetNodeInfo(*getter_AddRefs(ni)); - return PR_TRUE; - } + if (ni && ni->Equals(nsHTMLAtoms::body) && + (ni->NamespaceEquals(kNameSpaceID_None) || + ni->NamespaceEquals(kNameSpaceID_HTML))) { + mBodyContent = do_QueryInterface(child); + + return PR_TRUE; } - nsIDOMNode *tmpNode = child; - tmpNode->GetNextSibling(getter_AddRefs(child)); } return PR_FALSE; diff --git a/mozilla/content/html/style/src/nsCSSStyleSheet.cpp b/mozilla/content/html/style/src/nsCSSStyleSheet.cpp index 0bdc6d98e1f..264fc37440e 100644 --- a/mozilla/content/html/style/src/nsCSSStyleSheet.cpp +++ b/mozilla/content/html/style/src/nsCSSStyleSheet.cpp @@ -2657,7 +2657,7 @@ CSSStyleSheetImpl::SetDisabled(PRBool aDisabled) PRBool oldState = mDisabled; mDisabled = aDisabled; - if ((nsnull != mDocument) && (mDisabled != oldState)) { + if (mDocument && (mDisabled != oldState)) { mDocument->SetStyleSheetDisabledState(this, mDisabled); } diff --git a/mozilla/content/macbuild/content.xml b/mozilla/content/macbuild/content.xml index e9e8b57a950..755f6ba7cb6 100644 --- a/mozilla/content/macbuild/content.xml +++ b/mozilla/content/macbuild/content.xml @@ -2310,6 +2310,13 @@ Text Debug + + Name + nsFrameLoader.cpp + MacOS + Text + Debug + Name UnicharUtilsStatic.o @@ -3445,6 +3452,11 @@ nsContentAreaDragDrop.cpp MacOS + + Name + nsFrameLoader.cpp + MacOS + Name UnicharUtilsStatic.o @@ -5799,6 +5811,13 @@ Text Debug + + Name + nsFrameLoader.cpp + MacOS + Text + Debug + Name UnicharUtilsStaticDebug.o @@ -6934,6 +6953,11 @@ nsContentAreaDragDrop.cpp MacOS + + Name + nsFrameLoader.cpp + MacOS + Name UnicharUtilsStaticDebug.o @@ -7262,6 +7286,12 @@ nsContentAreaDragDrop.cpp MacOS + + content.shlb + Name + nsFrameLoader.cpp + MacOS + build diff --git a/mozilla/content/xul/document/src/nsXULDocument.cpp b/mozilla/content/xul/document/src/nsXULDocument.cpp index ce5e26270ca..881cc60d8c6 100644 --- a/mozilla/content/xul/document/src/nsXULDocument.cpp +++ b/mozilla/content/xul/document/src/nsXULDocument.cpp @@ -445,6 +445,8 @@ nsXULDocument::nsXULDocument(void) #ifdef IBMBIDI mBidiEnabled = PR_FALSE; #endif // IBMBIDI + + mSubDocuments = nsnull; } nsIFastLoadService* nsXULDocument::gFastLoadService = nsnull; @@ -472,14 +474,11 @@ nsXULDocument::~nsXULDocument() observer->DocumentWillBeDestroyed(this); } - // mParentDocument is never refcounted - // Delete references to sub-documents - { - i = mSubDocuments.Count(); - while (--i >= 0) { - nsIDocument* subdoc = (nsIDocument*) mSubDocuments.ElementAt(i); - NS_RELEASE(subdoc); - } + // Delete references to sub-documents and kill the subdocument map, + // if any. It holds strong references + if (mSubDocuments) { + PL_DHashTableDestroy(mSubDocuments); + mSubDocuments = nsnull; } // Delete references to style sheets but only if we aren't a popup document. @@ -526,7 +525,8 @@ nsXULDocument::~nsXULDocument() NS_IF_RELEASE(gXMLElementFactory); if (gNameSpaceManager) { - nsServiceManager::ReleaseService(kNameSpaceManagerCID, gNameSpaceManager); + nsServiceManager::ReleaseService(kNameSpaceManagerCID, + gNameSpaceManager); gNameSpaceManager = nsnull; } @@ -1122,27 +1122,154 @@ nsXULDocument::SetParentDocument(nsIDocument* aParent) return NS_OK; } -NS_IMETHODIMP -nsXULDocument::AddSubDocument(nsIDocument* aSubDoc) +PR_STATIC_CALLBACK(void) +SubDocClearEntry(PLDHashTable *table, PLDHashEntryHdr *entry) { - NS_ADDREF(aSubDoc); - mSubDocuments.AppendElement(aSubDoc); - return NS_OK; + SubDocMapEntry *e = NS_STATIC_CAST(SubDocMapEntry *, entry); + + NS_RELEASE(e->mKey); + NS_IF_RELEASE(e->mSubDocument); +} + +PR_STATIC_CALLBACK(void) +SubDocInitEntry(PLDHashTable *table, PLDHashEntryHdr *entry, const void *key) +{ + SubDocMapEntry *e = + NS_CONST_CAST(SubDocMapEntry *, + NS_STATIC_CAST(const SubDocMapEntry *, entry)); + + e->mKey = NS_CONST_CAST(nsIContent *, + NS_STATIC_CAST(const nsIContent *, key)); + NS_ADDREF(e->mKey); + + e->mSubDocument = nsnull; } NS_IMETHODIMP -nsXULDocument::GetNumberOfSubDocuments(PRInt32 *aCount) +nsXULDocument::SetSubDocumentFor(nsIContent *aContent, nsIDocument* aSubDoc) { - *aCount = mSubDocuments.Count(); - return NS_OK; + NS_ENSURE_TRUE(aContent, NS_ERROR_UNEXPECTED); + + if (!aSubDoc) { + // aSubDoc is nsnull, remove the mapping + + if (mSubDocuments) { + SubDocMapEntry *entry = + NS_STATIC_CAST(SubDocMapEntry*, + PL_DHashTableOperate(mSubDocuments, aContent, + PL_DHASH_LOOKUP)); + + if (PL_DHASH_ENTRY_IS_LIVE(entry)) { + entry->mSubDocument->SetParentDocument(nsnull); + + PL_DHashTableRawRemove(mSubDocuments, entry); + } + } + } else { + if (!mSubDocuments) { + // Create a new hashtable + + static PLDHashTableOps hash_table_ops = + { + PL_DHashAllocTable, + PL_DHashFreeTable, + PL_DHashGetKeyStub, + PL_DHashVoidPtrKeyStub, + PL_DHashMatchEntryStub, + PL_DHashMoveEntryStub, + SubDocClearEntry, + PL_DHashFinalizeStub, + SubDocInitEntry + }; + + mSubDocuments = PL_NewDHashTable(&hash_table_ops, nsnull, + sizeof(SubDocMapEntry), 16); + if (!mSubDocuments) { + return NS_ERROR_OUT_OF_MEMORY; + } + } + + // Add a mapping to the hash table + SubDocMapEntry *entry = + NS_STATIC_CAST(SubDocMapEntry*, + PL_DHashTableOperate(mSubDocuments, aContent, + PL_DHASH_ADD)); + + if (!entry) { + return NS_ERROR_OUT_OF_MEMORY; + } + + if (entry->mSubDocument) { + entry->mSubDocument->SetParentDocument(nsnull); + + // Release the old sub document + NS_RELEASE(entry->mSubDocument); + } + + entry->mSubDocument = aSubDoc; + NS_ADDREF(entry->mSubDocument); + + aSubDoc->SetParentDocument(this); + } + + return NS_OK; } NS_IMETHODIMP -nsXULDocument::GetSubDocumentAt(PRInt32 aIndex, nsIDocument** aSubDoc) +nsXULDocument::GetSubDocumentFor(nsIContent *aContent, nsIDocument** aSubDoc) { - *aSubDoc = (nsIDocument*) mSubDocuments.SafeElementAt(aIndex); - NS_IF_ADDREF(*aSubDoc); + *aSubDoc = nsnull; + + if (mSubDocuments) { + SubDocMapEntry *entry = + NS_STATIC_CAST(SubDocMapEntry*, + PL_DHashTableOperate(mSubDocuments, aContent, + PL_DHASH_LOOKUP)); + + if (PL_DHASH_ENTRY_IS_BUSY(entry)) { + *aSubDoc = entry->mSubDocument; + NS_ADDREF(*aSubDoc); + } + } + + return NS_OK; +} + +PR_STATIC_CALLBACK(PLDHashOperator) +FindContentEnumerator(PLDHashTable *table, PLDHashEntryHdr *hdr, + PRUint32 number, void *arg) +{ + SubDocMapEntry *entry = NS_STATIC_CAST(SubDocMapEntry*, hdr); + FindContentData *data = NS_STATIC_CAST(FindContentData*, arg); + + if (entry->mSubDocument == data->mSubDocument) { + data->mResult = NS_CONST_CAST(nsIContent *, entry->mKey); + + return PL_DHASH_STOP; + } + + return PL_DHASH_NEXT; +} + +NS_IMETHODIMP +nsXULDocument::FindContentForSubDocument(nsIDocument *aDocument, + nsIContent **aContent) +{ + NS_ENSURE_ARG_POINTER(aDocument); + + if (!mSubDocuments) { + *aContent = nsnull; + return NS_OK; + } + + FindContentData data(aDocument); + PL_DHashTableEnumerate(mSubDocuments, FindContentEnumerator, &data); + + *aContent = data.mResult; + NS_IF_ADDREF(*aContent); + + return NS_OK; } NS_IMETHODIMP @@ -2404,6 +2531,25 @@ nsXULDocument::RemoveReference(void *aKey, nsISupports **aOldReference) return NS_OK; } +NS_IMETHODIMP +nsXULDocument::SetContainer(nsISupports *aContainer) +{ + mDocumentContainer = dont_AddRef(NS_GetWeakReference(aContainer)); + + return NS_OK; +} + +NS_IMETHODIMP +nsXULDocument::GetContainer(nsISupports **aContainer) +{ + nsCOMPtr container = do_QueryReferent(mDocumentContainer); + + *aContainer = container; + NS_IF_ADDREF(*aContainer); + + return NS_OK; +} + void nsXULDocument::SetDisplaySelection(PRInt8 aToggle) { diff --git a/mozilla/content/xul/document/src/nsXULDocument.h b/mozilla/content/xul/document/src/nsXULDocument.h index 3d11bb9094c..3acb9a613fb 100644 --- a/mozilla/content/xul/document/src/nsXULDocument.h +++ b/mozilla/content/xul/document/src/nsXULDocument.h @@ -222,11 +222,12 @@ public: NS_IMETHOD SetParentDocument(nsIDocument* aParent); - NS_IMETHOD AddSubDocument(nsIDocument* aSubDoc); + NS_IMETHOD SetSubDocumentFor(nsIContent *aContent, nsIDocument* aSubDoc); - NS_IMETHOD GetNumberOfSubDocuments(PRInt32* aCount); + NS_IMETHOD GetSubDocumentFor(nsIContent *aContent, nsIDocument** aSubDoc); - NS_IMETHOD GetSubDocumentAt(PRInt32 aIndex, nsIDocument** aSubDoc); + NS_IMETHOD FindContentForSubDocument(nsIDocument *aDocument, + nsIContent **aContent); NS_IMETHOD GetRootContent(nsIContent** aRoot); @@ -333,6 +334,8 @@ public: NS_IMETHOD AddReference(void *aKey, nsISupports *aReference); NS_IMETHOD RemoveReference(void *aKey, nsISupports **aOldReference); + NS_IMETHOD SetContainer(nsISupports *aContainer); + NS_IMETHOD GetContainer(nsISupports **aContainer); virtual void SetDisplaySelection(PRInt8 aToggle); @@ -562,6 +565,7 @@ protected: nsCOMPtr mDocumentURL; // [OWNER] ??? compare with loader nsCOMPtr mDocumentBaseURL; nsWeakPtr mDocumentLoadGroup; // [WEAK] leads to loader + nsWeakPtr mDocumentContainer; // [WEAK] leads to container nsCOMPtr mDocumentPrincipal; // [OWNER] nsCOMPtr mRootContent; // [OWNER] nsIDocument* mParentDocument; // [WEAK] @@ -590,7 +594,7 @@ protected: nsCOMPtr mLocalStore; nsCOMPtr mLineBreaker; // [OWNER] nsCOMPtr mWordBreaker; // [OWNER] - nsVoidArray mSubDocuments; // [OWNER] of subelements + PLDHashTable *mSubDocuments; // [OWNER] of subelements PRPackedBool mIsPopup; PRPackedBool mIsFastLoad; PRPackedBool mApplyingPersistedAttrs; diff --git a/mozilla/docshell/base/nsDocShell.cpp b/mozilla/docshell/base/nsDocShell.cpp index de48e2d1c6e..84d89af82f6 100644 --- a/mozilla/docshell/base/nsDocShell.cpp +++ b/mozilla/docshell/base/nsDocShell.cpp @@ -1158,6 +1158,14 @@ nsDocShell::SetChromeEventHandler(nsIChromeEventHandler * aChromeEventHandler) { // Weak reference. Don't addref. mChromeEventHandler = aChromeEventHandler; + + NS_ASSERTION(!mScriptGlobal, + "SetChromeEventHandler() called after the script global " + "object was created! This means that the script global " + "object in this docshell won't get the right chrome event " + "handler. You really don't want to see this assert, FIX " + "YOUR CODE!"); + return NS_OK; } @@ -2441,7 +2449,6 @@ nsDocShell::Stop(PRUint32 aStopFlags) if (nsIWebNavigation::STOP_CONTENT & aStopFlags) { if (mContentViewer) mContentViewer->Stop(); - } if (nsIWebNavigation::STOP_NETWORK & aStopFlags) { @@ -2650,7 +2657,6 @@ nsDocShell::InitWindow(nativeWindow parentNativeWindow, NS_IMETHODIMP nsDocShell::Create() { - NS_ENSURE_STATE(!mContentViewer); mPrefs = do_GetService(NS_PREF_CONTRACTID); //GlobalHistory is now set in SetGlobalHistory // mGlobalHistory = do_GetService(NS_GLOBALHISTORY_CONTRACTID); @@ -2835,8 +2841,6 @@ nsDocShell::GetParentWidget(nsIWidget ** parentWidget) NS_IMETHODIMP nsDocShell::SetParentWidget(nsIWidget * aParentWidget) { - NS_ENSURE_STATE(!mContentViewer); - mParentWidget = aParentWidget; return NS_OK; @@ -3960,6 +3964,7 @@ nsDocShell::CreateAboutBlankContentViewer() // generate (about:blank) document to load docFactory->CreateBlankDocument(loadGroup, getter_AddRefs(blankDoc)); if (blankDoc) { + blankDoc->SetContainer(NS_STATIC_CAST(nsIDocShell *, this)); // create a content viewer for us and the new document docFactory->CreateInstanceForDocument(NS_ISUPPORTS_CAST(nsIDocShell *, this), @@ -4301,13 +4306,13 @@ nsDocShell::SetupNewViewer(nsIContentViewer * aNewViewer) nsCOMPtr widget; NS_ENSURE_SUCCESS(GetMainWidget(getter_AddRefs(widget)), NS_ERROR_FAILURE); - if (!widget) { - NS_ERROR("GetMainWidget coughed up a null widget"); - return NS_ERROR_FAILURE; + + if (widget) { + NS_ENSURE_SUCCESS(EnsureDeviceContext(), NS_ERROR_FAILURE); } nsRect bounds(x, y, cx, cy); - NS_ENSURE_SUCCESS(EnsureDeviceContext(), NS_ERROR_FAILURE); + if (NS_FAILED(mContentViewer->Init(widget, mDeviceContext, bounds))) { mContentViewer = nsnull; NS_ERROR("ContentViewer Initialization failed"); @@ -4330,7 +4335,7 @@ nsDocShell::SetupNewViewer(nsIContentViewer * aNewViewer) focusController->SetSuppressFocus(PR_FALSE, "Win32-Only Link Traversal Issue"); - if (bgSet) { + if (bgSet && widget) { // Stuff the bgcolor from the last view manager into the new // view manager. This improves page load continuity. nsCOMPtr docviewer = diff --git a/mozilla/docshell/base/nsWebShell.cpp b/mozilla/docshell/base/nsWebShell.cpp index 96a696364a4..814d19bd5c2 100644 --- a/mozilla/docshell/base/nsWebShell.cpp +++ b/mozilla/docshell/base/nsWebShell.cpp @@ -1254,7 +1254,7 @@ NS_IMETHODIMP nsWebShell::Create() // Set the webshell as the default IContentViewerContainer for the loader... mDocLoader->SetContainer(shellAsContainer); - return nsDocShell::Create(); + return nsDocShell::Create(); } NS_IMETHODIMP nsWebShell::Destroy() diff --git a/mozilla/dom/public/base/nsPIDOMWindow.h b/mozilla/dom/public/base/nsPIDOMWindow.h index 4818d3d93d9..426785c766d 100644 --- a/mozilla/dom/public/base/nsPIDOMWindow.h +++ b/mozilla/dom/public/base/nsPIDOMWindow.h @@ -46,6 +46,7 @@ #include "nsIDOMLocation.h" #include "nsIDOMXULCommandDispatcher.h" #include "nsIDocument.h" +#include "nsIDOMElement.h" class nsIDocShell; class nsIDOMWindowInternal; @@ -66,7 +67,7 @@ public: NS_IMETHOD GetObjectProperty(const PRUnichar* aProperty, nsISupports** aObject) = 0; - + // This is private because activate/deactivate events are not part // of the DOM spec. NS_IMETHOD Activate() = 0; @@ -84,6 +85,12 @@ public: NS_IMETHOD GetExtantDocument(nsIDOMDocument** aDocument) = 0; NS_IMETHOD ReallyCloseWindow() = 0; + + // Internal getter/setter for the frame element, this version of the + // getter crosses chrome boundaries whereas the public scriptable + // one doesn't for security reasons. + NS_IMETHOD GetFrameElementInternal(nsIDOMElement** aFrameElement) = 0; + NS_IMETHOD SetFrameElementInternal(nsIDOMElement* aFrameElement) = 0; }; #endif // nsPIDOMWindow_h__ diff --git a/mozilla/dom/public/idl/base/nsIDOMWindowInternal.idl b/mozilla/dom/public/idl/base/nsIDOMWindowInternal.idl index d549ea82980..3489a71b15a 100644 --- a/mozilla/dom/public/idl/base/nsIDOMWindowInternal.idl +++ b/mozilla/dom/public/idl/base/nsIDOMWindowInternal.idl @@ -185,4 +185,6 @@ interface nsIDOMWindowInternal : nsIDOMWindow // Ascii base64 data to binary data and vice versa... DOMString atob(in DOMString aAsciiString); DOMString btoa(in DOMString aBase64Data); + + readonly attribute nsIDOMElement frameElement; }; diff --git a/mozilla/dom/src/base/nsGlobalWindow.cpp b/mozilla/dom/src/base/nsGlobalWindow.cpp index b4cd26942cb..33161dfcf9a 100644 --- a/mozilla/dom/src/base/nsGlobalWindow.cpp +++ b/mozilla/dom/src/base/nsGlobalWindow.cpp @@ -185,7 +185,8 @@ GlobalWindowImpl::GlobalWindowImpl() : mLastMouseButtonAction(LL_ZERO), mFullScreen(PR_FALSE), mOriginalPos(nsnull), mOriginalSize(nsnull), mGlobalObjectOwner(nsnull), - mDocShell(nsnull), mMutationBits(0), mChromeEventHandler(nsnull) + mDocShell(nsnull), mMutationBits(0), mChromeEventHandler(nsnull), + mFrameElement(nsnull) { NS_INIT_REFCNT(); // We could have failed the first time through trying @@ -716,6 +717,38 @@ GlobalWindowImpl::HandleDOMEvent(nsIPresContext* aPresContext, } } + if (aEvent->message == NS_PAGE_LOAD) { + nsCOMPtr content(do_QueryInterface(mFrameElement)); + + nsCOMPtr parent; + GetParentInternal(getter_AddRefs(parent)); + + nsCOMPtr treeItem(do_QueryInterface(mDocShell)); + + PRInt32 itemType = nsIDocShellTreeItem::typeChrome; + + if (treeItem) { + treeItem->GetItemType(&itemType); + } + + if (content && parent && itemType != nsIDocShellTreeItem::typeChrome) { + // If we're not in chrome, or at a chrome boundary, fire the + // onload event for the frame element. + + nsCOMPtr ctx; + mDocShell->GetPresContext(getter_AddRefs(ctx)); + NS_ENSURE_TRUE(ctx, NS_OK); + + nsEventStatus status = nsEventStatus_eIgnore; + nsEvent event; + + event.eventStructType = NS_EVENT; + event.message = NS_PAGE_LOAD; + + return content->HandleDOMEvent(ctx, &event, nsnull, NS_EVENT_FLAG_INIT, + &status); + } + } if (NS_EVENT_FLAG_INIT & aFlags) { // We're leaving the DOM event loop so if we created an event, @@ -2813,6 +2846,53 @@ GlobalWindowImpl::ReallyCloseWindow() return NS_OK; } +NS_IMETHODIMP +GlobalWindowImpl::GetFrameElement(nsIDOMElement** aFrameElement) +{ + *aFrameElement = nsnull; + + nsCOMPtr docShell; + GetDocShell(getter_AddRefs(docShell)); + + nsCOMPtr docShellTI(do_QueryInterface(docShell)); + + if (!docShellTI) { + return NS_OK; + } + + nsCOMPtr parent; + docShellTI->GetSameTypeParent(getter_AddRefs(parent)); + + if (!parent || parent == docShellTI) { + // We're at a chrome boundary, don't expose the chrome iframe + // element to content code. + + return NS_OK; + } + + *aFrameElement = mFrameElement; + NS_IF_ADDREF(*aFrameElement); + + return NS_OK; +} + +NS_IMETHODIMP +GlobalWindowImpl::GetFrameElementInternal(nsIDOMElement** aFrameElement) +{ + *aFrameElement = mFrameElement; + NS_IF_ADDREF(*aFrameElement); + + return NS_OK; +} + +NS_IMETHODIMP +GlobalWindowImpl::SetFrameElementInternal(nsIDOMElement* aFrameElement) +{ + mFrameElement = aFrameElement; + + return NS_OK; +} + NS_IMETHODIMP GlobalWindowImpl::UpdateCommands(const nsAString& anAction) { @@ -4772,6 +4852,7 @@ nsGlobalChromeWindow::GetWindowState(PRUint16* aWindowState) break; case nsSizeMode_Normal: *aWindowState = nsIDOMChromeWindow::STATE_NORMAL; + break; default: NS_WARNING("Illegal window state for this chrome window"); break; diff --git a/mozilla/dom/src/base/nsGlobalWindow.h b/mozilla/dom/src/base/nsGlobalWindow.h index 8e071502b01..30deefc688a 100644 --- a/mozilla/dom/src/base/nsGlobalWindow.h +++ b/mozilla/dom/src/base/nsGlobalWindow.h @@ -188,6 +188,9 @@ public: NS_IMETHOD ReallyCloseWindow(); + NS_IMETHOD GetFrameElementInternal(nsIDOMElement** aFrameElement); + NS_IMETHOD SetFrameElementInternal(nsIDOMElement* aFrameElement); + // nsIDOMViewCSS NS_DECL_NSIDOMVIEWCSS @@ -302,6 +305,8 @@ protected: nsCOMPtr mPkcs11; nsCOMPtr mDocumentPrincipal; + nsIDOMElement* mFrameElement; // WEAK + friend class nsDOMScriptableHelper; static nsIXPConnect *sXPConnect; }; diff --git a/mozilla/dom/src/events/nsJSEventListener.cpp b/mozilla/dom/src/events/nsJSEventListener.cpp index 7ccbf6f760a..28f1c42c4a5 100644 --- a/mozilla/dom/src/events/nsJSEventListener.cpp +++ b/mozilla/dom/src/events/nsJSEventListener.cpp @@ -151,9 +151,11 @@ nsresult nsJSEventListener::HandleEvent(nsIDOMEvent* aEvent) nsEvent* event; priv->GetInternalNSEvent(&event); if (event->message == NS_SCRIPT_ERROR) { - nsScriptErrorEvent *scriptEvent = NS_STATIC_CAST(nsScriptErrorEvent*, event); + nsScriptErrorEvent *scriptEvent = + NS_STATIC_CAST(nsScriptErrorEvent*, event); + argv = ::JS_PushArguments(cx, &stackPtr, "WWi", scriptEvent->errorMsg, - scriptEvent->fileName, scriptEvent->lineNr); + scriptEvent->fileName, scriptEvent->lineNr); NS_ENSURE_TRUE(argv, NS_ERROR_OUT_OF_MEMORY); argc = 3; handledScriptError = PR_TRUE; diff --git a/mozilla/editor/libeditor/base/nsEditor.cpp b/mozilla/editor/libeditor/base/nsEditor.cpp index 52ddd146361..1f404c662a4 100644 --- a/mozilla/editor/libeditor/base/nsEditor.cpp +++ b/mozilla/editor/libeditor/base/nsEditor.cpp @@ -261,6 +261,8 @@ nsEditor::~nsEditor() IMETextTxn::ClassShutdown(); PR_AtomicDecrement(&gInstanceCount); + + NS_IF_RELEASE(mViewManager); } @@ -304,7 +306,6 @@ nsEditor::Init(nsIDOMDocument *aDoc, nsIPresShell* aPresShell, nsIContent *aRoot ps->GetViewManager(&mViewManager); if (!mViewManager) {return NS_ERROR_NULL_POINTER;} - mViewManager->Release(); //we want a weak link mUpdateCount=0; InsertTextTxn::ClassInit(); diff --git a/mozilla/extensions/inspector/base/src/inLayoutUtils.cpp b/mozilla/extensions/inspector/base/src/inLayoutUtils.cpp index 12a7a733330..b3de7a49420 100644 --- a/mozilla/extensions/inspector/base/src/inLayoutUtils.cpp +++ b/mozilla/extensions/inspector/base/src/inLayoutUtils.cpp @@ -1,4 +1,4 @@ -/* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */ +/* -*- Mode: C++; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*- */ /* ***** BEGIN LICENSE BLOCK ***** * Version: NPL 1.1/GPL 2.0/LGPL 2.1 * @@ -253,22 +253,12 @@ inLayoutUtils::GetSubDocumentFor(nsIDOMNode* aNode) nsCOMPtr doc; content->GetDocument(*getter_AddRefs(doc)); if (doc) { - nsCOMPtr shell; - doc->GetShellAt(0, getter_AddRefs(shell)); - if (shell) { - nsCOMPtr supports; - shell->GetSubShellFor(content, getter_AddRefs(supports)); - nsCOMPtr docShell = do_QueryInterface(supports); - if (docShell) { - nsCOMPtr contentViewer; - docShell->GetContentViewer(getter_AddRefs(contentViewer)); - if (contentViewer) { - nsCOMPtr domdoc; - contentViewer->GetDOMDocument(getter_AddRefs(domdoc)); - return domdoc; - } - } - } + nsCOMPtr sub_doc; + doc->GetSubDocumentFor(content, getter_AddRefs(sub_doc)); + + nsCOMPtr domdoc(do_QueryInterface(sub_doc)); + + return domdoc; } } @@ -279,6 +269,7 @@ nsIDOMNode* inLayoutUtils::GetContainerFor(nsIDOMDocument* aDoc) { nsCOMPtr container; + nsCOMPtr doc(do_QueryInterface(aDoc)); // get the doc shell for this document and look for the parent doc shell nsCOMPtr win = inLayoutUtils::GetWindowFor(aDoc); @@ -297,9 +288,17 @@ inLayoutUtils::GetContainerFor(nsIDOMDocument* aDoc) nsCOMPtr presShell; parentDocShell->GetPresShell(getter_AddRefs(presShell)); - nsCOMPtr content; - presShell->FindContentForShell(docShell, getter_AddRefs(content)); - nsCOMPtr node = do_QueryInterface(content); + nsCOMPtr parent_doc; + presShell->GetDocument(getter_AddRefs(parent_doc)); + + nsCOMPtr node; + + if (parent_doc) { + nsCOMPtr content; + parent_doc->FindContentForSubDocument(doc, getter_AddRefs(content)); + + node = do_QueryInterface(content); + } return node; } diff --git a/mozilla/layout/base/nsDocumentViewer.cpp b/mozilla/layout/base/nsDocumentViewer.cpp index 92f9c14d123..0ca981ca4ea 100644 --- a/mozilla/layout/base/nsDocumentViewer.cpp +++ b/mozilla/layout/base/nsDocumentViewer.cpp @@ -93,6 +93,7 @@ #include "nsIDocShellTreeNode.h" #include "nsIDocShellTreeOwner.h" #include "nsIDocShell.h" +#include "nsIBaseWindow.h" #include "nsIFrameDebug.h" #include "nsILayoutHistoryState.h" #include "nsLayoutAtoms.h" @@ -145,7 +146,7 @@ static NS_DEFINE_IID(kPrinterEnumeratorCID, NS_PRINTER_ENUMERATOR_CID); // Print Preview #include "nsIPrintPreviewContext.h" #include "imgIContainer.h" // image animation mode constants -#include "nsIScrollableView.h" +#include "nsIScrollableView.h" #include "nsIWebBrowserPrint.h" // needed for PrintPreview Navigation constants // Print Progress @@ -169,7 +170,7 @@ static NS_DEFINE_IID(kPrinterEnumeratorCID, NS_PRINTER_ENUMERATOR_CID); #include "nsIWebShell.h" //focus -#include "nsIDOMEventReceiver.h" +#include "nsIDOMEventReceiver.h" #include "nsIDOMFocusListener.h" #include "nsISelectionController.h" @@ -198,7 +199,7 @@ static NS_DEFINE_CID(kStyleSetCID, NS_STYLESET_CID); #ifdef DEBUG_PRINTING // XXX NOTE: I am including a header from the layout directory // merely to set up a file pointer for debug logging. This is -// fragile and may break in the future, which means it can be +// fragile and may break in the future, which means it can be // removed if necessary #if defined(XP_PC) #include "../../../layout/html/base/src/nsSimplePageSequence.h" @@ -212,20 +213,20 @@ static const char * gPrintRangeStr[] = {"kRangeAllPages", "kRangeSpecified static PRUint32 gDumpFileNameCnt = 0; static PRUint32 gDumpLOFileNameCnt = 0; -#define PRINT_DEBUG_MSG1(_msg1) fprintf(mPrt->mDebugFD, (_msg1)); -#define PRINT_DEBUG_MSG2(_msg1, _msg2) fprintf(mPrt->mDebugFD, (_msg1), (_msg2)); -#define PRINT_DEBUG_MSG3(_msg1, _msg2, _msg3) fprintf(mPrt->mDebugFD, (_msg1), (_msg2), (_msg3)); -#define PRINT_DEBUG_MSG4(_msg1, _msg2, _msg3, _msg4) fprintf(mPrt->mDebugFD, (_msg1), (_msg2), (_msg3), (_msg4)); -#define PRINT_DEBUG_MSG5(_msg1, _msg2, _msg3, _msg4, _msg5) fprintf(mPrt->mDebugFD, (_msg1), (_msg2), (_msg3), (_msg4), (_msg5)); +#define PRINT_DEBUG_MSG1(_msg1) fprintf(mPrt->mDebugFD, (_msg1)); +#define PRINT_DEBUG_MSG2(_msg1, _msg2) fprintf(mPrt->mDebugFD, (_msg1), (_msg2)); +#define PRINT_DEBUG_MSG3(_msg1, _msg2, _msg3) fprintf(mPrt->mDebugFD, (_msg1), (_msg2), (_msg3)); +#define PRINT_DEBUG_MSG4(_msg1, _msg2, _msg3, _msg4) fprintf(mPrt->mDebugFD, (_msg1), (_msg2), (_msg3), (_msg4)); +#define PRINT_DEBUG_MSG5(_msg1, _msg2, _msg3, _msg4, _msg5) fprintf(mPrt->mDebugFD, (_msg1), (_msg2), (_msg3), (_msg4), (_msg5)); #define PRINT_DEBUG_FLUSH fflush(mPrt->mDebugFD); #else //-------------- -#define PRT_YESNO(_p) -#define PRINT_DEBUG_MSG1(_msg) -#define PRINT_DEBUG_MSG2(_msg1, _msg2) -#define PRINT_DEBUG_MSG3(_msg1, _msg2, _msg3) -#define PRINT_DEBUG_MSG4(_msg1, _msg2, _msg3, _msg4) -#define PRINT_DEBUG_MSG5(_msg1, _msg2, _msg3, _msg4, _msg5) -#define PRINT_DEBUG_FLUSH +#define PRT_YESNO(_p) +#define PRINT_DEBUG_MSG1(_msg) +#define PRINT_DEBUG_MSG2(_msg1, _msg2) +#define PRINT_DEBUG_MSG3(_msg1, _msg2, _msg3) +#define PRINT_DEBUG_MSG4(_msg1, _msg2, _msg3, _msg4) +#define PRINT_DEBUG_MSG5(_msg1, _msg2, _msg3, _msg4, _msg5) +#define PRINT_DEBUG_FLUSH #endif @@ -251,7 +252,7 @@ public: NS_DECL_ISUPPORTS // nsISelectionListerner interface - NS_DECL_NSISELECTIONLISTENER + NS_DECL_NSISELECTIONLISTENER nsDocViewerSelectionListener() : mDocViewer(NULL) @@ -260,9 +261,9 @@ public: { NS_INIT_REFCNT(); } - + virtual ~nsDocViewerSelectionListener() {} - + nsresult Init(DocumentViewerImpl *aDocViewer); protected: @@ -270,13 +271,13 @@ protected: DocumentViewerImpl* mDocViewer; PRPackedBool mGotSelectionState; PRPackedBool mSelectionWasCollapsed; - + }; /** editor Implementation of the FocusListener interface */ -class nsDocViewerFocusListener : public nsIDOMFocusListener +class nsDocViewerFocusListener : public nsIDOMFocusListener { public: /** default constructor @@ -398,8 +399,8 @@ public: // Listener Helper Methods void OnEndPrinting(); void OnStartPrinting(); - static void DoOnProgressChange(nsVoidArray& aListeners, - PRInt32 aProgess, + static void DoOnProgressChange(nsVoidArray& aListeners, + PRInt32 aProgess, PRInt32 aMaxProgress, PRBool aDoStartStop = PR_FALSE, PRInt32 aFlag = 0); @@ -416,7 +417,7 @@ public: nsCOMPtr mPrintProgress; nsCOMPtr mPrintProgressParams; PRBool mShowProgressDialog; - + nsCOMPtr mCurrentFocusWin; // cache a pointer to the currently focused window nsVoidArray* mPrintDocList; @@ -472,11 +473,11 @@ class DocumentViewerImpl : public nsIDocumentViewer, friend class nsDocViewerSelectionListener; friend class nsPagePrintTimer; friend class PrintData; - + public: DocumentViewerImpl(); DocumentViewerImpl(nsIPresContext* aPresContext); - + NS_DECL_AND_IMPL_ZEROING_OPERATOR_NEW // nsISupports interface... @@ -511,15 +512,24 @@ public: nsresult CallChildren(CallChildFunc aFunc, void* aClosure); // Printing Methods - PRBool PrintPage(nsIPresContext* aPresContext,nsIPrintSettings* aPrintSettings,PrintObject* aPOect, PRBool& aInRange); + PRBool PrintPage(nsIPresContext* aPresContext, + nsIPrintSettings* aPrintSettings, + PrintObject* aPOect, PRBool& aInRange); PRBool DonePrintingPages(PrintObject* aPO); - + // helper method - static void GetWebShellTitleAndURL(nsIWebShell * aWebShell, PRUnichar** aTitle, PRUnichar** aURLStr); + static void GetWebShellTitleAndURL(nsIWebShell* aWebShell, + PRUnichar** aTitle, PRUnichar** aURLStr); // This enum tells indicates what the default should be for the title // if the title from the document is null - enum eDocTitleDefault {eDocTitleDefNone, eDocTitleDefBlank, eDocTitleDefDocument, eDocTitleDefURLDoc}; + enum eDocTitleDefault { + eDocTitleDefNone, + eDocTitleDefBlank, + eDocTitleDefDocument, + eDocTitleDefURLDoc + }; + static void GetDisplayTitleAndURL(PrintObject* aPO, nsIPrintSettings* aPrintSettings, const PRUnichar* aBrandName, @@ -539,12 +549,15 @@ private: nsIDeviceContext* aDeviceContext, const nsRect& aBounds, PRBool aDoCreation); - nsresult GetDocumentSelection(nsISelection **aSelection, nsIPresShell * aPresShell = nsnull); + nsresult InitPresentationStuff(PRBool aDoInitialReflow); + + nsresult GetDocumentSelection(nsISelection **aSelection, + nsIPresShell * aPresShell = nsnull); nsresult FindFrameSetWithIID(nsIContent * aParentContent, const nsIID& aIID); PRBool IsThereARangeSelection(nsIDOMWindowInternal * aDOMWin); PRBool IsParentAFrameSet(nsIWebShell * aParent); PRBool IsWebShellAFrameSet(nsIWebShell * aParent); - + PRBool IsThereAnIFrameSelected(nsIWebShell* aWebShell, nsIDOMWindowInternal * aDOMWin, PRPackedBool& aDoesContainFrameset); @@ -556,11 +569,12 @@ private: nsresult GetPopupImageNode(nsIDOMNode** aNode); //--------------------------------------------------------------------- - void BuildDocTree(nsIDocShellTreeNode * aParentNode, - nsVoidArray * aDocList, + void BuildDocTree(nsIDocShellTreeNode * aParentNode, + nsVoidArray * aDocList, PrintObject * aPO); - nsresult ReflowDocList(PrintObject * aPO, PRBool aSetPixelScale, PRBool aDoCalcShrink); - void SetClipRect(PrintObject* aPO, + nsresult ReflowDocList(PrintObject * aPO, PRBool aSetPixelScale, + PRBool aDoCalcShrink); + void SetClipRect(PrintObject* aPO, const nsRect& aClipRect, nscoord aOffsetX, nscoord aOffsetY, @@ -575,14 +589,18 @@ private: nsIContent* aContent); void MapContentToWebShells(PrintObject* aRootPO, PrintObject* aPO); nsresult MapSubDocFrameLocations(PrintObject* aPO); - PrintObject* FindPrintObjectByDOMWin(PrintObject* aParentObject, nsIDOMWindowInternal * aDOMWin); - void GetPresShellAndRootContent(nsIWebShell * aWebShell, nsIPresShell** aPresShell, nsIContent** aContent); + PrintObject* FindPrintObjectByDOMWin(PrintObject* aParentObject, + nsIDOMWindowInternal * aDOMWin); + void GetPresShellAndRootContent(nsIWebShell * aWebShell, + nsIPresShell** aPresShell, + nsIContent** aContent); void CalcNumPrintableDocsAndPages(PRInt32& aNumDocs, PRInt32& aNumPages); void DoProgressForAsIsFrames(); void DoProgressForSeparateFrames(); void DoPrintProgress(PRBool aIsForPrinting); - void SetDocAndURLIntoProgress(PrintObject* aPO, nsIPrintProgressParams* aParams); + void SetDocAndURLIntoProgress(PrintObject* aPO, + nsIPrintProgressParams* aParams); nsresult CheckForPrinters(nsIPrintOptions* aPrintOptions, nsIPrintSettings* aPrintSettings, PRUint32 aErrorCode, @@ -600,7 +618,8 @@ private: // nsresult DocumentReadyForPrinting(); //nsresult PrintSelection(nsIDeviceContextSpec * aDevSpec); - nsresult GetSelectionDocument(nsIDeviceContextSpec * aDevSpec, nsIDocument ** aNewDoc); + nsresult GetSelectionDocument(nsIDeviceContextSpec * aDevSpec, + nsIDocument ** aNewDoc); static void PR_CALLBACK HandlePLEvent(PLEvent* aEvent); static void PR_CALLBACK DestroyPLEvent(PLEvent* aEvent); @@ -610,12 +629,17 @@ private: nsIDOMWindowInternal* aCurrentFocusedDOMWin); nsresult EnablePOsForPrinting(); PrintObject* FindXMostPO(); - void FindXMostFrameSize(nsIPresContext* aPresContext, nsIRenderingContext* aRC, nsIFrame* aFrame, nscoord aX, nscoord aY, PRInt32& aMaxWidth); - void FindXMostFrameInList(nsIPresContext* aPresContext, nsIRenderingContext* aRC, nsIAtom* aList, nsIFrame* aFrame, - nscoord aX, nscoord aY, PRInt32& aMaxWidth); + void FindXMostFrameSize(nsIPresContext* aPresContext, + nsIRenderingContext* aRC, nsIFrame* aFrame, + nscoord aX, nscoord aY, PRInt32& aMaxWidth); + void FindXMostFrameInList(nsIPresContext* aPresContext, + nsIRenderingContext* aRC, nsIAtom* aList, + nsIFrame* aFrame, nscoord aX, nscoord aY, + PRInt32& aMaxWidth); PRBool PrintDocContent(PrintObject* aPO, nsresult& aStatus); - nsresult DoPrint(PrintObject * aPO, PRBool aDoSyncPrinting, PRBool& aDonePrinting); + nsresult DoPrint(PrintObject * aPO, PRBool aDoSyncPrinting, + PRBool& aDonePrinting); void SetPrintAsIs(PrintObject* aPO, PRBool aAsIs = PR_TRUE); void SetPrintPO(PrintObject* aPO, PRBool aPrint); @@ -630,15 +654,18 @@ private: // Timer Methods - nsresult StartPagePrintTimer(nsIPresContext * aPresContext, + nsresult StartPagePrintTimer(nsIPresContext * aPresContext, nsIPrintSettings* aPrintSettings, PrintObject* aPO, PRUint32 aDelay); void PrepareToStartLoad(void); - + + nsresult SyncParentSubDocMap(); + // Misc - static void ShowPrintErrorDialog(nsresult printerror, PRBool aIsPrinting = PR_TRUE); + static void ShowPrintErrorDialog(nsresult printerror, + PRBool aIsPrinting = PR_TRUE); protected: // IMPORTANT: The ownership implicit in the following member @@ -646,7 +673,7 @@ protected: // for owning pointers and raw COM interface pointers for weak // (ie, non owning) references. If you add any members to this // class, please make the ownership explicit (pinkerton, scc). - + nsISupports* mContainer; // [WEAK] it owns me! nsCOMPtr mDeviceContext; // ??? can't hurt, but... nsIView* mView; // [WEAK] cleaned up by view mgr @@ -664,7 +691,7 @@ protected: nsCOMPtr mSelectionListener; nsCOMPtr mFocusListener; - + nsCOMPtr mPreviousViewer; PRBool mEnableRendering; @@ -739,7 +766,7 @@ public: NS_WARNING("unable to start the timer"); } else { mTimer->Init(this, aUseDelay?mDelay:0, NS_PRIORITY_NORMAL, NS_TYPE_ONE_SHOT); - } + } return result; } @@ -760,7 +787,7 @@ public: if (mDocViewer->DonePrintingPages(mPrintObj)) { initNewTimer = PR_FALSE; } - } + } Stop(); if (initNewTimer) { @@ -773,15 +800,15 @@ public: } } - void Init(DocumentViewerImpl* aDocViewerImpl, + void Init(DocumentViewerImpl* aDocViewerImpl, nsIPresContext* aPresContext, nsIPrintSettings* aPrintSettings, PrintObject* aPO, - PRUint32 aDelay) + PRUint32 aDelay) { NS_IF_RELEASE(mDocViewer); mDocViewer = aDocViewerImpl; - NS_ADDREF(mDocViewer); + NS_ADDREF(mDocViewer); mPresContext = aPresContext; mPrintSettings = aPrintSettings; @@ -789,11 +816,11 @@ public: mDelay = aDelay; } - nsresult Start(DocumentViewerImpl* aDocViewerImpl, + nsresult Start(DocumentViewerImpl* aDocViewerImpl, nsIPresContext* aPresContext, nsIPrintSettings* aPrintSettings, PrintObject* aPO, - PRUint32 aDelay) + PRUint32 aDelay) { Init(aDocViewerImpl, aPresContext, aPrintSettings, aPO, aDelay); return StartTimer(PR_FALSE); @@ -843,7 +870,7 @@ static nsresult NS_NewUpdateTimer(nsPagePrintTimer **aResult) PrintData::PrintData() : mPrintView(nsnull), mDebugFilePtr(nsnull), mPrintObject(nsnull), mSelectedPO(nsnull), mShowProgressDialog(PR_TRUE), mPrintDocList(nsnull), mIsIFrameSelected(PR_FALSE), - mIsParentAFrameSet(PR_FALSE), mPrintingAsIsSubDoc(PR_FALSE), mOnStartSent(PR_FALSE), + mIsParentAFrameSet(PR_FALSE), mPrintingAsIsSubDoc(PR_FALSE), mOnStartSent(PR_FALSE), mIsAborted(PR_FALSE), mPreparingForPrint(PR_FALSE), mDocWasToBeDestroyed(PR_FALSE), mShrinkToFit(PR_FALSE), mPrintFrameType(nsIPrintSettings::kFramesAsIs), mNumPrintableDocs(0), mNumDocsPrinted(0), mNumPrintablePages(0), mNumPagesPrinted(0), @@ -869,7 +896,7 @@ PrintData::PrintData() : } -PrintData::~PrintData() +PrintData::~PrintData() { // removed any cached if (mCachedPresObj) { @@ -898,7 +925,7 @@ PrintData::~PrintData() if (!isCancelled && !mIsAborted) { rv = mPrintDC->EndDocument(); } else { - rv = mPrintDC->AbortDocument(); + rv = mPrintDC->AbortDocument(); } if (NS_FAILED(rv)) { DocumentViewerImpl::ShowPrintErrorDialog(rv); @@ -947,8 +974,8 @@ void PrintData::OnEndPrinting() } void -PrintData::DoOnProgressChange(nsVoidArray& aListeners, - PRInt32 aProgess, +PrintData::DoOnProgressChange(nsVoidArray& aListeners, + PRInt32 aProgess, PRInt32 aMaxProgress, PRBool aDoStartStop, PRInt32 aFlag) @@ -958,7 +985,7 @@ PrintData::DoOnProgressChange(nsVoidArray& aListeners, for (PRInt32 i=0;iOnProgressChange(nsnull, nsnull, aProgess, aMaxProgress, aProgess, aMaxProgress); + wpl->OnProgressChange(nsnull, nsnull, aProgess, aMaxProgress, aProgess, aMaxProgress); if (aDoStartStop) { wpl->OnStateChange(nsnull, nsnull, aFlag, 0); } @@ -969,10 +996,10 @@ PrintData::DoOnProgressChange(nsVoidArray& aListeners, //--------------------------------------------------- //-- PrintObject Class Impl //--------------------------------------------------- -PrintObject::PrintObject() : +PrintObject::PrintObject() : mFrameType(eFrame), mRootView(nsnull), mContent(nsnull), - mSeqFrame(nsnull), mPageFrame(nsnull), mPageNum(-1), + mSeqFrame(nsnull), mPageFrame(nsnull), mPageNum(-1), mRect(0,0,0,0), mReflowRect(0,0,0,0), mParent(nsnull), mHasBeenPrinted(PR_FALSE), mDontPrint(PR_TRUE), mPrintAsIs(PR_FALSE), mSkippedPageEject(PR_FALSE), mSharedPresShell(PR_FALSE), @@ -992,7 +1019,7 @@ PrintObject::~PrintObject() PrintObject* po = (PrintObject*)mKids[i]; NS_ASSERTION(po, "PrintObject can't be null!"); delete po; - } + } if (mPresShell && !mSharedPresShell) { mPresShell->Destroy(); @@ -1031,16 +1058,14 @@ PRBool DocumentViewerImpl::mIsDoingPrinting = PR_FALSE; nsresult NS_NewDocumentViewer(nsIDocumentViewer** aResult) { - NS_PRECONDITION(aResult, "null OUT ptr"); - if (!aResult) { - return NS_ERROR_NULL_POINTER; - } - DocumentViewerImpl* it = new DocumentViewerImpl(); - if (nsnull == it) { - *aResult = nsnull; + *aResult = new DocumentViewerImpl(); + if (!*aResult) { return NS_ERROR_OUT_OF_MEMORY; } - return CallQueryInterface(it, aResult); + + NS_ADDREF(*aResult); + + return NS_OK; } // Note: operator new zeros our memory @@ -1054,7 +1079,8 @@ DocumentViewerImpl::DocumentViewerImpl() #endif } -void DocumentViewerImpl::PrepareToStartLoad() { +void DocumentViewerImpl::PrepareToStartLoad() +{ mEnableRendering = PR_TRUE; mStopped = PR_FALSE; mLoaded = PR_FALSE; @@ -1092,12 +1118,14 @@ NS_IMPL_ISUPPORTS6(DocumentViewerImpl, DocumentViewerImpl::~DocumentViewerImpl() { NS_ASSERTION(!mDocument, "User did not call nsIContentViewer::Close"); - if (mDocument) + if (mDocument) { Close(); + } NS_ASSERTION(!mPresShell, "User did not call nsIContentViewer::Destroy"); - if (mPresShell) + if (mPresShell) { Destroy(); + } // XXX(?) Revoke pending invalidate events @@ -1125,10 +1153,10 @@ DocumentViewerImpl::LoadStart(nsISupports *aDoc) nsresult rv; if (!mDocument) { - mDocument = do_QueryInterface(aDoc,&rv); + mDocument = do_QueryInterface(aDoc, &rv); } else if (mDocument == aDoc) { - // Reset the document viewer's state back to what it was + // Reset the document viewer's state back to what it was // when the document load started. PrepareToStartLoad(); } @@ -1136,6 +1164,42 @@ DocumentViewerImpl::LoadStart(nsISupports *aDoc) return rv; } +nsresult +DocumentViewerImpl::SyncParentSubDocMap() +{ + nsCOMPtr item(do_QueryInterface(mContainer)); + nsCOMPtr win(do_GetInterface(item)); + nsCOMPtr pwin(do_QueryInterface(win)); + nsCOMPtr content; + + if (mDocument && pwin) { + nsCOMPtr frame_element; + pwin->GetFrameElementInternal(getter_AddRefs(frame_element)); + + content = do_QueryInterface(frame_element); + } + + if (content) { + nsCOMPtr parent; + item->GetParent(getter_AddRefs(parent)); + + nsCOMPtr parent_win(do_GetInterface(parent)); + + if (parent_win) { + nsCOMPtr dom_doc; + parent_win->GetDocument(getter_AddRefs(dom_doc)); + + nsCOMPtr parent_doc(do_QueryInterface(dom_doc)); + + if (parent_doc) { + return parent_doc->SetSubDocumentFor(content, mDocument); + } + } + } + + return NS_OK; +} + NS_IMETHODIMP DocumentViewerImpl::SetContainer(nsISupports* aContainer) { @@ -1143,7 +1207,12 @@ DocumentViewerImpl::SetContainer(nsISupports* aContainer) if (mPresContext) { mPresContext->SetContainer(aContainer); } - return NS_OK; + + // We're loading a new document into the window where this document + // viewer lives, sync the parent document's frame element -> sub + // document map + + return SyncParentSubDocMap(); } NS_IMETHODIMP @@ -1165,6 +1234,99 @@ DocumentViewerImpl::Init(nsIWidget* aParentWidget, return InitInternal(aParentWidget, aDeviceContext, aBounds, PR_TRUE); } +nsresult +DocumentViewerImpl::InitPresentationStuff(PRBool aDoInitialReflow) +{ + // Create the style set... + nsCOMPtr styleSet; + nsresult rv = CreateStyleSet(mDocument, getter_AddRefs(styleSet)); + NS_ENSURE_SUCCESS(rv, rv); + + // Now make the shell for the document + rv = mDocument->CreateShell(mPresContext, mViewManager, styleSet, + getter_AddRefs(mPresShell)); + NS_ENSURE_SUCCESS(rv, rv); + + mPresShell->BeginObservingDocument(); + + // Initialize our view manager + nsRect bounds; + mWindow->GetBounds(bounds); + + float p2t; + + mPresContext->GetPixelsToTwips(&p2t); + + nscoord width = NSIntPixelsToTwips(bounds.width, p2t); + nscoord height = NSIntPixelsToTwips(bounds.height, p2t); + + mViewManager->DisableRefresh(); + mViewManager->SetWindowDimensions(width, height); + + // Setup default view manager background color + + // This may be overridden by the docshell with the background color + // for the last document loaded into the docshell + nscolor bgcolor = NS_RGB(0, 0, 0); + mPresContext->GetDefaultBackgroundColor(&bgcolor); + mViewManager->SetDefaultBackgroundColor(bgcolor); + + if (aDoInitialReflow) { + // Initial refllow + mPresShell->InitialReflow(width, height); + + // Now trigger a refresh + if (mEnableRendering) { + mViewManager->EnableRefresh(NS_VMREFRESH_IMMEDIATE); + } + } + + // now register ourselves as a selection listener, so that we get + // called when the selection changes in the window + nsDocViewerSelectionListener *selectionListener = + new nsDocViewerSelectionListener(); + NS_ENSURE_TRUE(selectionListener, NS_ERROR_OUT_OF_MEMORY); + + selectionListener->Init(this); + + // mSelectionListener is a owning reference + mSelectionListener = selectionListener; + + nsCOMPtr selection; + rv = GetDocumentSelection(getter_AddRefs(selection)); + NS_ENSURE_SUCCESS(rv, rv); + + nsCOMPtr selPrivate(do_QueryInterface(selection)); + rv = selPrivate->AddSelectionListener(mSelectionListener); + if (NS_FAILED(rv)) + return rv; + + // focus listener + // + // now register ourselves as a focus listener, so that we get called + // when the focus changes in the window + nsDocViewerFocusListener *focusListener; + NS_NEWXPCOM(focusListener, nsDocViewerFocusListener); + NS_ENSURE_TRUE(focusListener, NS_ERROR_OUT_OF_MEMORY); + + focusListener->Init(this); + + // mFocusListener is a strong reference + mFocusListener = focusListener; + + // get the DOM event receiver + nsCOMPtr erP(do_QueryInterface(mDocument)); + NS_WARN_IF_FALSE(erP, "No event receiver in document!"); + + if (erP) { + rv = erP->AddEventListenerByIID(mFocusListener, + NS_GET_IID(nsIDOMFocusListener)); + NS_ASSERTION(NS_SUCCEEDED(rv), "failed to register focus listener"); + } + + return NS_OK; +} + //----------------------------------------------- // This method can be used to initial the "presentation" // The aDoCreation indicates whether it should create @@ -1175,16 +1337,16 @@ DocumentViewerImpl::InitInternal(nsIWidget* aParentWidget, const nsRect& aBounds, PRBool aDoCreation) { - NS_ASSERTION(aParentWidget != nsnull, "Null aParentWidget"); + nsresult rv = NS_OK; #ifdef NS_PRINT_PREVIEW mParentWidget = aParentWidget; // not ref counted #endif - nsresult rv; NS_ENSURE_TRUE(mDocument, NS_ERROR_NULL_POINTER); mDeviceContext = dont_QueryInterface(aDeviceContext); + #ifdef NS_PRINT_PREVIEW // Clear PrintPreview Alternate Device if (mDeviceContext) { @@ -1195,16 +1357,18 @@ DocumentViewerImpl::InitInternal(nsIWidget* aParentWidget, PRBool makeCX = PR_FALSE; if (aDoCreation) { - if (!mPresContext) { + if (aParentWidget && !mPresContext) { // Create presentation context if (mIsCreatingPrintPreview) { - mPresContext = do_CreateInstance(kPrintPreviewContextCID,&rv); + mPresContext = do_CreateInstance(kPrintPreviewContextCID, &rv); } else { - mPresContext = do_CreateInstance(kGalleyContextCID,&rv); + mPresContext = do_CreateInstance(kGalleyContextCID, &rv); } - if (NS_FAILED(rv)) return rv; + if (NS_FAILED(rv)) + return rv; mPresContext->Init(aDeviceContext); + #ifdef NS_PRINT_PREVIEW makeCX = !mIsDoingPrintPreview; // needs to be true except when we are already in PP #else @@ -1213,142 +1377,52 @@ DocumentViewerImpl::InitInternal(nsIWidget* aParentWidget, } } + if (aDoCreation && mPresContext) { + // Create the ViewManager and Root View... + + // We must do this before we tell the script global object about + // this new document since doing that will cause us to re-enter + // into nsHTMLFrameInnerFrame code through reflows caused by + // FlushPendingNotifications() calls down the road... + + rv = MakeWindow(aParentWidget, aBounds); + NS_ENSURE_SUCCESS(rv, rv); + Hide(); + } + nsCOMPtr requestor(do_QueryInterface(mContainer)); if (requestor) { - nsCOMPtr linkHandler; - requestor->GetInterface(NS_GET_IID(nsILinkHandler), - getter_AddRefs(linkHandler)); - mPresContext->SetContainer(mContainer); - mPresContext->SetLinkHandler(linkHandler); + if (mPresContext) { + nsCOMPtr linkHandler; + requestor->GetInterface(NS_GET_IID(nsILinkHandler), + getter_AddRefs(linkHandler)); + mPresContext->SetContainer(mContainer); + mPresContext->SetLinkHandler(linkHandler); + } if (!mIsDoingPrintPreview) { // Set script-context-owner in the document - nsCOMPtr owner; - requestor->GetInterface(NS_GET_IID(nsIScriptGlobalObjectOwner), - getter_AddRefs(owner)); - if (owner) { - nsCOMPtr global; - owner->GetScriptGlobalObject(getter_AddRefs(global)); + nsCOMPtr global; + requestor->GetInterface(NS_GET_IID(nsIScriptGlobalObject), + getter_AddRefs(global)); - if (global) { - mDocument->SetScriptGlobalObject(global); - nsCOMPtr domdoc(do_QueryInterface(mDocument)); + if (global) { + mDocument->SetScriptGlobalObject(global); + nsCOMPtr domdoc(do_QueryInterface(mDocument)); - if (domdoc) { - global->SetNewDocument(domdoc, PR_TRUE); - } + if (domdoc) { + global->SetNewDocument(domdoc, PR_TRUE); } } } } - if (aDoCreation) { - // Create the ViewManager and Root View... - rv = MakeWindow(aParentWidget, aBounds); - Hide(); + if (aDoCreation && mPresContext) { + // The ViewManager and Root View was created above (in + // MakeWindow())... - if (NS_FAILED(rv)) return rv; - - // Create the style set... - nsIStyleSet* styleSet; - rv = CreateStyleSet(mDocument, &styleSet); - if (NS_FAILED(rv)) return rv; - - // Now make the shell for the document - rv = mDocument->CreateShell(mPresContext, mViewManager, styleSet, - getter_AddRefs(mPresShell)); - NS_RELEASE(styleSet); - if (NS_FAILED(rv)) return rv; - - mPresShell->BeginObservingDocument(); - - // Initialize our view manager - nsRect bounds; - mWindow->GetBounds(bounds); - nscoord width = bounds.width; - nscoord height = bounds.height; - float p2t; - mPresContext->GetPixelsToTwips(&p2t); - width = NSIntPixelsToTwips(width, p2t); - height = NSIntPixelsToTwips(height, p2t); - mViewManager->DisableRefresh(); - mViewManager->SetWindowDimensions(width, height); - - /* Setup default view manager background color */ - /* This may be overridden by the docshell with the background color for the - last document loaded into the docshell */ - nscolor bgcolor = NS_RGB(0, 0, 0); - mPresContext->GetDefaultBackgroundColor(&bgcolor); - mViewManager->SetDefaultBackgroundColor(bgcolor); - - if (!makeCX) { - // Make shell an observer for next time - // XXX - we observe the docuement always, see above after preshell is created - // mPresShell->BeginObservingDocument(); - - //XXX I don't think this should be done *here*; and why paint nothing - //(which turns out to cause black flashes!)??? - // Resize-reflow this time - mPresShell->InitialReflow(width, height); - - // Now trigger a refresh - if (mEnableRendering) { - mViewManager->EnableRefresh(NS_VMREFRESH_IMMEDIATE); - } - } - } else { - mPresShell->BeginObservingDocument(); - } - // now register ourselves as a selection listener, so that we get called - // when the selection changes in the window - nsDocViewerSelectionListener *selectionListener; - NS_NEWXPCOM(selectionListener, nsDocViewerSelectionListener); - if (!selectionListener) return NS_ERROR_OUT_OF_MEMORY; - selectionListener->Init(this); - - // this is the owning reference. The nsCOMPtr will take care of releasing - // our ref to the listener on destruction. - NS_ADDREF(selectionListener); - mSelectionListener = do_QueryInterface(selectionListener); - NS_RELEASE(selectionListener); - if (NS_FAILED(rv)) return rv; - - nsCOMPtr selection; - rv = GetDocumentSelection(getter_AddRefs(selection)); - if (NS_FAILED(rv)) return rv; - - nsCOMPtr selPrivate(do_QueryInterface(selection)); - rv = selPrivate->AddSelectionListener(mSelectionListener); - if (NS_FAILED(rv)) return rv; - - //focus listener - // now register ourselves as a focus listener, so that we get called - // when the focus changes in the window - nsDocViewerFocusListener *focusListener; - NS_NEWXPCOM(focusListener, nsDocViewerFocusListener); - if (!focusListener) return NS_ERROR_OUT_OF_MEMORY; - focusListener->Init(this); - - // this is the owning reference. The nsCOMPtr will take care of releasing - // our ref to the listener on destruction. - NS_ADDREF(focusListener); - mFocusListener = do_QueryInterface(focusListener); - NS_RELEASE(focusListener); - if (NS_FAILED(rv)) - return rv; - - if(mDocument) - { - // get the DOM event receiver - nsCOMPtr erP (do_QueryInterface(mDocument, &rv)); - if(NS_FAILED(rv)) - return rv; - if(!erP) - return NS_ERROR_FAILURE; - - rv = erP->AddEventListenerByIID(mFocusListener, NS_GET_IID(nsIDOMFocusListener)); - NS_ASSERTION(NS_SUCCEEDED(rv), "failed to register focus listener"); + rv = InitPresentationStuff(!makeCX); } return rv; @@ -1374,14 +1448,14 @@ DocumentViewerImpl::LoadComplete(nsresult aStatus) rv = mDocument->GetScriptGlobalObject(getter_AddRefs(global)); // Fail if no ScriptGlobalObject is available... - NS_ASSERTION(global, "nsIScriptGlobalObject not set for document!"); - if (!global) return NS_ERROR_NULL_POINTER; + NS_ENSURE_TRUE(global, NS_ERROR_NULL_POINTER); mLoaded = PR_TRUE; - /* We need to protect ourself against auto-destruction in case the window is closed - while processing the OnLoad event. - See bug http://bugzilla.mozilla.org/show_bug.cgi?id=78445 for more explanation. + /* We need to protect ourself against auto-destruction in case the + window is closed while processing the OnLoad event. See bug + http://bugzilla.mozilla.org/show_bug.cgi?id=78445 for more + explanation. */ NS_ADDREF_THIS(); @@ -1397,11 +1471,14 @@ DocumentViewerImpl::LoadComplete(nsresult aStatus) #ifdef MOZ_TIMELINE // if navigator.xul's load is complete, the main nav window is visible // mark that point. + if (mDocument) { //printf("DEBUG: getting uri from document (%p)\n", mDocument.get()); + nsCOMPtr uri; mDocument->GetDocumentURL(getter_AddRefs(uri)); - if (uri.get() != nsnull) { + + if (uri) { //printf("DEBUG: getting spec fro uri (%p)\n", uri.get()); nsCAutoString spec; uri->GetSpec(spec); @@ -1414,11 +1491,12 @@ DocumentViewerImpl::LoadComplete(nsresult aStatus) } else { // XXX: Should fire error event to the document... } - + // Now that the document has loaded, we can tell the presshell // to unsuppress painting. - if (mPresShell && !mStopped) + if (mPresShell && !mStopped) { mPresShell->UnsuppressPainting(); + } NS_RELEASE_THIS(); @@ -1470,11 +1548,9 @@ DocumentViewerImpl::Close() // for an object that can be switched in and out so that we don't need // to disable scripts during paint suppression. - nsresult rv; - if (mDocument) { #ifdef NS_PRINT_PREVIEW - // Turn scripting back on + // Turn scripting back on // after PrintPreview had turned it off if (mPrtPreview) { TurnScriptingOn(PR_TRUE); @@ -1485,20 +1561,28 @@ DocumentViewerImpl::Close() // in the DocViewer Init nsCOMPtr globalObject; mDocument->GetScriptGlobalObject(getter_AddRefs(globalObject)); + if (globalObject) { globalObject->SetNewDocument(nsnull, PR_TRUE); } + // out of band cleanup of webshell mDocument->SetScriptGlobalObject(nsnull); + if (mFocusListener) { // get the DOM event receiver - nsCOMPtr erP( do_QueryInterface(mDocument, &rv) ); - if(NS_SUCCEEDED(rv) && erP) - erP->RemoveEventListenerByIID(mFocusListener, NS_GET_IID(nsIDOMFocusListener)); + nsCOMPtr erP(do_QueryInterface(mDocument)); + NS_WARN_IF_FALSE(erP, "No event receiver in document!"); + + if (erP) { + erP->RemoveEventListenerByIID(mFocusListener, + NS_GET_IID(nsIDOMFocusListener)); + } } - } + } mDocument = nsnull; + return NS_OK; } @@ -1558,15 +1642,19 @@ DocumentViewerImpl::Destroy() if (mPresShell) { // Break circular reference (or something) mPresShell->EndObservingDocument(); + nsCOMPtr selection; - nsresult rv = GetDocumentSelection(getter_AddRefs(selection)); + GetDocumentSelection(getter_AddRefs(selection)); + nsCOMPtr selPrivate(do_QueryInterface(selection)); - if (NS_SUCCEEDED(rv) && selPrivate && mSelectionListener) + + if (selPrivate && mSelectionListener) selPrivate->RemoveSelectionListener(mSelectionListener); + mPresShell->Destroy(); mPresShell = nsnull; } - + return NS_OK; } @@ -1601,15 +1689,17 @@ DocumentViewerImpl::SetDOMDocument(nsIDOMDocument *aDocument) // Assumptions: // // 1) this document viewer has been initialized with a call to Init(). - // 2) the stylesheets associated with the document have been added to the document. + // 2) the stylesheets associated with the document have been added + // to the document. - // XXX Right now, this method assumes that the layout of the current document - // hasn't started yet. More cleanup will probably be necessary to make this - // method work for the case when layout *has* occurred for the current document. + // XXX Right now, this method assumes that the layout of the current + // document hasn't started yet. More cleanup will probably be + // necessary to make this method work for the case when layout *has* + // occurred for the current document. // That work can happen when and if it is needed. - + nsresult rv; - if (nsnull == aDocument) + if (!aDocument) return NS_ERROR_NULL_POINTER; nsCOMPtr newDoc = do_QueryInterface(aDocument, &rv); @@ -1619,46 +1709,50 @@ DocumentViewerImpl::SetDOMDocument(nsIDOMDocument *aDocument) mDocument = newDoc; // 1) Set the script global object on the new document - nsCOMPtr requestor(do_QueryInterface(mContainer)); - if (requestor) { - nsCOMPtr owner; - requestor->GetInterface(NS_GET_IID(nsIScriptGlobalObjectOwner), - getter_AddRefs(owner)); - if (nsnull != owner) { - nsCOMPtr global; - rv = owner->GetScriptGlobalObject(getter_AddRefs(global)); - if (NS_SUCCEEDED(rv) && (nsnull != global)) { - mDocument->SetScriptGlobalObject(global); - global->SetNewDocument(aDocument, PR_TRUE); - } - } - } + nsCOMPtr global(do_GetInterface(mContainer)); - // 2) Create a new style set for the document - nsCOMPtr styleSet; - rv = CreateStyleSet(mDocument, getter_AddRefs(styleSet)); - if (NS_FAILED(rv)) return rv; + if (global) { + mDocument->SetScriptGlobalObject(global); + global->SetNewDocument(aDocument, PR_TRUE); - // 3) Replace the current pres shell with a new shell for the new document - mPresShell->EndObservingDocument(); - mPresShell->Destroy(); + rv = SyncParentSubDocMap(); + NS_ENSURE_SUCCESS(rv, rv); + } - mPresShell = nsnull; - rv = newDoc->CreateShell(mPresContext, mViewManager, styleSet, - getter_AddRefs(mPresShell)); - if (NS_FAILED(rv)) return rv; + // 2) Replace the current pres shell with a new shell for the new document - mPresShell->BeginObservingDocument(); + if (mPresShell) { + mPresShell->EndObservingDocument(); + mPresShell->Destroy(); + + mPresShell = nsnull; + } + + // And if we're already given a prescontext... + if (mPresContext) { + // 3) Create a new style set for the document + + nsCOMPtr styleSet; + rv = CreateStyleSet(mDocument, getter_AddRefs(styleSet)); + if (NS_FAILED(rv)) + return rv; + + rv = newDoc->CreateShell(mPresContext, mViewManager, styleSet, + getter_AddRefs(mPresShell)); + if (NS_FAILED(rv)) return rv; + + mPresShell->BeginObservingDocument(); + + // 4) Register the focus listener on the new document - // 4) Register the focus listener on the new document - if(mDocument) - { nsCOMPtr erP = do_QueryInterface(mDocument, &rv); - if(NS_FAILED(rv) || !erP) - return rv ? rv : NS_ERROR_FAILURE; + NS_WARN_IF_FALSE(erP, "No event receiver in document!"); - rv = erP->AddEventListenerByIID(mFocusListener, NS_GET_IID(nsIDOMFocusListener)); - NS_ASSERTION(NS_SUCCEEDED(rv), "failed to register focus listener"); + if (erP) { + rv = erP->AddEventListenerByIID(mFocusListener, + NS_GET_IID(nsIDOMFocusListener)); + NS_ASSERTION(NS_SUCCEEDED(rv), "failed to register focus listener"); + } } return rv; @@ -1675,7 +1769,7 @@ DocumentViewerImpl::SetUAStyleSheet(nsIStyleSheet* aUAStyleSheet) } return NS_OK; } - + NS_IMETHODIMP DocumentViewerImpl::GetDocument(nsIDocument*& aResult) { @@ -1683,7 +1777,7 @@ DocumentViewerImpl::GetDocument(nsIDocument*& aResult) NS_IF_ADDREF(aResult); return NS_OK; } - + NS_IMETHODIMP DocumentViewerImpl::GetPresShell(nsIPresShell*& aResult) { @@ -1691,7 +1785,7 @@ DocumentViewerImpl::GetPresShell(nsIPresShell*& aResult) NS_IF_ADDREF(aResult); return NS_OK; } - + NS_IMETHODIMP DocumentViewerImpl::GetPresContext(nsIPresContext*& aResult) { @@ -1733,7 +1827,7 @@ DocumentViewerImpl::SetPreviousViewer(nsIContentViewer* aViewer) "can't set previous viewer when there already is one"); // In a multiple chaining situation (which occurs when running a thrashing - // test like i-bench or jrgm's tests with no delay), we can build up a + // test like i-bench or jrgm's tests with no delay), we can build up a // whole chain of viewers. In order to avoid this, we always set our previous // viewer to the MOST previous viewer in the chain, and then dump the intermediate // link from the chain. This ensures that at most only 2 documents are alive @@ -1756,7 +1850,7 @@ NS_IMETHODIMP DocumentViewerImpl::SetBounds(const nsRect& aBounds) { NS_ENSURE_TRUE(mDocument, NS_ERROR_NOT_AVAILABLE); - NS_PRECONDITION(mWindow, "null window"); + if (mWindow) { // Don't have the widget repaint. Layout will generate repaint requests // during reflow @@ -1781,7 +1875,6 @@ NS_IMETHODIMP DocumentViewerImpl::Show(void) { NS_ENSURE_TRUE(mDocument, NS_ERROR_NOT_AVAILABLE); - NS_PRECONDITION(mWindow, "null window"); // We don't need the previous viewer anymore since we're not // displaying it. @@ -1796,6 +1889,114 @@ DocumentViewerImpl::Show(void) if (mWindow) { mWindow->Show(PR_TRUE); } + + if (mDocument && !mPresShell && !mWindow && !mDeviceContext) { + nsresult rv; + + nsCOMPtr base_win(do_QueryInterface(mContainer)); + NS_ENSURE_TRUE(base_win, NS_ERROR_UNEXPECTED); + + base_win->GetParentWidget(&mParentWidget); + NS_ENSURE_TRUE(mParentWidget, NS_ERROR_UNEXPECTED); + + if (!mDeviceContext) { + mDeviceContext = dont_AddRef(mParentWidget->GetDeviceContext()); + } + +#ifdef NS_PRINT_PREVIEW + // Clear PrintPreview Alternate Device + if (mDeviceContext) { + mDeviceContext->SetAltDevice(nsnull); + } +#endif + + PRBool makeCX = PR_FALSE; + + // Create presentation context + if (mIsCreatingPrintPreview) { + NS_ERROR("Whoa, we should not get here!"); + + return NS_ERROR_UNEXPECTED; + } + + mPresContext = do_CreateInstance(kGalleyContextCID, &rv); + NS_ENSURE_SUCCESS(rv, rv); + + mPresContext->Init(mDeviceContext); + + nsRect tbounds; + mParentWidget->GetBounds(tbounds); + + float p2t; + mPresContext->GetPixelsToTwips(&p2t); + tbounds *= p2t; + + // Create the view manager + mViewManager = do_CreateInstance(kViewManagerCID); + NS_ENSURE_TRUE(mViewManager, NS_ERROR_NOT_AVAILABLE); + + // Initialize the view manager with an offset. This allows the + // viewmanager to manage a coordinate space offset from (0,0) + rv = mViewManager->Init(mDeviceContext); + if (NS_FAILED(rv)) + return rv; + + rv = mViewManager->SetWindowOffset(tbounds.x, tbounds.y); + if (NS_FAILED(rv)) + return rv; + + // Reset the bounds offset so the root view is set to 0,0. The + // offset is specified in nsIViewManager::Init above. + // Besides, layout will reset the root view to (0,0) during reflow, + // so changing it to 0,0 eliminates placing the root view in the + // wrong place initially. + tbounds.x = 0; + tbounds.y = 0; + + // Create a child window of the parent that is our "root + // view/window" Create a view + rv = CallCreateInstance(kViewCID, &mView); + if (NS_FAILED(rv)) + return rv; + rv = mView->Init(mViewManager, tbounds, nsnull); + if (NS_FAILED(rv)) + return rv; + + rv = mView->CreateWidget(kWidgetCID, nsnull, + mParentWidget->GetNativeData(NS_NATIVE_WIDGET), + PR_TRUE, PR_FALSE); + + if (NS_FAILED(rv)) + return rv; + + // Setup hierarchical relationship in view manager + mViewManager->SetRootView(mView); + + mView->GetWidget(*getter_AddRefs(mWindow)); + + if (mPresContext && mContainer) { + nsCOMPtr linkHandler(do_GetInterface(mContainer)); + + if (linkHandler) { + mPresContext->SetLinkHandler(linkHandler); + } + + mPresContext->SetContainer(mContainer); + } + + if (mPresContext) { + Hide(); + + rv = InitPresentationStuff(PR_TRUE); + } + + // If we get here the document load has already started and the + // window is shown because some JS on the page caused it to be + // shown... + + mPresShell->UnsuppressPainting(); + } + return NS_OK; } @@ -1807,6 +2008,48 @@ DocumentViewerImpl::Hide(void) if (mWindow) { mWindow->Show(PR_FALSE); } + + if (!mPresShell) { + return NS_OK; + } + + // Avoid leaking the old viewer. + if (mPreviousViewer) { + mPreviousViewer->Destroy(); + mPreviousViewer = nsnull; + } + + if (mDeviceContext) + mDeviceContext->FlushFontCache(); + + // Break circular reference (or something) + mPresShell->EndObservingDocument(); + nsCOMPtr selection; + + GetDocumentSelection(getter_AddRefs(selection)); + + nsCOMPtr selPrivate(do_QueryInterface(selection)); + + if (selPrivate && mSelectionListener) + selPrivate->RemoveSelectionListener(mSelectionListener); + + mPresShell->Destroy(); + + mPresShell = nsnull; + mPresContext = nsnull; + mViewManager = nsnull; + mView = nsnull; + mWindow = nsnull; + mDeviceContext = nsnull; + mView = nsnull; + mParentWidget = nsnull; + + nsCOMPtr base_win(do_QueryInterface(mContainer)); + + if (base_win) { + base_win->SetParentWidget(nsnull); + } + return NS_OK; } @@ -1832,7 +2075,7 @@ DocumentViewerImpl::FindFrameSetWithIID(nsIContent * aParentContent, const nsIID } /** --------------------------------------------------- - * Helper function + * Helper function */ static nsIPresShell* GetPresShellFor(nsIDocShell* aDocShell) @@ -1859,10 +2102,10 @@ GetPresShellFor(nsIDocShell* aDocShell) #include "process.h" #include "direct.h" -#define MY_FINDFIRST(a,b) FindFirstFile(a,b) -#define MY_FINDNEXT(a,b) FindNextFile(a,b) -#define ISDIR(a) (a.dwFileAttributes & FILE_ATTRIBUTE_DIRECTORY) -#define MY_FINDCLOSE(a) FindClose(a) +#define MY_FINDFIRST(a,b) FindFirstFile(a,b) +#define MY_FINDNEXT(a,b) FindNextFile(a,b) +#define ISDIR(a) (a.dwFileAttributes & FILE_ATTRIBUTE_DIRECTORY) +#define MY_FINDCLOSE(a) FindClose(a) #define MY_FILENAME(a) a.cFileName #define MY_FILESIZE(a) (a.nFileSizeHigh * MAXDWORD) + a.nFileSizeLow @@ -1937,10 +2180,10 @@ static void RootFrameList(nsIPresContext* aPresContext, FILE* out, PRInt32 aInde /** --------------------------------------------------- * Dumps Frames for Printing */ -static void DumpFrames(FILE* out, - nsIPresContext* aPresContext, - nsIRenderingContext * aRendContext, - nsIFrame * aFrame, +static void DumpFrames(FILE* out, + nsIPresContext* aPresContext, + nsIRenderingContext * aRendContext, + nsIFrame * aFrame, PRInt32 aLevel) { NS_ASSERTION(out, "Pointer is null!"); @@ -2108,16 +2351,16 @@ static void DumpPrintObjectsList(nsVoidArray * aDocList, FILE* aFD = nsnull) } } - fprintf(fd, "%s %d %d %d %p %p %p %p %p %d %d,%d,%d,%d\n", types[po->mFrameType], + fprintf(fd, "%s %d %d %d %p %p %p %p %p %d %d,%d,%d,%d\n", types[po->mFrameType], po->IsPrintable(), po->mPrintAsIs, po->mHasBeenPrinted, po, po->mWebShell, po->mSeqFrame, - po->mPageFrame, rootFrame, po->mPageNum, po->mRect.x, po->mRect.y, po->mRect.width, po->mRect.height); + po->mPageFrame, rootFrame, po->mPageNum, po->mRect.x, po->mRect.y, po->mRect.width, po->mRect.height); if (fd != nsnull && fd != stdout) { - fprintf(stdout, "%s %d %d %d %p %p %p %p %p %d %d,%d,%d,%d\n", types[po->mFrameType], + fprintf(stdout, "%s %d %d %d %p %p %p %p %p %d %d,%d,%d,%d\n", types[po->mFrameType], po->IsPrintable(), po->mPrintAsIs, po->mHasBeenPrinted, po, po->mWebShell, po->mSeqFrame, - po->mPageFrame, rootFrame, po->mPageNum, po->mRect.x, po->mRect.y, po->mRect.width, po->mRect.height); + po->mPageFrame, rootFrame, po->mPageNum, po->mRect.x, po->mRect.y, po->mRect.width, po->mRect.height); } - } -} + } +} static void DumpPrintObjectsTree(PrintObject * aPO, int aLevel= 0, FILE* aFD = nsnull) { NS_ASSERTION(aPO, "Pointer is null!"); @@ -2134,11 +2377,12 @@ static void DumpPrintObjectsTree(PrintObject * aPO, int aLevel= 0, FILE* aFD = n NS_ASSERTION(po, "PrintObject can't be null!"); for (PRInt32 k=0;kmFrameType], po, po->mWebShell, po->mSeqFrame, - po->mPageFrame, po->mPageNum, po->mRect.x, po->mRect.y, po->mRect.width, po->mRect.height); - } + po->mPageFrame, po->mPageNum, po->mRect.x, po->mRect.y, po->mRect.width, po->mRect.height); + } } - -static void GetDocTitleAndURL(PrintObject* aPO, char *& aDocStr, char *& aURLStr) + +static void GetDocTitleAndURL(PrintObject* aPO, char *& aDocStr, + char *& aURLStr) { aDocStr = nsnull; aURLStr = nsnull; @@ -2146,7 +2390,9 @@ static void GetDocTitleAndURL(PrintObject* aPO, char *& aDocStr, char *& aURLStr PRUnichar * mozillaDoc = ToNewUnicode(NS_LITERAL_STRING("Mozilla Document")); PRUnichar * docTitleStr; PRUnichar * docURLStr; - DocumentViewerImpl::GetDisplayTitleAndURL(aPO, nsnull, mozillaDoc, &docTitleStr, &docURLStr, DocumentViewerImpl::eDocTitleDefURLDoc); + DocumentViewerImpl::GetDisplayTitleAndURL(aPO, nsnull, mozillaDoc, + &docTitleStr, &docURLStr, + DocumentViewerImpl::eDocTitleDefURLDoc); if (docTitleStr) { nsAutoString strDocTitle(docTitleStr); @@ -2165,7 +2411,7 @@ static void GetDocTitleAndURL(PrintObject* aPO, char *& aDocStr, char *& aURLStr } } -static void DumpPrintObjectsTreeLayout(PrintObject * aPO, +static void DumpPrintObjectsTreeLayout(PrintObject * aPO, nsIDeviceContext * aDC, int aLevel= 0, FILE * aFD = nsnull) { @@ -2189,7 +2435,7 @@ static void DumpPrintObjectsTreeLayout(PrintObject * aPO, } for (PRInt32 k=0;kmFrameType], aPO, aPO->mWebShell, aPO->mSeqFrame, - aPO->mPageFrame, aPO->mPageNum, aPO->mRect.x, aPO->mRect.y, aPO->mRect.width, aPO->mRect.height); + aPO->mPageFrame, aPO->mPageNum, aPO->mRect.x, aPO->mRect.y, aPO->mRect.width, aPO->mRect.height); if (aPO->IsPrintable()) { char * docStr; char * urlStr; @@ -2210,7 +2456,7 @@ static void DumpPrintObjectsTreeLayout(PrintObject * aPO, if (aLevel == 0 && fd) { fclose(fd); } -} +} static void DumpPrintObjectsListStart(char * aStr, nsVoidArray * aDocList, FILE* aFD = nsnull) { @@ -2228,7 +2474,7 @@ static void DumpPrintObjectsListStart(char * aStr, nsVoidArray * aDocList, FILE* #else #define DUMP_DOC_LIST(_title) #define DUMP_DOC_TREE -#define DUMP_DOC_TREELAYOUT +#define DUMP_DOC_TREELAYOUT #endif //--------------------------------------------------------------- @@ -2238,7 +2484,7 @@ static void DumpPrintObjectsListStart(char * aStr, nsVoidArray * aDocList, FILE* //--------------------------------------------------------------- /** --------------------------------------------------- - * Giving a child frame it searches "up" the tree until it + * Giving a child frame it searches "up" the tree until it * finds a "Page" frame. */ static nsIFrame * GetPageFrame(nsIFrame * aFrame) @@ -2263,7 +2509,7 @@ static nsIFrame * FindFrameByType(nsIPresContext* aPresContext, nsIFrame * aParentFrame, nsIAtom * aType, nsRect& aRect, - nsRect& aChildRect) + nsRect& aChildRect) { NS_ASSERTION(aPresContext, "Pointer is null!"); NS_ASSERTION(aParentFrame, "Pointer is null!"); @@ -2390,7 +2636,7 @@ static nsresult GetPageRangeForSelection(nsIPresShell * aPresShell, seqFrame->GetRect(rect); // start out with the sequence frame and search the entire frame tree - // capturing the the starting and ending child frames of the selection + // capturing the the starting and ending child frames of the selection // and their rects FindSelectionBounds(aPresContext, aRC, seqFrame, rect, startFrame, aStartRect, endFrame, aEndRect); @@ -2399,7 +2645,7 @@ static nsresult GetPageRangeForSelection(nsIPresShell * aPresShell, printf("End Frame: %p\n", endFrame); #endif - // initial the page numbers here + // initial the page numbers here // in case we don't find and frames aStartPageNum = -1; aEndPageNum = -1; @@ -2415,7 +2661,7 @@ static nsresult GetPageRangeForSelection(nsIPresShell * aPresShell, // Check to see if start should be same as end if // the end frame comes back null if (endFrame == nsnull) { - // XXX the "GetPageFrame" step could be integrated into + // XXX the "GetPageFrame" step could be integrated into // the FindSelectionBounds step, but walking up to find // the parent of a child frame isn't expensive and it makes // FindSelectionBounds a little easier to understand @@ -2455,7 +2701,7 @@ static nsresult GetPageRangeForSelection(nsIPresShell * aPresShell, while (page != nsnull) { if (page == startPageFrame) { aStartPageNum = pageNum; - } + } if (page == endPageFrame) { aEndPageNum = pageNum; } @@ -2475,7 +2721,7 @@ static nsresult GetPageRangeForSelection(nsIPresShell * aPresShell, } //------------------------------------------------------- -PRBool +PRBool DocumentViewerImpl::IsParentAFrameSet(nsIWebShell * aParent) { NS_ASSERTION(aParent, "Pointer is null!"); @@ -2484,8 +2730,8 @@ DocumentViewerImpl::IsParentAFrameSet(nsIWebShell * aParent) nsCOMPtr parentAsItem(do_QueryInterface(aParent)); if (!parentAsItem) return PR_FALSE; - // When it is the top level document we need to check - // to see if it contains a frameset. If it does, then + // When it is the top level document we need to check + // to see if it contains a frameset. If it does, then // we only want to print the doc's children and not the document itself // For anything else we always print all the children and the document // for example, if the doc contains an IFRAME we eant to print the child @@ -2494,10 +2740,10 @@ DocumentViewerImpl::IsParentAFrameSet(nsIWebShell * aParent) // XXX we really need to search the frame tree, and not the content // but there is no way to distinguish between IFRAMEs and FRAMEs // with the GetFrameType call. - // Bug 53459 has been files so we can eventually distinguish + // Bug 53459 has been files so we can eventually distinguish // between IFRAME frames and FRAME frames PRBool isFrameSet = PR_FALSE; - // only check to see if there is a frameset if there is + // only check to see if there is a frameset if there is // NO parent doc for this doc. meaning this parent is the root doc nsCOMPtr shell; mPresContext->GetShell(getter_AddRefs(shell)); @@ -2518,7 +2764,7 @@ DocumentViewerImpl::IsParentAFrameSet(nsIWebShell * aParent) } //------------------------------------------------------- -PRBool +PRBool DocumentViewerImpl::IsWebShellAFrameSet(nsIWebShell * aWebShell) { NS_ASSERTION(aWebShell, "Pointer is null!"); @@ -2537,8 +2783,8 @@ DocumentViewerImpl::IsWebShellAFrameSet(nsIWebShell * aWebShell) //------------------------------------------------------- void -DocumentViewerImpl::GetWebShellTitleAndURL(nsIWebShell * aWebShell, - PRUnichar** aTitle, +DocumentViewerImpl::GetWebShellTitleAndURL(nsIWebShell * aWebShell, + PRUnichar** aTitle, PRUnichar** aURLStr) { NS_ASSERTION(aWebShell, "Pointer is null!"); @@ -2634,7 +2880,7 @@ DocumentViewerImpl::GetDisplayTitleAndURL(PrintObject* aPO, case eDocTitleDefDocument: if (aBrandName) *aTitle = nsCRT::strdup(aBrandName); break; - case eDocTitleDefURLDoc: + case eDocTitleDefURLDoc: if (*aURLStr) { *aTitle = nsCRT::strdup(*aURLStr); } else { @@ -2770,12 +3016,12 @@ DocumentViewerImpl::PrintPage(nsIPresContext* aPresContext, if (mPrt->mPrintFrameType == nsIPrintSettings::kEachFrameSep) { DoProgressForSeparateFrames(); - } else if (mPrt->mPrintFrameType != nsIPrintSettings::kFramesAsIs || + } else if (mPrt->mPrintFrameType != nsIPrintSettings::kFramesAsIs || mPrt->mPrintObject->mFrameType == eDoc && aPO == mPrt->mPrintObject) { PrintData::DoOnProgressChange(mPrt->mPrintProgressListeners, curPage, endPage); } - // Set Clip when Printing "AsIs" or + // Set Clip when Printing "AsIs" or // when printing an IFrame for SelectedFrame or EachFrame PRBool setClip = PR_FALSE; switch (mPrt->mPrintFrameType) { @@ -2800,7 +3046,7 @@ DocumentViewerImpl::PrintPage(nsIPresContext* aPresContext, } break; - } //switch + } //switch if (setClip) { // Always set the clip x,y to zero because it isn't going to have any margins @@ -2814,7 +3060,7 @@ DocumentViewerImpl::PrintPage(nsIPresContext* aPresContext, // fail and the failure is passed back here. // Returning PR_TRUE means we are done printing. // - // When rv == NS_ERROR_ABORT, it means we want out of the + // When rv == NS_ERROR_ABORT, it means we want out of the // print job without displaying any error messages nsresult rv = mPageSeqFrame->PrintNextPage(aPresContext); if (NS_FAILED(rv)) { @@ -2823,7 +3069,7 @@ DocumentViewerImpl::PrintPage(nsIPresContext* aPresContext, mPrt->mIsAborted = PR_TRUE; } return PR_TRUE; - } + } // Now see if any of the SubDocs are on this page if (aPO->mPrintAsIs) { @@ -2889,9 +3135,9 @@ PrintObject * DocumentViewerImpl::FindPrintObjectByWS(PrintObject* aPO, nsIWebSh //------------------------------------------------------- // Recursively build a list of of sub documents to be printed // that mirrors the document tree -void -DocumentViewerImpl::BuildDocTree(nsIDocShellTreeNode * aParentNode, - nsVoidArray * aDocList, +void +DocumentViewerImpl::BuildDocTree(nsIDocShellTreeNode * aParentNode, + nsVoidArray * aDocList, PrintObject * aPO) { NS_ASSERTION(aParentNode, "Pointer is null!"); @@ -2899,7 +3145,7 @@ DocumentViewerImpl::BuildDocTree(nsIDocShellTreeNode * aParentNode, NS_ASSERTION(aPO, "Pointer is null!"); // Get the Doc and Title String - GetWebShellTitleAndURL(aPO->mWebShell, &aPO->mDocTitle, &aPO->mDocURL); + GetWebShellTitleAndURL(aPO->mWebShell, &aPO->mDocTitle, &aPO->mDocURL); PRInt32 childWebshellCount; aParentNode->GetChildCount(&childWebshellCount); @@ -2908,6 +3154,14 @@ DocumentViewerImpl::BuildDocTree(nsIDocShellTreeNode * aParentNode, nsCOMPtr child; aParentNode->GetChildAt(i, getter_AddRefs(child)); nsCOMPtr childAsShell(do_QueryInterface(child)); + + nsCOMPtr presShell; + childAsShell->GetPresShell(getter_AddRefs(presShell)); + + if (!presShell) { + continue; + } + nsCOMPtr viewer; childAsShell->GetContentViewer(getter_AddRefs(viewer)); if (viewer) { @@ -2938,7 +3192,7 @@ DocumentViewerImpl::SetPrintAsIs(PrintObject* aPO, PRBool aAsIs) aPO->mPrintAsIs = aAsIs; for (PRInt32 i=0;imKids.Count();i++) { SetPrintAsIs((PrintObject*)aPO->mKids[i], aAsIs); - } + } } //------------------------------------------------------- @@ -2952,7 +3206,7 @@ DocumentViewerImpl::SetPrintPO(PrintObject* aPO, PRBool aPrint) aPO->mDontPrint = !aPrint; for (PRInt32 i=0;imKids.Count();i++) { SetPrintPO((PrintObject*)aPO->mKids[i], aPrint); - } + } } //------------------------------------------------------- @@ -2962,7 +3216,7 @@ DocumentViewerImpl::SetPrintPO(PrintObject* aPO, PRBool aPrint) // NOTE: This MUST be done after the sub-doc has been laid out // This is called by "MapSubDocFrameLocations" // -nsresult +nsresult DocumentViewerImpl::CalcPageFrameLocation(nsIPresShell * aPresShell, PrintObject* aPO) { @@ -2973,7 +3227,7 @@ DocumentViewerImpl::CalcPageFrameLocation(nsIPresShell * aPresShell, // Find that frame for the sub-doc's content element // in the parent document - // if it comes back null it probably has the style + // if it comes back null it probably has the style // set to "display:none" nsIFrame * frame; aPresShell->GetPrimaryFrameFor(aPO->mContent, &frame); @@ -3003,9 +3257,9 @@ DocumentViewerImpl::CalcPageFrameLocation(nsIPresShell * aPresShell, rect.y += rr.y; nsIFrame * temp = parent; temp->GetParent(&parent); - // Keep a pointer to the Seq and Page frames + // Keep a pointer to the Seq and Page frames nsIPageSequenceFrame * sqf = nsnull; - if (parent != nsnull && + if (parent != nsnull && NS_SUCCEEDED(CallQueryInterface(parent, &sqf)) && sqf) { pageFrame = temp; seqFrame = parent; @@ -3069,17 +3323,17 @@ DocumentViewerImpl::MapSubDocFrameLocations(PrintObject* aPO) // // This "maps" or figures out which sub-doc represents a // given Frame or IFrame in it's parent sub-doc. -// +// // So the Mcontent pointer in the child sub-doc points to the // content in the it's parent document, that caused it to be printed. // This is used later to (after reflow) to find the absolute location -// of the sub-doc on it's parent's page frame so it can be +// of the sub-doc on it's parent's page frame so it can be // printed in the correct location. // // This method recursvely "walks" the content for a document finding // all the Frames and IFrames, then sets the "mFrameType" data member // which tells us what type of PO we have -void +void DocumentViewerImpl::MapContentForPO(PrintObject* aRootObject, nsIPresShell* aPresShell, nsIContent* aContent) @@ -3088,19 +3342,38 @@ DocumentViewerImpl::MapContentForPO(PrintObject* aRootObject, NS_ASSERTION(aPresShell, "Pointer is null!"); NS_ASSERTION(aContent, "Pointer is null!"); - nsCOMPtr supps; - aPresShell->GetSubShellFor(aContent, getter_AddRefs(supps)); - if (supps) { - nsCOMPtr webShell(do_QueryInterface(supps)); - if (webShell) { + nsCOMPtr doc; + aContent->GetDocument(*getter_AddRefs(doc)); + + if (!doc) { + NS_ERROR("No document!"); + + return; + } + + nsCOMPtr subDoc; + doc->GetSubDocumentFor(aContent, getter_AddRefs(subDoc)); + + if (subDoc) { + nsCOMPtr container; + subDoc->GetContainer(getter_AddRefs(container)); + + nsCOMPtr presShell; + subDoc->GetShellAt(0, getter_AddRefs(presShell)); + + nsCOMPtr webShell(do_QueryInterface(container)); + + if (presShell && webShell) { PrintObject * po = FindPrintObjectByWS(aRootObject, webShell); NS_ASSERTION(po, "PO can't be null!"); - if (po != nsnull) { + if (po) { po->mContent = aContent; - // Now, "type" the PO - nsCOMPtr frameSet(do_QueryInterface(aContent)); + // Now, "type" the PO + nsCOMPtr frameSet = + do_QueryInterface(aContent); + if (frameSet) { po->mFrameType = eFrameSet; } else { @@ -3108,8 +3381,11 @@ DocumentViewerImpl::MapContentForPO(PrintObject* aRootObject, if (frame) { po->mFrameType = eFrame; } else { - nsCOMPtr objElement(do_QueryInterface(aContent)); - nsCOMPtr iFrame(do_QueryInterface(aContent)); + nsCOMPtr objElement = + do_QueryInterface(aContent); + nsCOMPtr iFrame = + do_QueryInterface(aContent); + if (iFrame || objElement) { po->mFrameType = eIFrame; po->mPrintAsIs = PR_TRUE; @@ -3135,11 +3411,11 @@ DocumentViewerImpl::MapContentForPO(PrintObject* aRootObject, //------------------------------------------------------- // The walks the PO tree and for each document it walks the content -// tree looking for any content that are sub-shells +// tree looking for any content that are sub-shells // -// It then sets the mContent pointer in the "found" PO object back to the +// It then sets the mContent pointer in the "found" PO object back to the // the document that contained it. -void +void DocumentViewerImpl::MapContentToWebShells(PrintObject* aRootPO, PrintObject* aPO) { @@ -3157,16 +3433,16 @@ DocumentViewerImpl::MapContentToWebShells(PrintObject* aRootPO, // Continue recursively walking the chilren of this PO for (PRInt32 i=0;imKids.Count();i++) { MapContentToWebShells(aRootPO, (PrintObject*)aPO->mKids[i]); - } + } } //------------------------------------------------------- // This gets ref counted copies of the PresShell and Root Content // for a given nsIWebShell -void -DocumentViewerImpl::GetPresShellAndRootContent(nsIWebShell * aWebShell, - nsIPresShell** aPresShell, +void +DocumentViewerImpl::GetPresShellAndRootContent(nsIWebShell * aWebShell, + nsIPresShell** aPresShell, nsIContent** aContent) { NS_ASSERTION(aWebShell, "Pointer is null!"); @@ -3192,8 +3468,8 @@ DocumentViewerImpl::GetPresShellAndRootContent(nsIWebShell * aWebShell, //------------------------------------------------------- // Recursively sets the clip rect on all thchildren -void -DocumentViewerImpl::SetClipRect(PrintObject* aPO, +void +DocumentViewerImpl::SetClipRect(PrintObject* aPO, const nsRect& aClipRect, nscoord aOffsetX, nscoord aOffsetY, @@ -3207,8 +3483,8 @@ DocumentViewerImpl::SetClipRect(PrintObject* aPO, nscoord height = (aPO->mRect.y+aPO->mRect.height) > aClipRect.height?aClipRect.height-aPO->mRect.y:aPO->mRect.height; aPO->mClipRect.SetRect(aPO->mRect.x, aPO->mRect.y, width, height); - } - + } + PRBool doClip = aDoingSetClip; if (aPO->mFrameType == eFrame) { @@ -3249,7 +3525,7 @@ DocumentViewerImpl::SetClipRect(PrintObject* aPO, PRInt32 cnt = aPO->mKids.Count(); for (PRInt32 i=0;imKids[i], clipRect, + SetClipRect((PrintObject *)aPO->mKids[i], clipRect, aOffsetX+aPO->mRect.x, aOffsetY+aPO->mRect.y, doClip); } } @@ -3257,12 +3533,12 @@ DocumentViewerImpl::SetClipRect(PrintObject* aPO, //------------------------------------------------------- // Recursively reflow each sub-doc and then calc // all the frame locations of the sub-docs -nsresult +nsresult DocumentViewerImpl::ReflowDocList(PrintObject* aPO, PRBool aSetPixelScale, PRBool aDoCalcShrink) { NS_ASSERTION(aPO, "Pointer is null!"); - // Here is where we set the shrinkage value into the DC + // Here is where we set the shrinkage value into the DC // and this is what actually makes it shrink if (aSetPixelScale && aPO->mFrameType != eIFrame) { float ratio; @@ -3274,7 +3550,7 @@ DocumentViewerImpl::ReflowDocList(PrintObject* aPO, PRBool aSetPixelScale, PRBoo mPrt->mPrintDC->SetCanonicalPixelScale(ratio*mPrt->mOrigDCScale); } - // Reflow the PO + // Reflow the PO if (NS_FAILED(ReflowPrintObject(aPO, aDoCalcShrink))) { return NS_ERROR_FAILURE; } @@ -3354,7 +3630,8 @@ DocumentViewerImpl::ReflowPrintObject(PrintObject * aPO, PRBool aDoCalcShrink) return rv; } - rv = document->CreateShell(aPO->mPresContext, aPO->mViewManager, aPO->mStyleSet, getter_AddRefs(aPO->mPresShell)); + rv = document->CreateShell(aPO->mPresContext, aPO->mViewManager, + aPO->mStyleSet, getter_AddRefs(aPO->mPresShell)); if (NS_FAILED(rv)) { return rv; } @@ -3364,7 +3641,7 @@ DocumentViewerImpl::ReflowPrintObject(PrintObject * aPO, PRBool aDoCalcShrink) PRInt32 width, height; if (aPO->mContent == nsnull || !aPO->mPrintAsIs || - (aPO->mPrintAsIs && aPO->mParent != nsnull && !aPO->mParent->mPrintAsIs) || + (aPO->mPrintAsIs && aPO->mParent && !aPO->mParent->mPrintAsIs) || (aPO->mFrameType == eIFrame && aPO == mPrt->mSelectedPO)) { width = pageWidth; height = pageHeight; @@ -3375,22 +3652,25 @@ DocumentViewerImpl::ReflowPrintObject(PrintObject * aPO, PRBool aDoCalcShrink) PRINT_DEBUG_MSG5("In DV::ReflowPrintObject PO: %p (%9s) Setting w,h to %d,%d\n", aPO, gFrameTypesStr[aPO->mFrameType], width, height); - nsCOMPtr domWinIntl(do_QueryInterface(mPrt->mPrintDocDW)); + nsCOMPtr domWinIntl = + do_QueryInterface(mPrt->mPrintDocDW); // XXX - Hack Alert - // OK, so ther eis a selection, we will print the entire selection + // OK, so ther eis a selection, we will print the entire selection // on one page and then crop the page. - // This means you can never print any selection that is longer than one page - // put it keeps it from page breaking in the middle of your print of the selection - // (see also nsSimplePageSequence.cpp) + // This means you can never print any selection that is longer than + // one page put it keeps it from page breaking in the middle of your + // print of the selection (see also nsSimplePageSequence.cpp) PRInt16 printRangeType = nsIPrintSettings::kRangeAllPages; if (mPrt->mPrintSettings != nsnull) { mPrt->mPrintSettings->GetPrintRange(&printRangeType); } - if (printRangeType == nsIPrintSettings::kRangeSelection && IsThereARangeSelection(domWinIntl)) { + if (printRangeType == nsIPrintSettings::kRangeSelection && + IsThereARangeSelection(domWinIntl)) { height = NS_UNCONSTRAINEDSIZE; } + nsRect tbounds = nsRect(0, 0, width, height); // Create a child window of the parent that is our "root view/window" @@ -3404,7 +3684,7 @@ DocumentViewerImpl::ReflowPrintObject(PrintObject * aPO, PRBool aDoCalcShrink) } #ifdef NS_PRINT_PREVIEW - // Here we decide whether we need scrollbars and + // Here we decide whether we need scrollbars and // what the parent will be of the widget if (mIsCreatingPrintPreview) { PRBool canCreateScrollbars = PR_FALSE; @@ -3416,16 +3696,17 @@ DocumentViewerImpl::ReflowPrintObject(PrintObject * aPO, PRBool aDoCalcShrink) NS_ASSERTION(frameMan, "No Frame manager!"); nsIFrame* frame; frameMan->GetPrimaryFrameFor(aPO->mContent, &frame); - if (frame != nsnull && (aPO->mFrameType == eIFrame || aPO->mFrameType == eFrame)) { + if (frame && (aPO->mFrameType == eIFrame || aPO->mFrameType == eFrame)) { frame->FirstChild(aPO->mParent->mPresContext, nsnull, &frame); } - if (frame != nsnull) { + + if (frame) { nsIView* view = nsnull; frame->GetView(aPO->mParent->mPresContext, &view); - if (view != nsnull) { + if (view) { nsCOMPtr w2; view->GetWidget(*getter_AddRefs(w2)); - if (nsnull != w2) { + if (w2) { widget = w2; } canCreateScrollbars = PR_FALSE; @@ -3476,9 +3757,9 @@ DocumentViewerImpl::ReflowPrintObject(PrintObject * aPO, PRBool aDoCalcShrink) // initialize it with the default/generic case nsRect adjRect(aPO->mRect.x != 0?margin.left:0, aPO->mRect.y != 0?margin.top:0, width, height); - // XXX This is an arbitray height, + // XXX This is an arbitray height, // but reflow somethimes gets upset when using max int - // basically, we want to reflow a single page that is large + // basically, we want to reflow a single page that is large // enough to fit any atomic object like an IFrame const PRInt32 kFivePagesHigh = 5; @@ -3570,7 +3851,7 @@ DocumentViewerImpl::ReflowPrintObject(PrintObject * aPO, PRBool aDoCalcShrink) nsRect rect; child->GetRect(rect); - // Create a RenderingContext and set the PresContext + // Create a RenderingContext and set the PresContext // appropriately if we are printing selection nsCOMPtr rc; if (nsIPrintSettings::kRangeSelection == printRangeType) { @@ -3653,7 +3934,7 @@ DocumentViewerImpl::ReflowPrintObject(PrintObject * aPO, PRBool aDoCalcShrink) //------------------------------------------------------- // Given a DOMWindow it recursively finds the PO object that matches -PrintObject* +PrintObject* DocumentViewerImpl::FindPrintObjectByDOMWin(PrintObject* aPO, nsIDOMWindowInternal * aDOMWin) { NS_ASSERTION(aPO, "Pointer is null!"); @@ -3687,12 +3968,11 @@ DocumentViewerImpl::GetDOMWinForWebShell(nsIWebShell* aWebShell) NS_ASSERTION(aWebShell, "Pointer is null!"); nsCOMPtr domWin = do_GetInterface(aWebShell); - if (!domWin) return nsnull; nsCOMPtr domWinInt(do_QueryInterface(domWin)); if (!domWinInt) return nsnull; - nsIDOMWindowInternal * dw = NS_STATIC_CAST(nsIDOMWindowInternal *, domWinInt.get()); + nsIDOMWindowInternal * dw = domWinInt.get(); NS_ADDREF(dw); return dw; @@ -3710,10 +3990,10 @@ DocumentViewerImpl::EnablePOsForPrinting() return NS_ERROR_FAILURE; } - mPrt->mPrintFrameType = nsIPrintSettings::kNoFrames; + mPrt->mPrintFrameType = nsIPrintSettings::kNoFrames; mPrt->mPrintSettings->GetPrintFrameType(&mPrt->mPrintFrameType); - PRInt16 printHowEnable = nsIPrintSettings::kFrameEnableNone; + PRInt16 printHowEnable = nsIPrintSettings::kFrameEnableNone; mPrt->mPrintSettings->GetHowToEnableFrameUI(&printHowEnable); PRInt16 printRangeType = nsIPrintSettings::kRangeAllPages; @@ -3731,13 +4011,13 @@ DocumentViewerImpl::EnablePOsForPrinting() // then set the mPrintFrameType as if it were the selected frame if (printRangeType == nsIPrintSettings::kRangeSelection) { mPrt->mPrintFrameType = nsIPrintSettings::kSelectedFrame; - printHowEnable = nsIPrintSettings::kFrameEnableNone; + printHowEnable = nsIPrintSettings::kFrameEnableNone; } // This tells us that the "Frame" UI has turned off, // so therefore there are no FrameSets/Frames/IFrames to be printed // - // This means there are not FrameSets, + // This means there are not FrameSets, // but the document could contain an IFrame if (printHowEnable == nsIPrintSettings::kFrameEnableNone) { @@ -3763,7 +4043,7 @@ DocumentViewerImpl::EnablePOsForPrinting() PRINT_DEBUG_MSG2("PrintRange: %s \n", gPrintRangeStr[printRangeType]); return NS_OK; } - + // This means we are either printed a selected IFrame or // we are printing the current selection if (printRangeType == nsIPrintSettings::kRangeSelection) { @@ -3780,12 +4060,12 @@ DocumentViewerImpl::EnablePOsForPrinting() // Now, only enable this POs (the selected PO) and all of its children SetPrintPO(po, PR_TRUE); - // check to see if we have a range selection, + // check to see if we have a range selection, // as oppose to a insert selection - // this means if the user just clicked on the IFrame then + // this means if the user just clicked on the IFrame then // there will not be a selection so we want the entire page to print // - // XXX this is sort of a hack right here to make the page + // XXX this is sort of a hack right here to make the page // not try to reposition itself when printing selection nsCOMPtr domWin = getter_AddRefs(GetDOMWinForWebShell(po->mWebShell)); if (!IsThereARangeSelection(domWin)) { @@ -3827,12 +4107,12 @@ DocumentViewerImpl::EnablePOsForPrinting() // Now, only enable this POs (the selected PO) and all of its children SetPrintPO(po, PR_TRUE); - // check to see if we have a range selection, + // check to see if we have a range selection, // as oppose to a insert selection - // this means if the user just clicked on the IFrame then + // this means if the user just clicked on the IFrame then // there will not be a selection so we want the entire page to print // - // XXX this is sort of a hack right here to make the page + // XXX this is sort of a hack right here to make the page // not try to reposition itself when printing selection nsCOMPtr domWin = getter_AddRefs(GetDOMWinForWebShell(po->mWebShell)); if (!IsThereARangeSelection(domWin)) { @@ -3863,9 +4143,9 @@ DocumentViewerImpl::EnablePOsForPrinting() PrintObject * po = FindPrintObjectByDOMWin(mPrt->mPrintObject, mPrt->mCurrentFocusWin); if (po != nsnull) { mPrt->mSelectedPO = po; - // NOTE: Calling this sets the "po" and + // NOTE: Calling this sets the "po" and // we don't want to do this for documents that have no children, - // because then the "DoEndPage" gets called and it shouldn't + // because then the "DoEndPage" gets called and it shouldn't if (po->mKids.Count() > 0) { // Makes sure that itself, and all of its children are printed "AsIs" SetPrintAsIs(po); @@ -3876,10 +4156,10 @@ DocumentViewerImpl::EnablePOsForPrinting() } } return NS_OK; - } - - // If we are print each subdoc separately, - // then don't print any of the FraneSet Docs + } + + // If we are print each subdoc separately, + // then don't print any of the FraneSet Docs if (mPrt->mPrintFrameType == nsIPrintSettings::kEachFrameSep) { SetPrintPO(mPrt->mPrintObject, PR_TRUE); PRInt32 cnt = mPrt->mPrintDocList->Count(); @@ -3897,11 +4177,11 @@ DocumentViewerImpl::EnablePOsForPrinting() //--------------------------------------------------- // Find the Frame in a Frame List that is XMost -void -DocumentViewerImpl::FindXMostFrameInList(nsIPresContext* aPresContext, +void +DocumentViewerImpl::FindXMostFrameInList(nsIPresContext* aPresContext, nsIRenderingContext* aRC, nsIAtom* aList, - nsIFrame* aFrame, + nsIFrame* aFrame, nscoord aX, nscoord aY, PRInt32& aMaxWidth) @@ -3910,7 +4190,7 @@ DocumentViewerImpl::FindXMostFrameInList(nsIPresContext* aPresContext, aFrame->FirstChild(aPresContext, aList, &child); while (child) { PRBool isVisible = PR_TRUE; - // If the aRC is nsnull, then we skip the more expensive check and + // If the aRC is nsnull, then we skip the more expensive check and // just check visibility if (aRC) { child->IsVisibleForPainting(aPresContext, *aRC, PR_TRUE, &isVisible); @@ -3963,10 +4243,10 @@ DocumentViewerImpl::FindXMostFrameInList(nsIPresContext* aPresContext, //--------------------------------------------------- // Find the Frame that is XMost -void -DocumentViewerImpl::FindXMostFrameSize(nsIPresContext* aPresContext, +void +DocumentViewerImpl::FindXMostFrameSize(nsIPresContext* aPresContext, nsIRenderingContext* aRC, - nsIFrame* aFrame, + nsIFrame* aFrame, nscoord aX, nscoord aY, PRInt32& aMaxWidth) @@ -3981,15 +4261,15 @@ DocumentViewerImpl::FindXMostFrameSize(nsIPresContext* aPresContext, FindXMostFrameInList(aPresContext, aRC, childListName, aFrame, aX, aY, aMaxWidth); NS_IF_RELEASE(childListName); aFrame->GetAdditionalChildListName(childListIndex++, &childListName); - } while (childListName); + } while (childListName); } //------------------------------------------------------- -// Return the PrintObject with that is XMost (The widest frameset frame) AND -// contains the XMost (widest) layout frame -PrintObject* +// Return the PrintObject with that is XMost (The widest frameset frame) AND +// contains the XMost (widest) layout frame +PrintObject* DocumentViewerImpl::FindXMostPO() { nscoord xMostForPO = 0; @@ -4097,7 +4377,7 @@ DocumentViewerImpl::SetupToPrintContent(nsIWebShell* aParent, PRINT_DEBUG_MSG1("\n-------------------------------------------------------\n\n"); // Set up the clipping rectangle for all documents - // When frames are being printed as part of a frame set and also IFrames, + // When frames are being printed as part of a frame set and also IFrames, // they are reflowed with a very large page height. We need to setup the // clipping so they do not rpint over top of anything else PRINT_DEBUG_MSG1("SetClipRect-------------------------------------------------------\n"); @@ -4132,7 +4412,7 @@ DocumentViewerImpl::SetupToPrintContent(nsIWebShell* aParent, // This will print the webshell document // when it completes asynchronously in the DonePrintingPages method - // it will check to see if there are more webshells to be printed and + // it will check to see if there are more webshells to be printed and // then PrintDocContent will be called again. nsresult rv = NS_OK; @@ -4189,7 +4469,7 @@ DocumentViewerImpl::DoPrint(PrintObject * aPO, PRBool aDoSyncPrinting, PRBool& a if (aPO->mFrameType == eFrame) { switch (mPrt->mPrintFrameType) { - case nsIPrintSettings::kFramesAsIs: + case nsIPrintSettings::kFramesAsIs: skipAllPageAdjustments = PR_TRUE; doOffsetting = PR_TRUE; break; @@ -4238,7 +4518,7 @@ DocumentViewerImpl::DoPrint(PrintObject * aPO, PRBool aDoSyncPrinting, PRBool& a skipPageEjectOnly = aPO->mPrintAsIs; } - // That we are all configured, + // That we are all configured, // let's set everything up to print if (skipPageEjectOnly) { pageSequence->SkipPageEnd(); @@ -4272,8 +4552,8 @@ DocumentViewerImpl::DoPrint(PrintObject * aPO, PRBool aDoSyncPrinting, PRBool& a } } - PRINT_DEBUG_MSG5("*** skipPageEjectOnly: %s skipAllPageAdjustments: %s doOffsetting: %s doAddInParentsOffset: %s\n", - PRT_YESNO(skipPageEjectOnly), PRT_YESNO(skipAllPageAdjustments), + PRINT_DEBUG_MSG5("*** skipPageEjectOnly: %s skipAllPageAdjustments: %s doOffsetting: %s doAddInParentsOffset: %s\n", + PRT_YESNO(skipPageEjectOnly), PRT_YESNO(skipAllPageAdjustments), PRT_YESNO(doOffsetting), PRT_YESNO(doAddInParentsOffset)); // We are done preparing for printing, so we can turn this off @@ -4290,7 +4570,7 @@ DocumentViewerImpl::DoPrint(PrintObject * aPO, PRBool aDoSyncPrinting, PRBool& a if (NS_SUCCEEDED(CallQueryInterface(root, &fdbg))) { fdbg->DumpRegressionData(poPresContext, mPrt->mDebugFilePtr, 0, PR_TRUE); } - fclose(mPrt->mDebugFilePtr); + fclose(mPrt->mDebugFilePtr); #endif } else { nsIFrame* rootFrame; @@ -4311,9 +4591,10 @@ DocumentViewerImpl::DoPrint(PrintObject * aPO, PRBool aDoSyncPrinting, PRBool& a if (!skipSetTitle) { PRUnichar * docTitleStr; PRUnichar * docURLStr; - GetDisplayTitleAndURL(aPO, mPrt->mPrintSettings, mPrt->mBrandName, &docTitleStr, &docURLStr, eDocTitleDefBlank); + GetDisplayTitleAndURL(aPO, mPrt->mPrintSettings, mPrt->mBrandName, + &docTitleStr, &docURLStr, eDocTitleDefBlank); - // Set them down into the PrintOptions so + // Set them down into the PrintOptions so // they can used by the DeviceContext if (docTitleStr) { mPrt->mPrintOptions->SetTitle(docTitleStr); @@ -4347,8 +4628,8 @@ DocumentViewerImpl::DoPrint(PrintObject * aPO, PRBool aDoSyncPrinting, PRBool& a if (NS_SUCCEEDED(rvv) && selectionPS) { } - rv = GetPageRangeForSelection(poPresShell, poPresContext, *rc, selectionPS, pageSequence, - &startFrame, startPageNum, startRect, + rv = GetPageRangeForSelection(poPresShell, poPresContext, *rc, selectionPS, pageSequence, + &startFrame, startPageNum, startRect, &endFrame, endPageNum, endRect); if (NS_SUCCEEDED(rv)) { mPrt->mPrintSettings->SetStartPageRange(startPageNum); @@ -4516,7 +4797,7 @@ DocumentViewerImpl::PrintDocContent(PrintObject* aPO, nsresult& aStatus) if (!aPO->mHasBeenPrinted && aPO->IsPrintable()) { PRBool donePrinting; // donePrinting is only valid when when doing synchronous printing - aStatus = DoPrint(aPO, PR_FALSE, donePrinting); + aStatus = DoPrint(aPO, PR_FALSE, donePrinting); if (donePrinting) { return PR_TRUE; } @@ -4528,8 +4809,8 @@ DocumentViewerImpl::PrintDocContent(PrintObject* aPO, nsresult& aStatus) if (printed || NS_FAILED(aStatus)) { return PR_TRUE; } - } - return PR_FALSE; + } + return PR_FALSE; } NS_IMETHODIMP @@ -4540,11 +4821,11 @@ DocumentViewerImpl::SetEnableRendering(PRBool aOn) if (mViewManager) { if (aOn) { mViewManager->EnableRefresh(NS_VMREFRESH_IMMEDIATE); - nsIView* view; - mViewManager->GetRootView(view); // views are not refCounted - if (view) { + nsIView* view; + mViewManager->GetRootView(view); // views are not refCounted + if (view) { mViewManager->UpdateView(view, NS_VMREFRESH_IMMEDIATE); - } + } } else { mViewManager->DisableRefresh(); @@ -4604,7 +4885,7 @@ DocumentViewerImpl::CreateStyleSet(nsIDocument* aDocument, } } - nsCOMPtr chromeRegistry = + nsCOMPtr chromeRegistry = do_GetService("@mozilla.org/chrome/chrome-registry;1", &rv); if (NS_SUCCEEDED(rv) && chromeRegistry) { nsCOMPtr sheets; @@ -4660,7 +4941,7 @@ DocumentViewerImpl::MakeWindow(nsIWidget* aParentWidget, nsCOMPtr dx; mPresContext->GetDeviceContext(getter_AddRefs(dx)); - + nsRect tbounds = aBounds; float p2t; mPresContext->GetPixelsToTwips(&p2t); @@ -4675,11 +4956,11 @@ DocumentViewerImpl::MakeWindow(nsIWidget* aParentWidget, if (NS_FAILED(rv)) return rv; - // Reset the bounds offset so the root view is set to 0,0. The offset is - // specified in nsIViewManager::Init above. - // Besides, layout will reset the root view to (0,0) during reflow, - // so changing it to 0,0 eliminates placing - // the root view in the wrong place initially. + // Reset the bounds offset so the root view is set to 0,0. The + // offset is specified in nsIViewManager::Init above. + // Besides, layout will reset the root view to (0,0) during reflow, + // so changing it to 0,0 eliminates placing the root view in the + // wrong place initially. tbounds.x = 0; tbounds.y = 0; @@ -4694,7 +4975,7 @@ DocumentViewerImpl::MakeWindow(nsIWidget* aParentWidget, nsIView* containerView = nsnull; if (NS_SUCCEEDED(aParentWidget->GetClientData(clientData))) { nsISupports* data = (nsISupports*)clientData; - + if (nsnull != data) { data->QueryInterface(NS_GET_IID(nsIView), (void **)&containerView); } @@ -4718,7 +4999,7 @@ DocumentViewerImpl::MakeWindow(nsIWidget* aParentWidget, // // If the parent container is a chrome shell, or a frameset, then we won't hook into its view // tree. This will improve performance a little bit (especially given scrolling/painting perf bugs) - // but is really just for peace of mind. This check can be removed if we want to support fancy + // but is really just for peace of mind. This check can be removed if we want to support fancy // chrome effects like transparent controls floating over content, transparent Web browsers, and // things like that, and the perf bugs are fixed. nsCOMPtr container(do_QueryInterface(mContainer)); @@ -4775,8 +5056,8 @@ nsresult DocumentViewerImpl::GetDocumentSelection(nsISelection **aSelection, nsI nsCOMPtr selcon; selcon = do_QueryInterface(aPresShell); - if (selcon) - return selcon->GetSelection(nsISelectionController::SELECTION_NORMAL, aSelection); + if (selcon) + return selcon->GetSelection(nsISelectionController::SELECTION_NORMAL, aSelection); return NS_ERROR_FAILURE; } @@ -4788,13 +5069,13 @@ DocumentViewerImpl::CreateDocumentViewerUsing(nsIPresContext* aPresContext, // XXX better error return NS_ERROR_NULL_POINTER; } - if (nsnull == aPresContext) { + if (!aPresContext) { return NS_ERROR_NULL_POINTER; } // Create new viewer DocumentViewerImpl* viewer = new DocumentViewerImpl(aPresContext); - if (nsnull == viewer) { + if (!viewer) { return NS_ERROR_OUT_OF_MEMORY; } NS_ADDREF(viewer); @@ -4805,7 +5086,7 @@ DocumentViewerImpl::CreateDocumentViewerUsing(nsIPresContext* aPresContext, // Bind the new viewer to the old document nsresult rv = viewer->LoadStart(mDocument); - + aResult = viewer; return rv; @@ -4854,7 +5135,7 @@ nsresult DocumentViewerImpl::DocumentReadyForPrinting() return rv; } -NS_IMETHODIMP +NS_IMETHODIMP DocumentViewerImpl::SetTransformMediator(nsITransformMediator* aMediator) { NS_ASSERTION(nsnull == mTransformMediator, "nsXMLDocument::SetTransformMediator(): \ @@ -4906,7 +5187,7 @@ NS_IMETHODIMP DocumentViewerImpl::SelectAll() nsCOMPtr htmldoc = do_QueryInterface(mDocument); nsCOMPtr bodyNode; - + if (htmldoc) { nsCOMPtrbodyElement; @@ -4921,8 +5202,8 @@ NS_IMETHODIMP DocumentViewerImpl::SelectAll() mDocument->GetRootContent(getter_AddRefs(rootContent)); bodyNode = do_QueryInterface(rootContent); } - if (!bodyNode) return NS_ERROR_FAILURE; - + if (!bodyNode) return NS_ERROR_FAILURE; + rv = selection->RemoveAllRanges(); if (NS_FAILED(rv)) return rv; @@ -4975,10 +5256,10 @@ NS_IMETHODIMP DocumentViewerImpl::GetCopyable(PRBool *aCopyable) nsresult rv; rv = GetDocumentSelection(getter_AddRefs(selection)); if (NS_FAILED(rv)) return rv; - + PRBool isCollapsed; selection->GetIsCollapsed(&isCollapsed); - + *aCopyable = !isCollapsed; return NS_OK; } @@ -5063,7 +5344,7 @@ nsresult DocumentViewerImpl::GetSelectionDocument(nsIDeviceContextSpec * aDevSpe if (NS_FAILED(rv)) { return rv; } rv = htmlElement->AppendChildTo(bodyElement, PR_FALSE, PR_FALSE); if (NS_FAILED(rv)) { return rv; } - + // load the document into the docshell nsCOMPtr domDoc = do_QueryInterface(doc); if (!domDoc) { return NS_ERROR_NULL_POINTER; } @@ -5081,8 +5362,8 @@ nsresult DocumentViewerImpl::GetSelectionDocument(nsIDeviceContextSpec * aDevSpe } //------------------------------------------------------ -PRBool -DocumentViewerImpl::IsThereAnIFrameSelected(nsIWebShell* aWebShell, +PRBool +DocumentViewerImpl::IsThereAnIFrameSelected(nsIWebShell* aWebShell, nsIDOMWindowInternal * aDOMWin, PRPackedBool& aIsParentFrameSet) { @@ -5098,7 +5379,7 @@ DocumentViewerImpl::IsThereAnIFrameSelected(nsIWebShell* aWebShell, // if so, it means the selected frame is either the main webshell // or an IFRAME if (aDOMWin != nsnull) { - // Get the main webshell's DOMWin to see if it matches + // Get the main webshell's DOMWin to see if it matches // the frame that is selected nsCOMPtr domWin = getter_AddRefs(GetDOMWinForWebShell(aWebShell)); if (aDOMWin != nsnull && domWin != aDOMWin) { @@ -5112,7 +5393,7 @@ DocumentViewerImpl::IsThereAnIFrameSelected(nsIWebShell* aWebShell, //------------------------------------------------------ -PRBool +PRBool DocumentViewerImpl::IsThereARangeSelection(nsIDOMWindowInternal * aDOMWin) { nsCOMPtr presShell; @@ -5147,7 +5428,7 @@ DocumentViewerImpl::IsThereARangeSelection(nsIDOMWindowInternal * aDOMWin) //------------------------------------------------------- // Recursively walks the PrintObject tree and installs the DocViewer // as an event processor and it shows the window -nsresult +nsresult DocumentViewerImpl::ShowDocList(PrintObject* aPO, PRBool aShow) { NS_ASSERTION(aPO, "Pointer is null!"); @@ -5206,7 +5487,7 @@ DocumentViewerImpl::InstallPrintPreviewListener() //---------------------------------------------------------------------- static nsresult GetSeqFrameAndCountPages(PrintObject* aPO, - nsIFrame*& aSeqFrame, + nsIFrame*& aSeqFrame, PRInt32& aCount) { NS_ENSURE_ARG_POINTER(aPO); @@ -5353,7 +5634,7 @@ DocumentViewerImpl::PrintPreviewNavigate(PRInt16 aType, PRInt32 aPageNum) } /* readonly attribute boolean isFramesetDocument; */ -NS_IMETHODIMP +NS_IMETHODIMP DocumentViewerImpl::GetIsFramesetDocument(PRBool *aIsFramesetDocument) { nsCOMPtr webContainer(do_QueryInterface(mContainer)); @@ -5402,7 +5683,7 @@ DocumentViewerImpl::GetIsFramesetFrameSelected(PRBool *aIsFramesetFrameSelected) } /* readonly attribute long printPreviewNumPages; */ -NS_IMETHODIMP +NS_IMETHODIMP DocumentViewerImpl::GetPrintPreviewNumPages(PRInt32 *aPrintPreviewNumPages) { NS_ENSURE_ARG_POINTER(aPrintPreviewNumPages); @@ -5419,7 +5700,7 @@ DocumentViewerImpl::GetPrintPreviewNumPages(PRInt32 *aPrintPreviewNumPages) } /* void exitPrintPreview (); */ -NS_IMETHODIMP +NS_IMETHODIMP DocumentViewerImpl::ExitPrintPreview() { if (mIsDoingPrintPreview) { @@ -5465,7 +5746,7 @@ DocumentViewerImpl::InstallNewPresentation() nsCOMPtr selection; nsresult rv = GetDocumentSelection(getter_AddRefs(selection)); nsCOMPtr selPrivate(do_QueryInterface(selection)); - if (NS_SUCCEEDED(rv) && selPrivate && mSelectionListener) + if (NS_SUCCEEDED(rv) && selPrivate && mSelectionListener) selPrivate->RemoveSelectionListener(mSelectionListener); // We need to destroy the PreShell if there is an existing PP @@ -5501,7 +5782,7 @@ DocumentViewerImpl::InstallNewPresentation() // This is the new code for selecting the appropriate Frame of a Frameset // for Print Preview. But it can't be turned on yet -#if 0 +#if 0 // If it is a Frameset then choose the selected one // or select the one with the largest area if (mPrt->mPrintObject->mFrameType == eFrameSet) { @@ -5619,7 +5900,7 @@ DocumentViewerImpl::ReturnToGalleyPresentation() nsCOMPtr selection; nsresult rv = GetDocumentSelection(getter_AddRefs(selection)); nsCOMPtr selPrivate(do_QueryInterface(selection)); - if (NS_SUCCEEDED(rv) && selPrivate && mSelectionListener) + if (NS_SUCCEEDED(rv) && selPrivate && mSelectionListener) selPrivate->RemoveSelectionListener(mSelectionListener); mPresShell->Destroy(); } @@ -5680,7 +5961,7 @@ DocumentViewerImpl::ReturnToGalleyPresentation() // This method checks to see if there is at least one printer defined // and if so, it sets the first printer in the list as the default name // in the PrintSettings which is then used for Printer Preview -nsresult +nsresult DocumentViewerImpl::CheckForPrinters(nsIPrintOptions* aPrintOptions, nsIPrintSettings* aPrintSettings, PRUint32 aErrorCode, @@ -5698,7 +5979,7 @@ DocumentViewerImpl::CheckForPrinters(nsIPrintOptions* aPrintOptions, simpEnum->HasMoreElements(&fndPrinter); if (fndPrinter) { // For now, it assumes the first item in the list - // is the default printer, but only set the + // is the default printer, but only set the // printer name if there isn't one nsCOMPtr supps; simpEnum->GetNext(getter_AddRefs(supps)); @@ -5825,23 +6106,36 @@ DocumentViewerImpl::CheckDocumentForPPCaching() * See documentation above in the nsIContentViewerfile class definition * @update 11/01/01 rods * - * For a full and detailed understanding of the issues with - * PrintPreview: See the design spec that is attached to Bug 107562 + * For a full and detailed understanding of the issues with + * PrintPreview: See the design spec that is attached to Bug 107562 */ NS_IMETHODIMP DocumentViewerImpl::PrintPreview(nsIPrintSettings* aPrintSettings) { - // Get the webshell for this documentviewer - nsCOMPtr webContainer(do_QueryInterface(mContainer)); - // Get the DocShell and see if it is busy - // We can't Print or Print Preview this document if it is still busy - nsCOMPtr docShell(do_QueryInterface(webContainer)); - NS_ASSERTION(docShell.get(), "This has to be a docshell"); + nsCOMPtr docShell(do_QueryInterface(mContainer)); + NS_ASSERTION(docShell, "This has to be a docshell"); + + nsCOMPtr presShell; + docShell->GetPresShell(getter_AddRefs(presShell)); + + if (!presShell) { + // A frame that's not displayed can't be printed! + + return NS_OK; + } + + PRUint32 busyFlags = nsIDocShell::BUSY_FLAGS_NONE; - if (NS_FAILED(docShell->GetBusyFlags(&busyFlags)) || busyFlags != nsIDocShell::BUSY_FLAGS_NONE) { + + if (NS_FAILED(docShell->GetBusyFlags(&busyFlags)) || + busyFlags != nsIDocShell::BUSY_FLAGS_NONE) { ShowPrintErrorDialog(NS_ERROR_GFX_PRINTER_DOC_IS_BUSY_PP, PR_FALSE); return NS_ERROR_FAILURE; } + + // Get the webshell for this documentviewer + nsCOMPtr webContainer(do_QueryInterface(mContainer)); + nsresult rv = NS_OK; #if defined(XP_PC) && defined(DEBUG_rods) && defined(DEBUG_PRINTING) @@ -5872,12 +6166,13 @@ DocumentViewerImpl::PrintPreview(nsIPrintSettings* aPrintSettings) mOldPrtPreview->mCachedPresObj = nsnull; } - // You have to have both a PrintOptions and a PrintSetting to call CheckForPrinters. - // The user can pass in a null PrintSettings, - // but you can only create one if you have a PrintOptions. - // So we we might as check to if we have a PrintOptions first, - // because we can't do anything below without it - // then inside we check to se if the printSettings is null to know if we need to create on. + // You have to have both a PrintOptions and a PrintSetting to call + // CheckForPrinters. + // The user can pass in a null PrintSettings, but you can only + // create one if you have a PrintOptions. So we we might as check + // to if we have a PrintOptions first, because we can't do anything + // below without it then inside we check to se if the printSettings + // is null to know if we need to create on. mPrt->mPrintSettings = aPrintSettings; mPrt->mPrintOptions = do_GetService(kPrintOptionsCID, &rv); if (NS_SUCCEEDED(rv) && mPrt->mPrintOptions) { @@ -5894,7 +6189,7 @@ DocumentViewerImpl::PrintPreview(nsIPrintSettings* aPrintSettings) return NS_ERROR_FAILURE; } } - + // Let's print ... mIsCreatingPrintPreview = PR_TRUE; mIsDoingPrintPreview = PR_TRUE; @@ -5931,7 +6226,7 @@ DocumentViewerImpl::PrintPreview(nsIPrintSettings* aPrintSettings) mPrt->mPrintDocList->AppendElement(mPrt->mPrintObject); mPrt->mIsParentAFrameSet = IsParentAFrameSet(webContainer); - mPrt->mPrintObject->mFrameType = mPrt->mIsParentAFrameSet?eFrameSet:eDoc; + mPrt->mPrintObject->mFrameType = mPrt->mIsParentAFrameSet ? eFrameSet : eDoc; // Build the "tree" of PrintObjects nsCOMPtr parentAsNode(do_QueryInterface(webContainer)); @@ -5941,8 +6236,8 @@ DocumentViewerImpl::PrintPreview(nsIPrintSettings* aPrintSettings) // in the parent document MapContentToWebShells(mPrt->mPrintObject, mPrt->mPrintObject); - // Get whether the doc contains a frameset - // Also, check to see if the currently focus webshell + // Get whether the doc contains a frameset + // Also, check to see if the currently focus webshell // is a child of this webshell mPrt->mIsIFrameSelected = IsThereAnIFrameSelected(webContainer, mPrt->mCurrentFocusWin, mPrt->mIsParentAFrameSet); @@ -5969,7 +6264,7 @@ DocumentViewerImpl::PrintPreview(nsIPrintSettings* aPrintSettings) #ifdef DEBUG_PRINTING if (mPrt->mPrintSettings) { - PRInt16 printHowEnable = nsIPrintSettings::kFrameEnableNone; + PRInt16 printHowEnable = nsIPrintSettings::kFrameEnableNone; mPrt->mPrintSettings->GetHowToEnableFrameUI(&printHowEnable); PRBool val; mPrt->mPrintSettings->GetPrintOptions(nsIPrintSettings::kEnableSelectionRB, &val); @@ -5997,7 +6292,7 @@ DocumentViewerImpl::PrintPreview(nsIPrintSettings* aPrintSettings) nsCOMPtr dx; nsresult rv = factory->CreateDeviceContextSpec(mWindow, aPrintSettings, *getter_AddRefs(devspec), doSilent); if (NS_SUCCEEDED(rv)) { - rv = mDeviceContext->GetDeviceContextFor(devspec, *getter_AddRefs(ppDC)); + rv = mDeviceContext->GetDeviceContextFor(devspec, *getter_AddRefs(ppDC)); if (NS_SUCCEEDED(rv)) { mDeviceContext->SetAltDevice(ppDC); if (mPrt->mPrintSettings != nsnull) { @@ -6024,7 +6319,7 @@ DocumentViewerImpl::PrintPreview(nsIPrintSettings* aPrintSettings) mPrt->mPrintSettings->SetPrintRange(nsIPrintSettings::kRangeAllPages); } - mPrt->mPrintDC = mDeviceContext; + mPrt->mPrintDC = mDeviceContext; // Get the Original PixelScale incase we need to start changing it mPrt->mPrintDC->GetCanonicalPixelScale(mPrt->mOrigDCScale); @@ -6054,8 +6349,8 @@ DocumentViewerImpl::PrintPreview(nsIPrintSettings* aPrintSettings) } /* cleanup done, let's fire-up an error dialog to notify the user - * what went wrong... - */ + * what went wrong... + */ ShowPrintErrorDialog(rv, PR_FALSE); TurnScriptingOn(PR_TRUE); mIsCreatingPrintPreview = PR_FALSE; @@ -6064,7 +6359,7 @@ DocumentViewerImpl::PrintPreview(nsIPrintSettings* aPrintSettings) } - // At this point we are done preparing everything + // At this point we are done preparing everything // before it is to be created // Noew create the new Presentation and display it @@ -6161,7 +6456,7 @@ DocumentViewerImpl::DoPrintProgress(PRBool aIsForPrinting) */ NS_IMETHODIMP DocumentViewerImpl::Print(PRBool aSilent, - FILE * aDebugFile, + FILE * aDebugFile, nsIPrintSettings* aPrintSettings) { nsCOMPtr printSettings; @@ -6185,7 +6480,7 @@ DocumentViewerImpl::Print(PRBool aSilent, return Print(printSettings, nsnull); - + } /** --------------------------------------------------- @@ -6204,6 +6499,17 @@ DocumentViewerImpl::Print(nsIPrintSettings* aPrintSettings, nsresult rv = NS_ERROR_FAILURE; + nsCOMPtr docShell(do_QueryInterface(mContainer)); + NS_ASSERTION(docShell, "This has to be a docshell"); + + nsCOMPtr presShell; + docShell->GetPresShell(getter_AddRefs(presShell)); + + if (!presShell) { + // A frame that's not displayed can't be printed! + + return NS_OK; + } if (mIsDoingPrintPreview) { PRBool okToPrint = PR_FALSE; @@ -6218,7 +6524,7 @@ DocumentViewerImpl::Print(nsIPrintSettings* aPrintSettings, } // if we are printing another URL, then exit - // the reason we check here is because this method can be called while + // the reason we check here is because this method can be called while // another is still in here (the printing dialog is a good example). // the only time we can print more than one job at a time is the regression tests if (mIsDoingPrinting) { @@ -6227,7 +6533,7 @@ DocumentViewerImpl::Print(nsIPrintSettings* aPrintSettings, ShowPrintErrorDialog(rv); return rv; } - + mPrt = new PrintData(); if (mPrt == nsnull) { return NS_ERROR_OUT_OF_MEMORY; @@ -6266,7 +6572,7 @@ DocumentViewerImpl::Print(nsIPrintSettings* aPrintSettings, mPrt->mPrintProgressListeners.AppendElement((void*)aWebProgressListener); NS_ADDREF(aWebProgressListener); } - + // Get the currently focused window and cache it // because the Print Dialog will "steal" focus and later when you try // to get the currently focused windows it will be NULL @@ -6308,8 +6614,8 @@ DocumentViewerImpl::Print(nsIPrintSettings* aPrintSettings, MapContentToWebShells(mPrt->mPrintObject, mPrt->mPrintObject); - // Get whether the doc contains a frameset - // Also, check to see if the currently focus webshell + // Get whether the doc contains a frameset + // Also, check to see if the currently focus webshell // is a child of this webshell mPrt->mIsIFrameSelected = IsThereAnIFrameSelected(webContainer, mPrt->mCurrentFocusWin, mPrt->mIsParentAFrameSet); @@ -6331,7 +6637,7 @@ DocumentViewerImpl::Print(nsIPrintSettings* aPrintSettings, #ifdef DEBUG_PRINTING if (mPrt->mPrintSettings) { - PRInt16 printHowEnable = nsIPrintSettings::kFrameEnableNone; + PRInt16 printHowEnable = nsIPrintSettings::kFrameEnableNone; mPrt->mPrintSettings->GetHowToEnableFrameUI(&printHowEnable); PRBool val; mPrt->mPrintSettings->GetPrintOptions(nsIPrintSettings::kEnableSelectionRB, &val); @@ -6350,7 +6656,7 @@ DocumentViewerImpl::Print(nsIPrintSettings* aPrintSettings, /* create factory (incl. create print dialog) */ nsCOMPtr factory = do_CreateInstance(kDeviceContextSpecFactoryCID, &rv); - + if (NS_SUCCEEDED(rv)) { #ifdef DEBUG_dcone printf("PRINT JOB STARTING\n"); @@ -6472,7 +6778,7 @@ DocumentViewerImpl::Print(nsIPrintSettings* aPrintSettings, mPrt->mPrintFrameType = nsIPrintSettings::kEachFrameSep; mPrt->mPrintSettings->SetPrintFrameType(mPrt->mPrintFrameType); } else { - // First find out from the PrinService what options are available + // First find out from the PrinService what options are available // to us for Printing FrameSets PRInt16 howToEnableFrameUI; mPrt->mPrintSettings->GetHowToEnableFrameUI(&howToEnableFrameUI); @@ -6517,12 +6823,14 @@ DocumentViewerImpl::Print(nsIPrintSettings* aPrintSettings, PRUnichar * docTitleStr; PRUnichar * docURLStr; - GetDisplayTitleAndURL(mPrt->mPrintObject, mPrt->mPrintSettings, mPrt->mBrandName, &docTitleStr, &docURLStr, eDocTitleDefURLDoc); + GetDisplayTitleAndURL(mPrt->mPrintObject, mPrt->mPrintSettings, + mPrt->mBrandName, &docTitleStr, &docURLStr, + eDocTitleDefURLDoc); // BeginDocument may pass back a FAILURE code - // i.e. On Windows, if you are printing to a file and hit "Cancel" + // i.e. On Windows, if you are printing to a file and hit "Cancel" // to the "File Name" dialog, this comes back as an error - // Don't start printing when regression test are executed + // Don't start printing when regression test are executed rv = mPrt->mDebugFilePtr ? NS_OK: mPrt->mPrintDC->BeginDocument(docTitleStr); PRINT_DEBUG_MSG1("****************** Begin Document ************************\n"); @@ -6535,12 +6843,12 @@ DocumentViewerImpl::Print(nsIPrintSettings* aPrintSettings, // Print listener setup... if (mPrt != nsnull) { - mPrt->OnStartPrinting(); + mPrt->OnStartPrinting(); } // // The mIsPrinting flag is set when the ImageGroup observer is - // notified that images must be loaded as a result of the + // notified that images must be loaded as a result of the // InitialReflow... // if(!mIsPrinting || mPrt->mDebugFilePtr) { @@ -6553,20 +6861,18 @@ DocumentViewerImpl::Print(nsIPrintSettings* aPrintSettings, } } } - } + } } else { mPrt->mPrintSettings->SetIsCancelled(PR_TRUE); mPrt->mPrintOptions->SetIsCancelled(PR_TRUE); } - - // Set that we are once again in print preview + + // Set that we are once again in print preview if ( mIsDoingPrintPreview == PR_TRUE) { aPrintSettings->SetIsPrintPreview(PR_TRUE); } } - - /* cleaup on failure + notify user */ if (NS_FAILED(rv)) { /* cleanup... */ @@ -6574,7 +6880,7 @@ DocumentViewerImpl::Print(nsIPrintSettings* aPrintSettings, mPagePrintTimer->Stop(); NS_RELEASE(mPagePrintTimer); } - + if (mPrt) { delete mPrt; mPrt = nsnull; @@ -6582,16 +6888,16 @@ DocumentViewerImpl::Print(nsIPrintSettings* aPrintSettings, mIsDoingPrinting = PR_FALSE; /* cleanup done, let's fire-up an error dialog to notify the user - * what went wrong... - * - * When rv == NS_ERROR_ABORT, it means we want out of the + * what went wrong... + * + * When rv == NS_ERROR_ABORT, it means we want out of the * print job without displaying any error messages */ if (rv != NS_ERROR_ABORT) { ShowPrintErrorDialog(rv); } } - + return rv; } @@ -6600,19 +6906,19 @@ void DocumentViewerImpl::ShowPrintErrorDialog(nsresult aPrintError, PRBool aIsPrinting) { nsresult rv; - + static NS_DEFINE_CID(kCStringBundleServiceCID, NS_STRINGBUNDLESERVICE_CID); nsCOMPtr stringBundleService = do_GetService(kCStringBundleServiceCID); - - if (!stringBundleService) { + + if (!stringBundleService) { NS_WARNING("ERROR: Failed to get StringBundle Service instance.\n"); return; } nsCOMPtr myStringBundle; - rv = stringBundleService->CreateBundle(NS_ERROR_GFX_PRINTER_BUNDLE_URL, getter_AddRefs(myStringBundle)); - if (NS_FAILED(rv)) + rv = stringBundleService->CreateBundle(NS_ERROR_GFX_PRINTER_BUNDLE_URL, getter_AddRefs(myStringBundle)); + if (NS_FAILED(rv)) return; - + nsXPIDLString msg, title; nsAutoString stringName; @@ -6653,7 +6959,7 @@ DocumentViewerImpl::ShowPrintErrorDialog(nsresult aPrintError, PRBool aIsPrintin default: NS_ERROR_TO_LOCALIZED_PRINT_ERROR_MSG(NS_ERROR_FAILURE) -#undef NS_ERROR_TO_LOCALIZED_PRINT_ERROR_MSG +#undef NS_ERROR_TO_LOCALIZED_PRINT_ERROR_MSG } myStringBundle->GetStringFromName(stringName.get(), getter_Copies(msg)); @@ -6665,7 +6971,7 @@ DocumentViewerImpl::ShowPrintErrorDialog(nsresult aPrintError, PRBool aIsPrintin if (!msg) return; - + nsCOMPtr wwatch = do_GetService("@mozilla.org/embedcomp/window-watcher;1", &rv); if (NS_FAILED(rv)) return; @@ -6676,27 +6982,22 @@ DocumentViewerImpl::ShowPrintErrorDialog(nsresult aPrintError, PRBool aIsPrintin nsCOMPtr parent = do_QueryInterface(active, &rv); if (NS_FAILED(rv)) return; - - nsCOMPtr dialog; - parent->GetPrompter(getter_AddRefs(dialog)); + + nsCOMPtr dialog; + parent->GetPrompter(getter_AddRefs(dialog)); if (!dialog) return; - + dialog->Alert(title, msg); } // nsIContentViewerFile interface NS_IMETHODIMP -DocumentViewerImpl::GetPrintable(PRBool *aPrintable) +DocumentViewerImpl::GetPrintable(PRBool *aPrintable) { NS_ENSURE_ARG_POINTER(aPrintable); - - if(mIsDoingPrinting==PR_TRUE){ - *aPrintable = PR_FALSE; - } else { - *aPrintable = PR_TRUE; - } + *aPrintable = !mIsDoingPrinting; return NS_OK; } @@ -6707,7 +7008,7 @@ DocumentViewerImpl::GetPrintable(PRBool *aPrintable) //***************************************************************************** // nsIMarkupDocumentViewer -//***************************************************************************** +//***************************************************************************** NS_IMETHODIMP DocumentViewerImpl::ScrollToNode(nsIDOMNode* aNode) { @@ -6716,25 +7017,25 @@ NS_IMETHODIMP DocumentViewerImpl::ScrollToNode(nsIDOMNode* aNode) nsCOMPtr presShell; NS_ENSURE_SUCCESS(GetPresShell(*(getter_AddRefs(presShell))), NS_ERROR_FAILURE); - // Get the nsIContent interface, because that's what we need to + // Get the nsIContent interface, because that's what we need to // get the primary frame - + nsCOMPtr content(do_QueryInterface(aNode)); NS_ENSURE_TRUE(content, NS_ERROR_FAILURE); // Get the primary frame - nsIFrame* frame; // Remember Frames aren't ref-counted. They are in their + nsIFrame* frame; // Remember Frames aren't ref-counted. They are in their // own special little world. NS_ENSURE_SUCCESS(presShell->GetPrimaryFrameFor(content, &frame), NS_ERROR_FAILURE); // tell the pres shell to scroll to the frame - NS_ENSURE_SUCCESS(presShell->ScrollFrameIntoView(frame, - NS_PRESSHELL_SCROLL_TOP, - NS_PRESSHELL_SCROLL_ANYWHERE), - NS_ERROR_FAILURE); - return NS_OK; + NS_ENSURE_SUCCESS(presShell->ScrollFrameIntoView(frame, + NS_PRESSHELL_SCROLL_TOP, + NS_PRESSHELL_SCROLL_ANYWHERE), + NS_ERROR_FAILURE); + return NS_OK; } NS_IMETHODIMP DocumentViewerImpl::GetAllowPlugins(PRBool* aAllowPlugins) @@ -6760,17 +7061,17 @@ DocumentViewerImpl::CallChildren(CallChildFunc aFunc, void* aClosure) PRInt32 i; PRInt32 n; docShellNode->GetChildCount(&n); - for (i=0; i < n; i++) + for (i=0; i < n; i++) { nsCOMPtr child; docShellNode->GetChildAt(i, getter_AddRefs(child)); nsCOMPtr childAsShell(do_QueryInterface(child)); NS_ASSERTION(childAsShell, "null child in docshell"); - if (childAsShell) + if (childAsShell) { nsCOMPtr childCV; childAsShell->GetContentViewer(getter_AddRefs(childCV)); - if (childCV) + if (childCV) { nsCOMPtr markupCV = do_QueryInterface(childCV); if (markupCV) { @@ -6821,7 +7122,7 @@ NS_IMETHODIMP DocumentViewerImpl::GetTextZoom(float* aTextZoom) return NS_OK; } -// XXX: SEMANTIC CHANGE! +// XXX: SEMANTIC CHANGE! // returns a copy of the string. Caller is responsible for freeing result // using Recycle(aDefaultCharacterSet) NS_IMETHODIMP DocumentViewerImpl::GetDefaultCharacterSet(PRUnichar** aDefaultCharacterSet) @@ -6829,18 +7130,18 @@ NS_IMETHODIMP DocumentViewerImpl::GetDefaultCharacterSet(PRUnichar** aDefaultCha NS_ENSURE_ARG_POINTER(aDefaultCharacterSet); NS_ENSURE_STATE(mContainer); - if (mDefaultCharacterSet.IsEmpty()) + if (mDefaultCharacterSet.IsEmpty()) { nsXPIDLString defCharset; nsCOMPtr webShell; webShell = do_QueryInterface(mContainer); if (webShell) - { + { nsCOMPtr prefs(do_GetService(NS_PREF_CONTRACTID)); if (prefs) prefs->GetLocalizedUnicharPref("intl.charset.default", getter_Copies(defCharset)); - } + } if (!defCharset.IsEmpty()) mDefaultCharacterSet.Assign(defCharset.get()); @@ -6865,7 +7166,7 @@ NS_IMETHODIMP DocumentViewerImpl::SetDefaultCharacterSet(const PRUnichar* aDefau (void*) aDefaultCharacterSet); } -// XXX: SEMANTIC CHANGE! +// XXX: SEMANTIC CHANGE! // returns a copy of the string. Caller is responsible for freeing result // using Recycle(aForceCharacterSet) NS_IMETHODIMP DocumentViewerImpl::GetForceCharacterSet(PRUnichar** aForceCharacterSet) @@ -6895,7 +7196,7 @@ NS_IMETHODIMP DocumentViewerImpl::SetForceCharacterSet(const PRUnichar* aForceCh return CallChildren(SetChildForceCharacterSet, (void*) aForceCharacterSet); } -// XXX: SEMANTIC CHANGE! +// XXX: SEMANTIC CHANGE! // returns a copy of the string. Caller is responsible for freeing result // using Recycle(aHintCharacterSet) NS_IMETHODIMP DocumentViewerImpl::GetHintCharacterSet(PRUnichar * *aHintCharacterSet) @@ -6980,7 +7281,7 @@ NS_IMETHODIMP DocumentViewerImpl::GetBidiTextDirection(PRUint8* aTextDirection) #endif return NS_OK; } - + NS_IMETHODIMP DocumentViewerImpl::SetBidiTextType(PRUint8 aTextType) { #ifdef IBMBIDI @@ -7136,9 +7437,9 @@ NS_IMETHODIMP DocumentViewerImpl::SetBidiOptions(PRUint32 aBidiOptions) #ifdef IBMBIDI if (mPresContext) { #if 1 - // forcing reflow will cause bug 80352. Temp turn off force reflow and + // forcing reflow will cause bug 80352. Temp turn off force reflow and // wait for simon@softel.co.il to find the real solution - mPresContext->SetBidi(aBidiOptions, PR_FALSE); + mPresContext->SetBidi(aBidiOptions, PR_FALSE); #else mPresContext->SetBidi(aBidiOptions, PR_TRUE); // force reflow #endif @@ -7173,7 +7474,7 @@ NS_IMETHODIMP DocumentViewerImpl::SizeToContent() nsCOMPtr docShellParent; docShellAsItem->GetSameTypeParent(getter_AddRefs(docShellParent)); - // It's only valid to access this from a top frame. Doesn't work from + // It's only valid to access this from a top frame. Doesn't work from // sub-frames. NS_ENSURE_TRUE(!docShellParent, NS_ERROR_FAILURE); @@ -7262,7 +7563,7 @@ DocumentViewerImpl::GetPopupNode(nsIDOMNode** aNode) // get the internal dom window nsCOMPtr internalWin(do_QueryInterface(global, &rv)); NS_ENSURE_SUCCESS(rv, rv); - NS_ENSURE_TRUE(internalWin, NS_ERROR_FAILURE); + NS_ENSURE_TRUE(internalWin, NS_ERROR_FAILURE); // get the private dom window nsCOMPtr privateWin(do_QueryInterface(internalWin, &rv)); @@ -7434,20 +7735,20 @@ NS_IMETHODIMP nsDocViewerSelectionListener::NotifySelectionChanged(nsIDOMDocumen if (!mGotSelectionState || mSelectionWasCollapsed != selectionCollapsed) { nsCOMPtr theDoc; - mDocViewer->GetDocument(*getter_AddRefs(theDoc)); + mDocViewer->GetDocument(*getter_AddRefs(theDoc)); if (!theDoc) return NS_ERROR_FAILURE; - + nsCOMPtr scriptGlobalObject; theDoc->GetScriptGlobalObject(getter_AddRefs(scriptGlobalObject)); nsCOMPtr domWindow = do_QueryInterface(scriptGlobalObject); if (!domWindow) return NS_ERROR_FAILURE; - + domWindow->UpdateCommands(NS_LITERAL_STRING("select")); mGotSelectionState = PR_TRUE; mSelectionWasCollapsed = selectionCollapsed; - } - + } + return NS_OK; } @@ -7484,7 +7785,7 @@ nsDocViewerFocusListener::Focus(nsIDOMEvent* aEvent) selCon->GetDisplaySelection( &selectionStatus); //if selection was nsISelectionController::SELECTION_OFF, do nothing - //otherwise re-enable it. + //otherwise re-enable it. if(selectionStatus == nsISelectionController::SELECTION_DISABLED || selectionStatus == nsISelectionController::SELECTION_HIDDEN) { @@ -7498,7 +7799,7 @@ NS_IMETHODIMP nsDocViewerFocusListener::Blur(nsIDOMEvent* aEvent) { nsCOMPtr shell; - if(!mDocViewer) + if(!mDocViewer) return NS_ERROR_FAILURE; nsresult result = mDocViewer->GetPresShell(*getter_AddRefs(shell));//deref once cause it take a ptr ref @@ -7508,7 +7809,7 @@ nsDocViewerFocusListener::Blur(nsIDOMEvent* aEvent) selCon = do_QueryInterface(shell); PRInt16 selectionStatus; selCon->GetDisplaySelection(&selectionStatus); - + //if selection was nsISelectionController::SELECTION_OFF, do nothing //otherwise re-enable it. if(selectionStatus == nsISelectionController::SELECTION_ON) @@ -7528,7 +7829,7 @@ nsDocViewerFocusListener::Init(DocumentViewerImpl *aDocViewer) } -PRBool +PRBool DocumentViewerImpl::IsWindowsInOurSubTree(nsIDOMWindowInternal * aDOMWindow) { PRBool found = PR_FALSE; @@ -7569,7 +7870,7 @@ DocumentViewerImpl::IsWindowsInOurSubTree(nsIDOMWindowInternal * aDOMWindow) //---------------------------------------------------------------------------------- -void +void DocumentViewerImpl::CleanupDocTitleArray(PRUnichar**& aArray, PRInt32& aCount) { for (PRInt32 i = aCount - 1; i >= 0; i--) { @@ -7582,8 +7883,8 @@ DocumentViewerImpl::CleanupDocTitleArray(PRUnichar**& aArray, PRInt32& aCount) //---------------------------------------------------------------------------------- // Enumerate all the documents for their titles -NS_IMETHODIMP -DocumentViewerImpl::EnumerateDocumentNames(PRUint32* aCount, +NS_IMETHODIMP +DocumentViewerImpl::EnumerateDocumentNames(PRUint32* aCount, PRUnichar*** aResult) { NS_ENSURE_ARG(aCount); @@ -7591,12 +7892,12 @@ DocumentViewerImpl::EnumerateDocumentNames(PRUint32* aCount, *aCount = 0; *aResult = nsnull; - + PRInt32 numDocs = mPrt->mPrintDocList->Count(); PRUnichar** array = (PRUnichar**) nsMemory::Alloc(numDocs * sizeof(PRUnichar*)); - if (!array) + if (!array) return NS_ERROR_OUT_OF_MEMORY; - + for (PRInt32 i=0;imPrintDocList->ElementAt(i); NS_ASSERTION(po, "PrintObject can't be null!"); @@ -7629,7 +7930,7 @@ DocumentViewerImpl::EnumerateDocumentNames(PRUint32* aCount, } /* readonly attribute nsIPrintSettings newPrintSettings; */ -NS_IMETHODIMP +NS_IMETHODIMP DocumentViewerImpl::GetNewPrintSettings(nsIPrintSettings * *aNewPrintSettings) { NS_ENSURE_ARG_POINTER(aNewPrintSettings); @@ -7644,7 +7945,7 @@ DocumentViewerImpl::GetNewPrintSettings(nsIPrintSettings * *aNewPrintSettings) } /* readonly attribute wstring defaultPrinterName; */ -NS_IMETHODIMP +NS_IMETHODIMP DocumentViewerImpl::GetDefaultPrinterName(PRUnichar * *aDefaultPrinterName) { NS_ENSURE_ARG_POINTER(aDefaultPrinterName); @@ -7658,7 +7959,7 @@ DocumentViewerImpl::GetDefaultPrinterName(PRUnichar * *aDefaultPrinterName) } /* void initPrintSettingsFromPrinter (in wstring aPrinterName, in nsIPrintSettings aPrintSettings); */ -NS_IMETHODIMP +NS_IMETHODIMP DocumentViewerImpl::InitPrintSettingsFromPrinter(const PRUnichar *aPrinterName, nsIPrintSettings *aPrintSettings) { NS_ENSURE_ARG_POINTER(aPrintSettings); @@ -7680,7 +7981,7 @@ DocumentViewerImpl::InitPrintSettingsFromPrinter(const PRUnichar *aPrinterName, } /* readonly attribute nsIPrintSettings globalPrintSettings; */ -NS_IMETHODIMP +NS_IMETHODIMP DocumentViewerImpl::GetGlobalPrintSettings(nsIPrintSettings * *aGlobalPrintSettings) { NS_ENSURE_ARG_POINTER(aGlobalPrintSettings); @@ -7703,7 +8004,7 @@ DocumentViewerImpl::GetDoingPrintPreview(PRBool *aDoingPrintPreview) } /* readonly attribute nsIPrintSettings currentPrintSettings; */ -NS_IMETHODIMP +NS_IMETHODIMP DocumentViewerImpl::GetCurrentPrintSettings(nsIPrintSettings * *aCurrentPrintSettings) { NS_ENSURE_ARG_POINTER(aCurrentPrintSettings); @@ -7722,7 +8023,7 @@ DocumentViewerImpl::GetCurrentPrintSettings(nsIPrintSettings * *aCurrentPrintSet } /* void cancel (); */ -NS_IMETHODIMP +NS_IMETHODIMP DocumentViewerImpl::Cancel() { nsresult rv; @@ -7734,7 +8035,7 @@ DocumentViewerImpl::Cancel() } /* void initPrintSettingsFromPrefs (in nsIPrintSettings aPrintSettings, in boolean aUsePrinterNamePrefix, in unsigned long aFlags); */ -NS_IMETHODIMP +NS_IMETHODIMP DocumentViewerImpl::InitPrintSettingsFromPrefs(nsIPrintSettings *aPrintSettings, PRBool aUsePrinterNamePrefix, PRUint32 aFlags) { nsresult rv; @@ -7746,7 +8047,7 @@ DocumentViewerImpl::InitPrintSettingsFromPrefs(nsIPrintSettings *aPrintSettings, } /* void savePrintSettingsToPrefs (in nsIPrintSettings aPrintSettings, in boolean aUsePrinterNamePrefix, in unsigned long aFlags); */ -NS_IMETHODIMP +NS_IMETHODIMP DocumentViewerImpl::SavePrintSettingsToPrefs(nsIPrintSettings *aPrintSettings, PRBool aUsePrinterNamePrefix, PRUint32 aFlags) { nsresult rv; @@ -7759,7 +8060,7 @@ DocumentViewerImpl::SavePrintSettingsToPrefs(nsIPrintSettings *aPrintSettings, P /** --------------------------------------------------- * Get the Focused Frame for a documentviewer - * + * */ nsIDOMWindowInternal* DocumentViewerImpl::FindFocusedDOMWindowInternal() @@ -7770,7 +8071,7 @@ DocumentViewerImpl::FindFocusedDOMWindowInternal() nsCOMPtr focusController; nsIDOMWindowInternal * domWin = nsnull; - this->GetDocument(*getter_AddRefs(theDoc)); + this->GetDocument(*getter_AddRefs(theDoc)); if(theDoc){ theDoc->GetScriptGlobalObject(getter_AddRefs(theSGO)); if(theSGO){ @@ -7796,7 +8097,7 @@ DocumentViewerImpl::FindFocusedDOMWindowInternal() /*=============== Timer Related Code ======================*/ nsresult -DocumentViewerImpl::StartPagePrintTimer(nsIPresContext * aPresContext, +DocumentViewerImpl::StartPagePrintTimer(nsIPresContext * aPresContext, nsIPrintSettings* aPrintSettings, PrintObject* aPOect, PRUint32 aDelay) diff --git a/mozilla/layout/base/nsIPresShell.h b/mozilla/layout/base/nsIPresShell.h index e018c206ce5..8293f2fc5b2 100644 --- a/mozilla/layout/base/nsIPresShell.h +++ b/mozilla/layout/base/nsIPresShell.h @@ -265,28 +265,6 @@ public: NS_IMETHOD GetLayoutObjectFor(nsIContent* aContent, nsISupports** aResult) const = 0; - /** - * Returns the object that acts as a subshell for aContent. - * For example, for an html frame aResult will be an nsIDocShell. - */ - NS_IMETHOD GetSubShellFor(nsIContent* aContent, - nsISupports** aResult) const = 0; - - /** - * Establish a relationship between aContent and aSubShell. - * aSubShell will be returned from GetSubShellFor(aContent, ...); - */ - NS_IMETHOD SetSubShellFor(nsIContent* aContent, - nsISupports* aSubShell) = 0; - - /** - * Find the content in the map that has aSubShell set - * as its subshell. If there is more than one mapping for - * aSubShell, the result is undefined. - */ - NS_IMETHOD FindContentForShell(nsISupports* aSubShell, - nsIContent** aContent) const = 0; - /** * Gets the placeholder frame associated with the specified frame. This is * a helper frame that forwards the request to the frame manager. diff --git a/mozilla/layout/base/nsPresShell.cpp b/mozilla/layout/base/nsPresShell.cpp index 2a41450dfc7..4aab8ffa77a 100644 --- a/mozilla/layout/base/nsPresShell.cpp +++ b/mozilla/layout/base/nsPresShell.cpp @@ -166,9 +166,6 @@ #include "nsIContentViewer.h" #include "nsIDocumentViewer.h" -// SubShell map -#include "pldhash.h" - #ifdef IBMBIDI #include "nsIBidiKeyboard.h" #endif // IBMBIDI @@ -809,14 +806,6 @@ DummyLayoutRequest::Cancel(nsresult status) // ---------------------------------------------------------------------------- -class SubShellMapEntry : public PLDHashEntryHdr { - public: - nsIContent *key; // must be first, to look like PLDHashEntryStub - nsISupports *subShell; -}; - -// ---------------------------------------------------------------------------- - class PresShell : public nsIPresShell, public nsIViewObserver, private nsIDocumentObserver, public nsIFocusTracker, public nsISelectionController, @@ -877,12 +866,6 @@ public: nsIStyleContext** aStyleContext) const; NS_IMETHOD GetLayoutObjectFor(nsIContent* aContent, nsISupports** aResult) const; - NS_IMETHOD GetSubShellFor(nsIContent* aContent, - nsISupports** aResult) const; - NS_IMETHOD SetSubShellFor(nsIContent* aContent, - nsISupports* aSubShell); - NS_IMETHOD FindContentForShell(nsISupports* aSubShell, - nsIContent** aContent) const; NS_IMETHOD GetPlaceholderFrameFor(nsIFrame* aFrame, nsIFrame** aPlaceholderFrame) const; NS_IMETHOD AppendReflowCommand(nsHTMLReflowCommand* aReflowCommand); @@ -1235,9 +1218,6 @@ protected: static void sPaintSuppressionCallback(nsITimer* aTimer, void* aPresShell); // A callback for the timer. - // subshell map - PLDHashTable* mSubShellMap; // map of content/subshell pairs - MOZ_TIMER_DECLARE(mReflowWatch) // Used for measuring time spent in reflow MOZ_TIMER_DECLARE(mFrameCreationWatch) // Used for measuring time spent in frame creation @@ -1675,13 +1655,6 @@ PresShell::Destroy() // Clobber weak leaks in case of re-entrancy during tear down mHistoryState = nsnull; - // kill subshell map, if any. It holds only weak references - if (mSubShellMap) - { - PL_DHashTableDestroy(mSubShellMap); - mSubShellMap = nsnull; - } - // release current event content and any content on event stack NS_IF_RELEASE(mCurrentEventContent); @@ -5529,94 +5502,6 @@ PresShell::GetLayoutObjectFor(nsIContent* aContent, return result; } - -NS_IMETHODIMP -PresShell::GetSubShellFor(nsIContent* aContent, - nsISupports** aResult) const -{ - NS_ENSURE_ARG_POINTER(aContent); - - if (mSubShellMap) { - SubShellMapEntry *entry = NS_STATIC_CAST(SubShellMapEntry*, - PL_DHashTableOperate(mSubShellMap, aContent, PL_DHASH_LOOKUP)); - if (PL_DHASH_ENTRY_IS_BUSY(entry)) { - NS_ADDREF(*aResult = entry->subShell); - return NS_OK; - } - } - - *aResult = nsnull; - return NS_OK; -} - -NS_IMETHODIMP -PresShell::SetSubShellFor(nsIContent* aContent, - nsISupports* aSubShell) -{ - NS_ENSURE_ARG_POINTER(aContent); - - // If aSubShell is NULL, then remove the mapping - if (!aSubShell) { - if (mSubShellMap) - PL_DHashTableOperate(mSubShellMap, aContent, PL_DHASH_REMOVE); - } else { - // Create a new hashtable if necessary - if (!mSubShellMap) { - mSubShellMap = PL_NewDHashTable(PL_DHashGetStubOps(), nsnull, - sizeof(SubShellMapEntry), 16); - if (!mSubShellMap) - return NS_ERROR_OUT_OF_MEMORY; - } - - // Add a mapping to the hash table - SubShellMapEntry *entry = NS_STATIC_CAST(SubShellMapEntry*, - PL_DHashTableOperate(mSubShellMap, aContent, PL_DHASH_ADD)); - entry->key = aContent; - entry->subShell = aSubShell; - } - return NS_OK; -} - -struct FindContentData { - FindContentData(nsISupports *aSubShell) - : subShell(aSubShell), result(nsnull) {} - - nsISupports *subShell; - nsIContent *result; -}; - -PR_STATIC_CALLBACK(PLDHashOperator) -FindContentEnumerator(PLDHashTable *table, PLDHashEntryHdr *hdr, - PRUint32 number, void *arg) -{ - SubShellMapEntry *entry = NS_STATIC_CAST(SubShellMapEntry*, hdr); - FindContentData *data = NS_STATIC_CAST(FindContentData*, arg); - - if (entry->subShell == data->subShell) { - data->result = entry->key; - return PL_DHASH_STOP; - } - return PL_DHASH_NEXT; -} - -NS_IMETHODIMP -PresShell::FindContentForShell(nsISupports* aSubShell, - nsIContent** aContent) const -{ - NS_ENSURE_ARG_POINTER(aSubShell); - - if (!mSubShellMap) { - *aContent = nsnull; - return NS_OK; - } - - FindContentData data(aSubShell); - PL_DHashTableEnumerate(mSubShellMap, FindContentEnumerator, &data); - NS_IF_ADDREF(*aContent = data.result); - - return NS_OK; -} - NS_IMETHODIMP PresShell::GetPlaceholderFrameFor(nsIFrame* aFrame, nsIFrame** aResult) const diff --git a/mozilla/layout/base/public/nsIPresShell.h b/mozilla/layout/base/public/nsIPresShell.h index e018c206ce5..8293f2fc5b2 100644 --- a/mozilla/layout/base/public/nsIPresShell.h +++ b/mozilla/layout/base/public/nsIPresShell.h @@ -265,28 +265,6 @@ public: NS_IMETHOD GetLayoutObjectFor(nsIContent* aContent, nsISupports** aResult) const = 0; - /** - * Returns the object that acts as a subshell for aContent. - * For example, for an html frame aResult will be an nsIDocShell. - */ - NS_IMETHOD GetSubShellFor(nsIContent* aContent, - nsISupports** aResult) const = 0; - - /** - * Establish a relationship between aContent and aSubShell. - * aSubShell will be returned from GetSubShellFor(aContent, ...); - */ - NS_IMETHOD SetSubShellFor(nsIContent* aContent, - nsISupports* aSubShell) = 0; - - /** - * Find the content in the map that has aSubShell set - * as its subshell. If there is more than one mapping for - * aSubShell, the result is undefined. - */ - NS_IMETHOD FindContentForShell(nsISupports* aSubShell, - nsIContent** aContent) const = 0; - /** * Gets the placeholder frame associated with the specified frame. This is * a helper frame that forwards the request to the frame manager. diff --git a/mozilla/layout/build/nsContentDLF.cpp b/mozilla/layout/build/nsContentDLF.cpp index 5dbb7e3668c..98026f58e1d 100644 --- a/mozilla/layout/build/nsContentDLF.cpp +++ b/mozilla/layout/build/nsContentDLF.cpp @@ -416,6 +416,8 @@ nsContentDLF::CreateDocument(const char* aCommand, break; docv->SetUAStyleSheet(gUAStyleSheet); + doc->SetContainer(aContainer); + // Initialize the document to begin loading the data. An // nsIStreamListener connected to the parser is returned in // aDocListener. @@ -512,6 +514,9 @@ nsContentDLF::CreateRDFDocument(const char* aCommand, * An nsIStreamListener connected to the parser is returned in * aDocListener. */ + + doc->SetContainer(aContainer); + rv = doc->StartDocumentLoad(aCommand, aChannel, aLoadGroup, aContainer, aDocListener, PR_TRUE); if (NS_SUCCEEDED(rv)) { /* diff --git a/mozilla/layout/generic/nsFrameFrame.cpp b/mozilla/layout/generic/nsFrameFrame.cpp index 0970e11314c..aaaeb055145 100644 --- a/mozilla/layout/generic/nsFrameFrame.cpp +++ b/mozilla/layout/generic/nsFrameFrame.cpp @@ -72,6 +72,7 @@ #include "nsFrameSetFrame.h" #include "nsIDOMHTMLFrameElement.h" #include "nsIDOMHTMLIFrameElement.h" +#include "nsIFrameLoader.h" #include "nsLayoutAtoms.h" #include "nsIChromeEventHandler.h" #include "nsIScriptSecurityManager.h" @@ -88,9 +89,10 @@ #include "nsIDOMEventTarget.h" #include "nsIDOMEventListener.h" #include "nsIDOMWindow.h" +#include "nsIDOMDocument.h" #include "nsIRenderingContext.h" -// For Accessibility +// For Accessibility #ifdef ACCESSIBILITY #include "nsIAccessibilityService.h" #endif @@ -98,19 +100,12 @@ class nsHTMLFrame; -static NS_DEFINE_IID(kIFramesetFrameIID, NS_IFRAMESETFRAME_IID); -static NS_DEFINE_CID(kWebShellCID, NS_WEB_SHELL_CID); static NS_DEFINE_CID(kCViewCID, NS_VIEW_CID); static NS_DEFINE_CID(kCChildCID, NS_CHILD_CID); -// Bug 8065: Limit content frame depth to some reasonable level. -// This does not count chrome frames when determining depth, -// nor does it prevent chrome recursion. -#define MAX_DEPTH_CONTENT_FRAMES 25 - -/******************************************************************************* - * FrameLoadingInfo - ******************************************************************************/ +/****************************************************************************** + * FrameLoadingInfo + *****************************************************************************/ class FrameLoadingInfo : public nsISupports { public: @@ -127,9 +122,9 @@ public: }; -/******************************************************************************* +/****************************************************************************** * nsHTMLFrameOuterFrame - ******************************************************************************/ + *****************************************************************************/ #define nsHTMLFrameOuterFrameSuper nsHTMLContainerFrame class nsHTMLFrameOuterFrame : public nsHTMLFrameOuterFrameSuper { @@ -141,7 +136,7 @@ public: NS_IMETHOD GetFrameName(nsAString& aResult) const; #endif - // nsISupports + // nsISupports NS_IMETHOD QueryInterface(const nsIID& aIID, void** aInstancePtr); NS_IMETHOD GetFrameType(nsIAtom** aType) const; @@ -167,7 +162,7 @@ public: nsIContent* aChild, PRInt32 aNameSpaceID, nsIAtom* aAttribute, - PRInt32 aModType, + PRInt32 aModType, PRInt32 aHint); #ifdef ACCESSIBILITY @@ -187,11 +182,10 @@ protected: nsCOMPtr mPresContext; }; -/******************************************************************************* +/****************************************************************************** * nsHTMLFrameInnerFrame - ******************************************************************************/ + *****************************************************************************/ class nsHTMLFrameInnerFrame : public nsLeafFrame, - public nsIWebProgressListener, public nsSupportsWeakReference { public: @@ -201,8 +195,6 @@ public: NS_IMETHOD_(nsrefcnt) AddRef(void) { return 2; } NS_IMETHOD_(nsrefcnt) Release(void) { return 1; } - NS_DECL_NSIWEBPROGRESSLISTENER - #ifdef DEBUG NS_IMETHOD GetFrameName(nsAString& aResult) const; #endif @@ -236,7 +228,9 @@ public: nsIStyleContext* aContext, nsIFrame* aPrevInFlow); - NS_IMETHOD GetParentContent(nsIContent*& aContent); + void GetParentContent(nsIContent** aContent); + nsresult GetDocShell(nsIDocShell **aDocShell); + PRBool GetURL(nsIContent* aContent, nsString& aResult); PRBool GetName(nsIContent* aContent, nsString& aResult); PRInt32 GetScrolling(nsIContent* aContent); @@ -244,13 +238,10 @@ public: PRInt32 GetMarginWidth(nsIPresContext* aPresContext, nsIContent* aContent); PRInt32 GetMarginHeight(nsIPresContext* aPresContext, nsIContent* aContent); - nsresult ReloadURL(nsIPresContext* aPresContext); - friend class nsHTMLFrameOuterFrame; protected: - nsresult CreateDocShell(nsIPresContext* aPresContext); - nsresult DoLoadURL(nsIPresContext* aPresContext); + nsresult ShowDocShell(nsIPresContext* aPresContext); nsresult CreateViewAndWidget(nsIPresContext* aPresContext, nsIWidget** aWidget); @@ -260,15 +251,18 @@ protected: const nsHTMLReflowState& aReflowState, nsHTMLReflowMetrics& aDesiredSize); - nsCOMPtr mSubShell; - nsWeakPtr mPresShellWeak; // weak reference to the nsIPresShell - PRBool mCreatingViewer; + nsresult ReloadURL(); + + nsCOMPtr mFrameLoader; + PRPackedBool mOwnsFrameLoader; + + PRPackedBool mCreatingViewer; }; -/******************************************************************************* +/****************************************************************************** * nsHTMLFrameOuterFrame - ******************************************************************************/ + *****************************************************************************/ nsHTMLFrameOuterFrame::nsHTMLFrameOuterFrame() : nsHTMLContainerFrame() { @@ -348,7 +342,7 @@ nsHTMLFrameOuterFrame::Init(nsIPresContext* aPresContext, view->GetWidget(*getter_AddRefs(widget)); if (!widget) - view->CreateWidget(kCChildCID); + view->CreateWidget(kCChildCID); } nsCOMPtr shell; @@ -386,7 +380,7 @@ nsHTMLFrameOuterFrame::GetSkipSides() const return 0; } -void +void nsHTMLFrameOuterFrame::GetDesiredSize(nsIPresContext* aPresContext, const nsHTMLReflowState& aReflowState, nsHTMLReflowMetrics& aDesiredSize) @@ -421,7 +415,7 @@ nsHTMLFrameOuterFrame::GetDesiredSize(nsIPresContext* aPresContext, } PRBool nsHTMLFrameOuterFrame::IsInline() -{ +{ return mIsInline; } @@ -462,7 +456,7 @@ NS_IMETHODIMP nsHTMLFrameOuterFrame::GetFrameType(nsIAtom** aType) const { NS_PRECONDITION(nsnull != aType, "null OUT parameter pointer"); - *aType = nsLayoutAtoms::htmlFrameOuterFrame; + *aType = nsLayoutAtoms::htmlFrameOuterFrame; NS_ADDREF(*aType); return NS_OK; } @@ -475,7 +469,7 @@ nsHTMLFrameOuterFrame::Reflow(nsIPresContext* aPresContext, { DO_GLOBAL_REFLOW_COUNT("nsHTMLFrameOuterFrame", aReflowState.reason); DISPLAY_REFLOW(aPresContext, this, aReflowState, aDesiredSize, aStatus); - //printf("OuterFrame::Reflow %X (%d,%d) \n", this, aReflowState.availableWidth, aReflowState.availableHeight); + //printf("OuterFrame::Reflow %X (%d,%d) \n", this, aReflowState.availableWidth, aReflowState.availableHeight); NS_FRAME_TRACE(NS_FRAME_TRACE_CALLS, ("enter nsHTMLFrameOuterFrame::Reflow: maxSize=%d,%d reason=%d", aReflowState.availableWidth, aReflowState.availableHeight, aReflowState.reason)); @@ -550,37 +544,40 @@ nsHTMLFrameOuterFrame::AttributeChanged(nsIPresContext* aPresContext, nsIContent* aChild, PRInt32 aNameSpaceID, nsIAtom* aAttribute, - PRInt32 aModType, + PRInt32 aModType, PRInt32 aHint) { nsCOMPtr type; aChild->GetTag(*getter_AddRefs(type)); - if (((nsHTMLAtoms::src == aAttribute) && (nsHTMLAtoms::object != type)) || - ((nsHTMLAtoms::data == aAttribute) && (nsHTMLAtoms::object == type))) { - nsHTMLFrameInnerFrame* firstChild = NS_STATIC_CAST(nsHTMLFrameInnerFrame*, - mFrames.FirstChild()); + if ((type != nsHTMLAtoms::object && aAttribute == nsHTMLAtoms::src) || + (type == nsHTMLAtoms::object && aAttribute == nsHTMLAtoms::data)) { + nsHTMLFrameInnerFrame* firstChild = + NS_STATIC_CAST(nsHTMLFrameInnerFrame*, mFrames.FirstChild()); + if (firstChild) { - firstChild->ReloadURL(aPresContext); + firstChild->ReloadURL(); } } // If the noResize attribute changes, dis/allow frame to be resized - else if (nsHTMLAtoms::noresize == aAttribute) { + else if (aAttribute == nsHTMLAtoms::noresize) { nsCOMPtr parentContent; mContent->GetParent(*getter_AddRefs(parentContent)); nsCOMPtr parentTag; parentContent->GetTag(*getter_AddRefs(parentTag)); - if (nsHTMLAtoms::frameset == parentTag) { + if (parentTag == nsHTMLAtoms::frameset) { nsIFrame* parentFrame = nsnull; GetParent(&parentFrame); if (parentFrame) { - // There is no interface for kIFramesetFrameIID - // so QI'ing to concrete class, yay! + // There is no interface for nsHTMLFramesetFrame so QI'ing to + // concrete class, yay! nsHTMLFramesetFrame* framesetFrame = nsnull; - parentFrame->QueryInterface(kIFramesetFrameIID, (void **)&framesetFrame); + parentFrame->QueryInterface(NS_GET_IID(nsHTMLFramesetFrame), + (void **)&framesetFrame); + if (framesetFrame) { framesetFrame->RecalculateBorderResize(); } @@ -589,37 +586,45 @@ nsHTMLFrameOuterFrame::AttributeChanged(nsIPresContext* aPresContext, } else if (aAttribute == nsHTMLAtoms::type) { nsHTMLFrameInnerFrame* firstChild = NS_STATIC_CAST(nsHTMLFrameInnerFrame*, - mFrames.FirstChild()); - if (!firstChild) + mFrames.FirstChild()); + if (!firstChild || !firstChild->mFrameLoader) return NS_OK; nsAutoString value; aChild->GetAttr(kNameSpaceID_None, nsHTMLAtoms::type, value); - + // Notify our enclosing chrome that the primary content shell // has changed. - nsCOMPtr docShell(do_QueryInterface(firstChild->mSubShell)); - nsCOMPtr docShellAsItem(do_QueryInterface(firstChild->mSubShell)); - + + nsCOMPtr docShell; + firstChild->mFrameLoader->GetDocShell(getter_AddRefs(docShell)); + + nsCOMPtr docShellAsItem(do_QueryInterface(docShell)); + // If our container is a web-shell, inform it that it has a new // child. If it's not a web-shell then some things will not operate // properly. nsCOMPtr container; aPresContext->GetContainer(getter_AddRefs(container)); - if (container) { - nsCOMPtr parentAsNode(do_QueryInterface(container)); - if (parentAsNode) { - nsCOMPtr parentAsItem(do_QueryInterface(parentAsNode)); - - nsCOMPtr parentTreeOwner; - parentAsItem->GetTreeOwner(getter_AddRefs(parentTreeOwner)); - if (parentTreeOwner) - parentTreeOwner->ContentShellAdded(docShellAsItem, - value.EqualsIgnoreCase("content-primary") ? PR_TRUE : PR_FALSE, - value.get()); + + nsCOMPtr parentAsNode(do_QueryInterface(container)); + + if (parentAsNode) { + nsCOMPtr parentAsItem = + do_QueryInterface(parentAsNode); + + nsCOMPtr parentTreeOwner; + parentAsItem->GetTreeOwner(getter_AddRefs(parentTreeOwner)); + if (parentTreeOwner) { + PRBool is_primary_content = + value.EqualsIgnoreCase("content-primary"); + + parentTreeOwner->ContentShellAdded(docShellAsItem, is_primary_content, + value.get()); } } } + return NS_OK; } @@ -638,49 +643,50 @@ NS_NewHTMLFrameOuterFrame(nsIPresShell* aPresShell, nsIFrame** aNewFrame) return NS_OK; } -/******************************************************************************* +/****************************************************************************** * nsHTMLFrameInnerFrame - ******************************************************************************/ + *****************************************************************************/ nsHTMLFrameInnerFrame::nsHTMLFrameInnerFrame() - : nsLeafFrame() + : nsLeafFrame(), mOwnsFrameLoader(PR_FALSE), mCreatingViewer(PR_FALSE) { - mCreatingViewer = PR_FALSE; - mPresShellWeak = nsnull; } nsHTMLFrameInnerFrame::~nsHTMLFrameInnerFrame() { - //printf("nsHTMLFrameInnerFrame destructor %X \n", this); + //printf("nsHTMLFrameInnerFrame destructor %X \n", this); - nsCOMPtr win(do_GetInterface(mSubShell)); - nsCOMPtr eventTarget(do_QueryInterface(win)); - nsCOMPtr eventListener(do_QueryInterface(mContent)); + if (mFrameLoader) { + // Get the content viewer through the docshell, but don't call + // GetDocShell() since we don't want to create one if we don't + // have one. - if (eventTarget && eventListener) { - eventTarget->RemoveEventListener(NS_LITERAL_STRING("load"), eventListener, - PR_FALSE); - } + nsCOMPtr docShell; + mFrameLoader->GetDocShell(getter_AddRefs(docShell)); - if(mSubShell) { - // notify the pres shell that a docshell has been destroyed - if (mPresShellWeak) { - nsCOMPtr ps = do_QueryReferent(mPresShellWeak); - if (ps) { - ps->SetSubShellFor(mContent, nsnull); - } + nsCOMPtr content_viewer; + docShell->GetContentViewer(getter_AddRefs(content_viewer)); + + if (content_viewer) { + // Hide the content viewer now that the frame is going away... + + content_viewer->Hide(); } - mSubShell->Destroy(); } - mSubShell = nsnull; // This is the location it was released before... - // Not sure if there is ordering depending on this. + + if (mFrameLoader && mOwnsFrameLoader) { + // We own this frame loader, and we're going away, so destroy our + // frame loader. + + mFrameLoader->Destroy(); + } } PRBool nsHTMLFrameInnerFrame::GetURL(nsIContent* aContent, nsString& aResult) { - aResult.SetLength(0); + aResult.SetLength(0); nsCOMPtr type; aContent->GetTag(*getter_AddRefs(type)); - + if (type.get() == nsHTMLAtoms::object) { if (NS_CONTENT_ATTR_HAS_VALUE == (aContent->GetAttr(kNameSpaceID_None, nsHTMLAtoms::data, aResult))) if (aResult.Length() > 0) @@ -695,7 +701,7 @@ PRBool nsHTMLFrameInnerFrame::GetURL(nsIContent* aContent, nsString& aResult) PRBool nsHTMLFrameInnerFrame::GetName(nsIContent* aContent, nsString& aResult) { - aResult.SetLength(0); + aResult.SetLength(0); if (NS_CONTENT_ATTR_HAS_VALUE == (aContent->GetAttr(kNameSpaceID_None, nsHTMLAtoms::name, aResult))) { if (aResult.Length() > 0) { @@ -734,7 +740,7 @@ PRInt32 nsHTMLFrameInnerFrame::GetScrolling(nsIContent* aContent) returnValue = NS_STYLE_OVERFLOW_AUTO; break; } - } + } } // Check style for overflow @@ -808,12 +814,6 @@ nsHTMLFrameInnerFrame::QueryInterface(REFNSIID aIID, void** aInstancePtr) { NS_ENSURE_ARG_POINTER(aInstancePtr); - if (aIID.Equals(NS_GET_IID(nsIWebProgressListener))) { - nsISupports *tmp = NS_STATIC_CAST(nsIWebProgressListener *, this); - *aInstancePtr = tmp; - return NS_OK; - } - if (aIID.Equals(NS_GET_IID(nsISupportsWeakReference))) { nsISupports *tmp = NS_STATIC_CAST(nsISupportsWeakReference *, this); *aInstancePtr = tmp; @@ -823,60 +823,6 @@ nsHTMLFrameInnerFrame::QueryInterface(REFNSIID aIID, void** aInstancePtr) return nsLeafFrame::QueryInterface(aIID, aInstancePtr); } -NS_IMETHODIMP -nsHTMLFrameInnerFrame::OnStateChange(nsIWebProgress *aWebProgress, - nsIRequest *aRequest, - PRInt32 aStateFlags, PRUint32 aStatus) -{ - if (!((~aStateFlags) & (nsIWebProgressListener::STATE_IS_DOCUMENT | - nsIWebProgressListener::STATE_TRANSFERRING))) { - nsCOMPtr win(do_GetInterface(mSubShell)); - nsCOMPtr eventTarget(do_QueryInterface(win)); - nsCOMPtr eventListener(do_QueryInterface(mContent)); - - if (eventTarget && eventListener) { - eventTarget->AddEventListener(NS_LITERAL_STRING("load"), eventListener, - PR_FALSE); - } - } - - return NS_OK; -} - -NS_IMETHODIMP -nsHTMLFrameInnerFrame::OnProgressChange(nsIWebProgress *aWebProgress, - nsIRequest *aRequest, - PRInt32 aCurSelfProgress, - PRInt32 aMaxSelfProgress, - PRInt32 aCurTotalProgress, - PRInt32 aMaxTotalProgress) -{ - return NS_OK; -} - -NS_IMETHODIMP -nsHTMLFrameInnerFrame::OnLocationChange(nsIWebProgress *aWebProgress, - nsIRequest *aRequest, nsIURI *location) -{ - return NS_OK; -} - -NS_IMETHODIMP -nsHTMLFrameInnerFrame::OnStatusChange(nsIWebProgress *aWebProgress, - nsIRequest *aRequest, - nsresult aStatus, - const PRUnichar *aMessage) -{ - return NS_OK; -} - -NS_IMETHODIMP -nsHTMLFrameInnerFrame::OnSecurityChange(nsIWebProgress *aWebProgress, - nsIRequest *aRequest, PRInt32 state) -{ - return NS_OK; -} - #ifdef DEBUG NS_IMETHODIMP nsHTMLFrameInnerFrame::GetFrameName(nsAString& aResult) const { @@ -888,7 +834,7 @@ NS_IMETHODIMP nsHTMLFrameInnerFrame::GetFrameType(nsIAtom** aType) const { NS_PRECONDITION(nsnull != aType, "null OUT parameter pointer"); - *aType = nsLayoutAtoms::htmlFrameInnerFrame; + *aType = nsLayoutAtoms::htmlFrameInnerFrame; NS_ADDREF(*aType); return NS_OK; } @@ -900,33 +846,90 @@ nsHTMLFrameInnerFrame::Paint(nsIPresContext* aPresContext, nsFramePaintLayer aWhichLayer, PRUint32 aFlags) { - //printf("inner paint %X (%d,%d,%d,%d) \n", this, aDirtyRect.x, aDirtyRect.y, aDirtyRect.width, aDirtyRect.height); - // if there is not web shell paint based on our background color, - // otherwise let the web shell paint the sub document + //printf("inner paint %X (%d,%d,%d,%d) \n", this, aDirtyRect.x, + //aDirtyRect.y, aDirtyRect.width, aDirtyRect.height); if there is + //not web shell paint based on our background color, otherwise let + //the web shell paint the sub document - // isPaginated is a temporary fix for Bug 75737 - // and this should all be fixed correctly by Bug 75739 + // isPaginated is a temporary fix for Bug 75737 and this should all + // be fixed correctly by Bug 75739 PRBool isPaginated; aPresContext->IsPaginated(&isPaginated); - if (!mSubShell && !isPaginated) { - const nsStyleBackground* color = - (const nsStyleBackground*)mStyleContext->GetStyleData(eStyleStruct_Background); - aRenderingContext.SetColor(color->mBackgroundColor); - aRenderingContext.FillRect(mRect); + + if (!isPaginated) { + nsCOMPtr docShell; + GetDocShell(getter_AddRefs(docShell)); + + if (!docShell) { + const nsStyleBackground* color = + (const nsStyleBackground*)mStyleContext-> + GetStyleData(eStyleStruct_Background); + + aRenderingContext.SetColor(color->mBackgroundColor); + aRenderingContext.FillRect(mRect); + } } + DO_GLOBAL_REFLOW_COUNT_DSP("nsHTMLFrameInnerFrame", &aRenderingContext); + return NS_OK; } -NS_IMETHODIMP -nsHTMLFrameInnerFrame::GetParentContent(nsIContent*& aContent) +void +nsHTMLFrameInnerFrame::GetParentContent(nsIContent** aContent) { - nsHTMLFrameOuterFrame* parent; - nsresult rv = GetParent((nsIFrame**)&parent); - if (NS_SUCCEEDED(rv) && parent) { - rv = parent->GetContent(&aContent); + *aContent = nsnull; + + nsIFrame* parent = nsnull; + GetParent(&parent); + + if (parent) { + parent->GetContent(aContent); } - return rv; +} + +nsresult +nsHTMLFrameInnerFrame::GetDocShell(nsIDocShell **aDocShell) +{ + *aDocShell = nsnull; + + nsCOMPtr content; + GetParentContent(getter_AddRefs(content)); + + if (!content) { + // Hmm, no content in this frame (or in the parent, really), + // that's odd, not much to be done here then. + + return NS_OK; + } + + if (!mFrameLoader) { + nsCOMPtr frame_loader_owner = + do_QueryInterface(content); + + if (frame_loader_owner) { + frame_loader_owner->GetFrameLoader(getter_AddRefs(mFrameLoader)); + } + + if (!mFrameLoader) { + nsresult rv = NS_OK; + + // No frame loader available from the content, create our own... + mFrameLoader = do_CreateInstance(NS_FRAMELOADER_CONTRACTID, &rv); + NS_ENSURE_SUCCESS(rv, rv); + + // ... remember that we own this frame loader... + mOwnsFrameLoader = PR_TRUE; + + // ... initialize it... + mFrameLoader->Init(content); + + // ... and tell it to start loading. + mFrameLoader->LoadFrame(); + } + } + + return mFrameLoader->GetDocShell(aDocShell); } NS_IMETHODIMP @@ -952,287 +955,102 @@ nsHTMLFrameInnerFrame::DidReflow(nsIPresContext* aPresContext, if (newVis != oldVis) { nsCOMPtr vm; view->GetViewManager(*getter_AddRefs(vm)); - if (vm != nsnull) { + if (vm) { vm->SetViewVisibility(view, newVis); } } } } - + return rv; } nsresult -nsHTMLFrameInnerFrame::CreateDocShell(nsIPresContext* aPresContext) +nsHTMLFrameInnerFrame::ShowDocShell(nsIPresContext* aPresContext) { - nsresult rv; - nsCOMPtr parentContent; - GetParentContent(*getter_AddRefs(parentContent)); + nsCOMPtr docShell; + nsresult rv = GetDocShell(getter_AddRefs(docShell)); + NS_ENSURE_SUCCESS(rv, rv); - // Bug 8065: Don't exceed some maximum depth in content frames (MAX_DEPTH_CONTENT_FRAMES) - PRInt32 depth = 0; - nsCOMPtr parentAsSupports; - aPresContext->GetContainer(getter_AddRefs(parentAsSupports)); - if (parentAsSupports) { - nsCOMPtr parentAsItem(do_QueryInterface(parentAsSupports)); - while (parentAsItem) { - depth++; - if (MAX_DEPTH_CONTENT_FRAMES < depth) - return NS_ERROR_UNEXPECTED; // Too deep, give up! (silently?) + // Make sure there's a document in the docshell. + nsCOMPtr win(do_GetInterface(docShell)); + NS_ENSURE_TRUE(win, NS_ERROR_UNEXPECTED); - // Only count depth on content, not chrome. - // If we wanted to limit total depth, skip the following check: - PRInt32 parentType; - parentAsItem->GetItemType(&parentType); - if (nsIDocShellTreeItem::typeContent == parentType) { - nsIDocShellTreeItem* temp = parentAsItem; - temp->GetParent(getter_AddRefs(parentAsItem)); - } else { - break; // we have exited content, stop counting, depth is OK! - } - } - } - - mSubShell = do_CreateInstance(kWebShellCID); - NS_ENSURE_TRUE(mSubShell, NS_ERROR_FAILURE); - - // notify the pres shell that a docshell has been created - nsCOMPtr presShell; - aPresContext->GetShell(getter_AddRefs(presShell)); - if (presShell) { - nsCOMPtr subShellAsSupports(do_QueryInterface(mSubShell)); - NS_ENSURE_TRUE(subShellAsSupports, NS_ERROR_FAILURE); - presShell->SetSubShellFor(mContent, subShellAsSupports); - //We need to be able to get back to the presShell to unset the subshell at destruction - mPresShellWeak = getter_AddRefs(NS_GetWeakReference(presShell)); + nsCOMPtr dom_doc; + + // This will synchronously create a document if there is no + // document in the window yet. + + win->GetDocument(getter_AddRefs(dom_doc)); } - - nsCOMPtr docShell(do_QueryInterface(mSubShell)); - NS_ENSURE_TRUE(docShell, NS_ERROR_FAILURE); - // pass along marginwidth, marginheight, scrolling so sub document can use it - docShell->SetMarginWidth(GetMarginWidth(aPresContext, parentContent)); - docShell->SetMarginHeight(GetMarginHeight(aPresContext, parentContent)); + + nsCOMPtr presShell; + docShell->GetPresShell(getter_AddRefs(presShell)); + + if (presShell) { + // The docshell is already showing, nothing left to do... + + return NS_OK; + } + + nsCOMPtr docShellTreeItem(do_QueryInterface(docShell)); + + nsCOMPtr parentDocShellTreeItem; + docShellTreeItem->GetParent(getter_AddRefs(parentDocShellTreeItem)); + + nsCOMPtr parentDocShell = + do_QueryInterface(parentDocShellTreeItem); + + nsCOMPtr parentPresShell; + parentDocShell->GetPresShell(getter_AddRefs(parentPresShell)); + + nsCOMPtr content; + GetParentContent(getter_AddRefs(content)); + + // pass along marginwidth, marginheight, scrolling so sub document + // can use it + docShell->SetMarginWidth(GetMarginWidth(aPresContext, content)); + docShell->SetMarginHeight(GetMarginHeight(aPresContext, content)); // Current and initial scrolling is set so that all succeeding docs // will use the scrolling value set here, regardless if scrolling is // set by viewing a particular document (e.g. XUL turns off scrolling) - nsCOMPtr scrollableContainer(do_QueryInterface(mSubShell)); + nsCOMPtr scrollableContainer(do_QueryInterface(docShell)); + if (scrollableContainer) { scrollableContainer->SetDefaultScrollbarPreferences(nsIScrollable::ScrollOrientation_Y, - GetScrolling(parentContent)); + GetScrolling(content)); scrollableContainer->SetDefaultScrollbarPreferences(nsIScrollable::ScrollOrientation_X, - GetScrolling(parentContent)); + GetScrolling(content)); } - nsCOMPtr docShellAsItem(do_QueryInterface(mSubShell)); + nsCOMPtr docShellAsItem(do_QueryInterface(docShell)); NS_ENSURE_TRUE(docShellAsItem, NS_ERROR_FAILURE); - nsString frameName; - if (GetName(parentContent, frameName)) { - docShellAsItem->SetName(frameName.get()); - } - - // If our container is a web-shell, inform it that it has a new - // child. If it's not a web-shell then some things will not operate - // properly. - nsCOMPtr container; - aPresContext->GetContainer(getter_AddRefs(container)); - if (container) { - nsCOMPtr parentAsNode(do_QueryInterface(container)); - if (parentAsNode) { - nsCOMPtr parentAsItem(do_QueryInterface(parentAsNode)); - PRInt32 parentType; - parentAsItem->GetItemType(&parentType); - - nsIAtom* typeAtom = NS_NewAtom("type"); - nsAutoString value, valuePiece; - PRBool isContent; - - isContent = PR_FALSE; - if (NS_SUCCEEDED(parentContent->GetAttr(kNameSpaceID_None, - typeAtom, value))) { - - // we accept "content" and "content-xxx" values. - // at time of writing, we expect "xxx" to be "primary", but - // someday it might be an integer expressing priority - value.Left(valuePiece, 7); - if (valuePiece.EqualsIgnoreCase("content") && - (value.Length() == 7 || - value.Mid(valuePiece, 7, 1) == 1 && valuePiece.Equals(NS_LITERAL_STRING("-")))) - isContent = PR_TRUE; - } - NS_IF_RELEASE(typeAtom); - if (isContent) { - // The web shell's type is content. - docShellAsItem->SetItemType(nsIDocShellTreeItem::typeContent); - } else { - // Inherit our type from our parent webshell. If it is - // chrome, we'll be chrome. If it is content, we'll be - // content. - docShellAsItem->SetItemType(parentType); - } - - parentAsNode->AddChild(docShellAsItem); - - if (isContent) { - nsCOMPtr parentTreeOwner; - parentAsItem->GetTreeOwner(getter_AddRefs(parentTreeOwner)); - if(parentTreeOwner) - parentTreeOwner->ContentShellAdded(docShellAsItem, - value.EqualsIgnoreCase("content-primary") ? PR_TRUE : PR_FALSE, - value.get()); - } - // connect the container... - nsCOMPtr webShell(do_QueryInterface(mSubShell)); - nsCOMPtr outerContainer(do_QueryInterface(container)); - if (outerContainer) - webShell->SetContainer(outerContainer); - - - // Make sure all shells have links back to the content element in the - // nearest enclosing chrome shell. - nsCOMPtr parentShell(do_QueryInterface(parentAsNode)); - nsCOMPtr chromeEventHandler; - if (parentType == nsIDocShellTreeItem::typeChrome) { - // Our parent shell is a chrome shell. It is therefore our nearest - // enclosing chrome shell. - chromeEventHandler = do_QueryInterface(mContent); - NS_WARN_IF_FALSE(chromeEventHandler, "This mContent should implement this."); - } - else { - // Our parent shell is a content shell. Get the chrome info from - // it and use that for our shell as well. - parentShell->GetChromeEventHandler(getter_AddRefs(chromeEventHandler)); - } - - docShell->SetChromeEventHandler(chromeEventHandler); - } - } nsCOMPtr widget; + rv = CreateViewAndWidget(aPresContext, getter_AddRefs(widget)); if (NS_FAILED(rv)) { return rv; } - mSubShell->InitWindow(nsnull, widget, 0, 0, 10, 10); - mSubShell->Create(); + nsCOMPtr baseWindow(do_QueryInterface(docShell)); - mSubShell->SetVisibility(PR_TRUE); + if (baseWindow) { + baseWindow->InitWindow(nsnull, widget, 0, 0, 10, 10); + + // This is kinda whacky, this "Create()" calldoesn't really create + // anything, one starts to wonder why this was named "Create"... + + baseWindow->Create(); + + baseWindow->SetVisibility(PR_TRUE); + } return NS_OK; } -nsresult -nsHTMLFrameInnerFrame::DoLoadURL(nsIPresContext* aPresContext) -{ - // Bug 8065: Preventing frame nesting recursion - if the frames are - // too deep we don't create a mSubShell, so this isn't an assert: - if (!mSubShell) return NS_OK; - - // Prevent recursion - mCreatingViewer=PR_TRUE; - - // Get the URL to load - nsCOMPtr parentContent; - nsresult rv = GetParentContent(*getter_AddRefs(parentContent)); - NS_ENSURE_TRUE(NS_SUCCEEDED(rv) && parentContent, rv); - - nsAutoString url; - GetURL(parentContent, url); - url.Trim(" \t\n\r"); - if (url.IsEmpty()) // Load about:blank into a frame if not URL is specified (bug 35986) - url = NS_LITERAL_STRING("about:blank"); - - // Make an absolute URL - nsCOMPtr baseURL; - nsCOMPtr htmlContent = do_QueryInterface(parentContent, &rv); - nsCOMPtr doc; - if (NS_SUCCEEDED(rv) && htmlContent) { - htmlContent->GetBaseURL(*getter_AddRefs(baseURL)); - (void) htmlContent->GetDocument(*getter_AddRefs(doc)); - } - else { - rv = parentContent->GetDocument(*getter_AddRefs(doc)); - if (NS_SUCCEEDED(rv) && doc) { - doc->GetBaseURL(*getter_AddRefs(baseURL)); - } - } - if (!baseURL) return NS_ERROR_NULL_POINTER; - - nsAutoString docCharset; - if (doc) - (void) doc->GetDocumentCharacterSet(docCharset); - - nsAutoString absURL; - rv = NS_MakeAbsoluteURI(absURL, url, baseURL); - NS_ENSURE_SUCCESS(rv, rv); - - nsCOMPtr uri; - NS_NewURI(getter_AddRefs(uri), absURL, - docCharset.IsEmpty() ? nsnull : NS_ConvertUCS2toUTF8(docCharset).get()); - - // Check for security - nsCOMPtr secMan = - do_GetService(NS_SCRIPTSECURITYMANAGER_CONTRACTID, &rv); - NS_ENSURE_SUCCESS(rv, rv); - - // Get base URL - nsCOMPtr baseURI; - rv = aPresContext->GetBaseURL(getter_AddRefs(baseURI)); - - // Get docshell and create load info - nsCOMPtr docShell(do_QueryInterface(mSubShell)); - NS_ENSURE_TRUE(docShell, NS_ERROR_FAILURE); - nsCOMPtr loadInfo; - docShell->CreateLoadInfo(getter_AddRefs(loadInfo)); - NS_ENSURE_TRUE(loadInfo, NS_ERROR_FAILURE); - - // Get referring URL - nsCOMPtr referrer; - nsCOMPtr principal; - rv = secMan->GetSubjectPrincipal(getter_AddRefs(principal)); - NS_ENSURE_SUCCESS(rv, rv); - // If we were called from script, get the referring URL from the script - if (principal) { - nsCOMPtr codebase = do_QueryInterface(principal); - if (codebase) { - rv = codebase->GetURI(getter_AddRefs(referrer)); - NS_ENSURE_SUCCESS(rv, rv); - } - // Pass the script principal to the docshell - nsCOMPtr owner = do_QueryInterface(principal); - loadInfo->SetOwner(owner); - } - if (!referrer) { // We're not being called form script, tell the docshell - // to inherit an owner from the current document. - loadInfo->SetInheritOwner(PR_TRUE); - referrer = baseURI; - } - - loadInfo->SetReferrer(referrer); - - // Check if we are allowed to load absURL - nsCOMPtr newURI; - rv = NS_NewURI(getter_AddRefs(newURI), absURL, nsnull, baseURI); - NS_ENSURE_SUCCESS(rv, rv); - rv = secMan->CheckLoadURI(referrer, newURI, nsIScriptSecurityManager::STANDARD); - if (NS_FAILED(rv)) - return rv; // We're not - - nsCOMPtr webProgress(do_GetInterface(mSubShell)); - - if (webProgress) { - webProgress->AddProgressListener(this); - } - - rv = docShell->LoadURI(uri, loadInfo, nsIWebNavigation::LOAD_FLAGS_NONE, PR_FALSE); - NS_ASSERTION(NS_SUCCEEDED(rv), "failed to load URL"); - - return rv; -} - - nsresult nsHTMLFrameInnerFrame::CreateViewAndWidget(nsIPresContext* aPresContext, nsIWidget** aWidget) @@ -1242,28 +1060,29 @@ nsHTMLFrameInnerFrame::CreateViewAndWidget(nsIPresContext* aPresContext, nsCOMPtr presShell; aPresContext->GetShell(getter_AddRefs(presShell)); - if (!presShell) return NS_ERROR_FAILURE; + NS_ENSURE_TRUE(presShell, NS_ERROR_FAILURE); float t2p; aPresContext->GetTwipsToPixels(&t2p); // create, init, set the parent of the view nsIView* view; - nsresult rv = nsComponentManager::CreateInstance(kCViewCID, nsnull, NS_GET_IID(nsIView), - (void **)&view); + nsresult rv = nsComponentManager::CreateInstance(kCViewCID, nsnull, + NS_GET_IID(nsIView), + (void **)&view); + if (NS_FAILED(rv)) { + NS_ERROR("Could not create view for nsHTMLFrame"); - if (NS_OK != rv) { - NS_ASSERTION(0, "Could not create view for nsHTMLFrame"); return rv; } nsIView* parView; nsPoint origin; - GetOffsetFromView(aPresContext, origin, &parView); + GetOffsetFromView(aPresContext, origin, &parView); nsRect viewBounds(origin.x, origin.y, 10, 10); nsCOMPtr viewMan; - presShell->GetViewManager(getter_AddRefs(viewMan)); + presShell->GetViewManager(getter_AddRefs(viewMan)); rv = view->Init(viewMan, viewBounds, parView); // XXX put it at the end of the document order until we can do better viewMan->InsertChild(parView, view, nsnull, PR_TRUE); @@ -1292,41 +1111,39 @@ nsHTMLFrameInnerFrame::Init(nsIPresContext* aPresContext, nsIStyleContext* aContext, nsIFrame* aPrevInFlow) { - nsresult rv = nsLeafFrame::Init(aPresContext, aContent, aParent, aContext, aPrevInFlow); + nsresult rv = nsLeafFrame::Init(aPresContext, aContent, aParent, aContext, + aPrevInFlow); if (NS_FAILED(rv)) return rv; // determine if we are a printcontext PRBool shouldCreateDoc = PR_TRUE; - nsCOMPtr thePrinterContext = do_QueryInterface(aPresContext); - if (thePrinterContext) { + nsCOMPtr thePrinterContext(do_QueryInterface(aPresContext)); + + if (thePrinterContext) { // we are printing shouldCreateDoc = PR_FALSE; } - // for print preview we want to create the view and widget but + // for print preview we want to create the view and widget but // we do not want to load the document, it is alerady loaded. - nsCOMPtr thePrintPreviewContext = do_QueryInterface(aPresContext); - if (thePrintPreviewContext) { + nsCOMPtr thePrintPreviewContext = + do_QueryInterface(aPresContext); + + if (thePrintPreviewContext) { nsCOMPtr widget; rv = CreateViewAndWidget(aPresContext, getter_AddRefs(widget)); + if (NS_FAILED(rv)) { return rv; } + // we are in PrintPreview shouldCreateDoc = PR_FALSE; } - - if (!mCreatingViewer && shouldCreateDoc) { - // create the web shell - // we do this even if the size is not positive (bug 11762) - // we do this even if there is no src (bug 16218) - if (!mSubShell) - rv = CreateDocShell(aPresContext); - // Whether or not we had to create a webshell, load the document - if (NS_SUCCEEDED(rv)) { - DoLoadURL(aPresContext); - } + + if (shouldCreateDoc) { + ShowDocShell(aPresContext); } return NS_OK; @@ -1347,41 +1164,55 @@ nsHTMLFrameInnerFrame::Reflow(nsIPresContext* aPresContext, nsresult rv = NS_OK; - // use the max size set in aReflowState by the nsHTMLFrameOuterFrame as our size + // use the max size set in aReflowState by the nsHTMLFrameOuterFrame + // as our size GetDesiredSize(aPresContext, aReflowState, aDesiredSize); aStatus = NS_FRAME_COMPLETE; + nsCOMPtr docShell; + GetDocShell(getter_AddRefs(docShell)); + + nsCOMPtr baseWindow(do_QueryInterface(docShell)); + // resize the sub document - if(mSubShell) { + if (baseWindow) { float t2p; aPresContext->GetTwipsToPixels(&t2p); PRInt32 x = 0; PRInt32 y = 0; - mSubShell->GetPositionAndSize(&x, &y, nsnull, nsnull); - PRInt32 cx = NSToCoordRound(aDesiredSize.width * t2p); + baseWindow->GetPositionAndSize(&x, &y, nsnull, nsnull); + PRInt32 cx = NSToCoordRound(aDesiredSize.width * t2p); PRInt32 cy = NSToCoordRound(aDesiredSize.height * t2p); - mSubShell->SetPositionAndSize(x, y, cx, cy, PR_FALSE); + baseWindow->SetPositionAndSize(x, y, cx, cy, PR_FALSE); NS_FRAME_TRACE(NS_FRAME_TRACE_CALLS, - ("exit nsHTMLFrameInnerFrame::Reflow: size=%d,%d rv=%x", - aDesiredSize.width, aDesiredSize.height, aStatus)); + ("exit nsHTMLFrameInnerFrame::Reflow: size=%d,%d rv=%x", + aDesiredSize.width, aDesiredSize.height, aStatus)); } - + return rv; } // load a new url nsresult -nsHTMLFrameInnerFrame::ReloadURL(nsIPresContext* aPresContext) +nsHTMLFrameInnerFrame::ReloadURL() { - return DoLoadURL(aPresContext); + if (!mOwnsFrameLoader || !mFrameLoader) { + // If we don't own the frame loader, we're not in charge of what's + // loaded into it. + + return NS_OK; + } + + return mFrameLoader->LoadFrame(); } -void + +void nsHTMLFrameInnerFrame::GetDesiredSize(nsIPresContext* aPresContext, const nsHTMLReflowState& aReflowState, nsHTMLReflowMetrics& aDesiredSize) @@ -1391,19 +1222,28 @@ nsHTMLFrameInnerFrame::GetDesiredSize(nsIPresContext* aPresContext, aDesiredSize.ascent = aDesiredSize.height; aDesiredSize.descent = 0; - // For unknown reasons, the maxElementSize for the InnerFrame is used, but the - // maxElementSize for the OuterFrame is ignored, make sure to get it right here! + // For unknown reasons, the maxElementSize for the InnerFrame is + // used, but the maxElementSize for the OuterFrame is ignored, make + // sure to get it right here! + if (aDesiredSize.maxElementSize) { if ((NS_UNCONSTRAINEDSIZE == aReflowState.availableWidth) || - (eStyleUnit_Percent == aReflowState.mStylePosition->mWidth.GetUnit())) { - aDesiredSize.maxElementSize->width = 0; // percent width springy down to 0 px + (eStyleUnit_Percent == + aReflowState.mStylePosition->mWidth.GetUnit())) { + // percent width springy down to 0 px + + aDesiredSize.maxElementSize->width = 0; } else { aDesiredSize.maxElementSize->width = aDesiredSize.width; } + if ((NS_UNCONSTRAINEDSIZE == aReflowState.availableHeight) || - (eStyleUnit_Percent == aReflowState.mStylePosition->mHeight.GetUnit())) { - aDesiredSize.maxElementSize->height = 0; // percent height springy down to 0px + (eStyleUnit_Percent == + aReflowState.mStylePosition->mHeight.GetUnit())) { + // percent height springy down to 0px + + aDesiredSize.maxElementSize->height = 0; } else { aDesiredSize.maxElementSize->height = aDesiredSize.height; @@ -1411,9 +1251,9 @@ nsHTMLFrameInnerFrame::GetDesiredSize(nsIPresContext* aPresContext, } } -/******************************************************************************* +/****************************************************************************** * FrameLoadingInfo - ******************************************************************************/ + *****************************************************************************/ FrameLoadingInfo::FrameLoadingInfo(const nsSize& aSize) { NS_INIT_REFCNT(); diff --git a/mozilla/layout/generic/nsFrameSetFrame.cpp b/mozilla/layout/generic/nsFrameSetFrame.cpp index a1a4b002844..eecf2c845bc 100644 --- a/mozilla/layout/generic/nsFrameSetFrame.cpp +++ b/mozilla/layout/generic/nsFrameSetFrame.cpp @@ -63,7 +63,6 @@ #define ALL_VIS 0x000F #define NONE_VIS 0x0000 -static NS_DEFINE_IID(kIFramesetFrameIID, NS_IFRAMESETFRAME_IID); static NS_DEFINE_IID(kLookAndFeelCID, NS_LOOKANDFEEL_CID); /******************************************************************************* @@ -252,7 +251,7 @@ nsresult nsHTMLFramesetFrame::QueryInterface(const nsIID& aIID, { if (NULL == aInstancePtr) { return NS_ERROR_NULL_POINTER; - } else if (aIID.Equals(kIFramesetFrameIID)) { + } else if (aIID.Equals(NS_GET_IID(nsHTMLFramesetFrame))) { *aInstancePtr = (void*)this; return NS_OK; } else if (aIID.Equals(NS_GET_IID(nsIObserver))) { @@ -327,7 +326,8 @@ nsHTMLFramesetFrame::Init(nsIPresContext* aPresContext, mTopLevelFrameset = (nsHTMLFramesetFrame*)this; while (parentFrame) { nsHTMLFramesetFrame* frameset; - rv = parentFrame->QueryInterface(kIFramesetFrameIID, (void**)&frameset); + rv = parentFrame->QueryInterface(NS_GET_IID(nsHTMLFramesetFrame), + (void**)&frameset); if (NS_SUCCEEDED(rv)) { mTopLevelFrameset = frameset; parentFrame->GetParent((nsIFrame**)&parentFrame); @@ -1404,7 +1404,7 @@ PRBool nsHTMLFramesetFrame::ChildIsFrameset(nsIFrame* aChild) { nsIFrame* childFrame = nsnull; - aChild->QueryInterface(kIFramesetFrameIID, (void**)&childFrame); + aChild->QueryInterface(NS_GET_IID(nsHTMLFramesetFrame), (void**)&childFrame); if (childFrame) { return PR_TRUE; } diff --git a/mozilla/layout/generic/nsFrameSetFrame.h b/mozilla/layout/generic/nsFrameSetFrame.h index fe786185fd8..88000505dff 100644 --- a/mozilla/layout/generic/nsFrameSetFrame.h +++ b/mozilla/layout/generic/nsFrameSetFrame.h @@ -57,7 +57,8 @@ struct nsGUIEvent; class nsHTMLFramesetFrame; #define NS_IFRAMESETFRAME_IID \ -{ 0xf47deac0, 0x4200, 0x11d2, { 0x80, 0x3c, 0x0, 0x60, 0x8, 0x15, 0xa7, 0x91 } } +{ 0xf47deac0, 0x4200, 0x11d2, \ + { 0x80, 0x3c, 0x0, 0x60, 0x8, 0x15, 0xa7, 0x91 } } #define NO_COLOR 0xFFFFFFFA @@ -115,8 +116,10 @@ struct nsFramesetDrag { class nsHTMLFramesetFrame : public nsHTMLContainerFrame, public nsIObserver { - public: + // Woohoo, concrete class with an IID! + NS_DEFINE_STATIC_IID_ACCESSOR(NS_IFRAMESETFRAME_IID) + nsHTMLFramesetFrame(); virtual ~nsHTMLFramesetFrame(); diff --git a/mozilla/layout/html/base/src/nsPresShell.cpp b/mozilla/layout/html/base/src/nsPresShell.cpp index 2a41450dfc7..4aab8ffa77a 100644 --- a/mozilla/layout/html/base/src/nsPresShell.cpp +++ b/mozilla/layout/html/base/src/nsPresShell.cpp @@ -166,9 +166,6 @@ #include "nsIContentViewer.h" #include "nsIDocumentViewer.h" -// SubShell map -#include "pldhash.h" - #ifdef IBMBIDI #include "nsIBidiKeyboard.h" #endif // IBMBIDI @@ -809,14 +806,6 @@ DummyLayoutRequest::Cancel(nsresult status) // ---------------------------------------------------------------------------- -class SubShellMapEntry : public PLDHashEntryHdr { - public: - nsIContent *key; // must be first, to look like PLDHashEntryStub - nsISupports *subShell; -}; - -// ---------------------------------------------------------------------------- - class PresShell : public nsIPresShell, public nsIViewObserver, private nsIDocumentObserver, public nsIFocusTracker, public nsISelectionController, @@ -877,12 +866,6 @@ public: nsIStyleContext** aStyleContext) const; NS_IMETHOD GetLayoutObjectFor(nsIContent* aContent, nsISupports** aResult) const; - NS_IMETHOD GetSubShellFor(nsIContent* aContent, - nsISupports** aResult) const; - NS_IMETHOD SetSubShellFor(nsIContent* aContent, - nsISupports* aSubShell); - NS_IMETHOD FindContentForShell(nsISupports* aSubShell, - nsIContent** aContent) const; NS_IMETHOD GetPlaceholderFrameFor(nsIFrame* aFrame, nsIFrame** aPlaceholderFrame) const; NS_IMETHOD AppendReflowCommand(nsHTMLReflowCommand* aReflowCommand); @@ -1235,9 +1218,6 @@ protected: static void sPaintSuppressionCallback(nsITimer* aTimer, void* aPresShell); // A callback for the timer. - // subshell map - PLDHashTable* mSubShellMap; // map of content/subshell pairs - MOZ_TIMER_DECLARE(mReflowWatch) // Used for measuring time spent in reflow MOZ_TIMER_DECLARE(mFrameCreationWatch) // Used for measuring time spent in frame creation @@ -1675,13 +1655,6 @@ PresShell::Destroy() // Clobber weak leaks in case of re-entrancy during tear down mHistoryState = nsnull; - // kill subshell map, if any. It holds only weak references - if (mSubShellMap) - { - PL_DHashTableDestroy(mSubShellMap); - mSubShellMap = nsnull; - } - // release current event content and any content on event stack NS_IF_RELEASE(mCurrentEventContent); @@ -5529,94 +5502,6 @@ PresShell::GetLayoutObjectFor(nsIContent* aContent, return result; } - -NS_IMETHODIMP -PresShell::GetSubShellFor(nsIContent* aContent, - nsISupports** aResult) const -{ - NS_ENSURE_ARG_POINTER(aContent); - - if (mSubShellMap) { - SubShellMapEntry *entry = NS_STATIC_CAST(SubShellMapEntry*, - PL_DHashTableOperate(mSubShellMap, aContent, PL_DHASH_LOOKUP)); - if (PL_DHASH_ENTRY_IS_BUSY(entry)) { - NS_ADDREF(*aResult = entry->subShell); - return NS_OK; - } - } - - *aResult = nsnull; - return NS_OK; -} - -NS_IMETHODIMP -PresShell::SetSubShellFor(nsIContent* aContent, - nsISupports* aSubShell) -{ - NS_ENSURE_ARG_POINTER(aContent); - - // If aSubShell is NULL, then remove the mapping - if (!aSubShell) { - if (mSubShellMap) - PL_DHashTableOperate(mSubShellMap, aContent, PL_DHASH_REMOVE); - } else { - // Create a new hashtable if necessary - if (!mSubShellMap) { - mSubShellMap = PL_NewDHashTable(PL_DHashGetStubOps(), nsnull, - sizeof(SubShellMapEntry), 16); - if (!mSubShellMap) - return NS_ERROR_OUT_OF_MEMORY; - } - - // Add a mapping to the hash table - SubShellMapEntry *entry = NS_STATIC_CAST(SubShellMapEntry*, - PL_DHashTableOperate(mSubShellMap, aContent, PL_DHASH_ADD)); - entry->key = aContent; - entry->subShell = aSubShell; - } - return NS_OK; -} - -struct FindContentData { - FindContentData(nsISupports *aSubShell) - : subShell(aSubShell), result(nsnull) {} - - nsISupports *subShell; - nsIContent *result; -}; - -PR_STATIC_CALLBACK(PLDHashOperator) -FindContentEnumerator(PLDHashTable *table, PLDHashEntryHdr *hdr, - PRUint32 number, void *arg) -{ - SubShellMapEntry *entry = NS_STATIC_CAST(SubShellMapEntry*, hdr); - FindContentData *data = NS_STATIC_CAST(FindContentData*, arg); - - if (entry->subShell == data->subShell) { - data->result = entry->key; - return PL_DHASH_STOP; - } - return PL_DHASH_NEXT; -} - -NS_IMETHODIMP -PresShell::FindContentForShell(nsISupports* aSubShell, - nsIContent** aContent) const -{ - NS_ENSURE_ARG_POINTER(aSubShell); - - if (!mSubShellMap) { - *aContent = nsnull; - return NS_OK; - } - - FindContentData data(aSubShell); - PL_DHashTableEnumerate(mSubShellMap, FindContentEnumerator, &data); - NS_IF_ADDREF(*aContent = data.result); - - return NS_OK; -} - NS_IMETHODIMP PresShell::GetPlaceholderFrameFor(nsIFrame* aFrame, nsIFrame** aResult) const diff --git a/mozilla/layout/html/document/src/nsFrameFrame.cpp b/mozilla/layout/html/document/src/nsFrameFrame.cpp index 0970e11314c..aaaeb055145 100644 --- a/mozilla/layout/html/document/src/nsFrameFrame.cpp +++ b/mozilla/layout/html/document/src/nsFrameFrame.cpp @@ -72,6 +72,7 @@ #include "nsFrameSetFrame.h" #include "nsIDOMHTMLFrameElement.h" #include "nsIDOMHTMLIFrameElement.h" +#include "nsIFrameLoader.h" #include "nsLayoutAtoms.h" #include "nsIChromeEventHandler.h" #include "nsIScriptSecurityManager.h" @@ -88,9 +89,10 @@ #include "nsIDOMEventTarget.h" #include "nsIDOMEventListener.h" #include "nsIDOMWindow.h" +#include "nsIDOMDocument.h" #include "nsIRenderingContext.h" -// For Accessibility +// For Accessibility #ifdef ACCESSIBILITY #include "nsIAccessibilityService.h" #endif @@ -98,19 +100,12 @@ class nsHTMLFrame; -static NS_DEFINE_IID(kIFramesetFrameIID, NS_IFRAMESETFRAME_IID); -static NS_DEFINE_CID(kWebShellCID, NS_WEB_SHELL_CID); static NS_DEFINE_CID(kCViewCID, NS_VIEW_CID); static NS_DEFINE_CID(kCChildCID, NS_CHILD_CID); -// Bug 8065: Limit content frame depth to some reasonable level. -// This does not count chrome frames when determining depth, -// nor does it prevent chrome recursion. -#define MAX_DEPTH_CONTENT_FRAMES 25 - -/******************************************************************************* - * FrameLoadingInfo - ******************************************************************************/ +/****************************************************************************** + * FrameLoadingInfo + *****************************************************************************/ class FrameLoadingInfo : public nsISupports { public: @@ -127,9 +122,9 @@ public: }; -/******************************************************************************* +/****************************************************************************** * nsHTMLFrameOuterFrame - ******************************************************************************/ + *****************************************************************************/ #define nsHTMLFrameOuterFrameSuper nsHTMLContainerFrame class nsHTMLFrameOuterFrame : public nsHTMLFrameOuterFrameSuper { @@ -141,7 +136,7 @@ public: NS_IMETHOD GetFrameName(nsAString& aResult) const; #endif - // nsISupports + // nsISupports NS_IMETHOD QueryInterface(const nsIID& aIID, void** aInstancePtr); NS_IMETHOD GetFrameType(nsIAtom** aType) const; @@ -167,7 +162,7 @@ public: nsIContent* aChild, PRInt32 aNameSpaceID, nsIAtom* aAttribute, - PRInt32 aModType, + PRInt32 aModType, PRInt32 aHint); #ifdef ACCESSIBILITY @@ -187,11 +182,10 @@ protected: nsCOMPtr mPresContext; }; -/******************************************************************************* +/****************************************************************************** * nsHTMLFrameInnerFrame - ******************************************************************************/ + *****************************************************************************/ class nsHTMLFrameInnerFrame : public nsLeafFrame, - public nsIWebProgressListener, public nsSupportsWeakReference { public: @@ -201,8 +195,6 @@ public: NS_IMETHOD_(nsrefcnt) AddRef(void) { return 2; } NS_IMETHOD_(nsrefcnt) Release(void) { return 1; } - NS_DECL_NSIWEBPROGRESSLISTENER - #ifdef DEBUG NS_IMETHOD GetFrameName(nsAString& aResult) const; #endif @@ -236,7 +228,9 @@ public: nsIStyleContext* aContext, nsIFrame* aPrevInFlow); - NS_IMETHOD GetParentContent(nsIContent*& aContent); + void GetParentContent(nsIContent** aContent); + nsresult GetDocShell(nsIDocShell **aDocShell); + PRBool GetURL(nsIContent* aContent, nsString& aResult); PRBool GetName(nsIContent* aContent, nsString& aResult); PRInt32 GetScrolling(nsIContent* aContent); @@ -244,13 +238,10 @@ public: PRInt32 GetMarginWidth(nsIPresContext* aPresContext, nsIContent* aContent); PRInt32 GetMarginHeight(nsIPresContext* aPresContext, nsIContent* aContent); - nsresult ReloadURL(nsIPresContext* aPresContext); - friend class nsHTMLFrameOuterFrame; protected: - nsresult CreateDocShell(nsIPresContext* aPresContext); - nsresult DoLoadURL(nsIPresContext* aPresContext); + nsresult ShowDocShell(nsIPresContext* aPresContext); nsresult CreateViewAndWidget(nsIPresContext* aPresContext, nsIWidget** aWidget); @@ -260,15 +251,18 @@ protected: const nsHTMLReflowState& aReflowState, nsHTMLReflowMetrics& aDesiredSize); - nsCOMPtr mSubShell; - nsWeakPtr mPresShellWeak; // weak reference to the nsIPresShell - PRBool mCreatingViewer; + nsresult ReloadURL(); + + nsCOMPtr mFrameLoader; + PRPackedBool mOwnsFrameLoader; + + PRPackedBool mCreatingViewer; }; -/******************************************************************************* +/****************************************************************************** * nsHTMLFrameOuterFrame - ******************************************************************************/ + *****************************************************************************/ nsHTMLFrameOuterFrame::nsHTMLFrameOuterFrame() : nsHTMLContainerFrame() { @@ -348,7 +342,7 @@ nsHTMLFrameOuterFrame::Init(nsIPresContext* aPresContext, view->GetWidget(*getter_AddRefs(widget)); if (!widget) - view->CreateWidget(kCChildCID); + view->CreateWidget(kCChildCID); } nsCOMPtr shell; @@ -386,7 +380,7 @@ nsHTMLFrameOuterFrame::GetSkipSides() const return 0; } -void +void nsHTMLFrameOuterFrame::GetDesiredSize(nsIPresContext* aPresContext, const nsHTMLReflowState& aReflowState, nsHTMLReflowMetrics& aDesiredSize) @@ -421,7 +415,7 @@ nsHTMLFrameOuterFrame::GetDesiredSize(nsIPresContext* aPresContext, } PRBool nsHTMLFrameOuterFrame::IsInline() -{ +{ return mIsInline; } @@ -462,7 +456,7 @@ NS_IMETHODIMP nsHTMLFrameOuterFrame::GetFrameType(nsIAtom** aType) const { NS_PRECONDITION(nsnull != aType, "null OUT parameter pointer"); - *aType = nsLayoutAtoms::htmlFrameOuterFrame; + *aType = nsLayoutAtoms::htmlFrameOuterFrame; NS_ADDREF(*aType); return NS_OK; } @@ -475,7 +469,7 @@ nsHTMLFrameOuterFrame::Reflow(nsIPresContext* aPresContext, { DO_GLOBAL_REFLOW_COUNT("nsHTMLFrameOuterFrame", aReflowState.reason); DISPLAY_REFLOW(aPresContext, this, aReflowState, aDesiredSize, aStatus); - //printf("OuterFrame::Reflow %X (%d,%d) \n", this, aReflowState.availableWidth, aReflowState.availableHeight); + //printf("OuterFrame::Reflow %X (%d,%d) \n", this, aReflowState.availableWidth, aReflowState.availableHeight); NS_FRAME_TRACE(NS_FRAME_TRACE_CALLS, ("enter nsHTMLFrameOuterFrame::Reflow: maxSize=%d,%d reason=%d", aReflowState.availableWidth, aReflowState.availableHeight, aReflowState.reason)); @@ -550,37 +544,40 @@ nsHTMLFrameOuterFrame::AttributeChanged(nsIPresContext* aPresContext, nsIContent* aChild, PRInt32 aNameSpaceID, nsIAtom* aAttribute, - PRInt32 aModType, + PRInt32 aModType, PRInt32 aHint) { nsCOMPtr type; aChild->GetTag(*getter_AddRefs(type)); - if (((nsHTMLAtoms::src == aAttribute) && (nsHTMLAtoms::object != type)) || - ((nsHTMLAtoms::data == aAttribute) && (nsHTMLAtoms::object == type))) { - nsHTMLFrameInnerFrame* firstChild = NS_STATIC_CAST(nsHTMLFrameInnerFrame*, - mFrames.FirstChild()); + if ((type != nsHTMLAtoms::object && aAttribute == nsHTMLAtoms::src) || + (type == nsHTMLAtoms::object && aAttribute == nsHTMLAtoms::data)) { + nsHTMLFrameInnerFrame* firstChild = + NS_STATIC_CAST(nsHTMLFrameInnerFrame*, mFrames.FirstChild()); + if (firstChild) { - firstChild->ReloadURL(aPresContext); + firstChild->ReloadURL(); } } // If the noResize attribute changes, dis/allow frame to be resized - else if (nsHTMLAtoms::noresize == aAttribute) { + else if (aAttribute == nsHTMLAtoms::noresize) { nsCOMPtr parentContent; mContent->GetParent(*getter_AddRefs(parentContent)); nsCOMPtr parentTag; parentContent->GetTag(*getter_AddRefs(parentTag)); - if (nsHTMLAtoms::frameset == parentTag) { + if (parentTag == nsHTMLAtoms::frameset) { nsIFrame* parentFrame = nsnull; GetParent(&parentFrame); if (parentFrame) { - // There is no interface for kIFramesetFrameIID - // so QI'ing to concrete class, yay! + // There is no interface for nsHTMLFramesetFrame so QI'ing to + // concrete class, yay! nsHTMLFramesetFrame* framesetFrame = nsnull; - parentFrame->QueryInterface(kIFramesetFrameIID, (void **)&framesetFrame); + parentFrame->QueryInterface(NS_GET_IID(nsHTMLFramesetFrame), + (void **)&framesetFrame); + if (framesetFrame) { framesetFrame->RecalculateBorderResize(); } @@ -589,37 +586,45 @@ nsHTMLFrameOuterFrame::AttributeChanged(nsIPresContext* aPresContext, } else if (aAttribute == nsHTMLAtoms::type) { nsHTMLFrameInnerFrame* firstChild = NS_STATIC_CAST(nsHTMLFrameInnerFrame*, - mFrames.FirstChild()); - if (!firstChild) + mFrames.FirstChild()); + if (!firstChild || !firstChild->mFrameLoader) return NS_OK; nsAutoString value; aChild->GetAttr(kNameSpaceID_None, nsHTMLAtoms::type, value); - + // Notify our enclosing chrome that the primary content shell // has changed. - nsCOMPtr docShell(do_QueryInterface(firstChild->mSubShell)); - nsCOMPtr docShellAsItem(do_QueryInterface(firstChild->mSubShell)); - + + nsCOMPtr docShell; + firstChild->mFrameLoader->GetDocShell(getter_AddRefs(docShell)); + + nsCOMPtr docShellAsItem(do_QueryInterface(docShell)); + // If our container is a web-shell, inform it that it has a new // child. If it's not a web-shell then some things will not operate // properly. nsCOMPtr container; aPresContext->GetContainer(getter_AddRefs(container)); - if (container) { - nsCOMPtr parentAsNode(do_QueryInterface(container)); - if (parentAsNode) { - nsCOMPtr parentAsItem(do_QueryInterface(parentAsNode)); - - nsCOMPtr parentTreeOwner; - parentAsItem->GetTreeOwner(getter_AddRefs(parentTreeOwner)); - if (parentTreeOwner) - parentTreeOwner->ContentShellAdded(docShellAsItem, - value.EqualsIgnoreCase("content-primary") ? PR_TRUE : PR_FALSE, - value.get()); + + nsCOMPtr parentAsNode(do_QueryInterface(container)); + + if (parentAsNode) { + nsCOMPtr parentAsItem = + do_QueryInterface(parentAsNode); + + nsCOMPtr parentTreeOwner; + parentAsItem->GetTreeOwner(getter_AddRefs(parentTreeOwner)); + if (parentTreeOwner) { + PRBool is_primary_content = + value.EqualsIgnoreCase("content-primary"); + + parentTreeOwner->ContentShellAdded(docShellAsItem, is_primary_content, + value.get()); } } } + return NS_OK; } @@ -638,49 +643,50 @@ NS_NewHTMLFrameOuterFrame(nsIPresShell* aPresShell, nsIFrame** aNewFrame) return NS_OK; } -/******************************************************************************* +/****************************************************************************** * nsHTMLFrameInnerFrame - ******************************************************************************/ + *****************************************************************************/ nsHTMLFrameInnerFrame::nsHTMLFrameInnerFrame() - : nsLeafFrame() + : nsLeafFrame(), mOwnsFrameLoader(PR_FALSE), mCreatingViewer(PR_FALSE) { - mCreatingViewer = PR_FALSE; - mPresShellWeak = nsnull; } nsHTMLFrameInnerFrame::~nsHTMLFrameInnerFrame() { - //printf("nsHTMLFrameInnerFrame destructor %X \n", this); + //printf("nsHTMLFrameInnerFrame destructor %X \n", this); - nsCOMPtr win(do_GetInterface(mSubShell)); - nsCOMPtr eventTarget(do_QueryInterface(win)); - nsCOMPtr eventListener(do_QueryInterface(mContent)); + if (mFrameLoader) { + // Get the content viewer through the docshell, but don't call + // GetDocShell() since we don't want to create one if we don't + // have one. - if (eventTarget && eventListener) { - eventTarget->RemoveEventListener(NS_LITERAL_STRING("load"), eventListener, - PR_FALSE); - } + nsCOMPtr docShell; + mFrameLoader->GetDocShell(getter_AddRefs(docShell)); - if(mSubShell) { - // notify the pres shell that a docshell has been destroyed - if (mPresShellWeak) { - nsCOMPtr ps = do_QueryReferent(mPresShellWeak); - if (ps) { - ps->SetSubShellFor(mContent, nsnull); - } + nsCOMPtr content_viewer; + docShell->GetContentViewer(getter_AddRefs(content_viewer)); + + if (content_viewer) { + // Hide the content viewer now that the frame is going away... + + content_viewer->Hide(); } - mSubShell->Destroy(); } - mSubShell = nsnull; // This is the location it was released before... - // Not sure if there is ordering depending on this. + + if (mFrameLoader && mOwnsFrameLoader) { + // We own this frame loader, and we're going away, so destroy our + // frame loader. + + mFrameLoader->Destroy(); + } } PRBool nsHTMLFrameInnerFrame::GetURL(nsIContent* aContent, nsString& aResult) { - aResult.SetLength(0); + aResult.SetLength(0); nsCOMPtr type; aContent->GetTag(*getter_AddRefs(type)); - + if (type.get() == nsHTMLAtoms::object) { if (NS_CONTENT_ATTR_HAS_VALUE == (aContent->GetAttr(kNameSpaceID_None, nsHTMLAtoms::data, aResult))) if (aResult.Length() > 0) @@ -695,7 +701,7 @@ PRBool nsHTMLFrameInnerFrame::GetURL(nsIContent* aContent, nsString& aResult) PRBool nsHTMLFrameInnerFrame::GetName(nsIContent* aContent, nsString& aResult) { - aResult.SetLength(0); + aResult.SetLength(0); if (NS_CONTENT_ATTR_HAS_VALUE == (aContent->GetAttr(kNameSpaceID_None, nsHTMLAtoms::name, aResult))) { if (aResult.Length() > 0) { @@ -734,7 +740,7 @@ PRInt32 nsHTMLFrameInnerFrame::GetScrolling(nsIContent* aContent) returnValue = NS_STYLE_OVERFLOW_AUTO; break; } - } + } } // Check style for overflow @@ -808,12 +814,6 @@ nsHTMLFrameInnerFrame::QueryInterface(REFNSIID aIID, void** aInstancePtr) { NS_ENSURE_ARG_POINTER(aInstancePtr); - if (aIID.Equals(NS_GET_IID(nsIWebProgressListener))) { - nsISupports *tmp = NS_STATIC_CAST(nsIWebProgressListener *, this); - *aInstancePtr = tmp; - return NS_OK; - } - if (aIID.Equals(NS_GET_IID(nsISupportsWeakReference))) { nsISupports *tmp = NS_STATIC_CAST(nsISupportsWeakReference *, this); *aInstancePtr = tmp; @@ -823,60 +823,6 @@ nsHTMLFrameInnerFrame::QueryInterface(REFNSIID aIID, void** aInstancePtr) return nsLeafFrame::QueryInterface(aIID, aInstancePtr); } -NS_IMETHODIMP -nsHTMLFrameInnerFrame::OnStateChange(nsIWebProgress *aWebProgress, - nsIRequest *aRequest, - PRInt32 aStateFlags, PRUint32 aStatus) -{ - if (!((~aStateFlags) & (nsIWebProgressListener::STATE_IS_DOCUMENT | - nsIWebProgressListener::STATE_TRANSFERRING))) { - nsCOMPtr win(do_GetInterface(mSubShell)); - nsCOMPtr eventTarget(do_QueryInterface(win)); - nsCOMPtr eventListener(do_QueryInterface(mContent)); - - if (eventTarget && eventListener) { - eventTarget->AddEventListener(NS_LITERAL_STRING("load"), eventListener, - PR_FALSE); - } - } - - return NS_OK; -} - -NS_IMETHODIMP -nsHTMLFrameInnerFrame::OnProgressChange(nsIWebProgress *aWebProgress, - nsIRequest *aRequest, - PRInt32 aCurSelfProgress, - PRInt32 aMaxSelfProgress, - PRInt32 aCurTotalProgress, - PRInt32 aMaxTotalProgress) -{ - return NS_OK; -} - -NS_IMETHODIMP -nsHTMLFrameInnerFrame::OnLocationChange(nsIWebProgress *aWebProgress, - nsIRequest *aRequest, nsIURI *location) -{ - return NS_OK; -} - -NS_IMETHODIMP -nsHTMLFrameInnerFrame::OnStatusChange(nsIWebProgress *aWebProgress, - nsIRequest *aRequest, - nsresult aStatus, - const PRUnichar *aMessage) -{ - return NS_OK; -} - -NS_IMETHODIMP -nsHTMLFrameInnerFrame::OnSecurityChange(nsIWebProgress *aWebProgress, - nsIRequest *aRequest, PRInt32 state) -{ - return NS_OK; -} - #ifdef DEBUG NS_IMETHODIMP nsHTMLFrameInnerFrame::GetFrameName(nsAString& aResult) const { @@ -888,7 +834,7 @@ NS_IMETHODIMP nsHTMLFrameInnerFrame::GetFrameType(nsIAtom** aType) const { NS_PRECONDITION(nsnull != aType, "null OUT parameter pointer"); - *aType = nsLayoutAtoms::htmlFrameInnerFrame; + *aType = nsLayoutAtoms::htmlFrameInnerFrame; NS_ADDREF(*aType); return NS_OK; } @@ -900,33 +846,90 @@ nsHTMLFrameInnerFrame::Paint(nsIPresContext* aPresContext, nsFramePaintLayer aWhichLayer, PRUint32 aFlags) { - //printf("inner paint %X (%d,%d,%d,%d) \n", this, aDirtyRect.x, aDirtyRect.y, aDirtyRect.width, aDirtyRect.height); - // if there is not web shell paint based on our background color, - // otherwise let the web shell paint the sub document + //printf("inner paint %X (%d,%d,%d,%d) \n", this, aDirtyRect.x, + //aDirtyRect.y, aDirtyRect.width, aDirtyRect.height); if there is + //not web shell paint based on our background color, otherwise let + //the web shell paint the sub document - // isPaginated is a temporary fix for Bug 75737 - // and this should all be fixed correctly by Bug 75739 + // isPaginated is a temporary fix for Bug 75737 and this should all + // be fixed correctly by Bug 75739 PRBool isPaginated; aPresContext->IsPaginated(&isPaginated); - if (!mSubShell && !isPaginated) { - const nsStyleBackground* color = - (const nsStyleBackground*)mStyleContext->GetStyleData(eStyleStruct_Background); - aRenderingContext.SetColor(color->mBackgroundColor); - aRenderingContext.FillRect(mRect); + + if (!isPaginated) { + nsCOMPtr docShell; + GetDocShell(getter_AddRefs(docShell)); + + if (!docShell) { + const nsStyleBackground* color = + (const nsStyleBackground*)mStyleContext-> + GetStyleData(eStyleStruct_Background); + + aRenderingContext.SetColor(color->mBackgroundColor); + aRenderingContext.FillRect(mRect); + } } + DO_GLOBAL_REFLOW_COUNT_DSP("nsHTMLFrameInnerFrame", &aRenderingContext); + return NS_OK; } -NS_IMETHODIMP -nsHTMLFrameInnerFrame::GetParentContent(nsIContent*& aContent) +void +nsHTMLFrameInnerFrame::GetParentContent(nsIContent** aContent) { - nsHTMLFrameOuterFrame* parent; - nsresult rv = GetParent((nsIFrame**)&parent); - if (NS_SUCCEEDED(rv) && parent) { - rv = parent->GetContent(&aContent); + *aContent = nsnull; + + nsIFrame* parent = nsnull; + GetParent(&parent); + + if (parent) { + parent->GetContent(aContent); } - return rv; +} + +nsresult +nsHTMLFrameInnerFrame::GetDocShell(nsIDocShell **aDocShell) +{ + *aDocShell = nsnull; + + nsCOMPtr content; + GetParentContent(getter_AddRefs(content)); + + if (!content) { + // Hmm, no content in this frame (or in the parent, really), + // that's odd, not much to be done here then. + + return NS_OK; + } + + if (!mFrameLoader) { + nsCOMPtr frame_loader_owner = + do_QueryInterface(content); + + if (frame_loader_owner) { + frame_loader_owner->GetFrameLoader(getter_AddRefs(mFrameLoader)); + } + + if (!mFrameLoader) { + nsresult rv = NS_OK; + + // No frame loader available from the content, create our own... + mFrameLoader = do_CreateInstance(NS_FRAMELOADER_CONTRACTID, &rv); + NS_ENSURE_SUCCESS(rv, rv); + + // ... remember that we own this frame loader... + mOwnsFrameLoader = PR_TRUE; + + // ... initialize it... + mFrameLoader->Init(content); + + // ... and tell it to start loading. + mFrameLoader->LoadFrame(); + } + } + + return mFrameLoader->GetDocShell(aDocShell); } NS_IMETHODIMP @@ -952,287 +955,102 @@ nsHTMLFrameInnerFrame::DidReflow(nsIPresContext* aPresContext, if (newVis != oldVis) { nsCOMPtr vm; view->GetViewManager(*getter_AddRefs(vm)); - if (vm != nsnull) { + if (vm) { vm->SetViewVisibility(view, newVis); } } } } - + return rv; } nsresult -nsHTMLFrameInnerFrame::CreateDocShell(nsIPresContext* aPresContext) +nsHTMLFrameInnerFrame::ShowDocShell(nsIPresContext* aPresContext) { - nsresult rv; - nsCOMPtr parentContent; - GetParentContent(*getter_AddRefs(parentContent)); + nsCOMPtr docShell; + nsresult rv = GetDocShell(getter_AddRefs(docShell)); + NS_ENSURE_SUCCESS(rv, rv); - // Bug 8065: Don't exceed some maximum depth in content frames (MAX_DEPTH_CONTENT_FRAMES) - PRInt32 depth = 0; - nsCOMPtr parentAsSupports; - aPresContext->GetContainer(getter_AddRefs(parentAsSupports)); - if (parentAsSupports) { - nsCOMPtr parentAsItem(do_QueryInterface(parentAsSupports)); - while (parentAsItem) { - depth++; - if (MAX_DEPTH_CONTENT_FRAMES < depth) - return NS_ERROR_UNEXPECTED; // Too deep, give up! (silently?) + // Make sure there's a document in the docshell. + nsCOMPtr win(do_GetInterface(docShell)); + NS_ENSURE_TRUE(win, NS_ERROR_UNEXPECTED); - // Only count depth on content, not chrome. - // If we wanted to limit total depth, skip the following check: - PRInt32 parentType; - parentAsItem->GetItemType(&parentType); - if (nsIDocShellTreeItem::typeContent == parentType) { - nsIDocShellTreeItem* temp = parentAsItem; - temp->GetParent(getter_AddRefs(parentAsItem)); - } else { - break; // we have exited content, stop counting, depth is OK! - } - } - } - - mSubShell = do_CreateInstance(kWebShellCID); - NS_ENSURE_TRUE(mSubShell, NS_ERROR_FAILURE); - - // notify the pres shell that a docshell has been created - nsCOMPtr presShell; - aPresContext->GetShell(getter_AddRefs(presShell)); - if (presShell) { - nsCOMPtr subShellAsSupports(do_QueryInterface(mSubShell)); - NS_ENSURE_TRUE(subShellAsSupports, NS_ERROR_FAILURE); - presShell->SetSubShellFor(mContent, subShellAsSupports); - //We need to be able to get back to the presShell to unset the subshell at destruction - mPresShellWeak = getter_AddRefs(NS_GetWeakReference(presShell)); + nsCOMPtr dom_doc; + + // This will synchronously create a document if there is no + // document in the window yet. + + win->GetDocument(getter_AddRefs(dom_doc)); } - - nsCOMPtr docShell(do_QueryInterface(mSubShell)); - NS_ENSURE_TRUE(docShell, NS_ERROR_FAILURE); - // pass along marginwidth, marginheight, scrolling so sub document can use it - docShell->SetMarginWidth(GetMarginWidth(aPresContext, parentContent)); - docShell->SetMarginHeight(GetMarginHeight(aPresContext, parentContent)); + + nsCOMPtr presShell; + docShell->GetPresShell(getter_AddRefs(presShell)); + + if (presShell) { + // The docshell is already showing, nothing left to do... + + return NS_OK; + } + + nsCOMPtr docShellTreeItem(do_QueryInterface(docShell)); + + nsCOMPtr parentDocShellTreeItem; + docShellTreeItem->GetParent(getter_AddRefs(parentDocShellTreeItem)); + + nsCOMPtr parentDocShell = + do_QueryInterface(parentDocShellTreeItem); + + nsCOMPtr parentPresShell; + parentDocShell->GetPresShell(getter_AddRefs(parentPresShell)); + + nsCOMPtr content; + GetParentContent(getter_AddRefs(content)); + + // pass along marginwidth, marginheight, scrolling so sub document + // can use it + docShell->SetMarginWidth(GetMarginWidth(aPresContext, content)); + docShell->SetMarginHeight(GetMarginHeight(aPresContext, content)); // Current and initial scrolling is set so that all succeeding docs // will use the scrolling value set here, regardless if scrolling is // set by viewing a particular document (e.g. XUL turns off scrolling) - nsCOMPtr scrollableContainer(do_QueryInterface(mSubShell)); + nsCOMPtr scrollableContainer(do_QueryInterface(docShell)); + if (scrollableContainer) { scrollableContainer->SetDefaultScrollbarPreferences(nsIScrollable::ScrollOrientation_Y, - GetScrolling(parentContent)); + GetScrolling(content)); scrollableContainer->SetDefaultScrollbarPreferences(nsIScrollable::ScrollOrientation_X, - GetScrolling(parentContent)); + GetScrolling(content)); } - nsCOMPtr docShellAsItem(do_QueryInterface(mSubShell)); + nsCOMPtr docShellAsItem(do_QueryInterface(docShell)); NS_ENSURE_TRUE(docShellAsItem, NS_ERROR_FAILURE); - nsString frameName; - if (GetName(parentContent, frameName)) { - docShellAsItem->SetName(frameName.get()); - } - - // If our container is a web-shell, inform it that it has a new - // child. If it's not a web-shell then some things will not operate - // properly. - nsCOMPtr container; - aPresContext->GetContainer(getter_AddRefs(container)); - if (container) { - nsCOMPtr parentAsNode(do_QueryInterface(container)); - if (parentAsNode) { - nsCOMPtr parentAsItem(do_QueryInterface(parentAsNode)); - PRInt32 parentType; - parentAsItem->GetItemType(&parentType); - - nsIAtom* typeAtom = NS_NewAtom("type"); - nsAutoString value, valuePiece; - PRBool isContent; - - isContent = PR_FALSE; - if (NS_SUCCEEDED(parentContent->GetAttr(kNameSpaceID_None, - typeAtom, value))) { - - // we accept "content" and "content-xxx" values. - // at time of writing, we expect "xxx" to be "primary", but - // someday it might be an integer expressing priority - value.Left(valuePiece, 7); - if (valuePiece.EqualsIgnoreCase("content") && - (value.Length() == 7 || - value.Mid(valuePiece, 7, 1) == 1 && valuePiece.Equals(NS_LITERAL_STRING("-")))) - isContent = PR_TRUE; - } - NS_IF_RELEASE(typeAtom); - if (isContent) { - // The web shell's type is content. - docShellAsItem->SetItemType(nsIDocShellTreeItem::typeContent); - } else { - // Inherit our type from our parent webshell. If it is - // chrome, we'll be chrome. If it is content, we'll be - // content. - docShellAsItem->SetItemType(parentType); - } - - parentAsNode->AddChild(docShellAsItem); - - if (isContent) { - nsCOMPtr parentTreeOwner; - parentAsItem->GetTreeOwner(getter_AddRefs(parentTreeOwner)); - if(parentTreeOwner) - parentTreeOwner->ContentShellAdded(docShellAsItem, - value.EqualsIgnoreCase("content-primary") ? PR_TRUE : PR_FALSE, - value.get()); - } - // connect the container... - nsCOMPtr webShell(do_QueryInterface(mSubShell)); - nsCOMPtr outerContainer(do_QueryInterface(container)); - if (outerContainer) - webShell->SetContainer(outerContainer); - - - // Make sure all shells have links back to the content element in the - // nearest enclosing chrome shell. - nsCOMPtr parentShell(do_QueryInterface(parentAsNode)); - nsCOMPtr chromeEventHandler; - if (parentType == nsIDocShellTreeItem::typeChrome) { - // Our parent shell is a chrome shell. It is therefore our nearest - // enclosing chrome shell. - chromeEventHandler = do_QueryInterface(mContent); - NS_WARN_IF_FALSE(chromeEventHandler, "This mContent should implement this."); - } - else { - // Our parent shell is a content shell. Get the chrome info from - // it and use that for our shell as well. - parentShell->GetChromeEventHandler(getter_AddRefs(chromeEventHandler)); - } - - docShell->SetChromeEventHandler(chromeEventHandler); - } - } nsCOMPtr widget; + rv = CreateViewAndWidget(aPresContext, getter_AddRefs(widget)); if (NS_FAILED(rv)) { return rv; } - mSubShell->InitWindow(nsnull, widget, 0, 0, 10, 10); - mSubShell->Create(); + nsCOMPtr baseWindow(do_QueryInterface(docShell)); - mSubShell->SetVisibility(PR_TRUE); + if (baseWindow) { + baseWindow->InitWindow(nsnull, widget, 0, 0, 10, 10); + + // This is kinda whacky, this "Create()" calldoesn't really create + // anything, one starts to wonder why this was named "Create"... + + baseWindow->Create(); + + baseWindow->SetVisibility(PR_TRUE); + } return NS_OK; } -nsresult -nsHTMLFrameInnerFrame::DoLoadURL(nsIPresContext* aPresContext) -{ - // Bug 8065: Preventing frame nesting recursion - if the frames are - // too deep we don't create a mSubShell, so this isn't an assert: - if (!mSubShell) return NS_OK; - - // Prevent recursion - mCreatingViewer=PR_TRUE; - - // Get the URL to load - nsCOMPtr parentContent; - nsresult rv = GetParentContent(*getter_AddRefs(parentContent)); - NS_ENSURE_TRUE(NS_SUCCEEDED(rv) && parentContent, rv); - - nsAutoString url; - GetURL(parentContent, url); - url.Trim(" \t\n\r"); - if (url.IsEmpty()) // Load about:blank into a frame if not URL is specified (bug 35986) - url = NS_LITERAL_STRING("about:blank"); - - // Make an absolute URL - nsCOMPtr baseURL; - nsCOMPtr htmlContent = do_QueryInterface(parentContent, &rv); - nsCOMPtr doc; - if (NS_SUCCEEDED(rv) && htmlContent) { - htmlContent->GetBaseURL(*getter_AddRefs(baseURL)); - (void) htmlContent->GetDocument(*getter_AddRefs(doc)); - } - else { - rv = parentContent->GetDocument(*getter_AddRefs(doc)); - if (NS_SUCCEEDED(rv) && doc) { - doc->GetBaseURL(*getter_AddRefs(baseURL)); - } - } - if (!baseURL) return NS_ERROR_NULL_POINTER; - - nsAutoString docCharset; - if (doc) - (void) doc->GetDocumentCharacterSet(docCharset); - - nsAutoString absURL; - rv = NS_MakeAbsoluteURI(absURL, url, baseURL); - NS_ENSURE_SUCCESS(rv, rv); - - nsCOMPtr uri; - NS_NewURI(getter_AddRefs(uri), absURL, - docCharset.IsEmpty() ? nsnull : NS_ConvertUCS2toUTF8(docCharset).get()); - - // Check for security - nsCOMPtr secMan = - do_GetService(NS_SCRIPTSECURITYMANAGER_CONTRACTID, &rv); - NS_ENSURE_SUCCESS(rv, rv); - - // Get base URL - nsCOMPtr baseURI; - rv = aPresContext->GetBaseURL(getter_AddRefs(baseURI)); - - // Get docshell and create load info - nsCOMPtr docShell(do_QueryInterface(mSubShell)); - NS_ENSURE_TRUE(docShell, NS_ERROR_FAILURE); - nsCOMPtr loadInfo; - docShell->CreateLoadInfo(getter_AddRefs(loadInfo)); - NS_ENSURE_TRUE(loadInfo, NS_ERROR_FAILURE); - - // Get referring URL - nsCOMPtr referrer; - nsCOMPtr principal; - rv = secMan->GetSubjectPrincipal(getter_AddRefs(principal)); - NS_ENSURE_SUCCESS(rv, rv); - // If we were called from script, get the referring URL from the script - if (principal) { - nsCOMPtr codebase = do_QueryInterface(principal); - if (codebase) { - rv = codebase->GetURI(getter_AddRefs(referrer)); - NS_ENSURE_SUCCESS(rv, rv); - } - // Pass the script principal to the docshell - nsCOMPtr owner = do_QueryInterface(principal); - loadInfo->SetOwner(owner); - } - if (!referrer) { // We're not being called form script, tell the docshell - // to inherit an owner from the current document. - loadInfo->SetInheritOwner(PR_TRUE); - referrer = baseURI; - } - - loadInfo->SetReferrer(referrer); - - // Check if we are allowed to load absURL - nsCOMPtr newURI; - rv = NS_NewURI(getter_AddRefs(newURI), absURL, nsnull, baseURI); - NS_ENSURE_SUCCESS(rv, rv); - rv = secMan->CheckLoadURI(referrer, newURI, nsIScriptSecurityManager::STANDARD); - if (NS_FAILED(rv)) - return rv; // We're not - - nsCOMPtr webProgress(do_GetInterface(mSubShell)); - - if (webProgress) { - webProgress->AddProgressListener(this); - } - - rv = docShell->LoadURI(uri, loadInfo, nsIWebNavigation::LOAD_FLAGS_NONE, PR_FALSE); - NS_ASSERTION(NS_SUCCEEDED(rv), "failed to load URL"); - - return rv; -} - - nsresult nsHTMLFrameInnerFrame::CreateViewAndWidget(nsIPresContext* aPresContext, nsIWidget** aWidget) @@ -1242,28 +1060,29 @@ nsHTMLFrameInnerFrame::CreateViewAndWidget(nsIPresContext* aPresContext, nsCOMPtr presShell; aPresContext->GetShell(getter_AddRefs(presShell)); - if (!presShell) return NS_ERROR_FAILURE; + NS_ENSURE_TRUE(presShell, NS_ERROR_FAILURE); float t2p; aPresContext->GetTwipsToPixels(&t2p); // create, init, set the parent of the view nsIView* view; - nsresult rv = nsComponentManager::CreateInstance(kCViewCID, nsnull, NS_GET_IID(nsIView), - (void **)&view); + nsresult rv = nsComponentManager::CreateInstance(kCViewCID, nsnull, + NS_GET_IID(nsIView), + (void **)&view); + if (NS_FAILED(rv)) { + NS_ERROR("Could not create view for nsHTMLFrame"); - if (NS_OK != rv) { - NS_ASSERTION(0, "Could not create view for nsHTMLFrame"); return rv; } nsIView* parView; nsPoint origin; - GetOffsetFromView(aPresContext, origin, &parView); + GetOffsetFromView(aPresContext, origin, &parView); nsRect viewBounds(origin.x, origin.y, 10, 10); nsCOMPtr viewMan; - presShell->GetViewManager(getter_AddRefs(viewMan)); + presShell->GetViewManager(getter_AddRefs(viewMan)); rv = view->Init(viewMan, viewBounds, parView); // XXX put it at the end of the document order until we can do better viewMan->InsertChild(parView, view, nsnull, PR_TRUE); @@ -1292,41 +1111,39 @@ nsHTMLFrameInnerFrame::Init(nsIPresContext* aPresContext, nsIStyleContext* aContext, nsIFrame* aPrevInFlow) { - nsresult rv = nsLeafFrame::Init(aPresContext, aContent, aParent, aContext, aPrevInFlow); + nsresult rv = nsLeafFrame::Init(aPresContext, aContent, aParent, aContext, + aPrevInFlow); if (NS_FAILED(rv)) return rv; // determine if we are a printcontext PRBool shouldCreateDoc = PR_TRUE; - nsCOMPtr thePrinterContext = do_QueryInterface(aPresContext); - if (thePrinterContext) { + nsCOMPtr thePrinterContext(do_QueryInterface(aPresContext)); + + if (thePrinterContext) { // we are printing shouldCreateDoc = PR_FALSE; } - // for print preview we want to create the view and widget but + // for print preview we want to create the view and widget but // we do not want to load the document, it is alerady loaded. - nsCOMPtr thePrintPreviewContext = do_QueryInterface(aPresContext); - if (thePrintPreviewContext) { + nsCOMPtr thePrintPreviewContext = + do_QueryInterface(aPresContext); + + if (thePrintPreviewContext) { nsCOMPtr widget; rv = CreateViewAndWidget(aPresContext, getter_AddRefs(widget)); + if (NS_FAILED(rv)) { return rv; } + // we are in PrintPreview shouldCreateDoc = PR_FALSE; } - - if (!mCreatingViewer && shouldCreateDoc) { - // create the web shell - // we do this even if the size is not positive (bug 11762) - // we do this even if there is no src (bug 16218) - if (!mSubShell) - rv = CreateDocShell(aPresContext); - // Whether or not we had to create a webshell, load the document - if (NS_SUCCEEDED(rv)) { - DoLoadURL(aPresContext); - } + + if (shouldCreateDoc) { + ShowDocShell(aPresContext); } return NS_OK; @@ -1347,41 +1164,55 @@ nsHTMLFrameInnerFrame::Reflow(nsIPresContext* aPresContext, nsresult rv = NS_OK; - // use the max size set in aReflowState by the nsHTMLFrameOuterFrame as our size + // use the max size set in aReflowState by the nsHTMLFrameOuterFrame + // as our size GetDesiredSize(aPresContext, aReflowState, aDesiredSize); aStatus = NS_FRAME_COMPLETE; + nsCOMPtr docShell; + GetDocShell(getter_AddRefs(docShell)); + + nsCOMPtr baseWindow(do_QueryInterface(docShell)); + // resize the sub document - if(mSubShell) { + if (baseWindow) { float t2p; aPresContext->GetTwipsToPixels(&t2p); PRInt32 x = 0; PRInt32 y = 0; - mSubShell->GetPositionAndSize(&x, &y, nsnull, nsnull); - PRInt32 cx = NSToCoordRound(aDesiredSize.width * t2p); + baseWindow->GetPositionAndSize(&x, &y, nsnull, nsnull); + PRInt32 cx = NSToCoordRound(aDesiredSize.width * t2p); PRInt32 cy = NSToCoordRound(aDesiredSize.height * t2p); - mSubShell->SetPositionAndSize(x, y, cx, cy, PR_FALSE); + baseWindow->SetPositionAndSize(x, y, cx, cy, PR_FALSE); NS_FRAME_TRACE(NS_FRAME_TRACE_CALLS, - ("exit nsHTMLFrameInnerFrame::Reflow: size=%d,%d rv=%x", - aDesiredSize.width, aDesiredSize.height, aStatus)); + ("exit nsHTMLFrameInnerFrame::Reflow: size=%d,%d rv=%x", + aDesiredSize.width, aDesiredSize.height, aStatus)); } - + return rv; } // load a new url nsresult -nsHTMLFrameInnerFrame::ReloadURL(nsIPresContext* aPresContext) +nsHTMLFrameInnerFrame::ReloadURL() { - return DoLoadURL(aPresContext); + if (!mOwnsFrameLoader || !mFrameLoader) { + // If we don't own the frame loader, we're not in charge of what's + // loaded into it. + + return NS_OK; + } + + return mFrameLoader->LoadFrame(); } -void + +void nsHTMLFrameInnerFrame::GetDesiredSize(nsIPresContext* aPresContext, const nsHTMLReflowState& aReflowState, nsHTMLReflowMetrics& aDesiredSize) @@ -1391,19 +1222,28 @@ nsHTMLFrameInnerFrame::GetDesiredSize(nsIPresContext* aPresContext, aDesiredSize.ascent = aDesiredSize.height; aDesiredSize.descent = 0; - // For unknown reasons, the maxElementSize for the InnerFrame is used, but the - // maxElementSize for the OuterFrame is ignored, make sure to get it right here! + // For unknown reasons, the maxElementSize for the InnerFrame is + // used, but the maxElementSize for the OuterFrame is ignored, make + // sure to get it right here! + if (aDesiredSize.maxElementSize) { if ((NS_UNCONSTRAINEDSIZE == aReflowState.availableWidth) || - (eStyleUnit_Percent == aReflowState.mStylePosition->mWidth.GetUnit())) { - aDesiredSize.maxElementSize->width = 0; // percent width springy down to 0 px + (eStyleUnit_Percent == + aReflowState.mStylePosition->mWidth.GetUnit())) { + // percent width springy down to 0 px + + aDesiredSize.maxElementSize->width = 0; } else { aDesiredSize.maxElementSize->width = aDesiredSize.width; } + if ((NS_UNCONSTRAINEDSIZE == aReflowState.availableHeight) || - (eStyleUnit_Percent == aReflowState.mStylePosition->mHeight.GetUnit())) { - aDesiredSize.maxElementSize->height = 0; // percent height springy down to 0px + (eStyleUnit_Percent == + aReflowState.mStylePosition->mHeight.GetUnit())) { + // percent height springy down to 0px + + aDesiredSize.maxElementSize->height = 0; } else { aDesiredSize.maxElementSize->height = aDesiredSize.height; @@ -1411,9 +1251,9 @@ nsHTMLFrameInnerFrame::GetDesiredSize(nsIPresContext* aPresContext, } } -/******************************************************************************* +/****************************************************************************** * FrameLoadingInfo - ******************************************************************************/ + *****************************************************************************/ FrameLoadingInfo::FrameLoadingInfo(const nsSize& aSize) { NS_INIT_REFCNT(); diff --git a/mozilla/layout/html/document/src/nsFrameSetFrame.cpp b/mozilla/layout/html/document/src/nsFrameSetFrame.cpp index a1a4b002844..eecf2c845bc 100644 --- a/mozilla/layout/html/document/src/nsFrameSetFrame.cpp +++ b/mozilla/layout/html/document/src/nsFrameSetFrame.cpp @@ -63,7 +63,6 @@ #define ALL_VIS 0x000F #define NONE_VIS 0x0000 -static NS_DEFINE_IID(kIFramesetFrameIID, NS_IFRAMESETFRAME_IID); static NS_DEFINE_IID(kLookAndFeelCID, NS_LOOKANDFEEL_CID); /******************************************************************************* @@ -252,7 +251,7 @@ nsresult nsHTMLFramesetFrame::QueryInterface(const nsIID& aIID, { if (NULL == aInstancePtr) { return NS_ERROR_NULL_POINTER; - } else if (aIID.Equals(kIFramesetFrameIID)) { + } else if (aIID.Equals(NS_GET_IID(nsHTMLFramesetFrame))) { *aInstancePtr = (void*)this; return NS_OK; } else if (aIID.Equals(NS_GET_IID(nsIObserver))) { @@ -327,7 +326,8 @@ nsHTMLFramesetFrame::Init(nsIPresContext* aPresContext, mTopLevelFrameset = (nsHTMLFramesetFrame*)this; while (parentFrame) { nsHTMLFramesetFrame* frameset; - rv = parentFrame->QueryInterface(kIFramesetFrameIID, (void**)&frameset); + rv = parentFrame->QueryInterface(NS_GET_IID(nsHTMLFramesetFrame), + (void**)&frameset); if (NS_SUCCEEDED(rv)) { mTopLevelFrameset = frameset; parentFrame->GetParent((nsIFrame**)&parentFrame); @@ -1404,7 +1404,7 @@ PRBool nsHTMLFramesetFrame::ChildIsFrameset(nsIFrame* aChild) { nsIFrame* childFrame = nsnull; - aChild->QueryInterface(kIFramesetFrameIID, (void**)&childFrame); + aChild->QueryInterface(NS_GET_IID(nsHTMLFramesetFrame), (void**)&childFrame); if (childFrame) { return PR_TRUE; } diff --git a/mozilla/layout/html/document/src/nsFrameSetFrame.h b/mozilla/layout/html/document/src/nsFrameSetFrame.h index fe786185fd8..88000505dff 100644 --- a/mozilla/layout/html/document/src/nsFrameSetFrame.h +++ b/mozilla/layout/html/document/src/nsFrameSetFrame.h @@ -57,7 +57,8 @@ struct nsGUIEvent; class nsHTMLFramesetFrame; #define NS_IFRAMESETFRAME_IID \ -{ 0xf47deac0, 0x4200, 0x11d2, { 0x80, 0x3c, 0x0, 0x60, 0x8, 0x15, 0xa7, 0x91 } } +{ 0xf47deac0, 0x4200, 0x11d2, \ + { 0x80, 0x3c, 0x0, 0x60, 0x8, 0x15, 0xa7, 0x91 } } #define NO_COLOR 0xFFFFFFFA @@ -115,8 +116,10 @@ struct nsFramesetDrag { class nsHTMLFramesetFrame : public nsHTMLContainerFrame, public nsIObserver { - public: + // Woohoo, concrete class with an IID! + NS_DEFINE_STATIC_IID_ACCESSOR(NS_IFRAMESETFRAME_IID) + nsHTMLFramesetFrame(); virtual ~nsHTMLFramesetFrame(); diff --git a/mozilla/layout/style/nsCSSStyleSheet.cpp b/mozilla/layout/style/nsCSSStyleSheet.cpp index 0bdc6d98e1f..264fc37440e 100644 --- a/mozilla/layout/style/nsCSSStyleSheet.cpp +++ b/mozilla/layout/style/nsCSSStyleSheet.cpp @@ -2657,7 +2657,7 @@ CSSStyleSheetImpl::SetDisabled(PRBool aDisabled) PRBool oldState = mDisabled; mDisabled = aDisabled; - if ((nsnull != mDocument) && (mDisabled != oldState)) { + if (mDocument && (mDisabled != oldState)) { mDocument->SetStyleSheetDisabledState(this, mDisabled); } diff --git a/mozilla/layout/xul/base/src/nsBrowserBoxObject.cpp b/mozilla/layout/xul/base/src/nsBrowserBoxObject.cpp index 0bd87006df5..868e2563339 100644 --- a/mozilla/layout/xul/base/src/nsBrowserBoxObject.cpp +++ b/mozilla/layout/xul/base/src/nsBrowserBoxObject.cpp @@ -38,9 +38,9 @@ #include "nsCOMPtr.h" #include "nsIBrowserBoxObject.h" #include "nsBoxObject.h" -#include "nsIPresShell.h" #include "nsIFrame.h" #include "nsIDocShell.h" +#include "nsIDocument.h" #include "nsXPIDLString.h" class nsBrowserBoxObject : public nsIBrowserBoxObject, public nsBoxObject @@ -91,15 +91,27 @@ nsBrowserBoxObject::~nsBrowserBoxObject() NS_IMETHODIMP nsBrowserBoxObject::GetDocShell(nsIDocShell** aResult) { *aResult = nsnull; + if (!mPresShell) return NS_OK; - nsCOMPtr subShell; - mPresShell->GetSubShellFor(mContent, getter_AddRefs(subShell)); - if(!subShell) - return NS_OK; + nsCOMPtr doc, sub_doc; + mPresShell->GetDocument(getter_AddRefs(doc)); - return CallQueryInterface(subShell, aResult); //Addref happens here. + doc->GetSubDocumentFor(mContent, getter_AddRefs(sub_doc)); + + if (!sub_doc) { + return NS_OK; + } + + nsCOMPtr container; + sub_doc->GetContainer(getter_AddRefs(container)); + + if (!container) { + return NS_OK; + } + + return CallQueryInterface(container, aResult); } // Creation Routine /////////////////////////////////////////////////////////////////////// diff --git a/mozilla/layout/xul/base/src/nsEditorBoxObject.cpp b/mozilla/layout/xul/base/src/nsEditorBoxObject.cpp index ff597efeb25..7e48b0b6d11 100644 --- a/mozilla/layout/xul/base/src/nsEditorBoxObject.cpp +++ b/mozilla/layout/xul/base/src/nsEditorBoxObject.cpp @@ -38,7 +38,7 @@ #include "nsCOMPtr.h" #include "nsIEditorBoxObject.h" #include "nsBoxObject.h" -#include "nsIPresShell.h" +#include "nsIDocument.h" #include "nsIFrame.h" #include "nsIEditorShell.h" #include "nsIComponentManager.h" @@ -128,15 +128,27 @@ NS_IMETHODIMP nsEditorBoxObject::GetEditorShell(nsIEditorShell** aResult) NS_IMETHODIMP nsEditorBoxObject::GetDocShell(nsIDocShell** aResult) { *aResult = nsnull; + if (!mPresShell) return NS_OK; - nsCOMPtr subShell; - mPresShell->GetSubShellFor(mContent, getter_AddRefs(subShell)); - if(!subShell) - return NS_OK; + nsCOMPtr doc, sub_doc; + mPresShell->GetDocument(getter_AddRefs(doc)); - return CallQueryInterface(subShell, aResult); //Addref happens here. + doc->GetSubDocumentFor(mContent, getter_AddRefs(sub_doc)); + + if (!sub_doc) { + return NS_OK; + } + + nsCOMPtr container; + sub_doc->GetContainer(getter_AddRefs(container)); + + if (!container) { + return NS_OK; + } + + return CallQueryInterface(container, aResult); } // Creation Routine /////////////////////////////////////////////////////////////////////// diff --git a/mozilla/layout/xul/base/src/nsIFrameBoxObject.cpp b/mozilla/layout/xul/base/src/nsIFrameBoxObject.cpp index 4f8dbe35690..8179e508870 100644 --- a/mozilla/layout/xul/base/src/nsIFrameBoxObject.cpp +++ b/mozilla/layout/xul/base/src/nsIFrameBoxObject.cpp @@ -38,6 +38,7 @@ #include "nsCOMPtr.h" #include "nsIIFrameBoxObject.h" #include "nsBoxObject.h" +#include "nsIDocument.h" #include "nsIPresShell.h" #include "nsIFrame.h" #include "nsIDocShell.h" @@ -87,15 +88,27 @@ nsIFrameBoxObject::~nsIFrameBoxObject() NS_IMETHODIMP nsIFrameBoxObject::GetDocShell(nsIDocShell** aResult) { *aResult = nsnull; + if (!mPresShell) return NS_OK; - nsCOMPtr subShell; - mPresShell->GetSubShellFor(mContent, getter_AddRefs(subShell)); - if(!subShell) - return NS_OK; + nsCOMPtr doc, sub_doc; + mPresShell->GetDocument(getter_AddRefs(doc)); - return CallQueryInterface(subShell, aResult); //Addref happens here. + doc->GetSubDocumentFor(mContent, getter_AddRefs(sub_doc)); + + if (!sub_doc) { + return NS_OK; + } + + nsCOMPtr container; + sub_doc->GetContainer(getter_AddRefs(container)); + + if (!container) { + return NS_OK; + } + + return CallQueryInterface(container, aResult); } // Creation Routine /////////////////////////////////////////////////////////////////////// diff --git a/mozilla/uriloader/base/nsDocLoader.cpp b/mozilla/uriloader/base/nsDocLoader.cpp index dfe2a08af83..6771143f506 100644 --- a/mozilla/uriloader/base/nsDocLoader.cpp +++ b/mozilla/uriloader/base/nsDocLoader.cpp @@ -1,4 +1,4 @@ -/* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */ +/* -*- Mode: C++; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*- */ /* ***** BEGIN LICENSE BLOCK ***** * Version: NPL 1.1/GPL 2.0/LGPL 2.1 * @@ -804,7 +804,7 @@ nsDocLoaderImpl::GetDOMWindow(nsIDOMWindow **aResult) *aResult = window; NS_IF_ADDREF(*aResult); } else { - rv = NS_ERROR_FAILURE; + rv = NS_ERROR_FAILURE; } return rv;