1.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000 1.2 +++ b/docshell/base/nsDocShellEditorData.cpp Wed Dec 31 06:09:35 2014 +0100 1.3 @@ -0,0 +1,242 @@ 1.4 +/* -*- Mode: C++; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*- 1.5 + * 1.6 + * This Source Code Form is subject to the terms of the Mozilla Public 1.7 + * License, v. 2.0. If a copy of the MPL was not distributed with this 1.8 + * file, You can obtain one at http://mozilla.org/MPL/2.0/. */ 1.9 + 1.10 + 1.11 +#include "nsDocShellEditorData.h" 1.12 +#include "nsIInterfaceRequestorUtils.h" 1.13 +#include "nsComponentManagerUtils.h" 1.14 +#include "nsIDOMWindow.h" 1.15 +#include "nsIDOMDocument.h" 1.16 +#include "nsIEditor.h" 1.17 +#include "nsIEditingSession.h" 1.18 +#include "nsIDocShell.h" 1.19 + 1.20 +/*--------------------------------------------------------------------------- 1.21 + 1.22 + nsDocShellEditorData 1.23 + 1.24 +----------------------------------------------------------------------------*/ 1.25 + 1.26 +nsDocShellEditorData::nsDocShellEditorData(nsIDocShell* inOwningDocShell) 1.27 +: mDocShell(inOwningDocShell) 1.28 +, mMakeEditable(false) 1.29 +, mIsDetached(false) 1.30 +, mDetachedMakeEditable(false) 1.31 +, mDetachedEditingState(nsIHTMLDocument::eOff) 1.32 +{ 1.33 + NS_ASSERTION(mDocShell, "Where is my docShell?"); 1.34 +} 1.35 + 1.36 + 1.37 +/*--------------------------------------------------------------------------- 1.38 + 1.39 + ~nsDocShellEditorData 1.40 + 1.41 +----------------------------------------------------------------------------*/ 1.42 +nsDocShellEditorData::~nsDocShellEditorData() 1.43 +{ 1.44 + TearDownEditor(); 1.45 +} 1.46 + 1.47 +void 1.48 +nsDocShellEditorData::TearDownEditor() 1.49 +{ 1.50 + if (mEditor) { 1.51 + mEditor->PreDestroy(false); 1.52 + mEditor = nullptr; 1.53 + } 1.54 + mEditingSession = nullptr; 1.55 + mIsDetached = false; 1.56 +} 1.57 + 1.58 + 1.59 +/*--------------------------------------------------------------------------- 1.60 + 1.61 + MakeEditable 1.62 + 1.63 +----------------------------------------------------------------------------*/ 1.64 +nsresult 1.65 +nsDocShellEditorData::MakeEditable(bool inWaitForUriLoad) 1.66 +{ 1.67 + if (mMakeEditable) 1.68 + return NS_OK; 1.69 + 1.70 + // if we are already editable, and are getting turned off, 1.71 + // nuke the editor. 1.72 + if (mEditor) 1.73 + { 1.74 + NS_WARNING("Destroying existing editor on frame"); 1.75 + 1.76 + mEditor->PreDestroy(false); 1.77 + mEditor = nullptr; 1.78 + } 1.79 + 1.80 + if (inWaitForUriLoad) 1.81 + mMakeEditable = true; 1.82 + return NS_OK; 1.83 +} 1.84 + 1.85 + 1.86 +/*--------------------------------------------------------------------------- 1.87 + 1.88 + GetEditable 1.89 + 1.90 +----------------------------------------------------------------------------*/ 1.91 +bool 1.92 +nsDocShellEditorData::GetEditable() 1.93 +{ 1.94 + return mMakeEditable || (mEditor != nullptr); 1.95 +} 1.96 + 1.97 +/*--------------------------------------------------------------------------- 1.98 + 1.99 + CreateEditor 1.100 + 1.101 +----------------------------------------------------------------------------*/ 1.102 +nsresult 1.103 +nsDocShellEditorData::CreateEditor() 1.104 +{ 1.105 + nsCOMPtr<nsIEditingSession> editingSession; 1.106 + nsresult rv = GetEditingSession(getter_AddRefs(editingSession)); 1.107 + if (NS_FAILED(rv)) return rv; 1.108 + 1.109 + nsCOMPtr<nsIDOMWindow> domWindow = do_GetInterface(mDocShell); 1.110 + rv = editingSession->SetupEditorOnWindow(domWindow); 1.111 + if (NS_FAILED(rv)) return rv; 1.112 + 1.113 + return NS_OK; 1.114 +} 1.115 + 1.116 + 1.117 +/*--------------------------------------------------------------------------- 1.118 + 1.119 + GetEditingSession 1.120 + 1.121 +----------------------------------------------------------------------------*/ 1.122 +nsresult 1.123 +nsDocShellEditorData::GetEditingSession(nsIEditingSession **outEditingSession) 1.124 +{ 1.125 + nsresult rv = EnsureEditingSession(); 1.126 + NS_ENSURE_SUCCESS(rv, rv); 1.127 + 1.128 + NS_ADDREF(*outEditingSession = mEditingSession); 1.129 + 1.130 + return NS_OK; 1.131 +} 1.132 + 1.133 + 1.134 +/*--------------------------------------------------------------------------- 1.135 + 1.136 + GetEditor 1.137 + 1.138 +----------------------------------------------------------------------------*/ 1.139 +nsresult 1.140 +nsDocShellEditorData::GetEditor(nsIEditor **outEditor) 1.141 +{ 1.142 + NS_ENSURE_ARG_POINTER(outEditor); 1.143 + NS_IF_ADDREF(*outEditor = mEditor); 1.144 + return NS_OK; 1.145 +} 1.146 + 1.147 + 1.148 +/*--------------------------------------------------------------------------- 1.149 + 1.150 + SetEditor 1.151 + 1.152 +----------------------------------------------------------------------------*/ 1.153 +nsresult 1.154 +nsDocShellEditorData::SetEditor(nsIEditor *inEditor) 1.155 +{ 1.156 + // destroy any editor that we have. Checks for equality are 1.157 + // necessary to ensure that assigment into the nsCOMPtr does 1.158 + // not temporarily reduce the refCount of the editor to zero 1.159 + if (mEditor.get() != inEditor) 1.160 + { 1.161 + if (mEditor) 1.162 + { 1.163 + mEditor->PreDestroy(false); 1.164 + mEditor = nullptr; 1.165 + } 1.166 + 1.167 + mEditor = inEditor; // owning addref 1.168 + if (!mEditor) 1.169 + mMakeEditable = false; 1.170 + } 1.171 + 1.172 + return NS_OK; 1.173 +} 1.174 + 1.175 + 1.176 +/*--------------------------------------------------------------------------- 1.177 + 1.178 + EnsureEditingSession 1.179 + 1.180 + This creates the editing session on the content docShell that owns 1.181 + 'this'. 1.182 + 1.183 +----------------------------------------------------------------------------*/ 1.184 +nsresult 1.185 +nsDocShellEditorData::EnsureEditingSession() 1.186 +{ 1.187 + NS_ASSERTION(mDocShell, "Should have docShell here"); 1.188 + NS_ASSERTION(!mIsDetached, "This will stomp editing session!"); 1.189 + 1.190 + nsresult rv = NS_OK; 1.191 + 1.192 + if (!mEditingSession) 1.193 + { 1.194 + mEditingSession = 1.195 + do_CreateInstance("@mozilla.org/editor/editingsession;1", &rv); 1.196 + } 1.197 + 1.198 + return rv; 1.199 +} 1.200 + 1.201 +nsresult 1.202 +nsDocShellEditorData::DetachFromWindow() 1.203 +{ 1.204 + NS_ASSERTION(mEditingSession, 1.205 + "Can't detach when we don't have a session to detach!"); 1.206 + 1.207 + nsCOMPtr<nsIDOMWindow> domWindow = do_GetInterface(mDocShell); 1.208 + nsresult rv = mEditingSession->DetachFromWindow(domWindow); 1.209 + NS_ENSURE_SUCCESS(rv, rv); 1.210 + 1.211 + mIsDetached = true; 1.212 + mDetachedMakeEditable = mMakeEditable; 1.213 + mMakeEditable = false; 1.214 + 1.215 + nsCOMPtr<nsIDOMDocument> domDoc; 1.216 + domWindow->GetDocument(getter_AddRefs(domDoc)); 1.217 + nsCOMPtr<nsIHTMLDocument> htmlDoc = do_QueryInterface(domDoc); 1.218 + if (htmlDoc) 1.219 + mDetachedEditingState = htmlDoc->GetEditingState(); 1.220 + 1.221 + mDocShell = nullptr; 1.222 + 1.223 + return NS_OK; 1.224 +} 1.225 + 1.226 +nsresult 1.227 +nsDocShellEditorData::ReattachToWindow(nsIDocShell* aDocShell) 1.228 +{ 1.229 + mDocShell = aDocShell; 1.230 + 1.231 + nsCOMPtr<nsIDOMWindow> domWindow = do_GetInterface(mDocShell); 1.232 + nsresult rv = mEditingSession->ReattachToWindow(domWindow); 1.233 + NS_ENSURE_SUCCESS(rv, rv); 1.234 + 1.235 + mIsDetached = false; 1.236 + mMakeEditable = mDetachedMakeEditable; 1.237 + 1.238 + nsCOMPtr<nsIDOMDocument> domDoc; 1.239 + domWindow->GetDocument(getter_AddRefs(domDoc)); 1.240 + nsCOMPtr<nsIHTMLDocument> htmlDoc = do_QueryInterface(domDoc); 1.241 + if (htmlDoc) 1.242 + htmlDoc->SetEditingState(mDetachedEditingState); 1.243 + 1.244 + return NS_OK; 1.245 +}