Added command to notify when document url changes. b=181091, r=akkana, sr=sfraser

This commit is contained in:
cmanske%netscape.com 2002-11-27 00:35:09 +00:00
Родитель 14f4ce9143
Коммит 1c667569a9
7 изменённых файлов: 145 добавлений и 23 удалений

Просмотреть файл

@ -47,6 +47,8 @@
#include "nsIDOMElement.h"
#include "nsIDOMWindowInternal.h"
#include "nsIDOMDocument.h"
#include "nsIDocument.h"
#include "nsIURI.h"
#include "nsIClipboard.h"
@ -58,6 +60,7 @@
#include "nsICommandParams.h"
#include "nsComponentManagerUtils.h"
#include "nsCRT.h"
//prototype
nsresult GetListState(nsIEditor *aEditor, PRBool *aMixed, PRUnichar **tagStr);
nsresult RemoveOneProperty(nsIHTMLEditor *aEditor,const nsString& aProp,
@ -1747,9 +1750,10 @@ nsSetDocumentStateCommand::GetCommandStateParams(const char *aCommandName,
/**
* Commands just for state notification
* As of 11/11/02, possible commands are:
* As of 11/21/02, possible commands are:
* "obs_documentCreated"
* "obs_documentWillBeDestroyed"
* "obs_documentLocationChanged"
* Note that you can use the same command class, nsDocumentStateCommand
* for these or future observer commands.
* We check the input command param for different behavior
@ -1817,13 +1821,13 @@ nsDocumentStateCommand::GetCommandStateParams(const char *aCommandName,
nsICommandParams *aParams,
nsISupports *refCon)
{
NS_ENSURE_ARG_POINTER(aParams);
NS_ENSURE_ARG_POINTER(aCommandName);
nsCOMPtr<nsIEditingSession> editingSession = do_QueryInterface(refCon);
nsresult rv;
if (!nsCRT::strcmp(aCommandName, "obs_documentCreated"))
{
NS_ENSURE_ARG_POINTER(aParams);
PRUint32 editorStatus = nsIEditingSession::eEditorErrorUnknown;
if (editingSession)
@ -1833,7 +1837,7 @@ nsDocumentStateCommand::GetCommandStateParams(const char *aCommandName,
// Embedder gets error status if this fails
// If called before startup is finished,
// status = eEditorCreationInProgress
nsresult rv = editingSession->GetEditorStatus(&editorStatus);
rv = editingSession->GetEditorStatus(&editorStatus);
NS_ENSURE_SUCCESS(rv, rv);
}
else
@ -1849,6 +1853,25 @@ nsDocumentStateCommand::GetCommandStateParams(const char *aCommandName,
aParams->SetLongValue(STATE_DATA, editorStatus);
return NS_OK;
}
else if (!nsCRT::strcmp(aCommandName, "obs_documentLocationChanged"))
{
nsCOMPtr<nsIEditor> editor = do_QueryInterface(refCon);
if (editor)
{
nsCOMPtr<nsIDOMDocument> domDoc;
editor->GetDocument(getter_AddRefs(domDoc));
nsCOMPtr<nsIDocument> doc = do_QueryInterface(domDoc);
if (!doc) return NS_ERROR_FAILURE;
nsCOMPtr<nsIURI> uri;
rv = doc->GetDocumentURL(getter_AddRefs(uri));
NS_ENSURE_SUCCESS(rv, rv);
if (!uri) return NS_ERROR_FAILURE;
return aParams->SetISupportsValue(STATE_DATA, (nsISupports*)uri);
}
return NS_OK;
}
return NS_ERROR_NOT_IMPLEMENTED;
}

Просмотреть файл

@ -97,6 +97,7 @@ nsComposerController::RegisterEditorDocStateCommands(
// observer commands for document state
NS_REGISTER_ONE_COMMAND(nsDocumentStateCommand, "obs_documentCreated")
NS_REGISTER_ONE_COMMAND(nsDocumentStateCommand, "obs_documentWillBeDestroyed")
NS_REGISTER_ONE_COMMAND(nsDocumentStateCommand, "obs_documentLocationChanged")
// commands that may get or change state
NS_REGISTER_ONE_COMMAND(nsSetDocumentStateCommand, "cmd_setDocumentModified")

Просмотреть файл

@ -41,7 +41,9 @@
#include "nsIDOMWindow.h"
#include "nsIDOMWindowInternal.h"
#include "nsIDocument.h"
#include "nsIDOMDocument.h"
#include "nsIURI.h"
#include "nsIScriptGlobalObject.h"
#include "nsISelectionPrivate.h"
#include "nsITransactionManager.h"
@ -55,6 +57,8 @@
#include "nsIControllers.h"
#include "nsIController.h"
#include "nsIControllerContext.h"
#include "nsICommandManager.h"
#include "nsPICommandUpdater.h"
#include "nsIPresShell.h"
@ -74,7 +78,6 @@
#include "nsEditorParserObserver.h"
#if DEBUG
#include "nsIURI.h"
//#define NOISY_DOC_LOADING 1
#endif
@ -571,7 +574,8 @@ nsEditingSession::OnStateChange(nsIWebProgress *aWebProgress,
{
nsXPIDLCString spec;
uri->GetSpec(spec);
printf(" **** STATE_START: CHANNEL URI=%s, flags=%x\n",spec.get(), aStateFlags);
printf(" **** STATE_START: CHANNEL URI=%s,
flags=%x\n",spec.get(), aStateFlags);
}
}
else
@ -636,7 +640,8 @@ nsEditingSession::OnStateChange(nsIWebProgress *aWebProgress,
{
nsXPIDLCString spec;
uri->GetSpec(spec);
printf(" **** STATE_STOP: CHANNEL URI=%s, flags=%x\n",spec.get(), aStateFlags);
printf(" **** STATE_STOP: CHANNEL URI=%s,
flags=%x\n",spec.get(), aStateFlags);
}
}
else
@ -699,10 +704,34 @@ nsEditingSession::OnProgressChange(nsIWebProgress *aWebProgress,
----------------------------------------------------------------------------*/
NS_IMETHODIMP
nsEditingSession::OnLocationChange(nsIWebProgress *aWebProgress,
nsIRequest *aRequest, nsIURI *location)
nsIRequest *aRequest, nsIURI *aURI)
{
NS_NOTREACHED("notification excluded in AddProgressListener(...)");
return NS_OK;
nsCOMPtr<nsIDOMWindow> domWindow;
nsresult rv = aWebProgress->GetDOMWindow(getter_AddRefs(domWindow));
if (NS_FAILED(rv)) return rv;
nsCOMPtr<nsIDOMDocument> domDoc;
rv = domWindow->GetDocument(getter_AddRefs(domDoc));
if (NS_FAILED(rv)) return rv;
nsCOMPtr<nsIDocument> doc = do_QueryInterface(domDoc);
if (!doc) return NS_ERROR_FAILURE;
rv = doc->SetDocumentURL(aURI);
if (NS_FAILED(rv)) return rv;
// Notify the location-changed observer that
// the document URL has changed
nsCOMPtr<nsIDocShell> docShell;
rv = GetDocShellFromWindow(domWindow, getter_AddRefs(docShell));
if (NS_FAILED(rv)) return rv;
nsCOMPtr<nsICommandManager> commandManager = do_GetInterface(docShell);
nsCOMPtr<nsPICommandUpdater> commandUpdater =
do_QueryInterface(commandManager);
if (!commandUpdater) return NS_ERROR_FAILURE;
return commandUpdater->CommandStatusChanged("obs_documentLocationChanged");
}
/*---------------------------------------------------------------------------
@ -812,7 +841,8 @@ nsEditingSession::EndDocumentLoad(nsIWebProgress *aWebProgress,
#ifdef NOISY_DOC_LOADING
printf("Editing shell EndDocumentLoad\n");
#endif
// We want to call the base class EndDocumentLoad, but avoid some of the stuff
// We want to call the base class EndDocumentLoad,
// but avoid some of the stuff
// that nsWebShell does (need to refactor).
// OK, time to make an editor on this document
@ -853,9 +883,10 @@ nsEditingSession::EndDocumentLoad(nsIWebProgress *aWebProgress,
if (NS_FAILED(rv)) return rv;
mEditorStatus = eEditorCreationInProgress;
mLoadBlankDocTimer->InitWithFuncCallback(nsEditingSession::TimerCallback,
(void*)docShell,
10, nsITimer::TYPE_ONE_SHOT);
mLoadBlankDocTimer->InitWithFuncCallback(
nsEditingSession::TimerCallback,
(void*)docShell,
10, nsITimer::TYPE_ONE_SHOT);
}
}
}
@ -977,7 +1008,10 @@ nsEditingSession::PrepareForEditing()
nsCOMPtr<nsIWebProgress> webProgress = do_GetInterface(docShell);
if (!webProgress) return NS_ERROR_FAILURE;
return webProgress->AddProgressListener(this, nsIWebProgress::NOTIFY_STATE_ALL);
return webProgress->AddProgressListener(this,
(nsIWebProgress::NOTIFY_STATE_NETWORK |
nsIWebProgress::NOTIFY_STATE_DOCUMENT |
nsIWebProgress::NOTIFY_LOCATION));
}
/*---------------------------------------------------------------------------
@ -988,10 +1022,11 @@ nsEditingSession::PrepareForEditing()
get and return the controller ID, and set the refCon
----------------------------------------------------------------------------*/
nsresult
nsEditingSession::SetupEditorCommandController(const char *aControllerClassName,
nsIDOMWindow *aWindow,
nsISupports *aRefCon,
PRUint32 *aControllerId)
nsEditingSession::SetupEditorCommandController(
const char *aControllerClassName,
nsIDOMWindow *aWindow,
nsISupports *aRefCon,
PRUint32 *aControllerId)
{
NS_ENSURE_ARG_POINTER(aControllerClassName);
NS_ENSURE_ARG_POINTER(aWindow);
@ -999,7 +1034,8 @@ nsEditingSession::SetupEditorCommandController(const char *aControllerClassName,
NS_ENSURE_ARG_POINTER(aControllerId);
nsresult rv;
nsCOMPtr<nsIDOMWindowInternal> domWindowInt = do_QueryInterface(aWindow, &rv);
nsCOMPtr<nsIDOMWindowInternal> domWindowInt =
do_QueryInterface(aWindow, &rv);
if (NS_FAILED(rv)) return rv;
nsCOMPtr<nsIControllers> controllers;
@ -1043,7 +1079,8 @@ nsEditingSession::SetEditorOnControllers(nsIDOMWindow *aWindow,
nsresult rv;
// set the editor on the controller
nsCOMPtr<nsIDOMWindowInternal> domWindowInt = do_QueryInterface(aWindow, &rv);
nsCOMPtr<nsIDOMWindowInternal> domWindowInt =
do_QueryInterface(aWindow, &rv);
if (NS_FAILED(rv)) return rv;
nsCOMPtr<nsIControllers> controllers;

Просмотреть файл

@ -239,10 +239,21 @@ interface nsIHTMLEditor : nsISupports
void insertElementAtSelection(in nsIDOMElement aElement,
in boolean aDeleteSelection);
/** Set the documents title.
/**
* Set the documents title.
*/
void setDocumentTitle(in AString aTitle);
/**
* Set the BaseURL for the document to the current URL
* but only if the page doesn't have a <base> tag
* This should be done after the document URL has changed,
* such as after saving a file
* This is used as base for relativizing link and image urls
*/
void updateBaseURL();
/* ------------ Selection manipulation -------------- */
/* Should these be moved to nsISelection? */

Просмотреть файл

@ -1238,6 +1238,44 @@ PRBool nsHTMLEditor::IsModifiable()
#pragma mark -
#endif
NS_IMETHODIMP
nsHTMLEditor::UpdateBaseURL()
{
nsCOMPtr<nsIDOMDocument> domDoc;
GetDocument(getter_AddRefs(domDoc));
if (!domDoc) return NS_ERROR_FAILURE;
// Look for an HTML <base> tag
nsCOMPtr<nsIDOMNodeList> nodeList;
nsresult rv = domDoc->GetElementsByTagName(NS_LITERAL_STRING("base"), getter_AddRefs(nodeList));
NS_ENSURE_SUCCESS(rv, rv);
nsCOMPtr<nsIDOMNode> baseNode;
if (nodeList)
{
PRUint32 count;
nodeList->GetLength(&count);
if (count >= 1)
{
rv = nodeList->Item(0, getter_AddRefs(baseNode));
NS_ENSURE_SUCCESS(rv, rv);
}
}
// If no base tag, then set baseURL to the document's URL
// This is very important, else relative URLs for links and images are wrong
if (!baseNode)
{
nsCOMPtr<nsIDocument> doc = do_QueryInterface(domDoc);
if (!doc) return NS_ERROR_FAILURE;
nsCOMPtr<nsIURI> uri;
rv = doc->GetDocumentURL(getter_AddRefs(uri));
NS_ENSURE_SUCCESS(rv, rv);
return doc->SetBaseURL(uri);
}
return NS_OK;
}
NS_IMETHODIMP nsHTMLEditor::HandleKeyPress(nsIDOMKeyEvent* aKeyEvent)
{
PRUint32 keyCode, character;

Просмотреть файл

@ -124,6 +124,8 @@ public:
NS_IMETHODIMP BeginningOfDocument();
/* ------------ nsIHTMLEditor methods -------------- */
NS_IMETHOD UpdateBaseURL();
NS_IMETHOD CopyLastEditableChildStyles(nsIDOMNode *aPreviousBlock, nsIDOMNode *aNewBlock,
nsIDOMNode **aOutBrNode);

Просмотреть файл

@ -389,6 +389,15 @@ var gEditorDocumentObserver =
dump("obs_documentWillBeDestroyed notification\n");
break;
case "obs_documentLocationChanged":
// Ignore this when editor doesn't exist,
// which happens once when page load starts
if (editor)
try {
editor.updateBaseURL();
} catch(e) { dump (e); }
break;
case "cmd_bold":
// Update all style items
window.updateCommands("style");
@ -483,6 +492,7 @@ function EditorSharedStartup()
commandManager.addCommandObserver(gEditorDocumentObserver, "obs_documentCreated");
commandManager.addCommandObserver(gEditorDocumentObserver, "cmd_setDocumentModified");
commandManager.addCommandObserver(gEditorDocumentObserver, "obs_documentWillBeDestroyed");
commandManager.addCommandObserver(gEditorDocumentObserver, "obs_documentLocationChanged");
// Until nsIControllerCommandGroup-based code is implemented,
// we will observe just the bold command to trigger update of
@ -564,6 +574,7 @@ function EditorShutdown()
var commandManager = GetCurrentCommandManager();
commandManager.removeCommandObserver(gEditorDocumentObserver, "obs_documentCreated");
commandManager.removeCommandObserver(gEditorDocumentObserver, "obs_documentWillBeDestroyed");
commandManager.removeCommandObserver(gEditorDocumentObserver, "obs_documentLocationChanged");
} catch (e) { dump (e); }
}
@ -3199,4 +3210,3 @@ function FillInHTMLTooltip(tooltip)
}
return false;
}