1998-04-13 20:24:54 +00:00
|
|
|
/* -*- Mode: C++; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*-
|
|
|
|
*
|
1999-11-06 03:40:37 +00:00
|
|
|
* The contents of this file are subject to the Netscape Public
|
|
|
|
* License Version 1.1 (the "License"); you may not use this file
|
|
|
|
* except in compliance with the License. You may obtain a copy of
|
|
|
|
* the License at http://www.mozilla.org/NPL/
|
1998-04-13 20:24:54 +00:00
|
|
|
*
|
1999-11-06 03:40:37 +00:00
|
|
|
* Software distributed under the License is distributed on an "AS
|
|
|
|
* IS" basis, WITHOUT WARRANTY OF ANY KIND, either express or
|
|
|
|
* implied. See the License for the specific language governing
|
|
|
|
* rights and limitations under the License.
|
1998-04-13 20:24:54 +00:00
|
|
|
*
|
1999-11-06 03:40:37 +00:00
|
|
|
* The Original Code is mozilla.org code.
|
|
|
|
*
|
|
|
|
* The Initial Developer of the Original Code is Netscape
|
1998-04-13 20:24:54 +00:00
|
|
|
* Communications Corporation. Portions created by Netscape are
|
1999-11-06 03:40:37 +00:00
|
|
|
* Copyright (C) 1998 Netscape Communications Corporation. All
|
|
|
|
* Rights Reserved.
|
|
|
|
*
|
|
|
|
* Contributor(s):
|
2000-02-02 22:24:56 +00:00
|
|
|
* Pierre Phaneuf <pp@ludusdesign.com>
|
1998-05-21 20:37:41 +00:00
|
|
|
*/
|
1999-08-24 07:38:00 +00:00
|
|
|
#define NS_IMPL_IDS
|
|
|
|
#include "nsICharsetAlias.h"
|
|
|
|
#undef NS_IMPL_IDS
|
|
|
|
|
1999-02-12 17:45:58 +00:00
|
|
|
#include "nsCOMPtr.h"
|
1999-08-09 19:10:24 +00:00
|
|
|
#include "nsXPIDLString.h"
|
1998-04-13 20:24:54 +00:00
|
|
|
#include "nsHTMLDocument.h"
|
|
|
|
#include "nsIParser.h"
|
1999-07-14 15:33:48 +00:00
|
|
|
#include "nsIParserFilter.h"
|
1998-04-13 20:24:54 +00:00
|
|
|
#include "nsIHTMLContentSink.h"
|
|
|
|
#include "nsHTMLParts.h"
|
|
|
|
#include "nsIHTMLStyleSheet.h"
|
1998-05-13 23:43:44 +00:00
|
|
|
#include "nsIHTMLCSSStyleSheet.h"
|
1998-04-13 20:24:54 +00:00
|
|
|
#include "nsIStyleSet.h"
|
|
|
|
#include "nsHTMLAtoms.h"
|
1998-11-11 11:55:32 +00:00
|
|
|
#include "nsIPresShell.h"
|
1998-06-23 00:52:21 +00:00
|
|
|
#include "nsIPresContext.h"
|
1998-05-04 17:54:45 +00:00
|
|
|
#include "nsIHTMLContent.h"
|
1998-09-04 15:41:20 +00:00
|
|
|
#include "nsIDOMNode.h" // for Find
|
1999-01-19 23:07:33 +00:00
|
|
|
#include "nsIDOMNodeList.h"
|
1998-05-04 17:54:45 +00:00
|
|
|
#include "nsIDOMElement.h"
|
1998-05-04 20:34:37 +00:00
|
|
|
#include "nsIDOMText.h"
|
1999-02-16 07:38:27 +00:00
|
|
|
#include "nsIDOMComment.h"
|
1999-05-18 23:44:55 +00:00
|
|
|
#include "nsIDOMWindow.h"
|
1998-09-23 17:16:51 +00:00
|
|
|
#include "nsIDOMHTMLFormElement.h"
|
1998-07-01 11:16:09 +00:00
|
|
|
#include "nsIStreamListener.h"
|
1998-06-17 23:13:28 +00:00
|
|
|
#include "nsIURL.h"
|
1999-06-18 17:34:08 +00:00
|
|
|
#include "nsIIOService.h"
|
1999-06-23 03:29:44 +00:00
|
|
|
#include "nsIURL.h"
|
1999-11-30 04:50:42 +00:00
|
|
|
#include "nsNetUtil.h"
|
1999-11-19 07:35:27 +00:00
|
|
|
#include "nsIContentViewerContainer.h"
|
|
|
|
#include "nsIContentViewer.h"
|
|
|
|
#include "nsIMarkupDocumentViewer.h"
|
1998-07-18 21:47:56 +00:00
|
|
|
#include "nsIWebShell.h"
|
2000-03-11 00:35:36 +00:00
|
|
|
#include "nsIDocShell.h"
|
|
|
|
#include "nsIDocShellTreeItem.h"
|
1999-11-27 03:11:10 +00:00
|
|
|
#include "nsIBaseWindow.h"
|
1999-07-14 15:33:48 +00:00
|
|
|
#include "nsIWebShellServices.h"
|
1998-07-17 06:30:00 +00:00
|
|
|
#include "nsIDocumentLoader.h"
|
1998-07-02 08:14:22 +00:00
|
|
|
#include "CNavDTD.h"
|
1998-07-22 23:32:19 +00:00
|
|
|
#include "nsIScriptGlobalObject.h"
|
|
|
|
#include "nsContentList.h"
|
1999-09-08 23:18:27 +00:00
|
|
|
#include "nsDOMError.h"
|
1999-10-02 03:41:37 +00:00
|
|
|
#include "nsICodebasePrincipal.h"
|
|
|
|
#include "nsIScriptSecurityManager.h"
|
1999-06-18 17:34:08 +00:00
|
|
|
|
|
|
|
#include "nsIIOService.h"
|
1999-08-19 22:23:20 +00:00
|
|
|
#include "nsICookieService.h"
|
1999-06-18 17:34:08 +00:00
|
|
|
|
1999-09-30 22:07:04 +00:00
|
|
|
#include "nsIParserService.h"
|
1998-09-17 00:55:35 +00:00
|
|
|
#include "nsIServiceManager.h"
|
1998-08-04 00:05:22 +00:00
|
|
|
#include "nsIFormManager.h"
|
1999-03-09 09:44:27 +00:00
|
|
|
#include "nsIComponentManager.h"
|
1998-07-30 22:42:27 +00:00
|
|
|
#include "nsParserCIID.h"
|
1998-11-12 22:25:51 +00:00
|
|
|
#include "nsIDOMHTMLElement.h"
|
1999-01-09 00:15:19 +00:00
|
|
|
#include "nsIDOMHTMLMapElement.h"
|
1999-02-04 02:58:02 +00:00
|
|
|
#include "nsIDOMHTMLBodyElement.h"
|
1998-12-20 01:21:23 +00:00
|
|
|
#include "nsINameSpaceManager.h"
|
1999-07-07 04:52:27 +00:00
|
|
|
#include "nsGenericHTMLElement.h"
|
1999-01-19 16:58:45 +00:00
|
|
|
#include "nsGenericDOMNodeList.h"
|
1999-05-18 23:06:31 +00:00
|
|
|
#include "nsICSSLoader.h"
|
1999-08-09 19:10:24 +00:00
|
|
|
#include "nsIHTTPChannel.h"
|
2000-01-24 21:28:28 +00:00
|
|
|
#include "nsIFile.h"
|
1999-09-21 14:18:52 +00:00
|
|
|
#include "nsIEventListenerManager.h"
|
1999-11-14 00:34:15 +00:00
|
|
|
#include "nsISelectElement.h"
|
1999-07-14 15:33:48 +00:00
|
|
|
|
|
|
|
#include "nsICharsetDetector.h"
|
|
|
|
#include "nsICharsetDetectionAdaptor.h"
|
|
|
|
#include "nsCharsetDetectionAdaptorCID.h"
|
1999-08-24 07:38:00 +00:00
|
|
|
#include "nsICharsetAlias.h"
|
1999-07-14 15:33:48 +00:00
|
|
|
#include "nsIPref.h"
|
1999-12-18 20:29:29 +00:00
|
|
|
#include "nsLayoutUtils.h"
|
|
|
|
|
1999-09-23 02:10:15 +00:00
|
|
|
#define DETECTOR_PROGID_MAX 127
|
|
|
|
static char g_detector_progid[DETECTOR_PROGID_MAX + 1];
|
1999-07-14 15:33:48 +00:00
|
|
|
static PRBool gInitDetector = PR_FALSE;
|
|
|
|
static PRBool gPlugDetector = PR_FALSE;
|
|
|
|
|
1999-09-22 08:49:28 +00:00
|
|
|
|
1998-12-07 06:10:12 +00:00
|
|
|
#ifdef PCB_USE_PROTOCOL_CONNECTION
|
|
|
|
// beard: how else would we get the referrer to a URL?
|
|
|
|
#include "nsIProtocolConnection.h"
|
|
|
|
#include "net.h"
|
|
|
|
#endif
|
1998-07-10 05:35:23 +00:00
|
|
|
|
1999-07-14 17:13:05 +00:00
|
|
|
#include "prmem.h"
|
1999-11-12 02:06:54 +00:00
|
|
|
#include "prtime.h"
|
1999-07-14 17:13:05 +00:00
|
|
|
|
1998-08-28 15:55:31 +00:00
|
|
|
// Find/Serach Includes
|
|
|
|
const PRInt32 kForward = 0;
|
|
|
|
const PRInt32 kBackward = 1;
|
|
|
|
|
1999-12-13 21:00:47 +00:00
|
|
|
//#define DEBUG_charset
|
|
|
|
|
1998-08-28 15:55:31 +00:00
|
|
|
|
1998-07-10 05:35:23 +00:00
|
|
|
//#define rickgdebug 1
|
|
|
|
#ifdef rickgdebug
|
|
|
|
#include "nsHTMLContentSinkStream.h"
|
|
|
|
#endif
|
|
|
|
|
1999-05-17 21:17:48 +00:00
|
|
|
// XXX Used to control whether we implement document.layers
|
1999-06-30 00:14:21 +00:00
|
|
|
//#define NS_IMPLEMENT_DOCUMENT_LAYERS
|
1999-05-17 21:17:48 +00:00
|
|
|
|
1998-07-18 21:47:56 +00:00
|
|
|
static NS_DEFINE_IID(kIWebShellIID, NS_IWEB_SHELL_IID);
|
1998-04-13 20:24:54 +00:00
|
|
|
static NS_DEFINE_IID(kIDocumentIID, NS_IDOCUMENT_IID);
|
1998-05-04 20:34:37 +00:00
|
|
|
static NS_DEFINE_IID(kIDOMTextIID, NS_IDOMTEXT_IID);
|
1999-01-19 23:07:33 +00:00
|
|
|
static NS_DEFINE_IID(kIDOMNodeListIID, NS_IDOMNODELIST_IID);
|
1998-04-13 20:24:54 +00:00
|
|
|
static NS_DEFINE_IID(kIHTMLDocumentIID, NS_IHTMLDOCUMENT_IID);
|
1998-07-22 23:32:19 +00:00
|
|
|
static NS_DEFINE_IID(kIDOMHTMLDocumentIID, NS_IDOMHTMLDOCUMENT_IID);
|
1998-08-07 23:08:00 +00:00
|
|
|
static NS_DEFINE_IID(kIDOMNSHTMLDocumentIID, NS_IDOMNSHTMLDOCUMENT_IID);
|
1999-06-18 17:34:08 +00:00
|
|
|
|
|
|
|
static NS_DEFINE_IID(kIIOServiceIID, NS_IIOSERVICE_IID);
|
|
|
|
static NS_DEFINE_CID(kIOServiceCID, NS_IOSERVICE_CID);
|
1999-08-19 22:23:20 +00:00
|
|
|
static NS_DEFINE_IID(kCookieServiceCID, NS_COOKIESERVICE_CID);
|
1999-06-18 17:34:08 +00:00
|
|
|
|
1999-08-24 07:38:00 +00:00
|
|
|
|
|
|
|
|
|
|
|
|
1998-11-12 07:54:12 +00:00
|
|
|
static NS_DEFINE_IID(kIHTMLContentContainerIID, NS_IHTMLCONTENTCONTAINER_IID);
|
1999-02-04 02:58:02 +00:00
|
|
|
static NS_DEFINE_IID(kIDOMHTMLBodyElementIID, NS_IDOMHTMLBODYELEMENT_IID);
|
1998-10-06 01:39:33 +00:00
|
|
|
|
1999-07-14 15:33:48 +00:00
|
|
|
static NS_DEFINE_IID(kIParserFilterIID, NS_IPARSERFILTER_IID);
|
1999-09-23 02:10:15 +00:00
|
|
|
static int
|
|
|
|
MyPrefChangedCallback(const char*aPrefName, void* instance_data)
|
|
|
|
{
|
|
|
|
nsresult rv;
|
|
|
|
NS_WITH_SERVICE(nsIPref, prefs, "component://netscape/preferences", &rv);
|
|
|
|
char* detector_name = nsnull;
|
|
|
|
if(NS_SUCCEEDED(rv) && NS_SUCCEEDED(
|
|
|
|
rv = prefs->CopyCharPref("intl.charset.detector",
|
|
|
|
&detector_name)))
|
|
|
|
{
|
|
|
|
if(nsCRT::strlen(detector_name) > 0) {
|
|
|
|
PL_strncpy(g_detector_progid, NS_CHARSET_DETECTOR_PROGID_BASE,DETECTOR_PROGID_MAX);
|
|
|
|
PL_strncat(g_detector_progid, detector_name,DETECTOR_PROGID_MAX);
|
|
|
|
gPlugDetector = PR_TRUE;
|
|
|
|
} else {
|
|
|
|
g_detector_progid[0]=0;
|
|
|
|
gPlugDetector = PR_FALSE;
|
|
|
|
}
|
|
|
|
PR_FREEIF(detector_name);
|
|
|
|
}
|
|
|
|
return 0;
|
|
|
|
}
|
1999-01-19 16:58:45 +00:00
|
|
|
// ==================================================================
|
|
|
|
// =
|
|
|
|
// ==================================================================
|
1998-04-13 20:24:54 +00:00
|
|
|
NS_LAYOUT nsresult
|
|
|
|
NS_NewHTMLDocument(nsIDocument** aInstancePtrResult)
|
|
|
|
{
|
|
|
|
nsHTMLDocument* doc = new nsHTMLDocument();
|
1999-07-18 06:35:52 +00:00
|
|
|
if(doc)
|
|
|
|
return doc->QueryInterface(kIDocumentIID, (void**) aInstancePtrResult);
|
|
|
|
return NS_ERROR_OUT_OF_MEMORY;
|
1998-04-13 20:24:54 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
nsHTMLDocument::nsHTMLDocument()
|
1998-07-17 23:00:54 +00:00
|
|
|
: nsMarkupDocument(),
|
1998-09-02 02:06:39 +00:00
|
|
|
mAttrStyleSheet(nsnull),
|
1999-01-15 02:01:36 +00:00
|
|
|
mStyleAttrStyleSheet(nsnull),
|
|
|
|
mBaseURL(nsnull),
|
1999-08-09 19:10:24 +00:00
|
|
|
mBaseTarget(nsnull),
|
1999-09-17 06:56:39 +00:00
|
|
|
mLastModified(nsnull),
|
1999-09-26 10:07:16 +00:00
|
|
|
mReferrer(nsnull),
|
|
|
|
mIsWriting(0)
|
1998-04-13 20:24:54 +00:00
|
|
|
{
|
1998-07-22 23:32:19 +00:00
|
|
|
mImages = nsnull;
|
|
|
|
mApplets = nsnull;
|
|
|
|
mEmbeds = nsnull;
|
|
|
|
mLinks = nsnull;
|
|
|
|
mAnchors = nsnull;
|
1999-05-17 21:17:48 +00:00
|
|
|
mLayers = nsnull;
|
1998-08-04 00:05:22 +00:00
|
|
|
mNamedItems = nsnull;
|
1998-07-23 22:06:05 +00:00
|
|
|
mParser = nsnull;
|
1999-07-07 01:27:08 +00:00
|
|
|
mDTDMode = eDTDMode_Nav;
|
1999-05-18 23:06:31 +00:00
|
|
|
mCSSLoader = nsnull;
|
1999-09-15 17:57:16 +00:00
|
|
|
mDocTypeStr=nsnull;
|
1998-08-28 15:55:31 +00:00
|
|
|
|
|
|
|
// Find/Search Init
|
1998-08-28 18:15:14 +00:00
|
|
|
mSearchStr = nsnull;
|
1998-08-28 15:55:31 +00:00
|
|
|
mLastBlockSearchOffset = 0;
|
|
|
|
mAdjustToEnd = PR_FALSE;
|
|
|
|
mShouldMatchCase = PR_FALSE;
|
|
|
|
mIsPreTag = PR_FALSE;
|
|
|
|
|
|
|
|
mHoldBlockContent = nsnull;
|
|
|
|
|
|
|
|
// These will be converted to a nsDeque
|
1998-08-28 18:15:14 +00:00
|
|
|
mStackInx = 0;
|
1998-09-08 22:13:29 +00:00
|
|
|
mParentStack = (nsIDOMNode**) new PRUint32[32];
|
|
|
|
mChildStack = (nsIDOMNode**) new PRUint32[32];
|
1998-09-04 15:41:20 +00:00
|
|
|
mBodyContent = nsnull;
|
1998-09-23 17:16:51 +00:00
|
|
|
mForms = nsnull;
|
1999-02-03 19:38:16 +00:00
|
|
|
mIsWriting = 0;
|
|
|
|
mWriteLevel = 0;
|
1998-04-13 20:24:54 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
nsHTMLDocument::~nsHTMLDocument()
|
|
|
|
{
|
1998-08-15 16:25:33 +00:00
|
|
|
PRInt32 i;
|
1998-09-23 17:16:51 +00:00
|
|
|
|
1998-08-07 23:08:00 +00:00
|
|
|
DeleteNamedItems();
|
1998-07-22 23:32:19 +00:00
|
|
|
NS_IF_RELEASE(mImages);
|
|
|
|
NS_IF_RELEASE(mApplets);
|
|
|
|
NS_IF_RELEASE(mEmbeds);
|
|
|
|
NS_IF_RELEASE(mLinks);
|
|
|
|
NS_IF_RELEASE(mAnchors);
|
1999-05-17 21:17:48 +00:00
|
|
|
NS_IF_RELEASE(mLayers);
|
1998-11-26 01:34:53 +00:00
|
|
|
if (nsnull != mAttrStyleSheet) {
|
|
|
|
mAttrStyleSheet->SetOwningDocument(nsnull);
|
|
|
|
NS_RELEASE(mAttrStyleSheet);
|
|
|
|
}
|
|
|
|
if (nsnull != mStyleAttrStyleSheet) {
|
|
|
|
mStyleAttrStyleSheet->SetOwningDocument(nsnull);
|
|
|
|
NS_RELEASE(mStyleAttrStyleSheet);
|
|
|
|
}
|
1999-01-15 02:01:36 +00:00
|
|
|
NS_IF_RELEASE(mBaseURL);
|
|
|
|
if (nsnull != mBaseTarget) {
|
|
|
|
delete mBaseTarget;
|
|
|
|
mBaseTarget = nsnull;
|
|
|
|
}
|
1999-08-09 19:10:24 +00:00
|
|
|
if (nsnull != mLastModified) {
|
1999-09-17 06:56:39 +00:00
|
|
|
nsString::Recycle(mLastModified);
|
1999-08-09 19:10:24 +00:00
|
|
|
mLastModified = nsnull;
|
|
|
|
}
|
1999-09-17 06:56:39 +00:00
|
|
|
if (nsnull != mReferrer) {
|
|
|
|
nsString::Recycle(mReferrer);
|
|
|
|
mReferrer = nsnull;
|
|
|
|
}
|
1998-07-23 22:06:05 +00:00
|
|
|
NS_IF_RELEASE(mParser);
|
1998-08-15 16:25:33 +00:00
|
|
|
for (i = 0; i < mImageMaps.Count(); i++) {
|
1999-01-09 00:15:19 +00:00
|
|
|
nsIDOMHTMLMapElement* map = (nsIDOMHTMLMapElement*)mImageMaps.ElementAt(i);
|
1998-08-15 16:25:33 +00:00
|
|
|
NS_RELEASE(map);
|
|
|
|
}
|
1999-01-18 03:43:43 +00:00
|
|
|
NS_IF_RELEASE(mForms);
|
1999-05-26 23:50:26 +00:00
|
|
|
if (mCSSLoader) {
|
|
|
|
mCSSLoader->DropDocumentReference(); // release weak ref
|
|
|
|
NS_RELEASE(mCSSLoader);
|
|
|
|
}
|
1999-09-15 17:57:16 +00:00
|
|
|
if (nsnull != mDocTypeStr) {
|
|
|
|
delete mDocTypeStr;
|
|
|
|
mDocTypeStr = nsnull;
|
|
|
|
}
|
1999-01-18 03:43:43 +00:00
|
|
|
|
1998-08-28 15:55:31 +00:00
|
|
|
// These will be converted to a nsDeque
|
|
|
|
delete[] mParentStack;
|
|
|
|
delete[] mChildStack;
|
1998-08-28 18:15:14 +00:00
|
|
|
|
|
|
|
delete mSearchStr;
|
1998-09-04 15:41:20 +00:00
|
|
|
NS_IF_RELEASE(mBodyContent);
|
1998-04-13 20:24:54 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
NS_IMETHODIMP nsHTMLDocument::QueryInterface(REFNSIID aIID,
|
|
|
|
void** aInstancePtr)
|
|
|
|
{
|
|
|
|
NS_PRECONDITION(nsnull != aInstancePtr, "null ptr");
|
|
|
|
if (nsnull == aInstancePtr) {
|
|
|
|
return NS_ERROR_NULL_POINTER;
|
|
|
|
}
|
|
|
|
if (aIID.Equals(kIHTMLDocumentIID)) {
|
1998-09-12 19:33:48 +00:00
|
|
|
NS_ADDREF_THIS();
|
1998-07-22 23:32:19 +00:00
|
|
|
*aInstancePtr = (void**) (nsIHTMLDocument *)this;
|
|
|
|
return NS_OK;
|
|
|
|
}
|
|
|
|
if (aIID.Equals(kIDOMHTMLDocumentIID)) {
|
1998-09-12 19:33:48 +00:00
|
|
|
NS_ADDREF_THIS();
|
1998-07-22 23:32:19 +00:00
|
|
|
*aInstancePtr = (void**) (nsIDOMHTMLDocument *)this;
|
1998-04-13 20:24:54 +00:00
|
|
|
return NS_OK;
|
|
|
|
}
|
1998-08-07 23:08:00 +00:00
|
|
|
if (aIID.Equals(kIDOMNSHTMLDocumentIID)) {
|
1998-09-12 19:33:48 +00:00
|
|
|
NS_ADDREF_THIS();
|
1998-08-07 23:08:00 +00:00
|
|
|
*aInstancePtr = (void**) (nsIDOMNSHTMLDocument *)this;
|
|
|
|
return NS_OK;
|
|
|
|
}
|
1998-11-12 07:54:12 +00:00
|
|
|
if (aIID.Equals(kIHTMLContentContainerIID)) {
|
|
|
|
NS_ADDREF_THIS();
|
|
|
|
*aInstancePtr = (void**) (nsIHTMLContentContainer *)this;
|
|
|
|
return NS_OK;
|
|
|
|
}
|
1998-04-13 20:24:54 +00:00
|
|
|
return nsDocument::QueryInterface(aIID, aInstancePtr);
|
|
|
|
}
|
|
|
|
|
1998-07-22 23:32:19 +00:00
|
|
|
nsrefcnt nsHTMLDocument::AddRef()
|
|
|
|
{
|
|
|
|
return nsDocument::AddRef();
|
|
|
|
}
|
|
|
|
|
|
|
|
nsrefcnt nsHTMLDocument::Release()
|
|
|
|
{
|
|
|
|
return nsDocument::Release();
|
|
|
|
}
|
1998-07-01 11:16:09 +00:00
|
|
|
|
1999-01-06 00:32:41 +00:00
|
|
|
nsresult
|
1999-07-20 08:46:33 +00:00
|
|
|
nsHTMLDocument::Reset(nsIChannel* aChannel, nsILoadGroup* aLoadGroup)
|
1998-04-13 20:24:54 +00:00
|
|
|
{
|
1999-07-20 08:46:33 +00:00
|
|
|
nsresult result = nsDocument::Reset(aChannel, aLoadGroup);
|
1999-07-16 11:14:36 +00:00
|
|
|
nsCOMPtr<nsIURI> aURL;
|
|
|
|
result = aChannel->GetURI(getter_AddRefs(aURL));
|
|
|
|
if (NS_FAILED(result)) return result;
|
1999-01-06 00:32:41 +00:00
|
|
|
if (NS_FAILED(result)) {
|
|
|
|
return result;
|
1998-05-13 23:43:44 +00:00
|
|
|
}
|
1998-11-11 22:06:16 +00:00
|
|
|
|
1999-01-06 00:32:41 +00:00
|
|
|
PRInt32 i;
|
|
|
|
|
|
|
|
DeleteNamedItems();
|
|
|
|
NS_IF_RELEASE(mImages);
|
|
|
|
NS_IF_RELEASE(mApplets);
|
|
|
|
NS_IF_RELEASE(mEmbeds);
|
|
|
|
NS_IF_RELEASE(mLinks);
|
|
|
|
NS_IF_RELEASE(mAnchors);
|
1999-05-17 21:17:48 +00:00
|
|
|
NS_IF_RELEASE(mLayers);
|
1999-01-06 00:32:41 +00:00
|
|
|
|
|
|
|
for (i = 0; i < mImageMaps.Count(); i++) {
|
1999-01-09 00:15:19 +00:00
|
|
|
nsIDOMHTMLMapElement* map = (nsIDOMHTMLMapElement*)mImageMaps.ElementAt(i);
|
1999-01-06 00:32:41 +00:00
|
|
|
NS_RELEASE(map);
|
|
|
|
}
|
1999-01-18 03:43:43 +00:00
|
|
|
NS_IF_RELEASE(mForms);
|
1998-05-13 23:43:44 +00:00
|
|
|
|
1999-02-03 19:38:16 +00:00
|
|
|
if (nsnull == mAttrStyleSheet) {
|
|
|
|
result = NS_NewHTMLStyleSheet(&mAttrStyleSheet, aURL, this);
|
1998-11-26 01:34:53 +00:00
|
|
|
}
|
1999-02-03 19:38:16 +00:00
|
|
|
else {
|
|
|
|
result = mAttrStyleSheet->Reset(aURL);
|
1998-11-26 01:34:53 +00:00
|
|
|
}
|
1999-01-06 00:32:41 +00:00
|
|
|
if (NS_OK == result) {
|
|
|
|
AddStyleSheet(mAttrStyleSheet); // tell the world about our new style sheet
|
1999-02-03 19:38:16 +00:00
|
|
|
|
|
|
|
if (nsnull == mStyleAttrStyleSheet) {
|
|
|
|
result = NS_NewHTMLCSSStyleSheet(&mStyleAttrStyleSheet, aURL, this);
|
|
|
|
}
|
|
|
|
else {
|
|
|
|
result = mStyleAttrStyleSheet->Reset(aURL);
|
|
|
|
}
|
1999-01-06 00:32:41 +00:00
|
|
|
if (NS_OK == result) {
|
|
|
|
AddStyleSheet(mStyleAttrStyleSheet); // tell the world about our new style sheet
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
return result;
|
|
|
|
}
|
|
|
|
|
1999-05-11 20:22:35 +00:00
|
|
|
NS_IMETHODIMP
|
|
|
|
nsHTMLDocument::GetContentType(nsString& aContentType) const
|
|
|
|
{
|
2000-03-12 09:14:14 +00:00
|
|
|
aContentType.Assign("text/html");
|
1999-05-11 20:22:35 +00:00
|
|
|
return NS_OK;
|
|
|
|
}
|
|
|
|
|
1999-07-07 01:27:08 +00:00
|
|
|
NS_IMETHODIMP
|
|
|
|
nsHTMLDocument::CreateShell(nsIPresContext* aContext,
|
|
|
|
nsIViewManager* aViewManager,
|
|
|
|
nsIStyleSet* aStyleSet,
|
|
|
|
nsIPresShell** aInstancePtrResult)
|
|
|
|
{
|
|
|
|
nsresult result = nsMarkupDocument::CreateShell(aContext,
|
|
|
|
aViewManager,
|
|
|
|
aStyleSet,
|
|
|
|
aInstancePtrResult);
|
|
|
|
|
|
|
|
if (NS_SUCCEEDED(result)) {
|
|
|
|
aContext->SetCompatibilityMode(((eDTDMode_NoQuirks == mDTDMode) ?
|
|
|
|
eCompatibility_Standard :
|
|
|
|
eCompatibility_NavQuirks));
|
|
|
|
}
|
|
|
|
return result;
|
|
|
|
}
|
|
|
|
|
1999-01-06 00:32:41 +00:00
|
|
|
NS_IMETHODIMP
|
1999-07-16 11:14:36 +00:00
|
|
|
nsHTMLDocument::StartDocumentLoad(const char* aCommand,
|
|
|
|
nsIChannel* aChannel,
|
1999-07-20 08:46:33 +00:00
|
|
|
nsILoadGroup* aLoadGroup,
|
1999-11-15 22:17:54 +00:00
|
|
|
nsISupports* aContainer,
|
1999-07-16 11:14:36 +00:00
|
|
|
nsIStreamListener **aDocListener)
|
1999-01-06 00:32:41 +00:00
|
|
|
{
|
1999-12-09 07:18:38 +00:00
|
|
|
PRBool needsParser=PR_TRUE;
|
|
|
|
if (aCommand)
|
|
|
|
{
|
|
|
|
nsAutoString command(aCommand);
|
|
|
|
nsAutoString delayedView("view delayedContentLoad");
|
|
|
|
if (command.Equals(delayedView)) {
|
|
|
|
needsParser = PR_FALSE;
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
1999-07-16 11:14:36 +00:00
|
|
|
nsresult rv = nsDocument::StartDocumentLoad(aCommand,
|
1999-07-20 08:46:33 +00:00
|
|
|
aChannel, aLoadGroup,
|
1999-01-06 00:32:41 +00:00
|
|
|
aContainer,
|
1999-07-16 11:14:36 +00:00
|
|
|
aDocListener);
|
1999-12-09 07:18:38 +00:00
|
|
|
if (NS_FAILED(rv)) { return rv; }
|
1999-01-06 00:32:41 +00:00
|
|
|
|
1999-08-24 07:38:00 +00:00
|
|
|
nsAutoString charset = "ISO-8859-1"; // fallback value in case webShell return error
|
1999-08-25 21:42:30 +00:00
|
|
|
nsCharsetSource charsetSource = kCharsetFromWeakDocTypeDefault;
|
1999-01-06 00:32:41 +00:00
|
|
|
|
1999-07-16 11:14:36 +00:00
|
|
|
nsCOMPtr<nsIURI> aURL;
|
|
|
|
rv = aChannel->GetURI(getter_AddRefs(aURL));
|
|
|
|
if (NS_FAILED(rv)) return rv;
|
1999-08-09 19:10:24 +00:00
|
|
|
|
1999-11-12 02:06:54 +00:00
|
|
|
nsAutoString lastModified;
|
1999-08-09 19:10:24 +00:00
|
|
|
nsCOMPtr<nsIHTTPChannel> httpChannel = do_QueryInterface(aChannel);
|
1999-12-09 07:18:38 +00:00
|
|
|
if (httpChannel)
|
|
|
|
{
|
1999-09-17 06:56:39 +00:00
|
|
|
nsXPIDLCString lastModHeader;
|
|
|
|
nsIAtom* lastModKey = NS_NewAtom("last-modified");
|
1999-08-09 19:10:24 +00:00
|
|
|
|
1999-09-17 06:56:39 +00:00
|
|
|
rv = httpChannel->GetResponseHeader(lastModKey,
|
|
|
|
getter_Copies(lastModHeader));
|
1999-08-09 19:10:24 +00:00
|
|
|
|
1999-09-17 06:56:39 +00:00
|
|
|
NS_RELEASE(lastModKey);
|
1999-08-09 19:10:24 +00:00
|
|
|
if (NS_SUCCEEDED(rv)) {
|
1999-09-17 06:56:39 +00:00
|
|
|
lastModified = lastModHeader;
|
1999-08-09 19:10:24 +00:00
|
|
|
SetLastModified(lastModified);
|
|
|
|
}
|
1999-08-24 07:38:00 +00:00
|
|
|
|
1999-09-17 06:56:39 +00:00
|
|
|
nsXPIDLCString referrerHeader;
|
|
|
|
nsAutoString referrer;
|
|
|
|
// The misspelled key 'referer' is as per the HTTP spec
|
|
|
|
nsIAtom* referrerKey = NS_NewAtom("referer");
|
|
|
|
|
|
|
|
rv = httpChannel->GetRequestHeader(referrerKey,
|
|
|
|
getter_Copies(referrerHeader));
|
|
|
|
|
|
|
|
NS_RELEASE(referrerKey);
|
|
|
|
if (NS_SUCCEEDED(rv)) {
|
|
|
|
referrer = referrerHeader;
|
|
|
|
SetReferrer(referrer);
|
|
|
|
}
|
|
|
|
|
|
|
|
if(kCharsetFromHTTPHeader > charsetSource)
|
|
|
|
{
|
|
|
|
nsIAtom* contentTypeKey = NS_NewAtom("content-type");
|
|
|
|
nsXPIDLCString contenttypeheader;
|
|
|
|
rv = httpChannel->GetResponseHeader(contentTypeKey, getter_Copies(contenttypeheader));
|
|
|
|
NS_RELEASE(contentTypeKey);
|
|
|
|
if (NS_SUCCEEDED(rv)) {
|
|
|
|
nsAutoString contentType;
|
|
|
|
contentType = contenttypeheader;
|
|
|
|
PRInt32 start = contentType.RFind("charset=", PR_TRUE ) ;
|
|
|
|
if(kNotFound != start)
|
|
|
|
{
|
|
|
|
start += 8; // 8 = "charset=".length
|
|
|
|
PRInt32 end = contentType.FindCharInSet(";\n\r ", start );
|
|
|
|
if(kNotFound == end )
|
|
|
|
end = contentType.Length();
|
|
|
|
nsAutoString theCharset;
|
|
|
|
contentType.Mid(theCharset, start, end - start);
|
|
|
|
nsICharsetAlias* calias = nsnull;
|
|
|
|
rv = nsServiceManager::GetService(
|
|
|
|
kCharsetAliasCID,
|
2000-02-02 22:24:56 +00:00
|
|
|
NS_GET_IID(nsICharsetAlias),
|
1999-09-17 06:56:39 +00:00
|
|
|
(nsISupports**) &calias);
|
|
|
|
if(NS_SUCCEEDED(rv) && (nsnull != calias) )
|
|
|
|
{
|
|
|
|
nsAutoString preferred;
|
|
|
|
rv = calias->GetPreferred(theCharset, preferred);
|
|
|
|
if(NS_SUCCEEDED(rv))
|
|
|
|
{
|
1999-12-13 21:00:47 +00:00
|
|
|
#ifdef DEBUG_charset
|
|
|
|
char* cCharset = charset.ToNewCString();
|
|
|
|
printf("From HTTP Header, charset = %s\n", cCharset);
|
|
|
|
Recycle(cCharset);
|
|
|
|
#endif
|
1999-09-17 06:56:39 +00:00
|
|
|
charset = preferred;
|
|
|
|
charsetSource = kCharsetFromHTTPHeader;
|
|
|
|
}
|
|
|
|
nsServiceManager::ReleaseService(kCharsetAliasCID, calias);
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
1999-08-24 07:38:00 +00:00
|
|
|
|
1999-08-09 19:10:24 +00:00
|
|
|
// Don't propogate the result code beyond here, since it
|
|
|
|
// could just be that the response header wasn't found.
|
|
|
|
rv = NS_OK;
|
|
|
|
}
|
1999-07-16 11:14:36 +00:00
|
|
|
|
1999-11-12 02:06:54 +00:00
|
|
|
nsCOMPtr<nsIFileChannel> fileChannel = do_QueryInterface(aChannel);
|
|
|
|
if (fileChannel) {
|
|
|
|
PRTime modDate;
|
2000-01-24 21:28:28 +00:00
|
|
|
|
|
|
|
nsCOMPtr<nsIFile> file;
|
|
|
|
rv = fileChannel->GetFile(getter_AddRefs(file));
|
|
|
|
if (NS_FAILED(rv)) { return rv; }
|
|
|
|
rv = file->GetLastModificationDate(&modDate);
|
1999-12-09 07:18:38 +00:00
|
|
|
if (NS_FAILED(rv)) { return rv; }
|
|
|
|
PRExplodedTime prtime;
|
|
|
|
char buf[100];
|
|
|
|
PRInt64 prusec, scale;
|
|
|
|
|
2000-03-02 15:06:05 +00:00
|
|
|
|
|
|
|
#ifdef XP_PC
|
|
|
|
LL_I2L(scale, 1L);
|
|
|
|
#else
|
|
|
|
// nsIFile->GetLastModificationDate() uses stat on Unix and not
|
|
|
|
// PRFileInfo64() to get the modification date, untill that is changed
|
|
|
|
// we haveto do different scaling to get the date right.
|
1999-12-09 07:18:38 +00:00
|
|
|
LL_I2L(scale, 1000000L);
|
2000-03-02 15:06:05 +00:00
|
|
|
#endif
|
1999-12-09 07:18:38 +00:00
|
|
|
LL_MUL(prusec, modDate, scale);
|
|
|
|
PR_ExplodeTime(prusec, PR_LocalTimeParameters, &prtime);
|
1999-12-16 09:06:41 +00:00
|
|
|
|
|
|
|
// Use '%#c' for windows, because '%c' is backward-compatible and
|
|
|
|
// non-y2k with msvc; '%#c' requests that a full year be used in the
|
|
|
|
// result string. Other OSes just use "%c".
|
|
|
|
PR_FormatTime(buf, sizeof buf,
|
2000-03-02 15:06:05 +00:00
|
|
|
#ifdef XP_PC
|
1999-12-16 09:06:41 +00:00
|
|
|
"%#c",
|
|
|
|
#else
|
|
|
|
"%c",
|
|
|
|
#endif
|
|
|
|
&prtime);
|
2000-03-12 09:14:14 +00:00
|
|
|
lastModified.Assign(buf);
|
1999-12-09 07:18:38 +00:00
|
|
|
SetLastModified(lastModified);
|
1999-11-12 02:06:54 +00:00
|
|
|
}
|
|
|
|
|
1998-07-30 22:42:27 +00:00
|
|
|
static NS_DEFINE_IID(kCParserIID, NS_IPARSER_IID);
|
|
|
|
static NS_DEFINE_IID(kCParserCID, NS_PARSER_IID);
|
|
|
|
|
1999-12-09 07:18:38 +00:00
|
|
|
if (needsParser)
|
|
|
|
{
|
1999-03-09 09:44:27 +00:00
|
|
|
rv = nsComponentManager::CreateInstance(kCParserCID,
|
1999-12-09 07:18:38 +00:00
|
|
|
nsnull,
|
|
|
|
kCParserIID,
|
|
|
|
(void **)&mParser);
|
|
|
|
if (NS_FAILED(rv)) { return rv; }
|
|
|
|
}
|
1999-04-26 17:56:37 +00:00
|
|
|
|
1999-12-09 07:18:38 +00:00
|
|
|
PRUnichar* requestCharset = nsnull;
|
|
|
|
nsCharsetSource requestCharsetSource = kCharsetUninitialized;
|
|
|
|
|
|
|
|
nsIParserFilter *cdetflt = nsnull;
|
|
|
|
nsCOMPtr<nsIHTMLContentSink> sink;
|
1998-07-10 05:35:23 +00:00
|
|
|
#ifdef rickgdebug
|
1999-12-09 07:18:38 +00:00
|
|
|
nsString outString; // added out. Redirect to stdout if desired -- gpk 04/01/99
|
|
|
|
rv = NS_New_HTML_ContentSinkStream(getter_AddRefs(sink),&outString,0);
|
|
|
|
if (NS_FAILED(rv)) return rv;
|
|
|
|
NS_ASSERTION(sink, "null sink in debug code variant.");
|
1998-07-10 05:35:23 +00:00
|
|
|
#else
|
1999-12-09 07:18:38 +00:00
|
|
|
NS_PRECONDITION(nsnull != aContainer, "No content viewer container");
|
2000-03-11 00:35:36 +00:00
|
|
|
nsCOMPtr<nsIDocShell> docShell(do_QueryInterface(aContainer));
|
1999-12-09 07:18:38 +00:00
|
|
|
|
2000-01-18 02:40:45 +00:00
|
|
|
//
|
|
|
|
// The following logic is mirrored in nsWebShell::Embed!
|
|
|
|
//
|
1999-12-09 07:18:38 +00:00
|
|
|
nsCOMPtr<nsIMarkupDocumentViewer> muCV;
|
|
|
|
nsCOMPtr<nsIContentViewer> cv;
|
2000-03-11 00:35:36 +00:00
|
|
|
docShell->GetContentViewer(getter_AddRefs(cv));
|
1999-12-09 07:18:38 +00:00
|
|
|
if (cv) {
|
|
|
|
muCV = do_QueryInterface(cv);
|
1999-12-13 22:45:06 +00:00
|
|
|
} else {
|
|
|
|
// in this block of code, if we get an error result, we return it
|
|
|
|
// but if we get a null pointer, that's perfectly legal for parent and parentContentViewer
|
2000-03-11 00:35:36 +00:00
|
|
|
nsCOMPtr<nsIDocShellTreeItem> docShellAsItem(do_QueryInterface(docShell));
|
|
|
|
NS_ENSURE_TRUE(docShellAsItem, NS_ERROR_FAILURE);
|
|
|
|
|
|
|
|
nsCOMPtr<nsIDocShellTreeItem> parentAsItem;
|
|
|
|
docShellAsItem->GetSameTypeParent(getter_AddRefs(parentAsItem));
|
|
|
|
|
|
|
|
nsCOMPtr<nsIDocShell> parent(do_QueryInterface(parentAsItem));
|
1999-12-13 22:45:06 +00:00
|
|
|
if (parent) {
|
|
|
|
nsCOMPtr<nsIContentViewer> parentContentViewer;
|
|
|
|
rv = parent->GetContentViewer(getter_AddRefs(parentContentViewer));
|
|
|
|
if (NS_FAILED(rv)) { return rv; }
|
|
|
|
if (parentContentViewer) {
|
|
|
|
muCV = do_QueryInterface(parentContentViewer);
|
|
|
|
}
|
|
|
|
}
|
1999-12-09 07:18:38 +00:00
|
|
|
}
|
|
|
|
if(kCharsetFromUserDefault > charsetSource)
|
|
|
|
{
|
|
|
|
PRUnichar* defaultCharsetFromWebShell = NULL;
|
|
|
|
if (muCV) {
|
|
|
|
rv = muCV->GetDefaultCharacterSet(&defaultCharsetFromWebShell);
|
1999-12-13 22:45:06 +00:00
|
|
|
if(NS_SUCCEEDED(rv)) {
|
1999-12-13 21:00:47 +00:00
|
|
|
#ifdef DEBUG_charset
|
|
|
|
nsAutoString d(defaultCharsetFromWebShell);
|
|
|
|
char* cCharset = d.ToNewCString();
|
|
|
|
printf("From default charset, charset = %s\n", cCharset);
|
|
|
|
Recycle(cCharset);
|
|
|
|
#endif
|
1999-12-13 22:45:06 +00:00
|
|
|
charset = defaultCharsetFromWebShell;
|
|
|
|
Recycle(defaultCharsetFromWebShell);
|
|
|
|
charsetSource = kCharsetFromUserDefault;
|
|
|
|
}
|
1999-12-09 07:18:38 +00:00
|
|
|
}
|
|
|
|
// for html, we need to find out the Meta tag from the hint.
|
|
|
|
if (muCV) {
|
|
|
|
rv = muCV->GetHintCharacterSet(&requestCharset);
|
|
|
|
if(NS_SUCCEEDED(rv)) {
|
|
|
|
rv = muCV->GetHintCharacterSetSource((PRInt32*)(&requestCharsetSource));
|
1999-12-13 21:00:47 +00:00
|
|
|
if(kCharsetUninitialized != requestCharsetSource) {
|
|
|
|
muCV->SetHintCharacterSetSource((PRInt32)(kCharsetUninitialized));
|
|
|
|
}
|
1999-12-09 07:18:38 +00:00
|
|
|
}
|
|
|
|
}
|
|
|
|
if(NS_SUCCEEDED(rv))
|
|
|
|
{
|
|
|
|
if(requestCharsetSource > charsetSource)
|
|
|
|
{
|
1999-12-13 21:00:47 +00:00
|
|
|
#ifdef DEBUG_charset
|
|
|
|
nsAutoString d(requestCharset);
|
|
|
|
char* cCharset = d.ToNewCString();
|
|
|
|
printf("From request charset, charset = %s req=%d->%d\n",
|
|
|
|
cCharset, charsetSource, requestCharsetSource);
|
|
|
|
Recycle(cCharset);
|
|
|
|
#endif
|
1999-12-09 07:18:38 +00:00
|
|
|
charsetSource = requestCharsetSource;
|
|
|
|
charset = requestCharset;
|
|
|
|
Recycle(requestCharset);
|
|
|
|
}
|
|
|
|
}
|
|
|
|
if(kCharsetFromPreviousLoading > charsetSource)
|
1999-11-19 07:35:27 +00:00
|
|
|
{
|
1999-12-09 07:18:38 +00:00
|
|
|
PRUnichar* forceCharsetFromWebShell = NULL;
|
|
|
|
if (muCV) {
|
|
|
|
rv = muCV->GetForceCharacterSet(&forceCharsetFromWebShell);
|
1999-11-19 07:35:27 +00:00
|
|
|
}
|
1999-12-09 07:18:38 +00:00
|
|
|
if(NS_SUCCEEDED(rv) && (nsnull != forceCharsetFromWebShell))
|
1999-11-19 07:35:27 +00:00
|
|
|
{
|
1999-12-13 21:00:47 +00:00
|
|
|
#ifdef DEBUG_charset
|
|
|
|
nsAutoString d(forceCharsetFromWebShell);
|
|
|
|
char* cCharset = d.ToNewCString();
|
|
|
|
printf("From force, charset = %s \n", cCharset);
|
|
|
|
Recycle(cCharset);
|
|
|
|
#endif
|
1999-12-09 07:18:38 +00:00
|
|
|
charset = forceCharsetFromWebShell;
|
|
|
|
Recycle(forceCharsetFromWebShell);
|
|
|
|
//TODO: we should define appropriate constant for force charset
|
|
|
|
charsetSource = kCharsetFromPreviousLoading;
|
|
|
|
}
|
|
|
|
}
|
|
|
|
nsresult rv_detect = NS_OK;
|
|
|
|
if(! gInitDetector)
|
|
|
|
{
|
2000-03-02 07:13:02 +00:00
|
|
|
nsCOMPtr<nsIPref> pref(do_GetService(NS_PREF_PROGID));
|
|
|
|
if(pref)
|
1999-12-09 07:18:38 +00:00
|
|
|
{
|
|
|
|
char* detector_name = nsnull;
|
|
|
|
if(NS_SUCCEEDED(
|
|
|
|
rv_detect = pref->CopyCharPref("intl.charset.detector",
|
|
|
|
&detector_name)))
|
1999-11-19 07:35:27 +00:00
|
|
|
{
|
1999-12-09 07:18:38 +00:00
|
|
|
PL_strncpy(g_detector_progid, NS_CHARSET_DETECTOR_PROGID_BASE,DETECTOR_PROGID_MAX);
|
|
|
|
PL_strncat(g_detector_progid, detector_name,DETECTOR_PROGID_MAX);
|
|
|
|
gPlugDetector = PR_TRUE;
|
|
|
|
PR_FREEIF(detector_name);
|
1999-11-19 07:35:27 +00:00
|
|
|
}
|
1999-12-09 07:18:38 +00:00
|
|
|
pref->RegisterCallback("intl.charset.detector", MyPrefChangedCallback, nsnull);
|
|
|
|
}
|
|
|
|
gInitDetector = PR_TRUE;
|
|
|
|
}
|
|
|
|
|
|
|
|
if((kCharsetFromAutoDetection > charsetSource ) && gPlugDetector)
|
|
|
|
{
|
|
|
|
// we could do charset detection
|
|
|
|
nsICharsetDetector *cdet = nsnull;
|
|
|
|
nsIWebShellServices *wss = nsnull;
|
|
|
|
nsICharsetDetectionAdaptor *adp = nsnull;
|
|
|
|
|
|
|
|
if(NS_SUCCEEDED( rv_detect =
|
|
|
|
nsComponentManager::CreateInstance(g_detector_progid, nsnull,
|
2000-02-02 22:24:56 +00:00
|
|
|
NS_GET_IID(nsICharsetDetector), (void**)&cdet)))
|
1999-12-09 07:18:38 +00:00
|
|
|
{
|
|
|
|
if(NS_SUCCEEDED( rv_detect =
|
|
|
|
nsComponentManager::CreateInstance(
|
|
|
|
NS_CHARSET_DETECTION_ADAPTOR_PROGID, nsnull,
|
|
|
|
kIParserFilterIID, (void**)&cdetflt)))
|
1999-11-19 07:35:27 +00:00
|
|
|
{
|
1999-12-09 07:18:38 +00:00
|
|
|
if(cdetflt &&
|
|
|
|
NS_SUCCEEDED( rv_detect=
|
|
|
|
cdetflt->QueryInterface(
|
2000-02-02 22:24:56 +00:00
|
|
|
NS_GET_IID(nsICharsetDetectionAdaptor),(void**) &adp)))
|
1999-11-19 07:35:27 +00:00
|
|
|
{
|
1999-12-09 07:18:38 +00:00
|
|
|
if( NS_SUCCEEDED( rv_detect=
|
2000-03-11 00:35:36 +00:00
|
|
|
docShell->QueryInterface(
|
2000-02-02 22:24:56 +00:00
|
|
|
NS_GET_IID(nsIWebShellServices),(void**) &wss)))
|
1999-11-19 07:35:27 +00:00
|
|
|
{
|
2000-02-15 09:15:18 +00:00
|
|
|
rv_detect = adp->Init(wss, cdet, (nsIDocument*)this,
|
|
|
|
mParser, charset.GetUnicode(),aCommand);
|
1999-11-19 07:35:27 +00:00
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
1999-12-09 07:18:38 +00:00
|
|
|
else
|
|
|
|
{
|
|
|
|
// IF we cannot create the detector, don't bother to
|
|
|
|
// create one next time.
|
|
|
|
gPlugDetector = PR_FALSE;
|
|
|
|
}
|
|
|
|
NS_IF_RELEASE(wss);
|
|
|
|
NS_IF_RELEASE(cdet);
|
|
|
|
NS_IF_RELEASE(adp);
|
|
|
|
// NO NS_IF_RELEASE(cdetflt); here, do it after mParser->SetParserFilter
|
1999-04-26 17:56:37 +00:00
|
|
|
}
|
1999-12-09 07:18:38 +00:00
|
|
|
}
|
1998-07-10 05:35:23 +00:00
|
|
|
#endif
|
|
|
|
|
1999-12-09 07:18:38 +00:00
|
|
|
if (NS_FAILED(rv)) { return rv; }
|
|
|
|
|
|
|
|
rv = this->SetDocumentCharacterSet(charset);
|
|
|
|
if (NS_FAILED(rv)) { return rv; }
|
1999-04-27 21:49:25 +00:00
|
|
|
|
1999-12-09 07:18:38 +00:00
|
|
|
// Set the parser as the stream listener for the document loader...
|
|
|
|
if (mParser)
|
|
|
|
{
|
|
|
|
static NS_DEFINE_IID(kIStreamListenerIID, NS_ISTREAMLISTENER_IID);
|
|
|
|
rv = mParser->QueryInterface(kIStreamListenerIID, (void**)aDocListener);
|
|
|
|
if (NS_FAILED(rv)) { return rv; }
|
1998-07-01 11:16:09 +00:00
|
|
|
|
1998-07-02 08:14:22 +00:00
|
|
|
|
1999-12-09 07:18:38 +00:00
|
|
|
//The following lines were added by Rick.
|
|
|
|
//These perform "dynamic" DTD registration, allowing
|
|
|
|
//the caller total control over process, and decoupling
|
|
|
|
//parser from any given grammar.
|
1998-07-02 08:14:22 +00:00
|
|
|
|
1999-01-26 01:25:37 +00:00
|
|
|
// nsIDTD* theDTD=0;
|
|
|
|
// NS_NewNavHTMLDTD(&theDTD);
|
|
|
|
// mParser->RegisterDTD(theDTD);
|
1999-07-14 15:33:48 +00:00
|
|
|
|
1999-12-09 07:18:38 +00:00
|
|
|
nsIParserFilter *oldFilter = nsnull;
|
|
|
|
if(cdetflt)
|
|
|
|
oldFilter = mParser->SetParserFilter(cdetflt);
|
|
|
|
NS_IF_RELEASE(oldFilter);
|
|
|
|
NS_IF_RELEASE(cdetflt);
|
|
|
|
|
1999-12-13 21:00:47 +00:00
|
|
|
#ifdef DEBUG_charset
|
|
|
|
char* cCharset = charset.ToNewCString();
|
|
|
|
printf("set to parser charset = %s source %d\n",
|
|
|
|
cCharset, charsetSource);
|
|
|
|
Recycle(cCharset);
|
|
|
|
#endif
|
1999-12-09 07:18:38 +00:00
|
|
|
mParser->SetDocumentCharset( charset, charsetSource);
|
|
|
|
mParser->SetCommand(aCommand);
|
|
|
|
// create the content sink
|
2000-03-11 00:35:36 +00:00
|
|
|
nsCOMPtr<nsIWebShell> webShell(do_QueryInterface(docShell));
|
1999-12-09 07:18:38 +00:00
|
|
|
rv = NS_NewHTMLContentSink(getter_AddRefs(sink), this, aURL, webShell);
|
|
|
|
if (NS_FAILED(rv)) { return rv; }
|
|
|
|
NS_ASSERTION(sink, "null sink with successful result from factory method");
|
|
|
|
mParser->SetContentSink(sink);
|
|
|
|
// parser the content of the URL
|
|
|
|
mParser->Parse(aURL, nsnull, PR_FALSE, (void *)this);
|
1998-04-13 20:24:54 +00:00
|
|
|
}
|
1998-06-01 19:53:19 +00:00
|
|
|
|
|
|
|
return rv;
|
1998-04-13 20:24:54 +00:00
|
|
|
}
|
|
|
|
|
1998-07-23 22:06:05 +00:00
|
|
|
NS_IMETHODIMP
|
|
|
|
nsHTMLDocument::EndLoad()
|
|
|
|
{
|
|
|
|
NS_IF_RELEASE(mParser);
|
|
|
|
return nsDocument::EndLoad();
|
|
|
|
}
|
1998-07-01 11:16:09 +00:00
|
|
|
|
1998-04-13 20:24:54 +00:00
|
|
|
NS_IMETHODIMP nsHTMLDocument::SetTitle(const nsString& aTitle)
|
|
|
|
{
|
|
|
|
if (nsnull == mDocumentTitle) {
|
|
|
|
mDocumentTitle = new nsString(aTitle);
|
|
|
|
}
|
|
|
|
else {
|
|
|
|
*mDocumentTitle = aTitle;
|
|
|
|
}
|
|
|
|
|
|
|
|
// Pass on to any interested containers
|
1998-07-19 01:14:53 +00:00
|
|
|
PRInt32 i, n = mPresShells.Count();
|
1998-04-13 20:24:54 +00:00
|
|
|
for (i = 0; i < n; i++) {
|
|
|
|
nsIPresShell* shell = (nsIPresShell*) mPresShells.ElementAt(i);
|
1999-02-12 17:45:58 +00:00
|
|
|
nsCOMPtr<nsIPresContext> cx;
|
|
|
|
shell->GetPresContext(getter_AddRefs(cx));
|
1999-11-27 03:11:10 +00:00
|
|
|
nsCOMPtr<nsISupports> container;
|
|
|
|
if (NS_OK == cx->GetContainer(getter_AddRefs(container))) {
|
|
|
|
if (container) {
|
2000-02-08 13:40:10 +00:00
|
|
|
nsCOMPtr<nsIBaseWindow> docShell(do_QueryInterface(container));
|
|
|
|
if(docShell) {
|
|
|
|
docShell->SetTitle(aTitle.GetUnicode());
|
1998-04-13 20:24:54 +00:00
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
return NS_OK;
|
|
|
|
}
|
|
|
|
|
1999-01-09 00:15:19 +00:00
|
|
|
NS_IMETHODIMP
|
|
|
|
nsHTMLDocument::AddImageMap(nsIDOMHTMLMapElement* aMap)
|
1998-04-13 20:24:54 +00:00
|
|
|
{
|
|
|
|
NS_PRECONDITION(nsnull != aMap, "null ptr");
|
|
|
|
if (nsnull == aMap) {
|
|
|
|
return NS_ERROR_NULL_POINTER;
|
|
|
|
}
|
|
|
|
if (mImageMaps.AppendElement(aMap)) {
|
|
|
|
NS_ADDREF(aMap);
|
|
|
|
return NS_OK;
|
|
|
|
}
|
|
|
|
return NS_ERROR_OUT_OF_MEMORY;
|
|
|
|
}
|
|
|
|
|
1999-03-01 16:57:35 +00:00
|
|
|
NS_IMETHODIMP
|
|
|
|
nsHTMLDocument::RemoveImageMap(nsIDOMHTMLMapElement* aMap)
|
|
|
|
{
|
|
|
|
NS_PRECONDITION(nsnull != aMap, "null ptr");
|
|
|
|
if (nsnull == aMap) {
|
|
|
|
return NS_ERROR_NULL_POINTER;
|
|
|
|
}
|
|
|
|
if (mImageMaps.RemoveElement((void*)aMap)) {
|
|
|
|
NS_RELEASE(aMap);
|
|
|
|
}
|
|
|
|
return NS_OK;
|
|
|
|
}
|
|
|
|
|
1999-01-09 00:15:19 +00:00
|
|
|
NS_IMETHODIMP
|
|
|
|
nsHTMLDocument::GetImageMap(const nsString& aMapName,
|
|
|
|
nsIDOMHTMLMapElement** aResult)
|
1998-04-13 20:24:54 +00:00
|
|
|
{
|
|
|
|
NS_PRECONDITION(nsnull != aResult, "null ptr");
|
|
|
|
if (nsnull == aResult) {
|
|
|
|
return NS_ERROR_NULL_POINTER;
|
|
|
|
}
|
|
|
|
|
|
|
|
nsAutoString name;
|
|
|
|
PRInt32 i, n = mImageMaps.Count();
|
|
|
|
for (i = 0; i < n; i++) {
|
1999-01-09 00:15:19 +00:00
|
|
|
nsIDOMHTMLMapElement* map = (nsIDOMHTMLMapElement*)mImageMaps.ElementAt(i);
|
1998-04-13 20:24:54 +00:00
|
|
|
if (NS_OK == map->GetName(name)) {
|
|
|
|
if (name.EqualsIgnoreCase(aMapName)) {
|
|
|
|
*aResult = map;
|
|
|
|
NS_ADDREF(map);
|
|
|
|
return NS_OK;
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
1999-01-15 22:26:30 +00:00
|
|
|
return NS_ERROR_FAILURE;
|
1998-04-13 20:24:54 +00:00
|
|
|
}
|
|
|
|
|
1998-07-25 01:26:12 +00:00
|
|
|
NS_IMETHODIMP nsHTMLDocument::GetAttributeStyleSheet(nsIHTMLStyleSheet** aResult)
|
|
|
|
{
|
|
|
|
NS_PRECONDITION(nsnull != aResult, "null ptr");
|
|
|
|
if (nsnull == aResult) {
|
|
|
|
return NS_ERROR_NULL_POINTER;
|
|
|
|
}
|
|
|
|
*aResult = mAttrStyleSheet;
|
|
|
|
if (nsnull == mAttrStyleSheet) {
|
|
|
|
return NS_ERROR_NOT_AVAILABLE; // probably not the right error...
|
|
|
|
}
|
1998-09-12 02:43:19 +00:00
|
|
|
else {
|
|
|
|
NS_ADDREF(mAttrStyleSheet);
|
|
|
|
}
|
1998-07-25 01:26:12 +00:00
|
|
|
return NS_OK;
|
|
|
|
}
|
|
|
|
|
1998-12-02 00:35:41 +00:00
|
|
|
NS_IMETHODIMP nsHTMLDocument::GetInlineStyleSheet(nsIHTMLCSSStyleSheet** aResult)
|
|
|
|
{
|
|
|
|
NS_PRECONDITION(nsnull != aResult, "null ptr");
|
|
|
|
if (nsnull == aResult) {
|
|
|
|
return NS_ERROR_NULL_POINTER;
|
|
|
|
}
|
|
|
|
*aResult = mStyleAttrStyleSheet;
|
|
|
|
if (nsnull == mStyleAttrStyleSheet) {
|
|
|
|
return NS_ERROR_NOT_AVAILABLE; // probably not the right error...
|
|
|
|
}
|
|
|
|
else {
|
|
|
|
NS_ADDREF(mStyleAttrStyleSheet);
|
|
|
|
}
|
|
|
|
return NS_OK;
|
|
|
|
}
|
|
|
|
|
1999-01-23 07:07:09 +00:00
|
|
|
void nsHTMLDocument::InternalAddStyleSheet(nsIStyleSheet* aSheet) // subclass hook for sheet ordering
|
1998-04-13 20:24:54 +00:00
|
|
|
{
|
1999-01-23 07:07:09 +00:00
|
|
|
if (aSheet == mAttrStyleSheet) { // always first
|
|
|
|
mStyleSheets.InsertElementAt(aSheet, 0);
|
|
|
|
}
|
|
|
|
else if (aSheet == mStyleAttrStyleSheet) { // always last
|
|
|
|
mStyleSheets.AppendElement(aSheet);
|
1998-04-13 20:24:54 +00:00
|
|
|
}
|
|
|
|
else {
|
1999-01-23 07:07:09 +00:00
|
|
|
if (mStyleAttrStyleSheet == mStyleSheets.ElementAt(mStyleSheets.Count() - 1)) {
|
|
|
|
// keep attr sheet last
|
|
|
|
mStyleSheets.InsertElementAt(aSheet, mStyleSheets.Count() - 1);
|
|
|
|
}
|
|
|
|
else {
|
|
|
|
mStyleSheets.AppendElement(aSheet);
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
1999-05-18 23:06:31 +00:00
|
|
|
void
|
|
|
|
nsHTMLDocument::InternalInsertStyleSheetAt(nsIStyleSheet* aSheet, PRInt32 aIndex)
|
1999-01-23 07:07:09 +00:00
|
|
|
{
|
|
|
|
mStyleSheets.InsertElementAt(aSheet, aIndex + 1); // offset one for the attr style sheet
|
1998-04-13 20:24:54 +00:00
|
|
|
}
|
|
|
|
|
1999-01-15 02:01:36 +00:00
|
|
|
|
|
|
|
NS_IMETHODIMP
|
1999-06-23 03:29:44 +00:00
|
|
|
nsHTMLDocument::GetBaseURL(nsIURI*& aURL) const
|
1999-01-15 02:01:36 +00:00
|
|
|
{
|
|
|
|
if (nsnull != mBaseURL) {
|
|
|
|
NS_ADDREF(mBaseURL);
|
|
|
|
aURL = mBaseURL;
|
|
|
|
}
|
|
|
|
else {
|
|
|
|
aURL = GetDocumentURL();
|
|
|
|
}
|
|
|
|
return NS_OK;
|
|
|
|
}
|
|
|
|
|
|
|
|
NS_IMETHODIMP
|
|
|
|
nsHTMLDocument:: SetBaseURL(const nsString& aURLSpec)
|
|
|
|
{
|
|
|
|
nsresult result = NS_OK;
|
|
|
|
|
|
|
|
NS_IF_RELEASE(mBaseURL);
|
|
|
|
if (0 < aURLSpec.Length()) {
|
1999-06-23 19:55:21 +00:00
|
|
|
{
|
|
|
|
result = NS_NewURI(&mBaseURL, aURLSpec, mDocumentURL);
|
1999-01-15 02:01:36 +00:00
|
|
|
}
|
|
|
|
}
|
|
|
|
return result;
|
|
|
|
}
|
|
|
|
|
|
|
|
NS_IMETHODIMP
|
|
|
|
nsHTMLDocument:: GetBaseTarget(nsString& aTarget) const
|
|
|
|
{
|
|
|
|
if (nsnull != mBaseTarget) {
|
|
|
|
aTarget = *mBaseTarget;
|
|
|
|
}
|
|
|
|
else {
|
|
|
|
aTarget.Truncate();
|
|
|
|
}
|
|
|
|
return NS_OK;
|
|
|
|
}
|
|
|
|
|
|
|
|
NS_IMETHODIMP
|
|
|
|
nsHTMLDocument:: SetBaseTarget(const nsString& aTarget)
|
|
|
|
{
|
|
|
|
if (0 < aTarget.Length()) {
|
|
|
|
if (nsnull != mBaseTarget) {
|
|
|
|
*mBaseTarget = aTarget;
|
|
|
|
}
|
|
|
|
else {
|
|
|
|
mBaseTarget = aTarget.ToNewString();
|
|
|
|
}
|
|
|
|
}
|
|
|
|
else {
|
|
|
|
if (nsnull != mBaseTarget) {
|
|
|
|
delete mBaseTarget;
|
|
|
|
mBaseTarget = nsnull;
|
|
|
|
}
|
|
|
|
}
|
|
|
|
return NS_OK;
|
|
|
|
}
|
|
|
|
|
1999-08-09 19:10:24 +00:00
|
|
|
NS_IMETHODIMP
|
|
|
|
nsHTMLDocument::SetLastModified(const nsString& aLastModified)
|
|
|
|
{
|
|
|
|
if (0 < aLastModified.Length()) {
|
|
|
|
if (nsnull != mLastModified) {
|
|
|
|
*mLastModified = aLastModified;
|
|
|
|
}
|
|
|
|
else {
|
|
|
|
mLastModified = aLastModified.ToNewString();
|
|
|
|
}
|
|
|
|
}
|
|
|
|
else if (nsnull != mLastModified) {
|
1999-09-17 06:56:39 +00:00
|
|
|
nsString::Recycle(mLastModified);
|
1999-08-09 19:10:24 +00:00
|
|
|
mLastModified = nsnull;
|
|
|
|
}
|
|
|
|
|
|
|
|
return NS_OK;
|
|
|
|
}
|
|
|
|
|
1999-09-17 06:56:39 +00:00
|
|
|
NS_IMETHODIMP
|
|
|
|
nsHTMLDocument::SetReferrer(const nsString& aReferrer)
|
|
|
|
{
|
|
|
|
if (0 < aReferrer.Length()) {
|
|
|
|
if (nsnull != mReferrer) {
|
|
|
|
*mReferrer = aReferrer;
|
|
|
|
}
|
|
|
|
else {
|
|
|
|
mReferrer = aReferrer.ToNewString();
|
|
|
|
}
|
|
|
|
}
|
|
|
|
else if (nsnull != mReferrer) {
|
|
|
|
nsString::Recycle(mReferrer);
|
|
|
|
mReferrer = nsnull;
|
|
|
|
}
|
|
|
|
|
|
|
|
return NS_OK;
|
|
|
|
}
|
|
|
|
|
1999-05-18 23:06:31 +00:00
|
|
|
NS_IMETHODIMP
|
|
|
|
nsHTMLDocument::GetCSSLoader(nsICSSLoader*& aLoader)
|
|
|
|
{
|
|
|
|
nsresult result = NS_OK;
|
|
|
|
if (! mCSSLoader) {
|
|
|
|
result = NS_NewCSSLoader(this, &mCSSLoader);
|
|
|
|
}
|
1999-07-07 01:27:08 +00:00
|
|
|
if (mCSSLoader) {
|
|
|
|
mCSSLoader->SetCaseSensitive(PR_FALSE);
|
|
|
|
mCSSLoader->SetQuirkMode(PRBool(eDTDMode_NoQuirks != mDTDMode));
|
|
|
|
}
|
1999-05-18 23:06:31 +00:00
|
|
|
aLoader = mCSSLoader;
|
|
|
|
NS_IF_ADDREF(aLoader);
|
|
|
|
return result;
|
|
|
|
}
|
|
|
|
|
1999-01-15 02:01:36 +00:00
|
|
|
|
1998-09-02 02:06:39 +00:00
|
|
|
NS_IMETHODIMP
|
|
|
|
nsHTMLDocument::GetDTDMode(nsDTDMode& aMode)
|
|
|
|
{
|
|
|
|
aMode = mDTDMode;
|
|
|
|
return NS_OK;
|
|
|
|
}
|
|
|
|
|
|
|
|
NS_IMETHODIMP
|
|
|
|
nsHTMLDocument::SetDTDMode(nsDTDMode aMode)
|
|
|
|
{
|
|
|
|
mDTDMode = aMode;
|
1999-07-07 01:27:08 +00:00
|
|
|
if (mCSSLoader) {
|
|
|
|
mCSSLoader->SetQuirkMode(PRBool(eDTDMode_NoQuirks != mDTDMode));
|
|
|
|
}
|
1999-09-15 17:57:16 +00:00
|
|
|
|
|
|
|
nsIPresShell* shell = (nsIPresShell*) mPresShells.ElementAt(0);
|
|
|
|
if (nsnull != shell) {
|
|
|
|
nsCOMPtr<nsIPresContext> pc;
|
|
|
|
shell->GetPresContext(getter_AddRefs(pc));
|
|
|
|
if (pc) {
|
|
|
|
pc->SetCompatibilityMode(((eDTDMode_NoQuirks == mDTDMode) ?
|
|
|
|
eCompatibility_Standard :
|
|
|
|
eCompatibility_NavQuirks));
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
return NS_OK;
|
|
|
|
}
|
|
|
|
|
|
|
|
NS_IMETHODIMP
|
|
|
|
nsHTMLDocument::GetDocTypeStr(nsString& aDocTypeString)
|
|
|
|
{
|
|
|
|
if(mDocTypeStr) aDocTypeString = *mDocTypeStr;
|
1998-09-02 02:06:39 +00:00
|
|
|
return NS_OK;
|
|
|
|
}
|
|
|
|
|
1999-09-15 17:57:16 +00:00
|
|
|
NS_IMETHODIMP
|
|
|
|
nsHTMLDocument::AddDocTypeDecl(const nsString& aDocTypeString, nsDTDMode aMode)
|
|
|
|
{
|
|
|
|
nsresult result=NS_OK;
|
|
|
|
|
|
|
|
result=SetDTDMode(aMode);
|
|
|
|
if(result==NS_OK) {
|
|
|
|
if (mDocTypeStr == nsnull) {
|
|
|
|
if(aDocTypeString.Length()>0) {
|
|
|
|
mDocTypeStr = new nsString(aDocTypeString);
|
|
|
|
if (mDocTypeStr==nsnull) result=NS_ERROR_OUT_OF_MEMORY;
|
|
|
|
}
|
|
|
|
}
|
|
|
|
else {
|
|
|
|
mDocTypeStr->SetLength(0);
|
|
|
|
mDocTypeStr->Append(aDocTypeString);
|
|
|
|
}
|
|
|
|
}
|
|
|
|
return result;
|
|
|
|
}
|
|
|
|
|
1999-01-23 07:07:09 +00:00
|
|
|
NS_IMETHODIMP
|
|
|
|
nsHTMLDocument::SetHeaderData(nsIAtom* aHeaderField, const nsString& aData)
|
|
|
|
{
|
|
|
|
nsresult result = nsMarkupDocument::SetHeaderData(aHeaderField, aData);
|
|
|
|
|
|
|
|
if (NS_SUCCEEDED(result)) {
|
|
|
|
if (aHeaderField == nsHTMLAtoms::headerDefaultStyle) {
|
|
|
|
// switch alternate style sheets based on default
|
|
|
|
nsAutoString type;
|
|
|
|
nsAutoString title;
|
|
|
|
nsAutoString textHtml("text/html");
|
|
|
|
PRInt32 index;
|
|
|
|
PRInt32 count = mStyleSheets.Count();
|
|
|
|
for (index = 0; index < count; index++) {
|
|
|
|
nsIStyleSheet* sheet = (nsIStyleSheet*)mStyleSheets.ElementAt(index);
|
|
|
|
sheet->GetType(type);
|
|
|
|
if (PR_FALSE == type.Equals(textHtml)) {
|
|
|
|
sheet->GetTitle(title);
|
|
|
|
if (0 < title.Length()) { // if sheet has title
|
|
|
|
PRBool disabled = ((0 == aData.Length()) ||
|
|
|
|
(PR_FALSE == aData.EqualsIgnoreCase(title)));
|
|
|
|
SetStyleSheetDisabledState(sheet, disabled);
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
return result;
|
|
|
|
}
|
|
|
|
|
|
|
|
|
1998-11-28 23:51:06 +00:00
|
|
|
NS_IMETHODIMP
|
|
|
|
nsHTMLDocument::ContentAppended(nsIContent* aContainer,
|
|
|
|
PRInt32 aNewIndexInContainer)
|
|
|
|
{
|
|
|
|
if (nsnull != mNamedItems) {
|
|
|
|
nsIContent* child;
|
|
|
|
nsIAtom *name;
|
|
|
|
|
|
|
|
aContainer->GetTag(name);
|
|
|
|
aContainer->ChildAt(aNewIndexInContainer, child);
|
|
|
|
RegisterNamedItems(aContainer, name == nsHTMLAtoms::form);
|
|
|
|
NS_IF_RELEASE(child);
|
|
|
|
NS_IF_RELEASE(name);
|
|
|
|
}
|
|
|
|
|
|
|
|
return nsDocument::ContentAppended(aContainer, aNewIndexInContainer);
|
|
|
|
}
|
|
|
|
|
|
|
|
NS_IMETHODIMP
|
|
|
|
nsHTMLDocument::ContentInserted(nsIContent* aContainer,
|
|
|
|
nsIContent* aChild,
|
|
|
|
PRInt32 aIndexInContainer)
|
|
|
|
{
|
|
|
|
if (nsnull != mNamedItems) {
|
|
|
|
nsIAtom *name;
|
|
|
|
|
|
|
|
aContainer->GetTag(name);
|
|
|
|
RegisterNamedItems(aChild, name == nsHTMLAtoms::form);
|
|
|
|
NS_IF_RELEASE(name);
|
|
|
|
}
|
|
|
|
|
|
|
|
return nsDocument::ContentInserted(aContainer, aChild, aIndexInContainer);
|
|
|
|
}
|
|
|
|
|
|
|
|
NS_IMETHODIMP
|
|
|
|
nsHTMLDocument::ContentReplaced(nsIContent* aContainer,
|
|
|
|
nsIContent* aOldChild,
|
|
|
|
nsIContent* aNewChild,
|
|
|
|
PRInt32 aIndexInContainer)
|
|
|
|
{
|
|
|
|
if (nsnull != mNamedItems) {
|
|
|
|
nsIAtom *name;
|
|
|
|
|
|
|
|
aContainer->GetTag(name);
|
|
|
|
UnregisterNamedItems(aOldChild, name == nsHTMLAtoms::form);
|
|
|
|
RegisterNamedItems(aNewChild, name == nsHTMLAtoms::form);
|
|
|
|
|
|
|
|
NS_IF_RELEASE(name);
|
|
|
|
}
|
|
|
|
|
|
|
|
return nsDocument::ContentReplaced(aContainer, aOldChild,
|
|
|
|
aNewChild, aIndexInContainer);
|
|
|
|
}
|
|
|
|
|
|
|
|
NS_IMETHODIMP
|
|
|
|
nsHTMLDocument::ContentRemoved(nsIContent* aContainer,
|
|
|
|
nsIContent* aChild,
|
|
|
|
PRInt32 aIndexInContainer)
|
|
|
|
{
|
1999-02-03 19:38:16 +00:00
|
|
|
if ((nsnull != mNamedItems) && (nsnull != aContainer)) {
|
1998-11-28 23:51:06 +00:00
|
|
|
nsIAtom *name;
|
|
|
|
|
|
|
|
aContainer->GetTag(name);
|
|
|
|
UnregisterNamedItems(aChild, name == nsHTMLAtoms::form);
|
|
|
|
|
|
|
|
NS_IF_RELEASE(name);
|
|
|
|
}
|
|
|
|
|
|
|
|
return nsDocument::ContentRemoved(aContainer, aChild, aIndexInContainer);
|
|
|
|
}
|
|
|
|
|
2000-01-24 06:43:15 +00:00
|
|
|
NS_IMETHODIMP
|
|
|
|
nsHTMLDocument::FlushPendingNotifications()
|
|
|
|
{
|
|
|
|
nsresult result = NS_OK;
|
|
|
|
if (mParser) {
|
|
|
|
nsCOMPtr<nsIContentSink> sink;
|
|
|
|
|
|
|
|
// XXX Ack! Parser doesn't addref sink before passing it back
|
|
|
|
sink = mParser->GetContentSink();
|
|
|
|
if (sink) {
|
|
|
|
result = sink->FlushPendingNotifications();
|
|
|
|
}
|
|
|
|
}
|
|
|
|
if (NS_SUCCEEDED(result)) {
|
|
|
|
result = nsDocument::FlushPendingNotifications();
|
|
|
|
}
|
|
|
|
|
|
|
|
return result;
|
|
|
|
}
|
|
|
|
|
1998-07-22 23:32:19 +00:00
|
|
|
//
|
|
|
|
// nsIDOMDocument interface implementation
|
|
|
|
//
|
1998-07-14 18:44:44 +00:00
|
|
|
NS_IMETHODIMP
|
|
|
|
nsHTMLDocument::CreateElement(const nsString& aTagName,
|
|
|
|
nsIDOMElement** aReturn)
|
1998-05-04 17:54:45 +00:00
|
|
|
{
|
1999-10-08 20:41:19 +00:00
|
|
|
nsCOMPtr<nsIHTMLContent> content;
|
|
|
|
nsresult rv = NS_CreateHTMLElement(getter_AddRefs(content), aTagName);
|
|
|
|
if (NS_SUCCEEDED(rv)) {
|
|
|
|
rv = content->QueryInterface(kIDOMElementIID, (void**)aReturn);
|
1998-05-04 17:54:45 +00:00
|
|
|
}
|
|
|
|
return rv;
|
|
|
|
}
|
|
|
|
|
1998-07-22 23:32:19 +00:00
|
|
|
NS_IMETHODIMP
|
1998-10-20 17:07:23 +00:00
|
|
|
nsHTMLDocument::CreateProcessingInstruction(const nsString& aTarget,
|
|
|
|
const nsString& aData,
|
|
|
|
nsIDOMProcessingInstruction** aReturn)
|
1998-07-22 23:32:19 +00:00
|
|
|
{
|
1998-10-20 17:07:23 +00:00
|
|
|
// There are no PIs for HTML
|
|
|
|
*aReturn = nsnull;
|
|
|
|
|
1999-09-08 23:18:27 +00:00
|
|
|
return NS_ERROR_DOM_NOT_SUPPORTED_ERR;
|
1998-07-22 23:32:19 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
NS_IMETHODIMP
|
1998-10-20 17:07:23 +00:00
|
|
|
nsHTMLDocument::CreateCDATASection(const nsString& aData,
|
|
|
|
nsIDOMCDATASection** aReturn)
|
1998-07-22 23:32:19 +00:00
|
|
|
{
|
1998-10-20 17:07:23 +00:00
|
|
|
// There are no CDATASections in HTML
|
|
|
|
*aReturn = nsnull;
|
|
|
|
|
1999-09-08 23:18:27 +00:00
|
|
|
return NS_ERROR_DOM_NOT_SUPPORTED_ERR;
|
1998-10-20 17:07:23 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
NS_IMETHODIMP
|
|
|
|
nsHTMLDocument::CreateEntityReference(const nsString& aName,
|
|
|
|
nsIDOMEntityReference** aReturn)
|
|
|
|
{
|
|
|
|
// There are no EntityReferences in HTML
|
|
|
|
*aReturn = nsnull;
|
|
|
|
|
1999-09-08 23:18:27 +00:00
|
|
|
return NS_ERROR_DOM_NOT_SUPPORTED_ERR;
|
1998-07-22 23:32:19 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
NS_IMETHODIMP
|
1998-10-20 17:07:23 +00:00
|
|
|
nsHTMLDocument::GetDoctype(nsIDOMDocumentType** aDocumentType)
|
1998-07-22 23:32:19 +00:00
|
|
|
{
|
1998-10-20 17:07:23 +00:00
|
|
|
// There's no document type for a HTML document
|
|
|
|
*aDocumentType = nsnull;
|
|
|
|
return NS_OK;
|
|
|
|
}
|
|
|
|
|
1999-01-19 16:58:45 +00:00
|
|
|
NS_IMETHODIMP
|
|
|
|
nsHTMLDocument::GetImplementation(nsIDOMDOMImplementation** aImplementation)
|
|
|
|
{
|
|
|
|
return nsDocument::GetImplementation(aImplementation);
|
|
|
|
}
|
|
|
|
|
|
|
|
NS_IMETHODIMP
|
|
|
|
nsHTMLDocument::GetDocumentElement(nsIDOMElement** aDocumentElement)
|
|
|
|
{
|
|
|
|
return nsDocument::GetDocumentElement(aDocumentElement);
|
|
|
|
}
|
|
|
|
|
|
|
|
NS_IMETHODIMP
|
|
|
|
nsHTMLDocument::CreateDocumentFragment(nsIDOMDocumentFragment** aReturn)
|
|
|
|
{
|
|
|
|
return nsDocument::CreateDocumentFragment(aReturn);
|
|
|
|
}
|
|
|
|
|
|
|
|
NS_IMETHODIMP
|
|
|
|
nsHTMLDocument::CreateComment(const nsString& aData, nsIDOMComment** aReturn)
|
|
|
|
{
|
|
|
|
return nsDocument::CreateComment(aData, aReturn);
|
|
|
|
}
|
|
|
|
|
|
|
|
NS_IMETHODIMP
|
|
|
|
nsHTMLDocument::CreateAttribute(const nsString& aName, nsIDOMAttr** aReturn)
|
|
|
|
{
|
|
|
|
return nsDocument::CreateAttribute(aName, aReturn);
|
|
|
|
}
|
|
|
|
|
|
|
|
NS_IMETHODIMP
|
|
|
|
nsHTMLDocument::CreateTextNode(const nsString& aData, nsIDOMText** aReturn)
|
|
|
|
{
|
|
|
|
return nsDocument::CreateTextNode(aData, aReturn);
|
|
|
|
}
|
|
|
|
|
|
|
|
NS_IMETHODIMP
|
|
|
|
nsHTMLDocument::GetElementsByTagName(const nsString& aTagname, nsIDOMNodeList** aReturn)
|
|
|
|
{
|
|
|
|
return nsDocument::GetElementsByTagName(aTagname, aReturn);
|
|
|
|
}
|
|
|
|
|
|
|
|
//
|
|
|
|
// nsIDOMNode interface implementation
|
|
|
|
//
|
|
|
|
NS_IMETHODIMP
|
|
|
|
nsHTMLDocument::GetChildNodes(nsIDOMNodeList** aChildNodes)
|
|
|
|
{
|
1999-03-31 20:49:25 +00:00
|
|
|
return nsDocument::GetChildNodes(aChildNodes);
|
1999-01-19 16:58:45 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
NS_IMETHODIMP
|
|
|
|
nsHTMLDocument::GetFirstChild(nsIDOMNode** aFirstChild)
|
|
|
|
{
|
1999-03-31 20:49:25 +00:00
|
|
|
return nsDocument::GetFirstChild(aFirstChild);
|
1999-01-19 16:58:45 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
NS_IMETHODIMP
|
|
|
|
nsHTMLDocument::GetLastChild(nsIDOMNode** aLastChild)
|
|
|
|
{
|
1999-03-31 20:49:25 +00:00
|
|
|
return nsDocument::GetLastChild(aLastChild);
|
1999-01-19 16:58:45 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
NS_IMETHODIMP
|
|
|
|
nsHTMLDocument::InsertBefore(nsIDOMNode* aNewChild,
|
|
|
|
nsIDOMNode* aRefChild,
|
|
|
|
nsIDOMNode** aReturn)
|
|
|
|
{
|
1999-03-31 20:49:25 +00:00
|
|
|
return nsDocument::InsertBefore(aNewChild, aRefChild, aReturn);
|
1999-01-19 16:58:45 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
NS_IMETHODIMP
|
|
|
|
nsHTMLDocument::ReplaceChild(nsIDOMNode* aNewChild,
|
|
|
|
nsIDOMNode* aOldChild,
|
|
|
|
nsIDOMNode** aReturn)
|
|
|
|
{
|
1999-03-31 20:49:25 +00:00
|
|
|
return nsDocument::ReplaceChild(aNewChild, aOldChild, aReturn);
|
1999-01-19 16:58:45 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
NS_IMETHODIMP
|
|
|
|
nsHTMLDocument::RemoveChild(nsIDOMNode* aOldChild, nsIDOMNode** aReturn)
|
|
|
|
{
|
1999-03-31 20:49:25 +00:00
|
|
|
return nsDocument::RemoveChild(aOldChild, aReturn);
|
1999-01-19 16:58:45 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
NS_IMETHODIMP
|
|
|
|
nsHTMLDocument::AppendChild(nsIDOMNode* aNewChild, nsIDOMNode** aReturn)
|
|
|
|
{
|
1999-03-31 20:49:25 +00:00
|
|
|
return nsDocument::AppendChild(aNewChild, aReturn);
|
1999-01-19 16:58:45 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
NS_IMETHODIMP
|
|
|
|
nsHTMLDocument::HasChildNodes(PRBool* aReturn)
|
|
|
|
{
|
1999-03-31 20:49:25 +00:00
|
|
|
return nsDocument::HasChildNodes(aReturn);
|
1999-01-19 16:58:45 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
NS_IMETHODIMP
|
|
|
|
nsHTMLDocument::GetNodeName(nsString& aNodeName)
|
|
|
|
{
|
|
|
|
return nsDocument::GetNodeName(aNodeName);
|
|
|
|
}
|
|
|
|
|
|
|
|
NS_IMETHODIMP
|
|
|
|
nsHTMLDocument::GetNodeValue(nsString& aNodeValue)
|
|
|
|
{
|
|
|
|
return nsDocument::GetNodeValue(aNodeValue);
|
|
|
|
}
|
|
|
|
|
|
|
|
NS_IMETHODIMP
|
|
|
|
nsHTMLDocument::SetNodeValue(const nsString& aNodeValue)
|
|
|
|
{
|
|
|
|
return nsDocument::SetNodeValue(aNodeValue);
|
|
|
|
}
|
|
|
|
|
|
|
|
NS_IMETHODIMP
|
|
|
|
nsHTMLDocument::GetNodeType(PRUint16* aNodeType)
|
|
|
|
{
|
|
|
|
return nsDocument::GetNodeType(aNodeType);
|
|
|
|
}
|
|
|
|
|
|
|
|
NS_IMETHODIMP
|
|
|
|
nsHTMLDocument::GetParentNode(nsIDOMNode** aParentNode)
|
|
|
|
{
|
|
|
|
return nsDocument::GetParentNode(aParentNode);
|
|
|
|
}
|
|
|
|
|
|
|
|
NS_IMETHODIMP
|
|
|
|
nsHTMLDocument::GetPreviousSibling(nsIDOMNode** aPreviousSibling)
|
|
|
|
{
|
|
|
|
return nsDocument::GetPreviousSibling(aPreviousSibling);
|
|
|
|
}
|
|
|
|
|
|
|
|
NS_IMETHODIMP
|
|
|
|
nsHTMLDocument::GetNextSibling(nsIDOMNode** aNextSibling)
|
|
|
|
{
|
|
|
|
return nsDocument::GetNextSibling(aNextSibling);
|
|
|
|
}
|
|
|
|
|
|
|
|
NS_IMETHODIMP
|
|
|
|
nsHTMLDocument::GetAttributes(nsIDOMNamedNodeMap** aAttributes)
|
|
|
|
{
|
|
|
|
return nsDocument::GetAttributes(aAttributes);
|
|
|
|
}
|
|
|
|
|
|
|
|
NS_IMETHODIMP
|
|
|
|
nsHTMLDocument::GetOwnerDocument(nsIDOMDocument** aOwnerDocument)
|
|
|
|
{
|
|
|
|
return nsDocument::GetOwnerDocument(aOwnerDocument);
|
|
|
|
}
|
|
|
|
|
|
|
|
NS_IMETHODIMP
|
|
|
|
nsHTMLDocument::CloneNode(PRBool aDeep, nsIDOMNode** aReturn)
|
|
|
|
{
|
|
|
|
return nsDocument::CloneNode(aDeep, aReturn);
|
|
|
|
}
|
|
|
|
|
|
|
|
|
1998-10-20 17:07:23 +00:00
|
|
|
//
|
|
|
|
// nsIDOMHTMLDocument interface implementation
|
|
|
|
//
|
1998-12-07 06:10:12 +00:00
|
|
|
// see http://www.w3.org/TR/1998/REC-DOM-Level-1-19981001/level-one-html.html#ID-1006298752
|
|
|
|
// for full specification.
|
|
|
|
//
|
1998-10-20 17:07:23 +00:00
|
|
|
NS_IMETHODIMP
|
|
|
|
nsHTMLDocument::GetTitle(nsString& aTitle)
|
|
|
|
{
|
|
|
|
if (nsnull != mDocumentTitle) {
|
1999-04-22 05:49:39 +00:00
|
|
|
aTitle=*mDocumentTitle;
|
1998-10-20 17:07:23 +00:00
|
|
|
}
|
|
|
|
return NS_OK;
|
1998-07-22 23:32:19 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
NS_IMETHODIMP
|
1998-10-20 17:07:23 +00:00
|
|
|
nsHTMLDocument::GetReferrer(nsString& aReferrer)
|
1998-07-22 23:32:19 +00:00
|
|
|
{
|
1999-09-17 06:56:39 +00:00
|
|
|
if (nsnull != mReferrer) {
|
|
|
|
aReferrer = *mReferrer;
|
1998-12-07 06:10:12 +00:00
|
|
|
}
|
1999-09-17 06:56:39 +00:00
|
|
|
else {
|
|
|
|
aReferrer.Truncate();
|
|
|
|
}
|
|
|
|
|
1998-12-07 06:10:12 +00:00
|
|
|
return NS_OK;
|
1998-07-22 23:32:19 +00:00
|
|
|
}
|
|
|
|
|
1999-10-02 03:41:37 +00:00
|
|
|
NS_IMETHODIMP
|
|
|
|
nsHTMLDocument::GetDomainURI(nsIURI **uri)
|
|
|
|
{
|
2000-01-26 15:33:57 +00:00
|
|
|
nsCOMPtr<nsIPrincipal> principal;
|
|
|
|
if (NS_FAILED(GetPrincipal(getter_AddRefs(principal))))
|
1999-10-02 03:41:37 +00:00
|
|
|
return NS_ERROR_FAILURE;
|
|
|
|
nsCOMPtr<nsICodebasePrincipal> codebase = do_QueryInterface(principal);
|
|
|
|
if (!codebase)
|
|
|
|
return NS_ERROR_FAILURE;
|
|
|
|
return codebase->GetURI(uri);
|
|
|
|
}
|
|
|
|
|
|
|
|
|
1998-07-22 23:32:19 +00:00
|
|
|
NS_IMETHODIMP
|
|
|
|
nsHTMLDocument::GetDomain(nsString& aDomain)
|
|
|
|
{
|
1999-10-02 03:41:37 +00:00
|
|
|
nsCOMPtr<nsIURI> uri;
|
|
|
|
if (NS_FAILED(GetDomainURI(getter_AddRefs(uri))))
|
|
|
|
return NS_ERROR_FAILURE;
|
|
|
|
|
|
|
|
char *hostName;
|
|
|
|
if (NS_FAILED(uri->GetHost(&hostName)))
|
|
|
|
return NS_ERROR_FAILURE;
|
2000-03-12 09:14:14 +00:00
|
|
|
aDomain.Assign(hostName);
|
1999-10-02 03:41:37 +00:00
|
|
|
nsCRT::free(hostName);
|
|
|
|
|
1998-12-07 06:10:12 +00:00
|
|
|
return NS_OK;
|
1998-07-22 23:32:19 +00:00
|
|
|
}
|
|
|
|
|
1999-10-02 03:41:37 +00:00
|
|
|
NS_IMETHODIMP
|
|
|
|
nsHTMLDocument::SetDomain(const nsString& aDomain)
|
|
|
|
{
|
|
|
|
// Check new domain
|
|
|
|
nsAutoString current;
|
|
|
|
if (NS_FAILED(GetDomain(current)))
|
|
|
|
return NS_ERROR_FAILURE;
|
|
|
|
PRBool ok = PR_FALSE;
|
|
|
|
if (current.Equals(aDomain)) {
|
|
|
|
ok = PR_TRUE;
|
|
|
|
} else if (aDomain.Length() < current.Length()) {
|
|
|
|
nsAutoString suffix;
|
|
|
|
current.Right(suffix, aDomain.Length());
|
|
|
|
PRUnichar c = current.CharAt(current.Length() - aDomain.Length() - 1);
|
|
|
|
if (aDomain.EqualsIgnoreCase(suffix) && (c == '.' || c == '/'))
|
|
|
|
ok = PR_TRUE;
|
|
|
|
}
|
|
|
|
if (!ok) {
|
|
|
|
// Error: illegal domain
|
|
|
|
return NS_ERROR_DOM_BAD_DOCUMENT_DOMAIN;
|
|
|
|
}
|
|
|
|
|
|
|
|
// Create new URI
|
|
|
|
nsCOMPtr<nsIURI> uri;
|
|
|
|
if (NS_FAILED(GetDomainURI(getter_AddRefs(uri))))
|
|
|
|
return NS_ERROR_FAILURE;
|
|
|
|
nsXPIDLCString scheme;
|
|
|
|
if (NS_FAILED(uri->GetScheme(getter_Copies(scheme))))
|
|
|
|
return NS_ERROR_FAILURE;
|
|
|
|
nsXPIDLCString path;
|
|
|
|
if (NS_FAILED(uri->GetPath(getter_Copies(path))))
|
|
|
|
return NS_ERROR_FAILURE;
|
|
|
|
nsAutoString newURIString = (const char *)scheme;
|
|
|
|
newURIString += "://";
|
|
|
|
newURIString += aDomain;
|
|
|
|
newURIString += path;
|
|
|
|
nsIURI *newURI;
|
|
|
|
if (NS_FAILED(NS_NewURI(&newURI, newURIString)))
|
|
|
|
return NS_ERROR_FAILURE;
|
|
|
|
|
1999-11-16 05:07:31 +00:00
|
|
|
// Get codebase principal
|
1999-10-02 03:41:37 +00:00
|
|
|
nsresult rv;
|
|
|
|
NS_WITH_SERVICE(nsIScriptSecurityManager, securityManager,
|
|
|
|
NS_SCRIPTSECURITYMANAGER_PROGID, &rv);
|
|
|
|
if (NS_FAILED(rv))
|
|
|
|
return NS_ERROR_FAILURE;
|
1999-11-16 05:07:31 +00:00
|
|
|
return securityManager->GetCodebasePrincipal(newURI, &mPrincipal);
|
1999-10-02 03:41:37 +00:00
|
|
|
}
|
|
|
|
|
1998-07-22 23:32:19 +00:00
|
|
|
NS_IMETHODIMP
|
|
|
|
nsHTMLDocument::GetURL(nsString& aURL)
|
|
|
|
{
|
1998-11-24 21:07:43 +00:00
|
|
|
if (nsnull != mDocumentURL) {
|
1999-06-25 01:53:22 +00:00
|
|
|
char* str;
|
|
|
|
mDocumentURL->GetSpec(&str);
|
1998-12-16 05:40:20 +00:00
|
|
|
aURL = str;
|
1999-06-25 01:53:22 +00:00
|
|
|
nsCRT::free(str);
|
1998-11-24 21:07:43 +00:00
|
|
|
}
|
|
|
|
return NS_OK;
|
1998-07-22 23:32:19 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
NS_IMETHODIMP
|
|
|
|
nsHTMLDocument::GetBody(nsIDOMHTMLElement** aBody)
|
|
|
|
{
|
1998-11-12 22:25:51 +00:00
|
|
|
if (mBodyContent == nsnull && PR_FALSE == GetBodyContent()) {
|
|
|
|
return NS_ERROR_FAILURE;
|
|
|
|
}
|
|
|
|
return mBodyContent->QueryInterface(kIDOMHTMLElementIID, (void **)aBody);
|
1998-07-22 23:32:19 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
NS_IMETHODIMP
|
|
|
|
nsHTMLDocument::SetBody(nsIDOMHTMLElement* aBody)
|
|
|
|
{
|
1999-02-04 02:16:11 +00:00
|
|
|
nsresult result = NS_OK;
|
|
|
|
nsIDOMElement * root = nsnull;
|
|
|
|
result = GetDocumentElement(&root);
|
|
|
|
if (NS_OK != result) {
|
|
|
|
return result;
|
|
|
|
}
|
|
|
|
|
|
|
|
nsAutoString bodyStr("BODY");
|
|
|
|
nsIDOMNode * child;
|
|
|
|
root->GetFirstChild(&child);
|
|
|
|
|
|
|
|
while (child != nsnull) {
|
|
|
|
nsIDOMElement* domElement;
|
|
|
|
result = child->QueryInterface(kIDOMElementIID,(void **)&domElement);
|
|
|
|
if (NS_OK == result) {
|
|
|
|
nsString tagName;
|
|
|
|
domElement->GetTagName(tagName);
|
|
|
|
if (bodyStr.EqualsIgnoreCase(tagName)) {
|
|
|
|
nsIDOMNode* ret;
|
|
|
|
|
|
|
|
result = root->ReplaceChild(aBody, child, &ret);
|
|
|
|
NS_IF_RELEASE(ret);
|
|
|
|
NS_IF_RELEASE(mBodyContent);
|
|
|
|
|
|
|
|
NS_RELEASE(child);
|
|
|
|
NS_RELEASE(root);
|
|
|
|
NS_RELEASE(domElement);
|
|
|
|
return result;
|
|
|
|
}
|
|
|
|
NS_RELEASE(domElement);
|
|
|
|
}
|
|
|
|
nsIDOMNode * node = child;
|
|
|
|
NS_RELEASE(child);
|
|
|
|
node->GetNextSibling(&child);
|
|
|
|
}
|
|
|
|
NS_RELEASE(root);
|
|
|
|
return PR_FALSE;
|
1998-07-22 23:32:19 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
NS_IMETHODIMP
|
|
|
|
nsHTMLDocument::GetImages(nsIDOMHTMLCollection** aImages)
|
|
|
|
{
|
|
|
|
if (nsnull == mImages) {
|
1999-01-15 19:18:30 +00:00
|
|
|
mImages = new nsContentList(this, nsHTMLAtoms::img, kNameSpaceID_HTML);
|
1998-07-22 23:32:19 +00:00
|
|
|
if (nsnull == mImages) {
|
|
|
|
return NS_ERROR_OUT_OF_MEMORY;
|
|
|
|
}
|
|
|
|
NS_ADDREF(mImages);
|
|
|
|
}
|
|
|
|
|
|
|
|
*aImages = (nsIDOMHTMLCollection *)mImages;
|
|
|
|
NS_ADDREF(mImages);
|
|
|
|
|
|
|
|
return NS_OK;
|
|
|
|
}
|
|
|
|
|
|
|
|
NS_IMETHODIMP
|
|
|
|
nsHTMLDocument::GetApplets(nsIDOMHTMLCollection** aApplets)
|
|
|
|
{
|
|
|
|
if (nsnull == mApplets) {
|
1999-01-15 19:18:30 +00:00
|
|
|
mApplets = new nsContentList(this, nsHTMLAtoms::applet, kNameSpaceID_HTML);
|
1998-07-22 23:32:19 +00:00
|
|
|
if (nsnull == mApplets) {
|
|
|
|
return NS_ERROR_OUT_OF_MEMORY;
|
|
|
|
}
|
|
|
|
NS_ADDREF(mApplets);
|
|
|
|
}
|
1998-04-13 20:24:54 +00:00
|
|
|
|
1998-09-25 00:51:45 +00:00
|
|
|
*aApplets = (nsIDOMHTMLCollection *)mApplets;
|
|
|
|
NS_ADDREF(mApplets);
|
1998-04-13 20:24:54 +00:00
|
|
|
|
1998-07-22 23:32:19 +00:00
|
|
|
return NS_OK;
|
|
|
|
}
|
1998-04-13 20:24:54 +00:00
|
|
|
|
1998-07-22 23:32:19 +00:00
|
|
|
PRBool
|
1999-05-04 20:53:44 +00:00
|
|
|
nsHTMLDocument::MatchLinks(nsIContent *aContent, nsString* aData)
|
1998-07-22 23:32:19 +00:00
|
|
|
{
|
1998-08-29 20:20:38 +00:00
|
|
|
nsIAtom *name;
|
|
|
|
aContent->GetTag(name);
|
1998-07-22 23:32:19 +00:00
|
|
|
nsAutoString attr;
|
|
|
|
PRBool result = PR_FALSE;
|
|
|
|
|
|
|
|
if ((nsnull != name) &&
|
1999-01-15 19:18:30 +00:00
|
|
|
((nsHTMLAtoms::area == name) || (nsHTMLAtoms::a == name)) &&
|
1998-12-20 01:21:23 +00:00
|
|
|
(NS_CONTENT_ATTR_HAS_VALUE == aContent->GetAttribute(kNameSpaceID_HTML, nsHTMLAtoms::href, attr))) {
|
1998-07-22 23:32:19 +00:00
|
|
|
result = PR_TRUE;
|
|
|
|
}
|
|
|
|
|
|
|
|
NS_IF_RELEASE(name);
|
|
|
|
return result;
|
1998-04-13 20:24:54 +00:00
|
|
|
}
|
|
|
|
|
1998-07-22 23:32:19 +00:00
|
|
|
NS_IMETHODIMP
|
|
|
|
nsHTMLDocument::GetLinks(nsIDOMHTMLCollection** aLinks)
|
|
|
|
{
|
|
|
|
if (nsnull == mLinks) {
|
1999-02-04 23:23:07 +00:00
|
|
|
mLinks = new nsContentList(this, MatchLinks, nsnull);
|
1998-07-22 23:32:19 +00:00
|
|
|
if (nsnull == mLinks) {
|
|
|
|
return NS_ERROR_OUT_OF_MEMORY;
|
|
|
|
}
|
|
|
|
NS_ADDREF(mLinks);
|
|
|
|
}
|
|
|
|
|
|
|
|
*aLinks = (nsIDOMHTMLCollection *)mLinks;
|
|
|
|
NS_ADDREF(mLinks);
|
1998-04-13 20:24:54 +00:00
|
|
|
|
1998-07-22 23:32:19 +00:00
|
|
|
return NS_OK;
|
1998-04-13 20:24:54 +00:00
|
|
|
}
|
|
|
|
|
1998-07-22 23:32:19 +00:00
|
|
|
PRBool
|
1999-05-04 20:53:44 +00:00
|
|
|
nsHTMLDocument::MatchAnchors(nsIContent *aContent, nsString* aData)
|
1998-04-13 20:24:54 +00:00
|
|
|
{
|
1998-08-29 20:20:38 +00:00
|
|
|
nsIAtom *name;
|
|
|
|
aContent->GetTag(name);
|
1998-07-22 23:32:19 +00:00
|
|
|
nsAutoString attr;
|
|
|
|
PRBool result = PR_FALSE;
|
|
|
|
|
|
|
|
if ((nsnull != name) &&
|
1999-01-15 19:18:30 +00:00
|
|
|
(nsHTMLAtoms::a == name) &&
|
1998-12-20 01:21:23 +00:00
|
|
|
(NS_CONTENT_ATTR_HAS_VALUE == aContent->GetAttribute(kNameSpaceID_HTML, nsHTMLAtoms::name, attr))) {
|
1998-07-22 23:32:19 +00:00
|
|
|
result = PR_TRUE;
|
|
|
|
}
|
|
|
|
|
|
|
|
NS_IF_RELEASE(name);
|
|
|
|
return result;
|
1998-04-13 20:24:54 +00:00
|
|
|
}
|
|
|
|
|
1998-07-22 23:32:19 +00:00
|
|
|
NS_IMETHODIMP
|
|
|
|
nsHTMLDocument::GetAnchors(nsIDOMHTMLCollection** aAnchors)
|
|
|
|
{
|
|
|
|
if (nsnull == mAnchors) {
|
1999-02-04 23:23:07 +00:00
|
|
|
mAnchors = new nsContentList(this, MatchAnchors, nsnull);
|
1998-07-22 23:32:19 +00:00
|
|
|
if (nsnull == mAnchors) {
|
|
|
|
return NS_ERROR_OUT_OF_MEMORY;
|
|
|
|
}
|
|
|
|
NS_ADDREF(mAnchors);
|
|
|
|
}
|
|
|
|
|
|
|
|
*aAnchors = (nsIDOMHTMLCollection *)mAnchors;
|
|
|
|
NS_ADDREF(mAnchors);
|
|
|
|
|
|
|
|
return NS_OK;
|
1998-04-13 20:24:54 +00:00
|
|
|
}
|
|
|
|
|
1998-07-22 23:32:19 +00:00
|
|
|
NS_IMETHODIMP
|
|
|
|
nsHTMLDocument::GetCookie(nsString& aCookie)
|
|
|
|
{
|
1999-08-19 22:23:20 +00:00
|
|
|
nsresult result = NS_OK;
|
|
|
|
NS_WITH_SERVICE(nsICookieService, service, kCookieServiceCID, &result);
|
|
|
|
if ((NS_OK == result) && (nsnull != service) && (nsnull != mDocumentURL)) {
|
|
|
|
result = service->GetCookieString(mDocumentURL, aCookie);
|
|
|
|
}
|
|
|
|
return result;
|
1998-04-13 20:24:54 +00:00
|
|
|
}
|
|
|
|
|
1998-07-22 23:32:19 +00:00
|
|
|
NS_IMETHODIMP
|
|
|
|
nsHTMLDocument::SetCookie(const nsString& aCookie)
|
|
|
|
{
|
1999-08-19 22:23:20 +00:00
|
|
|
nsresult result = NS_OK;
|
|
|
|
NS_WITH_SERVICE(nsICookieService, service, kCookieServiceCID, &result);
|
|
|
|
if ((NS_OK == result) && (nsnull != service) && (nsnull != mDocumentURL)) {
|
|
|
|
result = service->SetCookieString(mDocumentURL, aCookie);
|
|
|
|
}
|
|
|
|
return result;
|
1998-04-13 20:24:54 +00:00
|
|
|
}
|
1998-07-22 23:32:19 +00:00
|
|
|
|
1999-05-18 23:44:55 +00:00
|
|
|
nsresult
|
|
|
|
nsHTMLDocument::GetSourceDocumentURL(JSContext* cx,
|
1999-06-23 03:29:44 +00:00
|
|
|
nsIURI** sourceURL)
|
1999-05-18 23:44:55 +00:00
|
|
|
{
|
|
|
|
// XXX Tom said this reminded him of the "Six Degrees of
|
|
|
|
// Kevin Bacon" game. We try to get from here to there using
|
|
|
|
// whatever connections possible. The problem is that this
|
|
|
|
// could break if any of the connections along the way change.
|
|
|
|
// I wish there were a better way.
|
1999-08-18 08:48:33 +00:00
|
|
|
*sourceURL = nsnull;
|
|
|
|
|
1999-12-18 20:29:29 +00:00
|
|
|
// XXX Question, why does this return NS_OK on failure?
|
|
|
|
nsresult result = NS_OK;
|
|
|
|
|
|
|
|
// We need to use the dynamically scoped global and assume that the
|
|
|
|
// current JSContext is a DOM context with a nsIScriptGlobalObject so
|
|
|
|
// that we can get the url of the caller.
|
|
|
|
// XXX This will fail on non-DOM contexts :(
|
1999-05-18 23:44:55 +00:00
|
|
|
|
1999-12-18 20:29:29 +00:00
|
|
|
nsCOMPtr<nsIScriptGlobalObject> global;
|
|
|
|
nsLayoutUtils::GetDynamicScriptGlobal(cx, getter_AddRefs(global));
|
|
|
|
if (global) {
|
|
|
|
nsCOMPtr<nsIDOMWindow> window(do_QueryInterface(global, &result));
|
1999-05-18 23:44:55 +00:00
|
|
|
|
1999-12-18 20:29:29 +00:00
|
|
|
if (window) {
|
|
|
|
nsCOMPtr<nsIDOMDocument> document;
|
|
|
|
|
|
|
|
result = window->GetDocument(getter_AddRefs(document));
|
|
|
|
if (NS_SUCCEEDED(result)) {
|
|
|
|
nsCOMPtr<nsIDocument> doc(do_QueryInterface(document, &result));
|
|
|
|
if (doc) {
|
|
|
|
*sourceURL = doc->GetDocumentURL();
|
|
|
|
result = sourceURL ? NS_OK : NS_ERROR_FAILURE;
|
|
|
|
}
|
1999-05-18 23:44:55 +00:00
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
return result;
|
|
|
|
}
|
|
|
|
|
1999-05-28 00:18:48 +00:00
|
|
|
|
|
|
|
// XXX TBI: accepting arguments to the open method.
|
|
|
|
nsresult
|
1999-06-23 03:29:44 +00:00
|
|
|
nsHTMLDocument::OpenCommon(nsIURI* aSourceURL)
|
1998-07-22 23:32:19 +00:00
|
|
|
{
|
1999-01-06 00:32:41 +00:00
|
|
|
nsresult result = NS_OK;
|
|
|
|
// The open occurred after the document finished loading.
|
|
|
|
// So we reset the document and create a new one.
|
|
|
|
if (nsnull == mParser) {
|
1999-07-20 08:46:33 +00:00
|
|
|
nsCOMPtr<nsIChannel> channel;
|
1999-09-21 06:44:56 +00:00
|
|
|
nsCOMPtr<nsILoadGroup> group = do_QueryReferent(mDocumentLoadGroup);
|
|
|
|
|
|
|
|
result = NS_OpenURI(getter_AddRefs(channel), aSourceURL, group);
|
1999-07-20 08:46:33 +00:00
|
|
|
if (NS_FAILED(result)) return result;
|
1999-09-21 06:44:56 +00:00
|
|
|
result = Reset(channel, group);
|
1999-07-20 08:46:33 +00:00
|
|
|
if (NS_FAILED(result)) return result;
|
1999-05-28 00:18:48 +00:00
|
|
|
if (NS_OK == result) {
|
|
|
|
static NS_DEFINE_IID(kCParserIID, NS_IPARSER_IID);
|
|
|
|
static NS_DEFINE_IID(kCParserCID, NS_PARSER_IID);
|
|
|
|
|
|
|
|
result = nsComponentManager::CreateInstance(kCParserCID,
|
|
|
|
nsnull,
|
|
|
|
kCParserIID,
|
|
|
|
(void **)&mParser);
|
|
|
|
mIsWriting = 1;
|
|
|
|
|
|
|
|
if (NS_OK == result) {
|
|
|
|
nsIHTMLContentSink* sink;
|
|
|
|
nsIWebShell* webShell = nsnull;
|
|
|
|
|
|
|
|
// Get the webshell of our primary presentation shell
|
|
|
|
nsIPresShell* shell = (nsIPresShell*) mPresShells.ElementAt(0);
|
|
|
|
if (nsnull != shell) {
|
|
|
|
nsCOMPtr<nsIPresContext> cx;
|
|
|
|
shell->GetPresContext(getter_AddRefs(cx));
|
|
|
|
nsISupports* container;
|
|
|
|
if (NS_OK == cx->GetContainer(&container)) {
|
|
|
|
if (nsnull != container) {
|
|
|
|
container->QueryInterface(kIWebShellIID, (void**) &webShell);
|
1999-01-06 00:32:41 +00:00
|
|
|
}
|
|
|
|
}
|
1999-05-28 00:18:48 +00:00
|
|
|
}
|
1999-01-06 00:32:41 +00:00
|
|
|
|
1999-05-28 00:18:48 +00:00
|
|
|
result = NS_NewHTMLContentSink(&sink, this, aSourceURL, webShell);
|
|
|
|
NS_IF_RELEASE(webShell);
|
|
|
|
|
|
|
|
if (NS_OK == result) {
|
|
|
|
nsIDTD* theDTD=0;
|
|
|
|
NS_NewNavHTMLDTD(&theDTD);
|
|
|
|
mParser->RegisterDTD(theDTD);
|
|
|
|
mParser->SetContentSink(sink);
|
|
|
|
NS_RELEASE(sink);
|
1999-01-06 00:32:41 +00:00
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
1999-05-28 00:18:48 +00:00
|
|
|
|
|
|
|
return result;
|
|
|
|
}
|
|
|
|
|
|
|
|
NS_IMETHODIMP
|
|
|
|
nsHTMLDocument::Open()
|
|
|
|
{
|
|
|
|
nsresult result = NS_OK;
|
1999-06-23 03:29:44 +00:00
|
|
|
nsIURI* sourceURL;
|
1999-05-28 00:18:48 +00:00
|
|
|
|
|
|
|
// XXX For the non-script Open case, we have to make
|
|
|
|
// up a URL.
|
1999-06-25 01:53:22 +00:00
|
|
|
result = NS_NewURI(&sourceURL, "about:blank");
|
1999-05-28 00:18:48 +00:00
|
|
|
|
|
|
|
if (NS_SUCCEEDED(result)) {
|
|
|
|
result = OpenCommon(sourceURL);
|
|
|
|
NS_RELEASE(sourceURL);
|
|
|
|
}
|
|
|
|
|
|
|
|
return result;
|
|
|
|
}
|
|
|
|
|
|
|
|
NS_IMETHODIMP
|
|
|
|
nsHTMLDocument::Open(JSContext *cx, jsval *argv, PRUint32 argc)
|
|
|
|
{
|
|
|
|
nsresult result = NS_OK;
|
1999-06-23 03:29:44 +00:00
|
|
|
nsIURI* sourceURL;
|
1999-05-28 00:18:48 +00:00
|
|
|
|
|
|
|
// XXX The URL of the newly created document will match
|
|
|
|
// that of the source document. Is this right?
|
|
|
|
result = GetSourceDocumentURL(cx, &sourceURL);
|
|
|
|
// Recover if we had a problem obtaining the source URL
|
|
|
|
if (nsnull == sourceURL) {
|
1999-06-23 19:55:21 +00:00
|
|
|
result = NS_NewURI(&sourceURL, "about:blank");
|
1999-05-28 00:18:48 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
if (NS_SUCCEEDED(result)) {
|
|
|
|
result = OpenCommon(sourceURL);
|
|
|
|
NS_RELEASE(sourceURL);
|
|
|
|
}
|
|
|
|
|
1999-01-06 00:32:41 +00:00
|
|
|
return result;
|
1998-07-22 23:32:19 +00:00
|
|
|
}
|
|
|
|
|
1999-02-03 19:38:16 +00:00
|
|
|
#define NS_GENERATE_PARSER_KEY() (void*)((mIsWriting << 31) | (mWriteLevel & 0x7fffffff))
|
|
|
|
|
1999-12-14 23:34:17 +00:00
|
|
|
NS_IMETHODIMP
|
2000-02-03 00:25:53 +00:00
|
|
|
nsHTMLDocument::Clear(JSContext* cx, jsval* argv, PRUint32 argc)
|
1999-12-14 23:34:17 +00:00
|
|
|
{
|
2000-02-03 00:25:53 +00:00
|
|
|
return Open(cx, argv, argc);
|
1999-12-14 23:34:17 +00:00
|
|
|
}
|
|
|
|
|
1998-07-22 23:32:19 +00:00
|
|
|
NS_IMETHODIMP
|
|
|
|
nsHTMLDocument::Close()
|
|
|
|
{
|
1999-02-03 19:38:16 +00:00
|
|
|
nsresult result = NS_OK;
|
|
|
|
|
|
|
|
if ((nsnull != mParser) && mIsWriting) {
|
|
|
|
nsAutoString emptyStr("</HTML>");
|
|
|
|
mWriteLevel++;
|
|
|
|
result = mParser->Parse(emptyStr, NS_GENERATE_PARSER_KEY(),
|
1999-02-16 07:38:27 +00:00
|
|
|
"text/html", PR_FALSE, PR_TRUE);
|
1999-02-03 19:38:16 +00:00
|
|
|
mWriteLevel--;
|
|
|
|
mIsWriting = 0;
|
|
|
|
}
|
|
|
|
|
|
|
|
return NS_OK;
|
1998-07-22 23:32:19 +00:00
|
|
|
}
|
|
|
|
|
1999-01-06 00:32:41 +00:00
|
|
|
nsresult
|
1999-05-28 00:18:48 +00:00
|
|
|
nsHTMLDocument::WriteCommon(const nsString& aText,
|
1999-01-06 00:32:41 +00:00
|
|
|
PRBool aNewlineTerminate)
|
1998-07-22 23:32:19 +00:00
|
|
|
{
|
1998-07-23 22:06:05 +00:00
|
|
|
nsresult result = NS_OK;
|
|
|
|
|
1999-05-28 00:18:48 +00:00
|
|
|
if (nsnull == mParser) {
|
|
|
|
result = Open();
|
|
|
|
if (NS_OK != result) {
|
|
|
|
return result;
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
nsAutoString str(aText);
|
|
|
|
|
|
|
|
if (aNewlineTerminate) {
|
|
|
|
str.Append('\n');
|
|
|
|
}
|
|
|
|
|
|
|
|
mWriteLevel++;
|
|
|
|
result = mParser->Parse(str, NS_GENERATE_PARSER_KEY(),
|
|
|
|
"text/html", PR_FALSE,
|
|
|
|
(!mIsWriting || (mWriteLevel > 1)));
|
|
|
|
mWriteLevel--;
|
|
|
|
if (NS_OK != result) {
|
|
|
|
return result;
|
|
|
|
}
|
|
|
|
|
|
|
|
return result;
|
|
|
|
}
|
|
|
|
|
|
|
|
NS_IMETHODIMP
|
|
|
|
nsHTMLDocument::Write(const nsString& aText)
|
|
|
|
{
|
|
|
|
return WriteCommon(aText, PR_FALSE);
|
|
|
|
}
|
|
|
|
|
|
|
|
NS_IMETHODIMP
|
|
|
|
nsHTMLDocument::Writeln(const nsString& aText)
|
|
|
|
{
|
|
|
|
return WriteCommon(aText, PR_TRUE);
|
|
|
|
}
|
|
|
|
|
|
|
|
nsresult
|
|
|
|
nsHTMLDocument::ScriptWriteCommon(JSContext *cx,
|
|
|
|
jsval *argv,
|
|
|
|
PRUint32 argc,
|
|
|
|
PRBool aNewlineTerminate)
|
|
|
|
{
|
|
|
|
nsresult result = NS_OK;
|
|
|
|
|
1998-07-23 22:06:05 +00:00
|
|
|
if (nsnull == mParser) {
|
1999-01-06 00:32:41 +00:00
|
|
|
result = Open(cx, argv, argc);
|
1999-02-03 19:38:16 +00:00
|
|
|
if (NS_OK != result) {
|
|
|
|
return result;
|
|
|
|
}
|
1998-07-23 22:06:05 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
if (argc > 0) {
|
|
|
|
PRUint32 index;
|
1998-09-12 00:04:22 +00:00
|
|
|
nsAutoString str;
|
1999-01-06 00:32:41 +00:00
|
|
|
str.Truncate();
|
1998-07-23 22:06:05 +00:00
|
|
|
for (index = 0; index < argc; index++) {
|
|
|
|
JSString *jsstring = JS_ValueToString(cx, argv[index]);
|
|
|
|
|
|
|
|
if (nsnull != jsstring) {
|
1999-12-14 23:34:17 +00:00
|
|
|
str.Append(JS_GetStringChars(jsstring), JS_GetStringLength(jsstring));
|
1998-07-23 22:06:05 +00:00
|
|
|
}
|
|
|
|
}
|
1999-01-06 00:32:41 +00:00
|
|
|
|
|
|
|
if (aNewlineTerminate) {
|
|
|
|
str.Append('\n');
|
|
|
|
}
|
|
|
|
|
1999-02-03 19:38:16 +00:00
|
|
|
mWriteLevel++;
|
|
|
|
result = mParser->Parse(str, NS_GENERATE_PARSER_KEY(),
|
1999-02-16 07:38:27 +00:00
|
|
|
"text/html", PR_FALSE,
|
1999-02-03 19:38:16 +00:00
|
|
|
(!mIsWriting || (mWriteLevel > 1)));
|
|
|
|
mWriteLevel--;
|
1998-09-12 00:04:22 +00:00
|
|
|
if (NS_OK != result) {
|
|
|
|
return result;
|
|
|
|
}
|
1998-07-23 22:06:05 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
return result;
|
1998-07-22 23:32:19 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
NS_IMETHODIMP
|
1999-01-06 00:32:41 +00:00
|
|
|
nsHTMLDocument::Write(JSContext *cx, jsval *argv, PRUint32 argc)
|
1998-07-22 23:32:19 +00:00
|
|
|
{
|
1999-05-28 00:18:48 +00:00
|
|
|
return ScriptWriteCommon(cx, argv, argc, PR_FALSE);
|
1999-01-06 00:32:41 +00:00
|
|
|
}
|
1998-07-23 22:06:05 +00:00
|
|
|
|
1999-01-06 00:32:41 +00:00
|
|
|
NS_IMETHODIMP
|
|
|
|
nsHTMLDocument::Writeln(JSContext *cx, jsval *argv, PRUint32 argc)
|
|
|
|
{
|
1999-05-28 00:18:48 +00:00
|
|
|
return ScriptWriteCommon(cx, argv, argc, PR_TRUE);
|
1998-07-22 23:32:19 +00:00
|
|
|
}
|
|
|
|
|
1998-08-07 23:08:00 +00:00
|
|
|
nsIContent *
|
|
|
|
nsHTMLDocument::MatchName(nsIContent *aContent, const nsString& aName)
|
|
|
|
{
|
|
|
|
nsAutoString value;
|
|
|
|
nsIContent *result = nsnull;
|
|
|
|
|
1998-12-20 01:21:23 +00:00
|
|
|
if ((NS_CONTENT_ATTR_HAS_VALUE == aContent->GetAttribute(kNameSpaceID_HTML, nsHTMLAtoms::id, value)) &&
|
1998-08-07 23:08:00 +00:00
|
|
|
aName.Equals(value)) {
|
|
|
|
return aContent;
|
|
|
|
}
|
1998-12-20 01:21:23 +00:00
|
|
|
else if ((NS_CONTENT_ATTR_HAS_VALUE == aContent->GetAttribute(kNameSpaceID_HTML, nsHTMLAtoms::name, value)) &&
|
1998-08-07 23:08:00 +00:00
|
|
|
aName.Equals(value)) {
|
|
|
|
return aContent;
|
|
|
|
}
|
|
|
|
|
|
|
|
PRInt32 i, count;
|
1998-08-29 20:20:38 +00:00
|
|
|
aContent->ChildCount(count);
|
1998-08-07 23:08:00 +00:00
|
|
|
for (i = 0; i < count && result == nsnull; i++) {
|
1998-08-29 20:20:38 +00:00
|
|
|
nsIContent *child;
|
|
|
|
aContent->ChildAt(i, child);
|
1998-08-07 23:08:00 +00:00
|
|
|
result = MatchName(child, aName);
|
|
|
|
NS_RELEASE(child);
|
|
|
|
}
|
|
|
|
|
|
|
|
return result;
|
|
|
|
}
|
1998-07-22 23:32:19 +00:00
|
|
|
|
|
|
|
NS_IMETHODIMP
|
|
|
|
nsHTMLDocument::GetElementById(const nsString& aElementId, nsIDOMElement** aReturn)
|
1998-08-07 23:08:00 +00:00
|
|
|
{
|
|
|
|
nsIContent *content;
|
|
|
|
|
|
|
|
// XXX For now, we do a brute force search of the content tree.
|
|
|
|
// We should come up with a more efficient solution.
|
|
|
|
content = MatchName(mRootContent, aElementId);
|
|
|
|
|
|
|
|
if (nsnull != content) {
|
|
|
|
return content->QueryInterface(kIDOMElementIID, (void **)aReturn);
|
|
|
|
}
|
|
|
|
else {
|
|
|
|
*aReturn = nsnull;
|
|
|
|
}
|
|
|
|
|
|
|
|
return NS_OK;
|
|
|
|
}
|
|
|
|
|
1999-02-04 23:23:07 +00:00
|
|
|
PRBool
|
1999-05-04 20:53:44 +00:00
|
|
|
nsHTMLDocument::MatchNameAttribute(nsIContent* aContent, nsString* aData)
|
1999-02-04 23:23:07 +00:00
|
|
|
{
|
|
|
|
nsresult result;
|
|
|
|
nsAutoString name;
|
|
|
|
|
|
|
|
result = aContent->GetAttribute(kNameSpaceID_None,
|
|
|
|
nsHTMLAtoms::name,
|
|
|
|
name);
|
1999-05-04 20:53:44 +00:00
|
|
|
if ((result == NS_OK) && (nsnull != aData) && name.Equals(*aData)) {
|
1999-02-04 23:23:07 +00:00
|
|
|
return PR_TRUE;
|
|
|
|
}
|
|
|
|
else {
|
|
|
|
return PR_FALSE;
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
1998-08-07 23:08:00 +00:00
|
|
|
NS_IMETHODIMP
|
1999-02-04 23:23:07 +00:00
|
|
|
nsHTMLDocument::GetElementsByName(const nsString& aElementName,
|
|
|
|
nsIDOMNodeList** aReturn)
|
1998-07-22 23:32:19 +00:00
|
|
|
{
|
1999-02-04 23:23:07 +00:00
|
|
|
nsContentList* elements = new nsContentList(this,
|
|
|
|
MatchNameAttribute,
|
1999-05-04 20:53:44 +00:00
|
|
|
&aElementName);
|
1999-02-04 23:23:07 +00:00
|
|
|
if (nsnull == elements) {
|
|
|
|
return NS_ERROR_OUT_OF_MEMORY;
|
|
|
|
}
|
|
|
|
|
|
|
|
return elements->QueryInterface(kIDOMNodeListIID, (void**)aReturn);
|
1998-07-22 23:32:19 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
NS_IMETHODIMP
|
1998-08-07 23:08:00 +00:00
|
|
|
nsHTMLDocument::GetAlinkColor(nsString& aAlinkColor)
|
1998-07-22 23:32:19 +00:00
|
|
|
{
|
1999-02-04 02:58:02 +00:00
|
|
|
nsresult result = NS_OK;
|
|
|
|
nsIDOMHTMLBodyElement* body;
|
|
|
|
|
1999-07-07 04:52:27 +00:00
|
|
|
aAlinkColor.Truncate();
|
1999-02-04 23:23:07 +00:00
|
|
|
result = GetBodyElement(&body);
|
1999-02-04 02:58:02 +00:00
|
|
|
if (NS_OK == result) {
|
|
|
|
result = body->GetALink(aAlinkColor);
|
|
|
|
NS_RELEASE(body);
|
|
|
|
}
|
1999-07-07 04:52:27 +00:00
|
|
|
else if (nsnull != mAttrStyleSheet) {
|
|
|
|
nscolor color;
|
|
|
|
result = mAttrStyleSheet->GetActiveLinkColor(color);
|
|
|
|
if (NS_OK == result) {
|
|
|
|
nsHTMLValue value(color);
|
|
|
|
nsGenericHTMLElement::ColorToString(value, aAlinkColor);
|
|
|
|
}
|
|
|
|
}
|
1999-02-04 02:58:02 +00:00
|
|
|
|
1999-07-07 04:52:27 +00:00
|
|
|
return NS_OK;
|
1998-07-22 23:32:19 +00:00
|
|
|
}
|
|
|
|
|
1998-08-07 23:08:00 +00:00
|
|
|
NS_IMETHODIMP
|
|
|
|
nsHTMLDocument::SetAlinkColor(const nsString& aAlinkColor)
|
1998-08-04 00:05:22 +00:00
|
|
|
{
|
1999-02-04 02:58:02 +00:00
|
|
|
nsresult result = NS_OK;
|
|
|
|
nsIDOMHTMLBodyElement* body;
|
|
|
|
|
1999-02-04 23:23:07 +00:00
|
|
|
result = GetBodyElement(&body);
|
1999-02-04 02:58:02 +00:00
|
|
|
if (NS_OK == result) {
|
|
|
|
result = body->SetALink(aAlinkColor);
|
|
|
|
NS_RELEASE(body);
|
|
|
|
}
|
1999-07-07 04:52:27 +00:00
|
|
|
else if (nsnull != mAttrStyleSheet) {
|
|
|
|
nsHTMLValue value;
|
|
|
|
|
1999-07-18 00:22:29 +00:00
|
|
|
if (nsGenericHTMLElement::ParseColor(aAlinkColor, this, value)) {
|
1999-07-07 04:52:27 +00:00
|
|
|
mAttrStyleSheet->SetActiveLinkColor(value.GetColorValue());
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
return NS_OK;
|
1998-08-07 23:08:00 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
NS_IMETHODIMP
|
|
|
|
nsHTMLDocument::GetLinkColor(nsString& aLinkColor)
|
|
|
|
{
|
1999-02-04 02:58:02 +00:00
|
|
|
nsresult result = NS_OK;
|
|
|
|
nsIDOMHTMLBodyElement* body;
|
|
|
|
|
1999-07-07 04:52:27 +00:00
|
|
|
aLinkColor.Truncate();
|
1999-02-04 23:23:07 +00:00
|
|
|
result = GetBodyElement(&body);
|
1999-02-04 02:58:02 +00:00
|
|
|
if (NS_OK == result) {
|
|
|
|
result = body->GetLink(aLinkColor);
|
|
|
|
NS_RELEASE(body);
|
|
|
|
}
|
1999-07-07 04:52:27 +00:00
|
|
|
else if (nsnull != mAttrStyleSheet) {
|
|
|
|
nscolor color;
|
|
|
|
result = mAttrStyleSheet->GetLinkColor(color);
|
|
|
|
if (NS_OK == result) {
|
|
|
|
nsHTMLValue value(color);
|
|
|
|
nsGenericHTMLElement::ColorToString(value, aLinkColor);
|
|
|
|
}
|
|
|
|
}
|
1999-02-04 02:58:02 +00:00
|
|
|
|
1999-07-07 04:52:27 +00:00
|
|
|
return NS_OK;
|
1998-08-07 23:08:00 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
NS_IMETHODIMP
|
|
|
|
nsHTMLDocument::SetLinkColor(const nsString& aLinkColor)
|
|
|
|
{
|
1999-02-04 02:58:02 +00:00
|
|
|
nsresult result = NS_OK;
|
|
|
|
nsIDOMHTMLBodyElement* body;
|
|
|
|
|
1999-02-04 23:23:07 +00:00
|
|
|
result = GetBodyElement(&body);
|
1999-02-04 02:58:02 +00:00
|
|
|
if (NS_OK == result) {
|
|
|
|
result = body->SetLink(aLinkColor);
|
|
|
|
NS_RELEASE(body);
|
|
|
|
}
|
1999-07-07 04:52:27 +00:00
|
|
|
else if (nsnull != mAttrStyleSheet) {
|
|
|
|
nsHTMLValue value;
|
1999-07-18 00:22:29 +00:00
|
|
|
if (nsGenericHTMLElement::ParseColor(aLinkColor, this, value)) {
|
1999-07-07 04:52:27 +00:00
|
|
|
mAttrStyleSheet->SetLinkColor(value.GetColorValue());
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
return NS_OK;
|
1998-08-07 23:08:00 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
NS_IMETHODIMP
|
|
|
|
nsHTMLDocument::GetVlinkColor(nsString& aVlinkColor)
|
|
|
|
{
|
1999-02-04 02:58:02 +00:00
|
|
|
nsresult result = NS_OK;
|
|
|
|
nsIDOMHTMLBodyElement* body;
|
|
|
|
|
1999-07-07 04:52:27 +00:00
|
|
|
aVlinkColor.Truncate();
|
1999-02-04 23:23:07 +00:00
|
|
|
result = GetBodyElement(&body);
|
1999-02-04 02:58:02 +00:00
|
|
|
if (NS_OK == result) {
|
1999-07-08 19:55:47 +00:00
|
|
|
result = body->GetVLink(aVlinkColor);
|
1999-02-04 02:58:02 +00:00
|
|
|
NS_RELEASE(body);
|
|
|
|
}
|
1999-07-07 04:52:27 +00:00
|
|
|
else if (nsnull != mAttrStyleSheet) {
|
|
|
|
nscolor color;
|
|
|
|
result = mAttrStyleSheet->GetVisitedLinkColor(color);
|
|
|
|
if (NS_OK == result) {
|
|
|
|
nsHTMLValue value(color);
|
|
|
|
nsGenericHTMLElement::ColorToString(value, aVlinkColor);
|
|
|
|
}
|
|
|
|
}
|
1999-02-04 02:58:02 +00:00
|
|
|
|
1999-07-07 04:52:27 +00:00
|
|
|
return NS_OK;
|
1998-08-07 23:08:00 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
NS_IMETHODIMP
|
|
|
|
nsHTMLDocument::SetVlinkColor(const nsString& aVlinkColor)
|
|
|
|
{
|
1999-02-04 02:58:02 +00:00
|
|
|
nsresult result = NS_OK;
|
|
|
|
nsIDOMHTMLBodyElement* body;
|
|
|
|
|
1999-02-04 23:23:07 +00:00
|
|
|
result = GetBodyElement(&body);
|
1999-02-04 02:58:02 +00:00
|
|
|
if (NS_OK == result) {
|
|
|
|
result = body->SetVLink(aVlinkColor);
|
|
|
|
NS_RELEASE(body);
|
|
|
|
}
|
1999-07-07 04:52:27 +00:00
|
|
|
else if (nsnull != mAttrStyleSheet) {
|
|
|
|
nsHTMLValue value;
|
1999-07-18 00:22:29 +00:00
|
|
|
if (nsGenericHTMLElement::ParseColor(aVlinkColor, this, value)) {
|
1999-07-07 04:52:27 +00:00
|
|
|
mAttrStyleSheet->SetVisitedLinkColor(value.GetColorValue());
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
return NS_OK;
|
1998-08-07 23:08:00 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
NS_IMETHODIMP
|
|
|
|
nsHTMLDocument::GetBgColor(nsString& aBgColor)
|
|
|
|
{
|
1999-02-04 02:58:02 +00:00
|
|
|
nsresult result = NS_OK;
|
|
|
|
nsIDOMHTMLBodyElement* body;
|
|
|
|
|
1999-07-07 04:52:27 +00:00
|
|
|
aBgColor.Truncate();
|
1999-02-04 23:23:07 +00:00
|
|
|
result = GetBodyElement(&body);
|
1999-02-04 02:58:02 +00:00
|
|
|
if (NS_OK == result) {
|
|
|
|
result = body->GetBgColor(aBgColor);
|
|
|
|
NS_RELEASE(body);
|
|
|
|
}
|
1999-07-07 04:52:27 +00:00
|
|
|
else if (nsnull != mAttrStyleSheet) {
|
|
|
|
nscolor color;
|
|
|
|
result = mAttrStyleSheet->GetDocumentBackgroundColor(color);
|
|
|
|
if (NS_OK == result) {
|
|
|
|
nsHTMLValue value(color);
|
|
|
|
nsGenericHTMLElement::ColorToString(value, aBgColor);
|
|
|
|
}
|
|
|
|
}
|
1999-02-04 02:58:02 +00:00
|
|
|
|
1999-07-07 04:52:27 +00:00
|
|
|
return NS_OK;
|
1998-08-07 23:08:00 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
NS_IMETHODIMP
|
|
|
|
nsHTMLDocument::SetBgColor(const nsString& aBgColor)
|
|
|
|
{
|
1999-02-04 02:58:02 +00:00
|
|
|
nsresult result = NS_OK;
|
|
|
|
nsIDOMHTMLBodyElement* body;
|
|
|
|
|
1999-02-04 23:23:07 +00:00
|
|
|
result = GetBodyElement(&body);
|
1999-02-04 02:58:02 +00:00
|
|
|
if (NS_OK == result) {
|
|
|
|
result = body->SetBgColor(aBgColor);
|
|
|
|
NS_RELEASE(body);
|
|
|
|
}
|
1999-07-07 04:52:27 +00:00
|
|
|
else if (nsnull != mAttrStyleSheet) {
|
|
|
|
nsHTMLValue value;
|
1999-07-18 00:22:29 +00:00
|
|
|
if (nsGenericHTMLElement::ParseColor(aBgColor, this, value)) {
|
1999-07-07 04:52:27 +00:00
|
|
|
mAttrStyleSheet->SetDocumentBackgroundColor(value.GetColorValue());
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
return NS_OK;
|
1998-08-07 23:08:00 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
NS_IMETHODIMP
|
|
|
|
nsHTMLDocument::GetFgColor(nsString& aFgColor)
|
|
|
|
{
|
1999-02-04 02:58:02 +00:00
|
|
|
nsresult result = NS_OK;
|
|
|
|
nsIDOMHTMLBodyElement* body;
|
|
|
|
|
1999-07-07 04:52:27 +00:00
|
|
|
aFgColor.Truncate();
|
1999-02-04 23:23:07 +00:00
|
|
|
result = GetBodyElement(&body);
|
1999-02-04 02:58:02 +00:00
|
|
|
if (NS_OK == result) {
|
|
|
|
result = body->GetText(aFgColor);
|
|
|
|
NS_RELEASE(body);
|
|
|
|
}
|
1999-07-07 04:52:27 +00:00
|
|
|
else if (nsnull != mAttrStyleSheet) {
|
|
|
|
nscolor color;
|
|
|
|
result = mAttrStyleSheet->GetDocumentForegroundColor(color);
|
|
|
|
if (NS_OK == result) {
|
|
|
|
nsHTMLValue value(color);
|
|
|
|
nsGenericHTMLElement::ColorToString(value, aFgColor);
|
|
|
|
}
|
|
|
|
}
|
1999-02-04 02:58:02 +00:00
|
|
|
|
1999-07-07 04:52:27 +00:00
|
|
|
return NS_OK;
|
1998-08-07 23:08:00 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
NS_IMETHODIMP
|
|
|
|
nsHTMLDocument::SetFgColor(const nsString& aFgColor)
|
|
|
|
{
|
1999-02-04 02:58:02 +00:00
|
|
|
nsresult result = NS_OK;
|
|
|
|
nsIDOMHTMLBodyElement* body;
|
|
|
|
|
1999-02-04 23:23:07 +00:00
|
|
|
result = GetBodyElement(&body);
|
1999-02-04 02:58:02 +00:00
|
|
|
if (NS_OK == result) {
|
|
|
|
result = body->SetText(aFgColor);
|
|
|
|
NS_RELEASE(body);
|
|
|
|
}
|
1999-07-07 04:52:27 +00:00
|
|
|
else if (nsnull != mAttrStyleSheet) {
|
|
|
|
nsHTMLValue value;
|
|
|
|
|
1999-07-18 00:22:29 +00:00
|
|
|
if (nsGenericHTMLElement::ParseColor(aFgColor, this, value)) {
|
1999-07-07 04:52:27 +00:00
|
|
|
mAttrStyleSheet->SetDocumentForegroundColor(value.GetColorValue());
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
return NS_OK;
|
1998-08-07 23:08:00 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
NS_IMETHODIMP
|
|
|
|
nsHTMLDocument::GetLastModified(nsString& aLastModified)
|
|
|
|
{
|
1999-08-09 19:10:24 +00:00
|
|
|
if (nsnull != mLastModified) {
|
|
|
|
aLastModified = *mLastModified;
|
|
|
|
}
|
|
|
|
else {
|
2000-03-12 09:14:14 +00:00
|
|
|
aLastModified.Assign("January 1, 1970 GMT");
|
1999-08-09 19:10:24 +00:00
|
|
|
}
|
|
|
|
|
1999-06-28 23:39:25 +00:00
|
|
|
return NS_OK;
|
1998-08-07 23:08:00 +00:00
|
|
|
}
|
|
|
|
|
1998-10-06 01:39:33 +00:00
|
|
|
|
1998-08-07 23:08:00 +00:00
|
|
|
NS_IMETHODIMP
|
|
|
|
nsHTMLDocument::GetEmbeds(nsIDOMHTMLCollection** aEmbeds)
|
|
|
|
{
|
1998-09-25 00:51:45 +00:00
|
|
|
if (nsnull == mEmbeds) {
|
1999-01-15 19:18:30 +00:00
|
|
|
mEmbeds = new nsContentList(this, nsHTMLAtoms::embed, kNameSpaceID_HTML);
|
1998-09-25 00:51:45 +00:00
|
|
|
if (nsnull == mEmbeds) {
|
|
|
|
return NS_ERROR_OUT_OF_MEMORY;
|
|
|
|
}
|
|
|
|
NS_ADDREF(mEmbeds);
|
|
|
|
}
|
|
|
|
|
|
|
|
*aEmbeds = (nsIDOMHTMLCollection *)mEmbeds;
|
|
|
|
NS_ADDREF(mEmbeds);
|
|
|
|
|
|
|
|
return NS_OK;
|
1998-08-07 23:08:00 +00:00
|
|
|
}
|
|
|
|
|
1999-05-17 21:17:48 +00:00
|
|
|
PRBool
|
|
|
|
nsHTMLDocument::MatchLayers(nsIContent *aContent, nsString* aData)
|
|
|
|
{
|
|
|
|
nsIAtom *name;
|
|
|
|
aContent->GetTag(name);
|
|
|
|
nsAutoString attr;
|
|
|
|
PRBool result = PR_FALSE;
|
|
|
|
|
|
|
|
if ((nsnull != name) &&
|
|
|
|
((nsHTMLAtoms::layer == name) || (nsHTMLAtoms::ilayer == name))) {
|
|
|
|
result = PR_TRUE;
|
|
|
|
}
|
|
|
|
|
|
|
|
NS_IF_RELEASE(name);
|
|
|
|
return result;
|
|
|
|
}
|
|
|
|
|
2000-01-18 23:35:47 +00:00
|
|
|
#ifdef NS_IMPLEMENT_DOCUMENT_LAYERS
|
1998-08-07 23:08:00 +00:00
|
|
|
NS_IMETHODIMP
|
|
|
|
nsHTMLDocument::GetLayers(nsIDOMHTMLCollection** aLayers)
|
|
|
|
{
|
1999-05-17 21:17:48 +00:00
|
|
|
if (nsnull == mLayers) {
|
1999-06-30 00:14:21 +00:00
|
|
|
mLayers = new nsContentList(this, MatchLayers, nsnull);
|
1999-05-17 21:17:48 +00:00
|
|
|
if (nsnull == mLayers) {
|
|
|
|
return NS_ERROR_OUT_OF_MEMORY;
|
|
|
|
}
|
|
|
|
NS_ADDREF(mLayers);
|
|
|
|
}
|
|
|
|
|
|
|
|
*aLayers = (nsIDOMHTMLCollection *)mLayers;
|
|
|
|
NS_ADDREF(mLayers);
|
|
|
|
*aLayers = nsnull;
|
|
|
|
|
|
|
|
return NS_OK;
|
1998-08-07 23:08:00 +00:00
|
|
|
}
|
2000-01-18 23:35:47 +00:00
|
|
|
#endif
|
1998-08-07 23:08:00 +00:00
|
|
|
|
|
|
|
NS_IMETHODIMP
|
|
|
|
nsHTMLDocument::GetPlugins(nsIDOMHTMLCollection** aPlugins)
|
|
|
|
{
|
1999-06-28 23:39:25 +00:00
|
|
|
//XXX TBImplemented
|
|
|
|
*aPlugins = nsnull;
|
|
|
|
return NS_OK;
|
1998-08-07 23:08:00 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
NS_IMETHODIMP
|
|
|
|
nsHTMLDocument::GetSelection(nsString& aReturn)
|
|
|
|
{
|
1999-06-28 23:39:25 +00:00
|
|
|
//XXX TBImplemented
|
|
|
|
aReturn.Truncate();
|
|
|
|
return NS_OK;
|
1998-08-07 23:08:00 +00:00
|
|
|
}
|
|
|
|
|
1999-09-21 14:18:52 +00:00
|
|
|
NS_IMETHODIMP
|
|
|
|
nsHTMLDocument::CaptureEvents(PRInt32 aEventFlags)
|
|
|
|
{
|
|
|
|
nsIEventListenerManager *manager;
|
|
|
|
|
|
|
|
if (NS_OK == GetListenerManager(&manager)) {
|
2000-02-16 06:59:07 +00:00
|
|
|
manager->CaptureEvent(aEventFlags);
|
1999-09-21 14:18:52 +00:00
|
|
|
NS_RELEASE(manager);
|
|
|
|
return NS_OK;
|
|
|
|
}
|
2000-02-16 06:59:07 +00:00
|
|
|
|
1999-09-21 14:18:52 +00:00
|
|
|
return NS_ERROR_FAILURE;
|
|
|
|
}
|
|
|
|
|
|
|
|
NS_IMETHODIMP
|
|
|
|
nsHTMLDocument::ReleaseEvents(PRInt32 aEventFlags)
|
|
|
|
{
|
2000-02-16 06:59:07 +00:00
|
|
|
nsIEventListenerManager *manager;
|
|
|
|
|
|
|
|
if (NS_OK == GetListenerManager(&manager)) {
|
|
|
|
manager->ReleaseEvent(aEventFlags);
|
|
|
|
NS_RELEASE(manager);
|
1999-09-21 14:18:52 +00:00
|
|
|
return NS_OK;
|
|
|
|
}
|
2000-02-16 06:59:07 +00:00
|
|
|
|
1999-09-21 14:18:52 +00:00
|
|
|
return NS_ERROR_FAILURE;
|
|
|
|
}
|
|
|
|
|
|
|
|
NS_IMETHODIMP
|
|
|
|
nsHTMLDocument::RouteEvent(nsIDOMEvent* aEvt)
|
|
|
|
{
|
|
|
|
//XXX Not the best solution -joki
|
|
|
|
return NS_OK;
|
|
|
|
}
|
|
|
|
|
1998-08-07 23:08:00 +00:00
|
|
|
PRIntn
|
|
|
|
nsHTMLDocument::RemoveStrings(PLHashEntry *he, PRIntn i, void *arg)
|
|
|
|
{
|
|
|
|
char *str = (char *)he->key;
|
|
|
|
|
1999-10-26 14:56:41 +00:00
|
|
|
Recycle(str);
|
1998-08-07 23:08:00 +00:00
|
|
|
return HT_ENUMERATE_REMOVE;
|
|
|
|
}
|
|
|
|
|
|
|
|
void
|
|
|
|
nsHTMLDocument::DeleteNamedItems()
|
|
|
|
{
|
|
|
|
if (nsnull != mNamedItems) {
|
|
|
|
PL_HashTableEnumerateEntries(mNamedItems, RemoveStrings, nsnull);
|
|
|
|
PL_HashTableDestroy(mNamedItems);
|
|
|
|
mNamedItems = nsnull;
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
1998-11-28 23:51:06 +00:00
|
|
|
static PRBool
|
|
|
|
IsNamedItem(nsIContent* aContent, nsIAtom *aTag,
|
|
|
|
PRBool aInForm, nsString& aName)
|
1998-08-07 23:08:00 +00:00
|
|
|
{
|
|
|
|
// Only the content types reflected in Level 0 with a NAME
|
1999-05-17 21:17:48 +00:00
|
|
|
// attribute are registered. Images, layers and forms always get
|
1998-08-07 23:08:00 +00:00
|
|
|
// reflected up to the document. Applets and embeds only go
|
|
|
|
// to the closest container (which could be a form).
|
1998-11-28 23:51:06 +00:00
|
|
|
if ((aTag == nsHTMLAtoms::img) || (aTag == nsHTMLAtoms::form) ||
|
|
|
|
(!aInForm && ((aTag == nsHTMLAtoms::applet) ||
|
|
|
|
(aTag == nsHTMLAtoms::embed)))) {
|
1999-09-30 22:07:04 +00:00
|
|
|
if ((NS_CONTENT_ATTR_HAS_VALUE == aContent->GetAttribute(kNameSpaceID_HTML, nsHTMLAtoms::name, aName)) ||
|
|
|
|
(NS_CONTENT_ATTR_HAS_VALUE == aContent->GetAttribute(kNameSpaceID_HTML, nsHTMLAtoms::id, aName))) {
|
1998-11-28 23:51:06 +00:00
|
|
|
return PR_TRUE;
|
1998-08-07 23:08:00 +00:00
|
|
|
}
|
|
|
|
}
|
|
|
|
|
1999-12-14 23:34:17 +00:00
|
|
|
#ifdef NS_IMPLEMENT_DOCUMENT_LAYERS
|
1999-05-17 21:17:48 +00:00
|
|
|
if ((aTag == nsHTMLAtoms::layer) || (aTag == nsHTMLAtoms::ilayer)) {
|
|
|
|
if ((NS_CONTENT_ATTR_HAS_VALUE == aContent->GetAttribute(kNameSpaceID_HTML, nsHTMLAtoms::name, aName)) ||
|
|
|
|
(NS_CONTENT_ATTR_HAS_VALUE == aContent->GetAttribute(kNameSpaceID_HTML, nsHTMLAtoms::id, aName))) {
|
|
|
|
return PR_TRUE;
|
|
|
|
}
|
|
|
|
}
|
1999-12-14 23:34:17 +00:00
|
|
|
#endif
|
1999-05-17 21:17:48 +00:00
|
|
|
|
1998-11-28 23:51:06 +00:00
|
|
|
return PR_FALSE;
|
|
|
|
}
|
|
|
|
|
|
|
|
void
|
|
|
|
nsHTMLDocument::UnregisterNamedItems(nsIContent *aContent, PRBool aInForm)
|
|
|
|
{
|
|
|
|
nsAutoString value;
|
|
|
|
nsIAtom *tag;
|
|
|
|
aContent->GetTag(tag);
|
|
|
|
PRBool inForm;
|
|
|
|
|
|
|
|
if (IsNamedItem(aContent, tag, aInForm, value)) {
|
|
|
|
char *nameStr = value.ToNewCString();
|
|
|
|
// XXX What about the string held in the hash table entry
|
|
|
|
PL_HashTableRemove(mNamedItems, nameStr);
|
1999-10-26 14:56:41 +00:00
|
|
|
Recycle(nameStr);
|
1998-11-28 23:51:06 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
inForm = aInForm || (tag == nsHTMLAtoms::form);
|
|
|
|
NS_IF_RELEASE(tag);
|
|
|
|
|
|
|
|
PRInt32 i, count;
|
|
|
|
aContent->ChildCount(count);
|
|
|
|
for (i = 0; i < count; i++) {
|
|
|
|
nsIContent *child;
|
|
|
|
aContent->ChildAt(i, child);
|
|
|
|
UnregisterNamedItems(child, inForm);
|
|
|
|
NS_RELEASE(child);
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
void
|
|
|
|
nsHTMLDocument::RegisterNamedItems(nsIContent *aContent, PRBool aInForm)
|
|
|
|
{
|
|
|
|
nsAutoString value;
|
|
|
|
nsIAtom *tag;
|
|
|
|
aContent->GetTag(tag);
|
|
|
|
PRBool inForm;
|
|
|
|
|
|
|
|
if (IsNamedItem(aContent, tag, aInForm, value)) {
|
|
|
|
char *nameStr = value.ToNewCString();
|
|
|
|
PL_HashTableAdd(mNamedItems, nameStr, aContent);
|
|
|
|
}
|
|
|
|
|
1998-08-07 23:08:00 +00:00
|
|
|
inForm = aInForm || (tag == nsHTMLAtoms::form);
|
|
|
|
NS_IF_RELEASE(tag);
|
|
|
|
|
|
|
|
PRInt32 i, count;
|
1998-08-29 20:20:38 +00:00
|
|
|
aContent->ChildCount(count);
|
1998-08-07 23:08:00 +00:00
|
|
|
for (i = 0; i < count; i++) {
|
1998-08-29 20:20:38 +00:00
|
|
|
nsIContent *child;
|
|
|
|
aContent->ChildAt(i, child);
|
1998-08-07 23:08:00 +00:00
|
|
|
RegisterNamedItems(child, inForm);
|
|
|
|
NS_RELEASE(child);
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
1998-11-28 23:51:06 +00:00
|
|
|
nsIContent*
|
|
|
|
nsHTMLDocument::FindNamedItem(nsIContent *aContent,
|
|
|
|
const nsString& aName,
|
|
|
|
PRBool aInForm)
|
|
|
|
{
|
|
|
|
nsAutoString value;
|
|
|
|
nsIAtom *tag;
|
|
|
|
aContent->GetTag(tag);
|
|
|
|
PRBool inForm;
|
|
|
|
|
|
|
|
if (IsNamedItem(aContent, tag, aInForm, value)) {
|
|
|
|
if (aName.Equals(value)) {
|
|
|
|
NS_IF_RELEASE(tag);
|
|
|
|
return aContent;
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
inForm = aInForm || (tag == nsHTMLAtoms::form);
|
|
|
|
NS_IF_RELEASE(tag);
|
|
|
|
|
|
|
|
PRInt32 i, count;
|
|
|
|
nsIContent *result = nsnull;
|
|
|
|
aContent->ChildCount(count);
|
|
|
|
for (i = 0; (i < count) && (nsnull == result); i++) {
|
|
|
|
nsIContent *child;
|
|
|
|
aContent->ChildAt(i, child);
|
|
|
|
result = FindNamedItem(child, aName, inForm);
|
|
|
|
NS_RELEASE(child);
|
|
|
|
}
|
|
|
|
|
|
|
|
return result;
|
|
|
|
}
|
|
|
|
|
1998-08-07 23:08:00 +00:00
|
|
|
NS_IMETHODIMP
|
|
|
|
nsHTMLDocument::NamedItem(const nsString& aName, nsIDOMElement** aReturn)
|
|
|
|
{
|
|
|
|
nsresult result = NS_OK;
|
1998-11-28 23:51:06 +00:00
|
|
|
nsIContent *content = nsnull;
|
|
|
|
|
|
|
|
// XXX If we have a parser, it means that we're still loading the
|
|
|
|
// document. Since there's still content coming in (and not all
|
|
|
|
// may yet have been explicitly added to the document), we do
|
|
|
|
// a depth-first search rather than build up a table.
|
|
|
|
// Obviously, this may be inefficient for large documents.
|
|
|
|
if (nsnull != mParser) {
|
|
|
|
content = FindNamedItem(mRootContent, aName, PR_FALSE);
|
1998-08-07 23:08:00 +00:00
|
|
|
}
|
1998-11-28 23:51:06 +00:00
|
|
|
else {
|
|
|
|
// If the document has completed loading, we build a table and
|
|
|
|
// cache the named items. The table will be updated as content
|
|
|
|
// is added and removed.
|
|
|
|
if (nsnull == mNamedItems) {
|
|
|
|
mNamedItems = PL_NewHashTable(10, PL_HashString, PL_CompareStrings,
|
|
|
|
PL_CompareValues, nsnull, nsnull);
|
|
|
|
RegisterNamedItems(mRootContent, PR_FALSE);
|
|
|
|
}
|
1998-08-07 23:08:00 +00:00
|
|
|
|
1998-11-28 23:51:06 +00:00
|
|
|
char *str = aName.ToNewCString();
|
|
|
|
content = (nsIContent *)PL_HashTableLookup(mNamedItems, str);
|
1999-10-26 14:56:41 +00:00
|
|
|
Recycle(str);
|
1998-11-28 23:51:06 +00:00
|
|
|
}
|
1998-08-07 23:08:00 +00:00
|
|
|
|
|
|
|
if (nsnull != content) {
|
|
|
|
result = content->QueryInterface(kIDOMElementIID, (void **)aReturn);
|
|
|
|
}
|
|
|
|
else {
|
|
|
|
*aReturn = nsnull;
|
|
|
|
}
|
|
|
|
|
|
|
|
return result;
|
1998-08-04 00:05:22 +00:00
|
|
|
}
|
1998-07-22 23:32:19 +00:00
|
|
|
|
|
|
|
NS_IMETHODIMP
|
|
|
|
nsHTMLDocument::GetScriptObject(nsIScriptContext *aContext, void** aScriptObject)
|
|
|
|
{
|
|
|
|
nsresult res = NS_OK;
|
1999-09-14 04:17:07 +00:00
|
|
|
nsCOMPtr<nsIScriptGlobalObject> global;
|
1998-07-22 23:32:19 +00:00
|
|
|
|
|
|
|
if (nsnull == mScriptObject) {
|
1999-09-14 04:17:07 +00:00
|
|
|
// XXX We make the (possibly erroneous) assumption that the first
|
|
|
|
// presentation shell represents the "primary view" of the document
|
|
|
|
// and that the JS parent chain should incorporate just that view.
|
|
|
|
// This is done for lack of a better model when we have multiple
|
|
|
|
// views.
|
|
|
|
nsIPresShell* shell = (nsIPresShell*) mPresShells.ElementAt(0);
|
|
|
|
if (shell) {
|
|
|
|
nsCOMPtr<nsIPresContext> cx;
|
|
|
|
shell->GetPresContext(getter_AddRefs(cx));
|
|
|
|
nsCOMPtr<nsISupports> container;
|
|
|
|
|
|
|
|
res = cx->GetContainer(getter_AddRefs(container));
|
|
|
|
if (NS_SUCCEEDED(res) && container) {
|
1999-12-03 09:24:22 +00:00
|
|
|
global = do_GetInterface(container);
|
1999-09-14 04:17:07 +00:00
|
|
|
}
|
|
|
|
}
|
|
|
|
// XXX If we can't find a view, parent to the calling context's
|
|
|
|
// global object. This may not be right either, but we need
|
|
|
|
// something.
|
|
|
|
else {
|
|
|
|
global = getter_AddRefs(aContext->GetGlobalObject());
|
|
|
|
}
|
|
|
|
|
|
|
|
if (NS_SUCCEEDED(res)) {
|
|
|
|
res = NS_NewScriptHTMLDocument(aContext,
|
|
|
|
(nsISupports *)(nsIDOMHTMLDocument *)this,
|
|
|
|
(nsISupports *)global,
|
|
|
|
(void**)&mScriptObject);
|
|
|
|
}
|
1998-07-22 23:32:19 +00:00
|
|
|
}
|
1999-09-14 04:17:07 +00:00
|
|
|
|
1998-07-22 23:32:19 +00:00
|
|
|
*aScriptObject = mScriptObject;
|
|
|
|
|
|
|
|
return res;
|
|
|
|
}
|
|
|
|
|
1999-11-25 00:05:21 +00:00
|
|
|
PRBool
|
1999-12-18 20:29:29 +00:00
|
|
|
nsHTMLDocument::Resolve(JSContext *aContext, JSObject *aObj, jsval aID)
|
1999-11-25 00:05:21 +00:00
|
|
|
{
|
2000-03-14 03:18:43 +00:00
|
|
|
if (!JSVAL_IS_STRING(aID)) {
|
|
|
|
return PR_TRUE;
|
|
|
|
}
|
|
|
|
|
1999-11-29 20:44:36 +00:00
|
|
|
nsresult result;
|
1999-11-25 00:05:21 +00:00
|
|
|
nsCOMPtr<nsIDOMElement> element;
|
1999-11-29 20:44:36 +00:00
|
|
|
char* str = JS_GetStringBytes(JSVAL_TO_STRING(aID));
|
1999-11-25 00:05:21 +00:00
|
|
|
nsAutoString name(str);
|
|
|
|
PRBool ret = PR_TRUE;
|
|
|
|
|
|
|
|
result = NamedItem(name, getter_AddRefs(element));
|
|
|
|
if (NS_SUCCEEDED(result) && element) {
|
|
|
|
nsCOMPtr<nsIScriptObjectOwner> owner = do_QueryInterface(element);
|
|
|
|
|
|
|
|
if (owner) {
|
|
|
|
nsCOMPtr<nsIScriptContext> scriptContext;
|
1999-12-18 20:29:29 +00:00
|
|
|
nsLayoutUtils::GetStaticScriptContext(aContext, aObj,
|
|
|
|
getter_AddRefs(scriptContext));
|
1999-11-25 00:05:21 +00:00
|
|
|
if (scriptContext) {
|
1999-11-29 20:44:36 +00:00
|
|
|
JSObject* obj;
|
1999-11-25 00:05:21 +00:00
|
|
|
result = owner->GetScriptObject(scriptContext, (void**)&obj);
|
1999-11-29 20:44:36 +00:00
|
|
|
if (NS_SUCCEEDED(result) && obj) {
|
1999-12-18 20:29:29 +00:00
|
|
|
ret = ::JS_DefineProperty(aContext, aObj,
|
|
|
|
str, OBJECT_TO_JSVAL(obj),
|
|
|
|
nsnull, nsnull, 0);
|
1999-11-25 00:05:21 +00:00
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
if (NS_FAILED(result)) {
|
|
|
|
ret = PR_FALSE;
|
|
|
|
}
|
|
|
|
|
|
|
|
return ret;
|
|
|
|
}
|
1998-08-28 15:55:31 +00:00
|
|
|
|
|
|
|
//----------------------------
|
1999-04-01 23:54:23 +00:00
|
|
|
static PRBool IsInline(eHTMLTags aTag)
|
1998-08-28 15:55:31 +00:00
|
|
|
{
|
|
|
|
PRBool result = PR_FALSE;
|
|
|
|
|
|
|
|
switch (aTag)
|
|
|
|
{
|
|
|
|
case eHTMLTag_a:
|
|
|
|
case eHTMLTag_address:
|
|
|
|
case eHTMLTag_big:
|
|
|
|
case eHTMLTag_blink:
|
|
|
|
case eHTMLTag_b:
|
|
|
|
case eHTMLTag_br:
|
|
|
|
case eHTMLTag_cite:
|
|
|
|
case eHTMLTag_code:
|
|
|
|
case eHTMLTag_dfn:
|
|
|
|
case eHTMLTag_em:
|
|
|
|
case eHTMLTag_font:
|
|
|
|
case eHTMLTag_img:
|
|
|
|
case eHTMLTag_i:
|
|
|
|
case eHTMLTag_kbd:
|
|
|
|
case eHTMLTag_keygen:
|
|
|
|
case eHTMLTag_nobr:
|
|
|
|
case eHTMLTag_samp:
|
|
|
|
case eHTMLTag_small:
|
|
|
|
case eHTMLTag_spacer:
|
|
|
|
case eHTMLTag_span:
|
|
|
|
case eHTMLTag_strike:
|
|
|
|
case eHTMLTag_strong:
|
|
|
|
case eHTMLTag_sub:
|
|
|
|
case eHTMLTag_sup:
|
|
|
|
case eHTMLTag_td:
|
|
|
|
case eHTMLTag_textarea:
|
|
|
|
case eHTMLTag_tt:
|
|
|
|
case eHTMLTag_var:
|
|
|
|
case eHTMLTag_wbr:
|
|
|
|
|
|
|
|
result = PR_TRUE;
|
|
|
|
break;
|
|
|
|
|
|
|
|
default:
|
|
|
|
break;
|
|
|
|
|
|
|
|
}
|
|
|
|
return result;
|
|
|
|
}
|
|
|
|
|
|
|
|
//----------------------------
|
1999-04-01 23:54:23 +00:00
|
|
|
static PRBool IsBlockLevel(eHTMLTags aTag, PRBool &isPreTag)
|
1998-08-28 15:55:31 +00:00
|
|
|
{
|
|
|
|
isPreTag = (aTag == eHTMLTag_pre);
|
|
|
|
|
|
|
|
return !IsInline(aTag);
|
|
|
|
}
|
|
|
|
|
|
|
|
//----------------------------
|
|
|
|
class SubText {
|
|
|
|
public:
|
1998-09-08 22:13:29 +00:00
|
|
|
nsIDOMNode * mContentNode;
|
1998-08-28 15:55:31 +00:00
|
|
|
PRInt32 mOffset;
|
|
|
|
PRInt32 mLength;
|
|
|
|
};
|
|
|
|
|
|
|
|
//----------------------------
|
|
|
|
class BlockText {
|
|
|
|
nsString mText;
|
|
|
|
SubText * mSubTexts[512];
|
|
|
|
PRInt32 mNumSubTexts;
|
|
|
|
public:
|
1998-09-08 22:13:29 +00:00
|
|
|
BlockText() : mNumSubTexts(0) { PRInt32 i; for (i=0;i<512;i++) mSubTexts[i] = 0; } // debug only
|
1998-08-28 15:55:31 +00:00
|
|
|
virtual ~BlockText();
|
|
|
|
|
1998-09-08 22:13:29 +00:00
|
|
|
char * GetText() { return mText.ToNewCString(); }
|
1998-08-28 18:15:14 +00:00
|
|
|
const nsString & GetNSString() { return mText; }
|
|
|
|
|
1998-09-08 22:13:29 +00:00
|
|
|
void ClearBlock();
|
|
|
|
PRInt32 GetNumItems() { return mNumSubTexts; }
|
1998-09-03 20:09:33 +00:00
|
|
|
|
1998-09-08 22:13:29 +00:00
|
|
|
void AddSubText(nsIDOMNode * aNode, nsString & aStr, PRInt32 aDirection, PRInt32 & aOffset);
|
1998-08-28 15:55:31 +00:00
|
|
|
PRInt32 GetStartEnd(PRInt32 anIndex, PRInt32 aLength,
|
1998-09-08 22:13:29 +00:00
|
|
|
nsIDOMNode ** aStartNode, PRInt32 & aStartOffset,
|
|
|
|
nsIDOMNode ** aEndNode, PRInt32 & aEndOffset,
|
1998-08-28 15:55:31 +00:00
|
|
|
PRInt32 aDirection);
|
|
|
|
};
|
|
|
|
|
|
|
|
//----------------------------
|
|
|
|
BlockText::~BlockText()
|
1998-09-03 20:09:33 +00:00
|
|
|
{
|
|
|
|
ClearBlock();
|
|
|
|
}
|
|
|
|
|
|
|
|
//----------------------------
|
|
|
|
void BlockText::ClearBlock()
|
1998-08-28 15:55:31 +00:00
|
|
|
{
|
|
|
|
PRInt32 i;
|
|
|
|
for (i=0;i<mNumSubTexts;i++) {
|
|
|
|
delete mSubTexts[i];
|
|
|
|
}
|
1998-09-03 20:09:33 +00:00
|
|
|
mNumSubTexts = 0;
|
|
|
|
mText.SetLength(0);
|
1998-08-28 15:55:31 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
//----------------------------
|
1998-09-08 22:13:29 +00:00
|
|
|
void BlockText::AddSubText(nsIDOMNode * aNode, nsString & aStr, PRInt32 aDirection, PRInt32 & aOffset)
|
|
|
|
{
|
1999-07-18 06:35:52 +00:00
|
|
|
SubText* subTxt = new SubText();
|
|
|
|
if(subTxt) {
|
|
|
|
subTxt->mContentNode = aNode;
|
|
|
|
subTxt->mLength = aStr.Length();
|
|
|
|
if (aDirection == kForward) {
|
|
|
|
subTxt->mOffset = mText.Length();
|
|
|
|
mText.Append(aStr);
|
|
|
|
mSubTexts[mNumSubTexts++] = subTxt;
|
|
|
|
}
|
|
|
|
else {
|
|
|
|
subTxt->mOffset = 0;
|
|
|
|
// Shift them all down one slot
|
|
|
|
PRInt32 i;
|
|
|
|
for (i=mNumSubTexts;i>0;i--) {
|
|
|
|
mSubTexts[i] = mSubTexts[i-1];
|
|
|
|
mSubTexts[i]->mOffset += aStr.Length();
|
|
|
|
}
|
|
|
|
mNumSubTexts++;
|
|
|
|
mText.Insert(aStr, 0, aStr.Length());
|
|
|
|
mSubTexts[0] = subTxt;
|
1998-09-08 22:13:29 +00:00
|
|
|
}
|
|
|
|
}
|
1998-08-28 15:55:31 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
//-----------------------------------------------
|
|
|
|
PRInt32 BlockText::GetStartEnd(PRInt32 anIndex, PRInt32 aLength,
|
1998-09-08 22:13:29 +00:00
|
|
|
nsIDOMNode ** aStartNode, PRInt32 & aStartOffset,
|
|
|
|
nsIDOMNode ** aEndNode, PRInt32 & aEndOffset,
|
1998-08-28 15:55:31 +00:00
|
|
|
PRInt32 aDirection)
|
|
|
|
{
|
1998-09-03 20:09:33 +00:00
|
|
|
|
1998-08-28 15:55:31 +00:00
|
|
|
PRInt32 i = 0;
|
|
|
|
PRInt32 endPos = anIndex + aLength;
|
|
|
|
while (anIndex > mSubTexts[i]->mOffset+mSubTexts[i]->mLength) {
|
|
|
|
i++;
|
|
|
|
}
|
|
|
|
aStartOffset = anIndex - mSubTexts[i]->mOffset;
|
1998-09-08 22:13:29 +00:00
|
|
|
*aStartNode = mSubTexts[i]->mContentNode;
|
1998-08-28 15:55:31 +00:00
|
|
|
if (endPos <= mSubTexts[i]->mOffset+mSubTexts[i]->mLength) {
|
|
|
|
aEndOffset = aStartOffset + aLength;
|
1998-09-08 22:13:29 +00:00
|
|
|
*aEndNode = *aStartNode;
|
1998-08-28 15:55:31 +00:00
|
|
|
} else {
|
|
|
|
|
|
|
|
while (endPos > mSubTexts[i]->mOffset+mSubTexts[i]->mLength) {
|
|
|
|
i++;
|
|
|
|
}
|
|
|
|
aEndOffset = endPos - mSubTexts[i]->mOffset;
|
1998-09-08 22:13:29 +00:00
|
|
|
*aEndNode = mSubTexts[i]->mContentNode;
|
1998-08-28 15:55:31 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
if (aDirection == kBackward) {
|
|
|
|
endPos -= aLength;
|
|
|
|
}
|
|
|
|
return endPos;
|
|
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
//-----------------------------------------------
|
1998-09-08 22:13:29 +00:00
|
|
|
PRBool nsHTMLDocument::SearchBlock(BlockText & aBlockText,
|
|
|
|
nsString & aStr,
|
|
|
|
nsIDOMNode * aCurrentBlock)
|
1998-08-28 15:55:31 +00:00
|
|
|
{
|
|
|
|
PRBool found = PR_FALSE;
|
|
|
|
|
1998-09-08 22:13:29 +00:00
|
|
|
PRInt32 lastBlockSearchOffset;
|
1998-09-03 20:09:33 +00:00
|
|
|
PRBool adjustToEnd;
|
|
|
|
|
1998-09-08 22:13:29 +00:00
|
|
|
if (aCurrentBlock == mHoldBlockContent || mHoldBlockContent == nsnull) {
|
1998-09-03 20:09:33 +00:00
|
|
|
lastBlockSearchOffset = mLastBlockSearchOffset;
|
|
|
|
adjustToEnd = mAdjustToEnd;
|
|
|
|
} else {
|
|
|
|
lastBlockSearchOffset = 0;
|
|
|
|
adjustToEnd = PR_TRUE;
|
|
|
|
}
|
1998-08-28 15:55:31 +00:00
|
|
|
|
1998-08-28 18:15:14 +00:00
|
|
|
char * searchStr;
|
|
|
|
char * contentStr;
|
|
|
|
|
|
|
|
if (!mShouldMatchCase) {
|
|
|
|
nsString searchTxt(aStr);
|
|
|
|
nsString blockTxt(aBlockText.GetNSString());
|
|
|
|
|
|
|
|
searchTxt.ToLowerCase();
|
|
|
|
blockTxt.ToLowerCase();
|
|
|
|
searchStr = searchTxt.ToNewCString();
|
|
|
|
contentStr = blockTxt.ToNewCString();
|
|
|
|
} else {
|
|
|
|
searchStr = aStr.ToNewCString();
|
|
|
|
contentStr = aBlockText.GetText();
|
|
|
|
}
|
1998-08-28 15:55:31 +00:00
|
|
|
|
|
|
|
char * adjustedContent;
|
|
|
|
char * str = nsnull;
|
|
|
|
|
|
|
|
if (mSearchDirection == kForward) {
|
1998-09-03 20:09:33 +00:00
|
|
|
adjustedContent = contentStr + lastBlockSearchOffset;
|
1998-08-28 15:55:31 +00:00
|
|
|
str = strstr(adjustedContent, searchStr);
|
|
|
|
} else {
|
|
|
|
adjustedContent = contentStr;
|
|
|
|
size_t adjLen;
|
1998-08-31 21:56:57 +00:00
|
|
|
size_t srchLen = strlen(searchStr);
|
1998-09-03 20:09:33 +00:00
|
|
|
if (adjustToEnd) {
|
1998-08-28 15:55:31 +00:00
|
|
|
adjLen = strlen(adjustedContent);
|
1998-08-31 21:56:57 +00:00
|
|
|
if (srchLen > adjLen) {
|
|
|
|
str = nsnull;
|
|
|
|
} else if (adjLen == srchLen && !strncmp(adjustedContent, searchStr, srchLen)) {
|
|
|
|
str = adjustedContent;
|
|
|
|
} else {
|
|
|
|
str = adjustedContent + adjLen - srchLen;
|
|
|
|
while (strncmp(str, searchStr, srchLen)) {
|
|
|
|
str--;
|
|
|
|
if (str < adjustedContent) {
|
|
|
|
str = nsnull;
|
|
|
|
break;
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
1998-08-28 15:55:31 +00:00
|
|
|
} else {
|
1998-09-03 20:09:33 +00:00
|
|
|
adjLen = lastBlockSearchOffset;
|
|
|
|
if (lastBlockSearchOffset > 0) {
|
1998-08-31 21:56:57 +00:00
|
|
|
str = adjustedContent + adjLen - 1;
|
|
|
|
while (strncmp(str, searchStr, srchLen)) {
|
|
|
|
str--;
|
|
|
|
if (str < adjustedContent) {
|
|
|
|
str = nsnull;
|
|
|
|
break;
|
|
|
|
}
|
1998-08-28 15:55:31 +00:00
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
1998-12-08 18:26:06 +00:00
|
|
|
#if 0
|
|
|
|
//DEBUG MJUDGE
|
1998-08-28 15:55:31 +00:00
|
|
|
if (str) {
|
|
|
|
PRInt32 inx = str - contentStr;
|
|
|
|
|
1998-09-08 22:13:29 +00:00
|
|
|
nsIDOMNode * startNode;
|
1998-08-28 15:55:31 +00:00
|
|
|
PRInt32 startOffset;
|
1998-09-08 22:13:29 +00:00
|
|
|
nsIDOMNode * endNode;
|
1998-08-28 15:55:31 +00:00
|
|
|
PRInt32 endOffset;
|
|
|
|
|
1998-09-08 22:13:29 +00:00
|
|
|
mLastBlockSearchOffset = aBlockText.GetStartEnd(inx, aStr.Length(), &startNode, startOffset, &endNode, endOffset, mSearchDirection);
|
|
|
|
mHoldBlockContent = aCurrentBlock;
|
1998-08-28 15:55:31 +00:00
|
|
|
nsSelectionRange * range = mSelection->GetRange();
|
|
|
|
nsSelectionPoint * startPnt = range->GetStartPoint();
|
|
|
|
nsSelectionPoint * endPnt = range->GetEndPoint();
|
1998-09-08 22:13:29 +00:00
|
|
|
|
|
|
|
nsIContent* content;
|
|
|
|
nsresult rv = startNode->QueryInterface(kIContentIID,(void **)&content);
|
|
|
|
if (NS_OK == rv) {
|
|
|
|
startPnt->SetPoint(content, startOffset, PR_TRUE);
|
|
|
|
NS_RELEASE(content);
|
|
|
|
}
|
|
|
|
rv = endNode->QueryInterface(kIContentIID,(void **)&content);
|
|
|
|
if (NS_OK == rv) {
|
|
|
|
endPnt->SetPoint(content, endOffset, PR_FALSE);
|
|
|
|
NS_RELEASE(content);
|
|
|
|
}
|
1998-08-28 15:55:31 +00:00
|
|
|
|
|
|
|
found = PR_TRUE;
|
|
|
|
}
|
1998-12-08 18:26:06 +00:00
|
|
|
#endif //0
|
1998-08-28 15:55:31 +00:00
|
|
|
delete[] searchStr;
|
|
|
|
delete[] contentStr;
|
|
|
|
|
|
|
|
return found;
|
|
|
|
}
|
|
|
|
|
1999-09-30 22:07:04 +00:00
|
|
|
static NS_DEFINE_CID(kParserServiceCID, NS_PARSERSERVICE_CID);
|
|
|
|
|
1998-08-28 15:55:31 +00:00
|
|
|
////////////////////////////////////////////////////
|
|
|
|
// Check to see if a Content node is a block tag
|
|
|
|
////////////////////////////////////////////////////
|
1998-09-08 22:13:29 +00:00
|
|
|
PRBool nsHTMLDocument::NodeIsBlock(nsIDOMNode * aNode)
|
|
|
|
{
|
|
|
|
PRBool isBlock = PR_FALSE;
|
|
|
|
|
|
|
|
nsIDOMElement* domElement;
|
|
|
|
nsresult rv = aNode->QueryInterface(kIDOMElementIID,(void **)&domElement);
|
|
|
|
if (NS_OK != rv) {
|
|
|
|
return isBlock;
|
1998-08-28 15:55:31 +00:00
|
|
|
}
|
1999-07-18 00:22:29 +00:00
|
|
|
nsAutoString tagName;
|
1998-09-08 22:13:29 +00:00
|
|
|
domElement->GetTagName(tagName);
|
|
|
|
NS_RELEASE(domElement);
|
|
|
|
|
1999-09-30 22:07:04 +00:00
|
|
|
// XXX Should be done at a higher level than this routine
|
|
|
|
// since getting the service is not the cheapest operation.
|
|
|
|
// Waiting for mjudge to tell me where since it looks like
|
|
|
|
// this code is still in development.
|
|
|
|
|
|
|
|
NS_WITH_SERVICE(nsIParserService, service, kParserServiceCID, &rv);
|
|
|
|
|
|
|
|
if (NS_SUCCEEDED(rv)) {
|
|
|
|
PRInt32 id;
|
|
|
|
|
|
|
|
service->HTMLStringTagToId(tagName, &id);
|
|
|
|
isBlock = IsBlockLevel(nsHTMLTag(id), mIsPreTag);
|
|
|
|
}
|
1998-09-08 22:13:29 +00:00
|
|
|
|
1998-08-28 15:55:31 +00:00
|
|
|
return isBlock;
|
|
|
|
}
|
|
|
|
|
|
|
|
/////////////////////////////////////////////
|
|
|
|
// This function moves up the parent hierarchy
|
|
|
|
// looking for a parent that is a "block"
|
|
|
|
/////////////////////////////////////////////
|
1998-09-08 22:13:29 +00:00
|
|
|
nsIDOMNode * nsHTMLDocument::FindBlockParent(nsIDOMNode * aNode,
|
1998-08-28 18:15:14 +00:00
|
|
|
PRBool aSkipThisContent)
|
1998-08-28 15:55:31 +00:00
|
|
|
{
|
1998-08-28 18:15:14 +00:00
|
|
|
// Clear up stack and release content nodes on it
|
|
|
|
PRInt32 i;
|
|
|
|
for (i=0;i<mStackInx;i++) {
|
|
|
|
NS_RELEASE(mParentStack[i]);
|
|
|
|
NS_RELEASE(mChildStack[i]);
|
|
|
|
}
|
1998-08-28 15:55:31 +00:00
|
|
|
mStackInx = 0;
|
1998-09-08 22:13:29 +00:00
|
|
|
nsIDOMNode * parent;
|
|
|
|
aNode->GetParentNode(&parent);
|
|
|
|
nsIDOMNode * child;
|
1998-08-28 15:55:31 +00:00
|
|
|
|
|
|
|
if (parent == nsnull) {
|
|
|
|
return nsnull;
|
|
|
|
}
|
1998-09-08 22:13:29 +00:00
|
|
|
NS_ADDREF(aNode);
|
1998-08-28 15:55:31 +00:00
|
|
|
|
1998-09-08 22:13:29 +00:00
|
|
|
// This method enables the param "aNode" be part of the "path"
|
1998-09-03 20:09:33 +00:00
|
|
|
// on the stack as the it look for the block parent.
|
1998-08-28 15:55:31 +00:00
|
|
|
//
|
1998-09-08 22:13:29 +00:00
|
|
|
// There are times when we don't want to include the aNode
|
|
|
|
// as part of the path so we skip to its prev/next sibling. If it was
|
|
|
|
// the first/last sibling then we jump up to it's parent.
|
1998-08-28 15:55:31 +00:00
|
|
|
if (aSkipThisContent) {
|
1998-09-08 22:13:29 +00:00
|
|
|
child = aNode;
|
|
|
|
nsIDOMNode * nextChild;
|
|
|
|
|
1998-08-28 15:55:31 +00:00
|
|
|
PRBool done = PR_FALSE;
|
|
|
|
while (!done) {
|
1998-09-08 22:13:29 +00:00
|
|
|
|
|
|
|
if (mSearchDirection == kForward) {
|
|
|
|
child->GetNextSibling(&nextChild);
|
|
|
|
} else {
|
|
|
|
child->GetPreviousSibling(&nextChild);
|
|
|
|
}
|
|
|
|
|
|
|
|
if (nextChild == nsnull) {
|
1998-08-28 15:55:31 +00:00
|
|
|
NS_RELEASE(child);
|
1998-09-08 22:13:29 +00:00
|
|
|
child = parent;
|
|
|
|
child->GetParentNode(&parent);
|
1998-08-28 15:55:31 +00:00
|
|
|
if (parent == nsnull) {
|
|
|
|
NS_RELEASE(child);
|
|
|
|
return nsnull;
|
|
|
|
}
|
|
|
|
} else {
|
|
|
|
NS_RELEASE(child);
|
1998-09-08 22:13:29 +00:00
|
|
|
child = nextChild;
|
|
|
|
done = PR_TRUE;
|
1998-08-28 15:55:31 +00:00
|
|
|
}
|
1998-09-08 22:13:29 +00:00
|
|
|
} // while
|
|
|
|
|
1998-08-28 15:55:31 +00:00
|
|
|
} else {
|
1998-09-08 22:13:29 +00:00
|
|
|
child = aNode;
|
1998-08-28 15:55:31 +00:00
|
|
|
}
|
|
|
|
|
1998-09-08 22:13:29 +00:00
|
|
|
// This travels up through the parents looking for the parent who
|
1998-09-03 20:09:33 +00:00
|
|
|
// is a block tag. We place the child/parent pairs onto a stack
|
|
|
|
// so we know what nodes to skip as we work our way back down into
|
|
|
|
// the block
|
|
|
|
do {
|
|
|
|
|
|
|
|
NS_ADDREF(parent);
|
|
|
|
NS_ADDREF(child);
|
|
|
|
mParentStack[mStackInx] = parent;
|
|
|
|
mChildStack[mStackInx++] = child;
|
|
|
|
|
|
|
|
if (parent == mBodyContent) {
|
|
|
|
break;
|
|
|
|
}
|
|
|
|
|
1998-09-08 22:13:29 +00:00
|
|
|
nsIDOMNode * oldChild = child;
|
1998-09-03 20:09:33 +00:00
|
|
|
child = parent;
|
1998-09-08 22:13:29 +00:00
|
|
|
child->GetParentNode(&parent);
|
1998-09-03 20:09:33 +00:00
|
|
|
NS_RELEASE(oldChild);
|
|
|
|
} while (parent != nsnull);
|
|
|
|
|
1998-08-28 15:55:31 +00:00
|
|
|
|
|
|
|
NS_RELEASE(child);
|
|
|
|
return parent;
|
|
|
|
}
|
|
|
|
|
|
|
|
//-----------------------------------------------
|
1998-09-08 22:13:29 +00:00
|
|
|
PRBool nsHTMLDocument::BuildBlockFromContent(nsIDOMNode * aNode,
|
|
|
|
BlockText & aBlockText,
|
|
|
|
nsIDOMNode * aCurrentBlock)
|
1998-08-28 15:55:31 +00:00
|
|
|
{
|
|
|
|
// First check to see if it is a new Block node
|
|
|
|
// If it is then we need to check the current block text (aBlockText)
|
|
|
|
// to see if it holds the search string
|
1998-09-08 22:13:29 +00:00
|
|
|
if (NodeIsBlock(aNode)) {
|
1998-08-28 15:55:31 +00:00
|
|
|
|
|
|
|
// Search current block of text
|
1998-09-08 22:13:29 +00:00
|
|
|
if (SearchBlock(aBlockText, *mSearchStr, aCurrentBlock)) {
|
1998-08-28 15:55:31 +00:00
|
|
|
return PR_TRUE;
|
|
|
|
}
|
|
|
|
|
1998-09-03 20:09:33 +00:00
|
|
|
// Clear the text we have already searched
|
|
|
|
aBlockText.ClearBlock();
|
|
|
|
|
1998-08-28 15:55:31 +00:00
|
|
|
// Start new search here on down with a new block
|
|
|
|
BlockText blockText;
|
1998-09-08 22:13:29 +00:00
|
|
|
if (!BuildBlockTraversing(aNode, blockText, aNode)) {
|
1998-08-28 15:55:31 +00:00
|
|
|
// down inside the search string wasn't found check the full block text
|
|
|
|
// for the search text
|
1998-09-08 22:13:29 +00:00
|
|
|
if (SearchBlock(blockText, *mSearchStr, aNode)) {
|
1998-08-28 15:55:31 +00:00
|
|
|
return PR_TRUE;
|
|
|
|
}
|
|
|
|
} else {
|
|
|
|
// search text was found down inside, so leave
|
|
|
|
return PR_TRUE;
|
|
|
|
}
|
|
|
|
|
|
|
|
} else {
|
1998-09-08 22:13:29 +00:00
|
|
|
if (BuildBlockTraversing(aNode, aBlockText, aCurrentBlock)) {
|
1998-09-03 20:09:33 +00:00
|
|
|
return PR_TRUE;
|
|
|
|
}
|
1998-08-28 15:55:31 +00:00
|
|
|
}
|
1998-09-03 20:09:33 +00:00
|
|
|
|
1998-08-28 15:55:31 +00:00
|
|
|
return PR_FALSE;
|
|
|
|
}
|
|
|
|
|
|
|
|
//----------------------------------
|
|
|
|
// This function moves down through
|
|
|
|
// the hiearchy and build the block of text
|
|
|
|
//-----------------------------------------
|
1998-09-08 22:13:29 +00:00
|
|
|
PRBool nsHTMLDocument::BuildBlockTraversing(nsIDOMNode * aParent,
|
|
|
|
BlockText & aBlockText,
|
|
|
|
nsIDOMNode * aCurrentBlock)
|
|
|
|
{
|
|
|
|
nsIDOMText* textContent;
|
|
|
|
nsresult rv = aParent->QueryInterface(kIDOMTextIID,(void **)&textContent);
|
|
|
|
if (NS_OK == rv) {
|
|
|
|
nsString stringBuf;
|
|
|
|
textContent->GetData(stringBuf);
|
|
|
|
|
|
|
|
if (aCurrentBlock == mHoldBlockContent || mHoldBlockContent == nsnull) {
|
|
|
|
if (mSearchDirection == kBackward && aBlockText.GetNumItems() > 0) {
|
|
|
|
mLastBlockSearchOffset += stringBuf.Length();
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
aBlockText.AddSubText(aParent, stringBuf, mSearchDirection, mLastBlockSearchOffset);
|
|
|
|
NS_RELEASE(textContent);
|
|
|
|
} else {
|
|
|
|
PRBool hasChildNode;
|
1998-10-20 17:07:23 +00:00
|
|
|
aParent->HasChildNodes(&hasChildNode);
|
1998-09-08 22:13:29 +00:00
|
|
|
if (hasChildNode) {
|
|
|
|
nsIDOMNode * child;
|
1998-08-28 15:55:31 +00:00
|
|
|
if (mSearchDirection == kForward) {
|
1998-09-08 22:13:29 +00:00
|
|
|
aParent->GetFirstChild(&child);
|
|
|
|
} else {
|
|
|
|
aParent->GetLastChild(&child);
|
|
|
|
}
|
|
|
|
while (nsnull != child) {
|
|
|
|
PRBool found = BuildBlockFromContent(child, aBlockText, aCurrentBlock);
|
|
|
|
nsIDOMNode * sibling = child;
|
|
|
|
NS_IF_RELEASE(child);
|
|
|
|
if (found) {
|
|
|
|
return PR_TRUE;
|
1998-08-28 15:55:31 +00:00
|
|
|
}
|
1998-09-08 22:13:29 +00:00
|
|
|
if (mSearchDirection == kForward) {
|
|
|
|
sibling->GetNextSibling(&child);
|
|
|
|
} else {
|
|
|
|
sibling->GetPreviousSibling(&child);
|
1998-08-28 15:55:31 +00:00
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
1998-09-08 22:13:29 +00:00
|
|
|
|
1998-08-28 15:55:31 +00:00
|
|
|
return PR_FALSE;
|
|
|
|
}
|
|
|
|
|
|
|
|
//----------------------------------
|
|
|
|
// This function moves down through
|
|
|
|
// the hiearchy and build the block of text
|
|
|
|
//-----------------------------------------
|
1998-09-08 22:13:29 +00:00
|
|
|
PRBool nsHTMLDocument::BuildBlockFromStack(nsIDOMNode * aParent,
|
1998-08-28 18:15:14 +00:00
|
|
|
BlockText & aBlockText,
|
1998-09-08 22:13:29 +00:00
|
|
|
PRInt32 aStackInx,
|
|
|
|
nsIDOMNode * aCurrentBlock)
|
1998-08-28 15:55:31 +00:00
|
|
|
{
|
1998-09-08 22:13:29 +00:00
|
|
|
nsIDOMNode * stackChild = mChildStack[aStackInx];
|
1998-08-28 15:55:31 +00:00
|
|
|
|
1998-09-08 22:13:29 +00:00
|
|
|
PRBool hasChildNode;
|
1998-10-20 17:07:23 +00:00
|
|
|
aParent->HasChildNodes(&hasChildNode);
|
1998-09-08 22:13:29 +00:00
|
|
|
if (hasChildNode) {
|
|
|
|
nsIDOMNode * child = stackChild;
|
|
|
|
NS_ADDREF(child);
|
|
|
|
|
|
|
|
while (nsnull != child) {
|
1998-08-28 15:55:31 +00:00
|
|
|
|
1998-08-31 21:56:57 +00:00
|
|
|
if (child == stackChild && aStackInx > 0) {
|
1998-09-08 22:13:29 +00:00
|
|
|
if (NodeIsBlock(child)) {
|
|
|
|
if (SearchBlock(aBlockText, *mSearchStr, aCurrentBlock)) {
|
1998-08-28 18:15:14 +00:00
|
|
|
NS_IF_RELEASE(child);
|
1998-08-28 15:55:31 +00:00
|
|
|
return PR_TRUE;
|
1998-09-08 22:13:29 +00:00
|
|
|
} else {
|
|
|
|
aBlockText.ClearBlock();
|
1998-08-28 15:55:31 +00:00
|
|
|
}
|
1998-09-03 20:09:33 +00:00
|
|
|
BlockText blockText;
|
1998-09-08 22:13:29 +00:00
|
|
|
if (BuildBlockFromStack(child, blockText, aStackInx-1, child)) {
|
1998-09-03 20:09:33 +00:00
|
|
|
NS_IF_RELEASE(child);
|
|
|
|
return PR_TRUE;
|
|
|
|
}
|
1998-09-08 22:13:29 +00:00
|
|
|
if (SearchBlock(blockText, *mSearchStr, child)) {
|
1998-09-03 20:09:33 +00:00
|
|
|
return PR_TRUE;
|
|
|
|
}
|
1998-08-28 15:55:31 +00:00
|
|
|
} else {
|
1998-09-08 22:13:29 +00:00
|
|
|
if (BuildBlockFromStack(child, aBlockText, aStackInx-1, aCurrentBlock)) {
|
1998-09-03 20:09:33 +00:00
|
|
|
NS_IF_RELEASE(child);
|
|
|
|
return PR_TRUE;
|
|
|
|
}
|
1998-08-28 15:55:31 +00:00
|
|
|
}
|
1998-09-03 20:09:33 +00:00
|
|
|
} else {
|
1998-09-08 22:13:29 +00:00
|
|
|
if (BuildBlockFromContent(child, aBlockText, aCurrentBlock)) {
|
|
|
|
NS_IF_RELEASE(child);
|
1998-09-03 20:09:33 +00:00
|
|
|
return PR_TRUE;
|
|
|
|
}
|
1998-09-08 22:13:29 +00:00
|
|
|
}
|
1998-09-03 20:09:33 +00:00
|
|
|
|
1998-09-08 22:13:29 +00:00
|
|
|
nsIDOMNode * sibling = child;
|
|
|
|
NS_RELEASE(child);
|
|
|
|
if (mSearchDirection == kForward) {
|
|
|
|
sibling->GetNextSibling(&child);
|
|
|
|
} else {
|
|
|
|
sibling->GetPreviousSibling(&child);
|
1998-08-28 15:55:31 +00:00
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
1998-09-08 22:13:29 +00:00
|
|
|
return PR_FALSE;
|
1998-08-28 15:55:31 +00:00
|
|
|
|
|
|
|
}
|
1998-08-31 21:56:57 +00:00
|
|
|
|
1998-08-28 15:55:31 +00:00
|
|
|
|
1998-09-04 15:41:20 +00:00
|
|
|
#if 0 // debug
|
|
|
|
void printDOMRefs(nsIDOMNode * aNode, PRInt32 aLevel)
|
|
|
|
{
|
|
|
|
char * cStr = nsnull;
|
|
|
|
|
|
|
|
PRInt32 i;
|
|
|
|
for (i=0;i<aLevel;i++) {
|
|
|
|
printf(".");
|
|
|
|
}
|
1998-09-08 22:13:29 +00:00
|
|
|
|
1998-09-04 15:41:20 +00:00
|
|
|
nsIDOMElement* domElement;
|
|
|
|
nsresult rv = aNode->QueryInterface(kIDOMElementIID,(void **)&domElement);
|
|
|
|
if (NS_OK == rv) {
|
|
|
|
nsString tagName;
|
|
|
|
domElement->GetTagName(tagName);
|
|
|
|
cStr = tagName.ToNewCString();
|
|
|
|
NS_RELEASE(domElement);
|
|
|
|
}
|
|
|
|
|
|
|
|
static NS_DEFINE_IID(kIDOMTextIID, NS_IDOMTEXT_IID);
|
|
|
|
nsIDOMText* textContent;
|
|
|
|
rv = aNode->QueryInterface(kIDOMTextIID,(void **)&textContent);
|
|
|
|
if (NS_OK == rv) {
|
|
|
|
nsString stringBuf;
|
|
|
|
textContent->GetData(stringBuf);
|
|
|
|
cStr = stringBuf.ToNewCString();
|
|
|
|
NS_RELEASE(textContent);
|
|
|
|
}
|
|
|
|
|
|
|
|
if (cStr) {
|
1998-09-08 22:13:29 +00:00
|
|
|
for (i=0;i<PRInt32(strlen(cStr));i++) {
|
1998-09-04 15:41:20 +00:00
|
|
|
if (cStr[i] < 15) {
|
|
|
|
cStr[i] = ' ';
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
printf("[%s] (0x%x)\n", (cStr?cStr:"<?>"), aNode);
|
|
|
|
delete[] cStr;
|
|
|
|
|
|
|
|
PRBool hasChildren;
|
1998-10-20 17:07:23 +00:00
|
|
|
aNode->HasChildNodes(&hasChildren);
|
1998-09-04 15:41:20 +00:00
|
|
|
if (hasChildren) {
|
|
|
|
nsIDOMNode * childNode;
|
|
|
|
aNode->GetFirstChild(&childNode);
|
|
|
|
while (childNode != nsnull) {
|
|
|
|
printDOMRefs(childNode, aLevel+2);
|
|
|
|
nsIDOMNode * oldChild = childNode;
|
|
|
|
oldChild->GetNextSibling(&childNode);
|
|
|
|
NS_RELEASE(oldChild);
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
#endif
|
|
|
|
|
|
|
|
|
|
|
|
|
1999-04-01 23:54:23 +00:00
|
|
|
static nsIDOMNode * FindDOMNode(nsIDOMNode * aNode, nsIContent * aContent)
|
1998-09-04 15:41:20 +00:00
|
|
|
{
|
|
|
|
nsIContent* content;
|
|
|
|
nsresult rv = aNode->QueryInterface(kIContentIID,(void **)&content);
|
|
|
|
if (NS_OK == rv) {
|
|
|
|
if (content == aContent) {
|
|
|
|
return aNode;
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
PRBool hasChildren;
|
1998-10-20 17:07:23 +00:00
|
|
|
aNode->HasChildNodes(&hasChildren);
|
1998-09-04 15:41:20 +00:00
|
|
|
if (hasChildren) {
|
|
|
|
nsIDOMNode * childNode;
|
|
|
|
aNode->GetFirstChild(&childNode);
|
|
|
|
while (childNode != nsnull) {
|
|
|
|
nsIDOMNode * node = FindDOMNode(childNode, aContent);
|
|
|
|
if (node != nsnull) {
|
|
|
|
return node;
|
|
|
|
}
|
|
|
|
nsIDOMNode * oldChild = childNode;
|
|
|
|
oldChild->GetNextSibling(&childNode);
|
|
|
|
NS_RELEASE(oldChild);
|
|
|
|
}
|
|
|
|
}
|
|
|
|
return nsnull;
|
|
|
|
}
|
|
|
|
|
1998-08-28 15:55:31 +00:00
|
|
|
/**
|
|
|
|
* Finds text in content
|
|
|
|
*/
|
|
|
|
NS_IMETHODIMP nsHTMLDocument::FindNext(const nsString &aSearchStr, PRBool aMatchCase, PRBool aSearchDown, PRBool &aIsFound)
|
|
|
|
{
|
1998-12-08 18:26:06 +00:00
|
|
|
#if 0
|
|
|
|
//DEBUG MJUDGE
|
1998-08-28 18:15:14 +00:00
|
|
|
aIsFound = PR_FALSE;
|
|
|
|
mShouldMatchCase = aMatchCase;
|
1998-08-28 15:55:31 +00:00
|
|
|
|
1998-08-28 18:15:14 +00:00
|
|
|
if (mSearchStr == nsnull) {
|
|
|
|
mSearchStr = new nsString(aSearchStr);
|
|
|
|
} else {
|
|
|
|
mSearchStr->SetLength(0);
|
|
|
|
mSearchStr->Append(aSearchStr);
|
|
|
|
}
|
1998-08-28 15:55:31 +00:00
|
|
|
|
1998-09-04 15:41:20 +00:00
|
|
|
// Temporary
|
|
|
|
PRBool doReplace = PR_FALSE;
|
|
|
|
nsString replacementStr("xxxx");
|
1999-07-26 00:37:24 +00:00
|
|
|
PRInt32 inx = mSearchStr->FindChar('/');
|
1998-09-04 15:41:20 +00:00
|
|
|
if (inx > -1) {
|
|
|
|
if (inx == mSearchStr->Length()-1) {
|
|
|
|
replacementStr.SetLength(0);
|
|
|
|
} else {
|
|
|
|
replacementStr = *mSearchStr;
|
|
|
|
replacementStr.Cut(0, inx+1);
|
|
|
|
}
|
|
|
|
mSearchStr->Truncate(inx);
|
|
|
|
|
|
|
|
doReplace = PR_TRUE;
|
|
|
|
}
|
|
|
|
|
1998-09-08 22:13:29 +00:00
|
|
|
nsIDOMElement * root = nsnull;
|
|
|
|
if (NS_OK != GetDocumentElement(&root)) {
|
|
|
|
return PR_FALSE;
|
|
|
|
}
|
|
|
|
|
|
|
|
// DEBUG printDOMRefs(root, 0);
|
|
|
|
|
|
|
|
nsIDOMNode * start = nsnull;
|
|
|
|
nsIDOMNode * end = nsnull;
|
|
|
|
nsIDOMNode * child;
|
1998-08-28 15:55:31 +00:00
|
|
|
|
1998-11-12 22:25:51 +00:00
|
|
|
if (mBodyContent == nsnull && PR_FALSE == GetBodyContent()) {
|
1998-08-28 15:55:31 +00:00
|
|
|
return NS_OK;
|
|
|
|
}
|
|
|
|
|
1998-09-04 15:41:20 +00:00
|
|
|
//printRefs(mBodyContent, 0);
|
1998-09-03 20:09:33 +00:00
|
|
|
|
1998-09-04 15:41:20 +00:00
|
|
|
start = mBodyContent;
|
|
|
|
NS_ADDREF(start);
|
1998-09-08 22:13:29 +00:00
|
|
|
|
|
|
|
// Find very first Piece of Content
|
|
|
|
while (1) {
|
|
|
|
start->GetFirstChild(&child);
|
|
|
|
if (child == nsnull) {
|
1998-08-29 20:44:42 +00:00
|
|
|
break;
|
|
|
|
}
|
1998-09-08 22:13:29 +00:00
|
|
|
NS_RELEASE(start);
|
|
|
|
start = child;
|
1998-08-28 15:55:31 +00:00
|
|
|
}
|
|
|
|
|
1998-09-04 15:41:20 +00:00
|
|
|
end = mBodyContent;
|
|
|
|
NS_ADDREF(end);
|
1998-09-08 22:13:29 +00:00
|
|
|
|
|
|
|
// Find very last piece of Content
|
|
|
|
while (1) {
|
|
|
|
end->GetLastChild(&child);
|
|
|
|
if (child == nsnull) {
|
1998-08-29 20:44:42 +00:00
|
|
|
break;
|
|
|
|
}
|
1998-09-08 22:13:29 +00:00
|
|
|
NS_RELEASE(end);
|
|
|
|
end = child;
|
1998-08-28 15:55:31 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
nsSelectionRange * range = mSelection->GetRange();
|
|
|
|
nsSelectionPoint * startPnt = range->GetStartPoint();
|
|
|
|
nsSelectionPoint * endPnt = range->GetEndPoint();
|
1998-09-08 22:13:29 +00:00
|
|
|
nsIContent * endContent = range->GetEndContent();
|
|
|
|
nsIContent * startContent;
|
1998-08-28 15:55:31 +00:00
|
|
|
|
|
|
|
mSearchDirection = aSearchDown? kForward:kBackward;
|
1998-09-08 22:13:29 +00:00
|
|
|
nsIDOMNode * searchNode = nsnull;
|
1998-08-28 15:55:31 +00:00
|
|
|
|
1998-09-08 22:13:29 +00:00
|
|
|
// This is a short circut for starting to search
|
|
|
|
// at the beginning of the doocument forward
|
1998-08-28 15:55:31 +00:00
|
|
|
if (endContent == nsnull && mSearchDirection == kForward) {
|
1998-09-08 22:13:29 +00:00
|
|
|
searchNode = mBodyContent;
|
1998-08-28 15:55:31 +00:00
|
|
|
BlockText blockText;
|
1998-09-08 22:13:29 +00:00
|
|
|
if (!BuildBlockTraversing(searchNode, blockText, mBodyContent)) {
|
|
|
|
if (SearchBlock(blockText, *mSearchStr, mBodyContent)) {
|
1998-08-28 15:55:31 +00:00
|
|
|
aIsFound = PR_TRUE;
|
|
|
|
}
|
1998-09-04 15:41:20 +00:00
|
|
|
} else {
|
|
|
|
aIsFound = PR_TRUE;
|
1998-08-28 15:55:31 +00:00
|
|
|
}
|
|
|
|
} else {
|
1998-09-08 22:13:29 +00:00
|
|
|
|
1998-08-28 15:55:31 +00:00
|
|
|
mAdjustToEnd = PR_FALSE;
|
1998-09-08 22:13:29 +00:00
|
|
|
|
|
|
|
// Convert the nsICOntent Node in the Selection Points
|
|
|
|
// to their DOM Node counter part
|
|
|
|
if (mSearchDirection == kForward) {
|
|
|
|
nsIDOMNode * endNode;
|
|
|
|
nsresult rv = endContent->QueryInterface(kIDOMNodeIID,(void **)&endNode);
|
|
|
|
if (NS_OK == rv) {
|
|
|
|
searchNode = endNode;
|
|
|
|
}
|
|
|
|
mLastBlockSearchOffset = endPnt->GetOffset();
|
|
|
|
} else {
|
|
|
|
nsIContent * startContent = range->GetStartContent();
|
|
|
|
if (startContent == nsnull) {
|
|
|
|
searchNode = end;
|
|
|
|
mAdjustToEnd = PR_TRUE;
|
|
|
|
} else {
|
|
|
|
nsIDOMNode * startNode;
|
|
|
|
nsresult rv = startContent->QueryInterface(kIDOMNodeIID,(void **)&startNode);
|
|
|
|
if (NS_OK == rv) {
|
|
|
|
searchNode = startNode;
|
|
|
|
}
|
|
|
|
mLastBlockSearchOffset = startPnt->GetOffset();
|
|
|
|
NS_IF_RELEASE(startContent);
|
1998-09-03 20:09:33 +00:00
|
|
|
}
|
1998-08-28 15:55:31 +00:00
|
|
|
}
|
1998-09-08 22:13:29 +00:00
|
|
|
|
|
|
|
nsIDOMNode * blockContent = FindBlockParent(searchNode); // this ref counts blockContent
|
1998-08-28 15:55:31 +00:00
|
|
|
while (blockContent != nsnull) {
|
|
|
|
|
|
|
|
BlockText blockText;
|
1998-09-08 22:13:29 +00:00
|
|
|
if (BuildBlockFromStack(blockContent, blockText, mStackInx-1, blockContent)) {
|
1998-08-28 15:55:31 +00:00
|
|
|
aIsFound = PR_TRUE;
|
|
|
|
break;
|
|
|
|
}
|
1998-09-08 22:13:29 +00:00
|
|
|
if (SearchBlock(blockText, *mSearchStr, blockContent)) {
|
|
|
|
return PR_TRUE;
|
|
|
|
}
|
1998-08-28 15:55:31 +00:00
|
|
|
|
|
|
|
mLastBlockSearchOffset = 0;
|
|
|
|
mAdjustToEnd = PR_TRUE;
|
1998-08-28 18:15:14 +00:00
|
|
|
|
1998-09-08 22:13:29 +00:00
|
|
|
nsIDOMNode * blockChild = blockContent;
|
1998-08-31 21:56:57 +00:00
|
|
|
blockContent = FindBlockParent(blockChild, PR_TRUE);
|
|
|
|
NS_RELEASE(blockChild);
|
1998-08-28 15:55:31 +00:00
|
|
|
}
|
1998-08-28 18:15:14 +00:00
|
|
|
|
|
|
|
// Clear up stack and release content nodes on it
|
|
|
|
PRInt32 i;
|
|
|
|
for (i=0;i<mStackInx;i++) {
|
|
|
|
NS_RELEASE(mParentStack[i]);
|
|
|
|
NS_RELEASE(mChildStack[i]);
|
|
|
|
}
|
1998-08-31 21:56:57 +00:00
|
|
|
mStackInx = 0;
|
1998-08-28 15:55:31 +00:00
|
|
|
}
|
|
|
|
|
1998-08-28 19:55:03 +00:00
|
|
|
NS_IF_RELEASE(endContent);
|
1998-09-08 22:13:29 +00:00
|
|
|
NS_IF_RELEASE(searchNode);
|
1998-08-28 19:55:03 +00:00
|
|
|
NS_IF_RELEASE(start);
|
|
|
|
NS_IF_RELEASE(end);
|
1998-08-28 18:15:14 +00:00
|
|
|
|
1998-08-28 15:55:31 +00:00
|
|
|
SetDisplaySelection(PR_TRUE);
|
|
|
|
|
1998-09-04 15:41:20 +00:00
|
|
|
|
|
|
|
if (aIsFound && doReplace) {
|
|
|
|
range = mSelection->GetRange();
|
|
|
|
startContent = range->GetStartContent();
|
|
|
|
endContent = range->GetEndContent();
|
|
|
|
startPnt = range->GetStartPoint();
|
|
|
|
endPnt = range->GetEndPoint();
|
|
|
|
|
1998-09-08 22:13:29 +00:00
|
|
|
nsIDOMElement * root = nsnull;
|
1998-09-04 15:41:20 +00:00
|
|
|
if (NS_OK == GetDocumentElement(&root)) {
|
|
|
|
nsIDOMNode * node = FindDOMNode(root, startContent);
|
|
|
|
|
|
|
|
nsString contentStr;
|
1998-09-08 22:13:29 +00:00
|
|
|
//static NS_DEFINE_IID(kIDOMTextIID, NS_IDOMTEXT_IID);
|
1998-09-04 15:41:20 +00:00
|
|
|
nsIDOMText* textContent;
|
|
|
|
nsresult rv = node->QueryInterface(kIDOMTextIID,(void **)&textContent);
|
|
|
|
if (NS_OK == rv) {
|
|
|
|
textContent->GetData(contentStr);
|
|
|
|
NS_RELEASE(textContent);
|
|
|
|
}
|
|
|
|
|
|
|
|
//PRInt32 offset = contentStr.Find(*mSearchStr, !mShouldMatchCase);
|
|
|
|
PRInt32 offset;
|
|
|
|
// temporary
|
|
|
|
if (mShouldMatchCase) {
|
|
|
|
offset = contentStr.Find(*mSearchStr);
|
|
|
|
if (offset == -1) {
|
|
|
|
offset = contentStr.RFind(*mSearchStr);
|
|
|
|
}
|
|
|
|
} else {
|
|
|
|
nsString cs(contentStr);
|
|
|
|
nsString ss(*mSearchStr);
|
|
|
|
cs.ToLowerCase();
|
|
|
|
ss.ToLowerCase();
|
|
|
|
offset = cs.Find(ss);
|
|
|
|
if (offset == -1) {
|
|
|
|
offset = cs.RFind(ss);
|
|
|
|
}
|
|
|
|
}
|
|
|
|
// end temporary
|
|
|
|
|
|
|
|
if (offset > -1) {
|
|
|
|
contentStr.Cut(offset, mSearchStr->Length());
|
|
|
|
contentStr.Insert(replacementStr, offset, replacementStr.Length());
|
|
|
|
|
|
|
|
nsIDOMNode * parent;
|
|
|
|
node->GetParentNode(&parent);
|
|
|
|
|
|
|
|
//nsIDOMNode * delNode;
|
|
|
|
//parent->ReplaceChild(newNode, node, &delNode);
|
|
|
|
|
|
|
|
PRBool nodeWasAdded = PR_FALSE;
|
|
|
|
nsIDOMNode * nextNode;
|
|
|
|
nsIDOMNode * prevNode;
|
|
|
|
nsIDOMNode * delNode;
|
|
|
|
|
|
|
|
node->GetPreviousSibling(&prevNode);
|
|
|
|
node->GetNextSibling(&nextNode);
|
|
|
|
|
|
|
|
parent->RemoveChild(node, &delNode);
|
|
|
|
NS_IF_RELEASE(delNode);
|
|
|
|
|
|
|
|
nsIDOMNode * contentNode = nsnull;
|
|
|
|
PRInt32 newOffset;
|
|
|
|
|
|
|
|
if (contentStr.Length() > 0) {
|
|
|
|
nsIDOMNode * retNode;
|
|
|
|
nsIDOMText * newNode;
|
|
|
|
CreateTextNode(contentStr, &newNode);
|
|
|
|
if (nsnull != nextNode) {
|
|
|
|
parent->InsertBefore(newNode, nextNode, &retNode);
|
|
|
|
} else {
|
|
|
|
parent->AppendChild(newNode, &retNode);
|
|
|
|
}
|
|
|
|
|
|
|
|
newOffset = offset + replacementStr.Length();
|
|
|
|
contentNode = newNode;
|
|
|
|
nodeWasAdded = PR_TRUE;
|
|
|
|
|
|
|
|
NS_IF_RELEASE(newNode);
|
|
|
|
NS_IF_RELEASE(retNode);
|
|
|
|
} else {
|
|
|
|
newOffset = 0;
|
|
|
|
contentNode = (nextNode == nsnull ? prevNode : nextNode);
|
|
|
|
// XXX Bummer if previous is also null then this was the only child
|
|
|
|
// now we have to go find a different node to set the content to for selection
|
|
|
|
// So we will use the parent node for now, but this needs to be changed
|
|
|
|
if (contentNode == nsnull) {
|
|
|
|
contentNode = parent;
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
NS_ADDREF(contentNode);
|
|
|
|
|
|
|
|
NS_IF_RELEASE(nextNode);
|
|
|
|
NS_IF_RELEASE(prevNode);
|
|
|
|
|
|
|
|
if (contentNode != nsnull) {
|
|
|
|
static NS_DEFINE_IID(kIContentIID, NS_ICONTENT_IID);
|
|
|
|
nsIContent* content;
|
|
|
|
rv = contentNode->QueryInterface(kIContentIID,(void **)&content);
|
|
|
|
if (NS_OK == rv) {
|
|
|
|
//range = mSelection->GetRange();
|
|
|
|
//startPnt = range->GetStartPoint();
|
|
|
|
//endPnt = range->GetEndPoint();
|
|
|
|
|
|
|
|
startPnt->SetContent(content);
|
|
|
|
startPnt->SetOffset(newOffset);
|
|
|
|
endPnt->SetContent(content);
|
|
|
|
endPnt->SetOffset(newOffset);
|
|
|
|
range->SetStartPoint(startPnt);
|
|
|
|
range->SetEndPoint(endPnt);
|
|
|
|
NS_RELEASE(content);
|
|
|
|
}
|
|
|
|
}
|
|
|
|
NS_IF_RELEASE(contentNode);
|
|
|
|
NS_IF_RELEASE(parent);
|
|
|
|
NS_IF_RELEASE(node);
|
|
|
|
NS_IF_RELEASE(root);
|
|
|
|
}
|
|
|
|
}
|
|
|
|
NS_RELEASE(startContent);
|
|
|
|
NS_RELEASE(endContent);
|
|
|
|
}
|
1998-12-08 18:26:06 +00:00
|
|
|
#endif //0
|
1998-11-12 22:25:51 +00:00
|
|
|
return NS_OK;
|
|
|
|
}
|
1998-09-04 15:41:20 +00:00
|
|
|
|
1998-11-12 22:25:51 +00:00
|
|
|
PRBool
|
|
|
|
nsHTMLDocument::GetBodyContent()
|
|
|
|
{
|
|
|
|
nsIDOMElement * root = nsnull;
|
|
|
|
if (NS_OK != GetDocumentElement(&root)) {
|
|
|
|
return PR_FALSE;
|
|
|
|
}
|
1998-09-04 15:41:20 +00:00
|
|
|
|
1998-11-12 22:25:51 +00:00
|
|
|
nsAutoString bodyStr("BODY");
|
|
|
|
nsIDOMNode * child;
|
|
|
|
root->GetFirstChild(&child);
|
|
|
|
|
|
|
|
while (child != nsnull) {
|
|
|
|
nsIDOMElement* domElement;
|
|
|
|
nsresult rv = child->QueryInterface(kIDOMElementIID,(void **)&domElement);
|
|
|
|
if (NS_OK == rv) {
|
|
|
|
nsString tagName;
|
|
|
|
domElement->GetTagName(tagName);
|
|
|
|
if (bodyStr.EqualsIgnoreCase(tagName)) {
|
|
|
|
mBodyContent = child;
|
|
|
|
NS_RELEASE(root);
|
|
|
|
NS_RELEASE(domElement);
|
|
|
|
return PR_TRUE;
|
|
|
|
}
|
|
|
|
NS_RELEASE(domElement);
|
|
|
|
}
|
|
|
|
nsIDOMNode * node = child;
|
|
|
|
NS_RELEASE(child);
|
|
|
|
node->GetNextSibling(&child);
|
|
|
|
}
|
|
|
|
NS_RELEASE(root);
|
|
|
|
return PR_FALSE;
|
1998-08-28 15:55:31 +00:00
|
|
|
}
|
|
|
|
|
1999-02-04 23:23:07 +00:00
|
|
|
nsresult
|
|
|
|
nsHTMLDocument::GetBodyElement(nsIDOMHTMLBodyElement** aBody)
|
|
|
|
{
|
|
|
|
if (mBodyContent == nsnull && PR_FALSE == GetBodyContent()) {
|
|
|
|
return NS_ERROR_FAILURE;
|
|
|
|
}
|
|
|
|
|
|
|
|
return mBodyContent->QueryInterface(kIDOMHTMLBodyElementIID,
|
|
|
|
(void**)aBody);
|
|
|
|
}
|
|
|
|
|
1998-09-23 17:16:51 +00:00
|
|
|
// forms related stuff
|
|
|
|
|
|
|
|
NS_IMETHODIMP
|
|
|
|
nsHTMLDocument::AddForm(nsIDOMHTMLFormElement *aForm)
|
|
|
|
{
|
1999-01-18 03:43:43 +00:00
|
|
|
#if 0
|
|
|
|
// Not necessary anymore since forms are real content now
|
1998-09-23 17:16:51 +00:00
|
|
|
NS_PRECONDITION(nsnull != aForm, "null ptr");
|
|
|
|
if (nsnull == aForm) {
|
|
|
|
return NS_ERROR_NULL_POINTER;
|
|
|
|
}
|
1998-10-21 09:26:33 +00:00
|
|
|
|
1998-09-23 17:16:51 +00:00
|
|
|
nsIContent* iContent = nsnull;
|
|
|
|
nsresult result = aForm->QueryInterface(kIContentIID, (void**)&iContent);
|
|
|
|
if ((NS_OK == result) && iContent) {
|
1998-10-21 09:26:33 +00:00
|
|
|
nsIDOMHTMLCollection* forms = nsnull;
|
|
|
|
|
|
|
|
// Initialize mForms if necessary...
|
|
|
|
if (nsnull == mForms) {
|
1999-01-15 19:18:30 +00:00
|
|
|
mForms = new nsContentList(this, nsHTMLAtoms::form, kNameSpaceID_HTML);
|
1998-10-22 23:00:37 +00:00
|
|
|
NS_ADDREF(mForms);
|
1998-10-21 09:26:33 +00:00
|
|
|
}
|
|
|
|
|
1998-10-22 23:00:37 +00:00
|
|
|
mForms->Add(iContent);
|
1998-10-21 09:26:33 +00:00
|
|
|
NS_RELEASE(iContent);
|
1998-09-23 17:16:51 +00:00
|
|
|
}
|
|
|
|
return result;
|
1999-01-18 03:43:43 +00:00
|
|
|
#endif
|
|
|
|
return NS_OK;
|
1998-09-23 17:16:51 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
NS_IMETHODIMP
|
|
|
|
nsHTMLDocument::GetForms(nsIDOMHTMLCollection** aForms)
|
|
|
|
{
|
|
|
|
if (nsnull == mForms) {
|
1999-01-15 19:18:30 +00:00
|
|
|
mForms = new nsContentList(this, nsHTMLAtoms::form, kNameSpaceID_HTML);
|
1998-09-23 17:16:51 +00:00
|
|
|
if (nsnull == mForms) {
|
|
|
|
return NS_ERROR_OUT_OF_MEMORY;
|
|
|
|
}
|
1998-10-21 09:26:33 +00:00
|
|
|
NS_ADDREF(mForms);
|
1998-09-23 17:16:51 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
*aForms = (nsIDOMHTMLCollection *)mForms;
|
|
|
|
NS_ADDREF(mForms);
|
|
|
|
|
|
|
|
return NS_OK;
|
|
|
|
}
|
|
|
|
|
1999-12-08 02:05:16 +00:00
|
|
|
PRBool
|
|
|
|
nsHTMLDocument::IsInSelection(nsIDOMSelection* aSelection,
|
|
|
|
const nsIContent* aContent) const
|
|
|
|
{
|
|
|
|
// HTML document has to include body in the selection,
|
|
|
|
// so that output can see style nodes on the body.
|
|
|
|
nsIAtom* tag;
|
|
|
|
nsresult rv = aContent->GetTag(tag);
|
|
|
|
PRBool retval = (NS_SUCCEEDED(rv) && tag == nsHTMLAtoms::body);
|
|
|
|
NS_IF_RELEASE(tag);
|
|
|
|
if (retval)
|
|
|
|
return retval;
|
|
|
|
|
|
|
|
return nsDocument::IsInSelection(aSelection, aContent);
|
|
|
|
}
|
|
|
|
|
|
|
|
|
1998-09-23 17:16:51 +00:00
|
|
|
|
|
|
|
|