1 /* -*- Mode: C++; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
2 /* This Source Code Form is subject to the terms of the Mozilla Public
3 * License, v. 2.0. If a copy of the MPL was not distributed with this
4 * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
8 #include "nsReadableUtils.h"
9 #include "nsUnicharUtils.h"
11 #include "nsIBaseWindow.h"
12 #include "nsIWidget.h"
13 #include "nsIDOMWindow.h"
14 #include "nsIObserverService.h"
15 #include "nsIServiceManager.h"
16 #include "nsISimpleEnumerator.h"
17 #include "nsAppShellWindowEnumerator.h"
18 #include "nsWindowMediator.h"
19 #include "nsIWindowMediatorListener.h"
20 #include "nsXPIDLString.h"
21 #include "nsGlobalWindow.h"
23 #include "nsIDocShell.h"
24 #include "nsIInterfaceRequestor.h"
25 #include "nsIInterfaceRequestorUtils.h"
26 #include "nsIXULWindow.h"
28 using namespace mozilla
;
30 static nsresult
GetDOMWindow(nsIXULWindow
* inWindow
,
31 nsCOMPtr
< nsIDOMWindow
>& outDOMWindow
);
33 static bool notifyOpenWindow(nsIWindowMediatorListener
*aElement
, void* aData
);
34 static bool notifyCloseWindow(nsIWindowMediatorListener
*aElement
, void* aData
);
35 static bool notifyWindowTitleChange(nsIWindowMediatorListener
*aElement
, void* aData
);
37 // for notifyWindowTitleChange
38 struct WindowTitleData
{
39 nsIXULWindow
* mWindow
;
40 const PRUnichar
*mTitle
;
44 GetDOMWindow(nsIXULWindow
* inWindow
, nsCOMPtr
<nsIDOMWindow
>& outDOMWindow
)
46 nsCOMPtr
<nsIDocShell
> docShell
;
48 inWindow
->GetDocShell(getter_AddRefs(docShell
));
49 outDOMWindow
= do_GetInterface(docShell
);
50 return outDOMWindow
? NS_OK
: NS_ERROR_FAILURE
;
53 nsWindowMediator::nsWindowMediator() :
54 mEnumeratorList(), mOldestWindow(nullptr), mTopmostWindow(nullptr),
55 mTimeStamp(0), mSortingZOrder(false), mReady(false),
56 mListLock("nsWindowMediator.mListLock")
60 nsWindowMediator::~nsWindowMediator()
63 UnregisterWindow(mOldestWindow
);
66 nsresult
nsWindowMediator::Init()
69 nsCOMPtr
<nsIObserverService
> obsSvc
=
70 do_GetService("@mozilla.org/observer-service;1", &rv
);
71 NS_ENSURE_SUCCESS(rv
, rv
);
72 rv
= obsSvc
->AddObserver(this, "xpcom-shutdown", true);
73 NS_ENSURE_SUCCESS(rv
, rv
);
79 NS_IMETHODIMP
nsWindowMediator::RegisterWindow(nsIXULWindow
* inWindow
)
81 NS_ENSURE_STATE(mReady
);
83 if (GetInfoFor(inWindow
)) {
84 NS_ERROR("multiple window registration");
85 return NS_ERROR_FAILURE
;
90 // Create window info struct and add to list of windows
91 nsWindowInfo
* windowInfo
= new nsWindowInfo(inWindow
, mTimeStamp
);
93 return NS_ERROR_OUT_OF_MEMORY
;
95 WindowTitleData winData
= { inWindow
, nullptr };
96 mListeners
.EnumerateForwards(notifyOpenWindow
, &winData
);
98 MutexAutoLock
lock(mListLock
);
100 windowInfo
->InsertAfter(mOldestWindow
->mOlder
, nullptr);
102 mOldestWindow
= windowInfo
;
108 nsWindowMediator::UnregisterWindow(nsIXULWindow
* inWindow
)
110 NS_ENSURE_STATE(mReady
);
111 MutexAutoLock
lock(mListLock
);
112 nsWindowInfo
*info
= GetInfoFor(inWindow
);
114 return UnregisterWindow(info
);
115 return NS_ERROR_INVALID_ARG
;
119 nsWindowMediator::UnregisterWindow(nsWindowInfo
*inInfo
)
121 // Inform the iterators
123 while (index
< mEnumeratorList
.Length()) {
124 mEnumeratorList
[index
]->WindowRemoved(inInfo
);
128 WindowTitleData winData
= { inInfo
->mWindow
.get(), nullptr };
129 mListeners
.EnumerateForwards(notifyCloseWindow
, &winData
);
131 // Remove from the lists and free up
132 if (inInfo
== mOldestWindow
)
133 mOldestWindow
= inInfo
->mYounger
;
134 if (inInfo
== mTopmostWindow
)
135 mTopmostWindow
= inInfo
->mLower
;
136 inInfo
->Unlink(true, true);
137 if (inInfo
== mOldestWindow
)
138 mOldestWindow
= nullptr;
139 if (inInfo
== mTopmostWindow
)
140 mTopmostWindow
= nullptr;
147 nsWindowMediator::GetInfoFor(nsIXULWindow
*aWindow
)
155 info
= mOldestWindow
;
157 while (info
!= listEnd
) {
158 if (info
->mWindow
.get() == aWindow
)
160 info
= info
->mYounger
;
161 listEnd
= mOldestWindow
;
167 nsWindowMediator::GetInfoFor(nsIWidget
*aWindow
)
175 info
= mOldestWindow
;
178 nsCOMPtr
<nsIWidget
> scanWidget
;
179 while (info
!= listEnd
) {
180 nsCOMPtr
<nsIBaseWindow
> base(do_QueryInterface(info
->mWindow
));
182 base
->GetMainWidget(getter_AddRefs(scanWidget
));
183 if (aWindow
== scanWidget
.get())
185 info
= info
->mYounger
;
186 listEnd
= mOldestWindow
;
192 nsWindowMediator::GetEnumerator(const PRUnichar
* inType
, nsISimpleEnumerator
** outEnumerator
)
194 NS_ENSURE_ARG_POINTER(outEnumerator
);
195 NS_ENSURE_STATE(mReady
);
196 MutexAutoLock
lock(mListLock
);
197 nsAppShellWindowEnumerator
*enumerator
= new nsASDOMWindowEarlyToLateEnumerator(inType
, *this);
199 return enumerator
->QueryInterface(NS_GET_IID(nsISimpleEnumerator
) , (void**)outEnumerator
);
201 return NS_ERROR_OUT_OF_MEMORY
;
205 nsWindowMediator::GetXULWindowEnumerator(const PRUnichar
* inType
, nsISimpleEnumerator
** outEnumerator
)
207 NS_ENSURE_ARG_POINTER(outEnumerator
);
208 NS_ENSURE_STATE(mReady
);
209 MutexAutoLock
lock(mListLock
);
210 nsAppShellWindowEnumerator
*enumerator
= new nsASXULWindowEarlyToLateEnumerator(inType
, *this);
212 return enumerator
->QueryInterface(NS_GET_IID(nsISimpleEnumerator
) , (void**)outEnumerator
);
214 return NS_ERROR_OUT_OF_MEMORY
;
218 nsWindowMediator::GetZOrderDOMWindowEnumerator(
219 const PRUnichar
*aWindowType
, bool aFrontToBack
,
220 nsISimpleEnumerator
**_retval
)
222 NS_ENSURE_ARG_POINTER(_retval
);
223 NS_ENSURE_STATE(mReady
);
224 MutexAutoLock
lock(mListLock
);
225 nsAppShellWindowEnumerator
*enumerator
;
227 enumerator
= new nsASDOMWindowFrontToBackEnumerator(aWindowType
, *this);
229 enumerator
= new nsASDOMWindowBackToFrontEnumerator(aWindowType
, *this);
231 return CallQueryInterface(enumerator
, _retval
);
233 return NS_ERROR_OUT_OF_MEMORY
;
237 nsWindowMediator::GetZOrderXULWindowEnumerator(
238 const PRUnichar
*aWindowType
, bool aFrontToBack
,
239 nsISimpleEnumerator
**_retval
)
241 NS_ENSURE_ARG_POINTER(_retval
);
242 NS_ENSURE_STATE(mReady
);
243 MutexAutoLock
lock(mListLock
);
244 nsAppShellWindowEnumerator
*enumerator
;
246 enumerator
= new nsASXULWindowFrontToBackEnumerator(aWindowType
, *this);
248 enumerator
= new nsASXULWindowBackToFrontEnumerator(aWindowType
, *this);
250 return CallQueryInterface(enumerator
, _retval
);
252 return NS_ERROR_OUT_OF_MEMORY
;
256 nsWindowMediator::AddEnumerator(nsAppShellWindowEnumerator
* inEnumerator
)
258 return mEnumeratorList
.AppendElement(inEnumerator
) != nullptr;
262 nsWindowMediator::RemoveEnumerator(nsAppShellWindowEnumerator
* inEnumerator
)
264 return mEnumeratorList
.RemoveElement(inEnumerator
);
267 // Returns the window of type inType ( if null return any window type ) which has the most recent
270 nsWindowMediator::GetMostRecentWindow(const PRUnichar
* inType
, nsIDOMWindow
** outWindow
)
272 NS_ENSURE_ARG_POINTER(outWindow
);
273 *outWindow
= nullptr;
277 // Find the most window with the highest time stamp that matches
278 // the requested type
280 MutexAutoLock
lock(mListLock
);
281 nsWindowInfo
*info
= MostRecentWindowInfo(inType
);
283 if (info
&& info
->mWindow
) {
284 nsCOMPtr
<nsIDOMWindow
> DOMWindow
;
285 if (NS_SUCCEEDED(GetDOMWindow(info
->mWindow
, DOMWindow
))) {
286 *outWindow
= DOMWindow
;
287 NS_ADDREF(*outWindow
);
290 return NS_ERROR_FAILURE
;
297 nsWindowMediator::MostRecentWindowInfo(const PRUnichar
* inType
)
299 int32_t lastTimeStamp
= -1;
300 nsAutoString
typeString(inType
);
301 bool allWindows
= !inType
|| typeString
.IsEmpty();
303 // Find the most window with the highest time stamp that matches
304 // the requested type
305 nsWindowInfo
*searchInfo
,
307 *foundInfo
= nullptr;
309 searchInfo
= mOldestWindow
;
311 while (searchInfo
!= listEnd
) {
312 if ((allWindows
|| searchInfo
->TypeEquals(typeString
)) &&
313 searchInfo
->mTimeStamp
>= lastTimeStamp
) {
315 foundInfo
= searchInfo
;
316 lastTimeStamp
= searchInfo
->mTimeStamp
;
318 searchInfo
= searchInfo
->mYounger
;
319 listEnd
= mOldestWindow
;
325 nsWindowMediator::GetOuterWindowWithId(uint64_t aWindowID
,
326 nsIDOMWindow
** aWindow
)
328 *aWindow
= nsGlobalWindow::GetOuterWindowWithId(aWindowID
);
329 NS_IF_ADDREF(*aWindow
);
334 nsWindowMediator::UpdateWindowTimeStamp(nsIXULWindow
* inWindow
)
336 NS_ENSURE_STATE(mReady
);
337 MutexAutoLock
lock(mListLock
);
338 nsWindowInfo
*info
= GetInfoFor(inWindow
);
340 // increment the window's time stamp
341 info
->mTimeStamp
= ++mTimeStamp
;
344 return NS_ERROR_FAILURE
;
348 nsWindowMediator::UpdateWindowTitle(nsIXULWindow
* inWindow
,
349 const PRUnichar
* inTitle
)
351 NS_ENSURE_STATE(mReady
);
352 MutexAutoLock
lock(mListLock
);
353 if (GetInfoFor(inWindow
)) {
354 WindowTitleData winData
= { inWindow
, inTitle
};
355 mListeners
.EnumerateForwards(notifyWindowTitleChange
, &winData
);
361 /* This method's plan is to intervene only when absolutely necessary.
362 We will get requests to place our windows behind unknown windows.
363 For the most part, we need to leave those alone (turning them into
364 explicit requests to be on top breaks Windows.) So generally we
365 calculate a change as seldom as possible.
368 nsWindowMediator::CalculateZPosition(
369 nsIXULWindow
*inWindow
,
372 uint32_t *outPosition
,
373 nsIWidget
**outBelow
,
376 NS_ENSURE_ARG_POINTER(outBelow
);
377 NS_ENSURE_STATE(mReady
);
381 if (!inWindow
|| !outPosition
|| !outAltered
)
382 return NS_ERROR_NULL_POINTER
;
384 if (inPosition
!= nsIWindowMediator::zLevelTop
&&
385 inPosition
!= nsIWindowMediator::zLevelBottom
&&
386 inPosition
!= nsIWindowMediator::zLevelBelow
)
387 return NS_ERROR_INVALID_ARG
;
389 nsWindowInfo
*info
= mTopmostWindow
;
390 nsIXULWindow
*belowWindow
= nullptr;
392 nsresult result
= NS_OK
;
394 *outPosition
= inPosition
;
397 if (mSortingZOrder
) { // don't fight SortZOrder()
399 NS_IF_ADDREF(*outBelow
);
404 GetZLevel(inWindow
, &inZ
);
406 MutexAutoLock
lock(mListLock
);
408 if (inPosition
== nsIWindowMediator::zLevelBelow
) {
409 // locate inBelow. use topmost if it can't be found or isn't in the
411 info
= GetInfoFor(inBelow
);
412 if (!info
|| (info
->mYounger
!= info
&& info
->mLower
== info
))
413 info
= mTopmostWindow
;
418 /* Treat unknown windows as a request to be on top.
419 Not as it should be, but that's what Windows gives us.
420 Note we change inPosition, but not *outPosition. This forces
421 us to go through the "on top" calculation just below, without
422 necessarily changing the output parameters. */
423 inPosition
= nsIWindowMediator::zLevelTop
;
427 if (inPosition
== nsIWindowMediator::zLevelTop
) {
428 if (mTopmostWindow
&& mTopmostWindow
->mZLevel
> inZ
) {
429 // asked for topmost, can't have it. locate highest allowed position.
431 if (info
->mZLevel
<= inZ
)
434 } while (info
!= mTopmostWindow
);
436 *outPosition
= nsIWindowMediator::zLevelBelow
;
437 belowWindow
= info
->mHigher
->mWindow
;
440 } else if (inPosition
== nsIWindowMediator::zLevelBottom
) {
441 if (mTopmostWindow
&& mTopmostWindow
->mHigher
->mZLevel
< inZ
) {
442 // asked for bottommost, can't have it. locate lowest allowed position.
444 info
= info
->mHigher
;
445 if (info
->mZLevel
>= inZ
)
447 } while (info
!= mTopmostWindow
);
449 *outPosition
= nsIWindowMediator::zLevelBelow
;
450 belowWindow
= info
->mWindow
;
454 unsigned long relativeZ
;
456 // check that we're in the right z-plane
458 belowWindow
= info
->mWindow
;
459 relativeZ
= info
->mZLevel
;
460 if (relativeZ
> inZ
) {
461 // might be OK. is lower window, if any, lower?
462 if (info
->mLower
!= info
&& info
->mLower
->mZLevel
> inZ
) {
464 if (info
->mZLevel
<= inZ
)
467 } while (info
!= mTopmostWindow
);
469 belowWindow
= info
->mHigher
->mWindow
;
472 } else if (relativeZ
< inZ
) {
473 // nope. look for a higher window to be behind.
475 info
= info
->mHigher
;
476 if (info
->mZLevel
>= inZ
)
478 } while (info
!= mTopmostWindow
);
480 if (info
->mZLevel
>= inZ
)
481 belowWindow
= info
->mWindow
;
483 *outPosition
= nsIWindowMediator::zLevelTop
;
485 } // else they're equal, so it's OK
489 if (NS_SUCCEEDED(result
) && belowWindow
) {
490 nsCOMPtr
<nsIBaseWindow
> base(do_QueryInterface(belowWindow
));
492 base
->GetMainWidget(outBelow
);
494 result
= NS_ERROR_NO_INTERFACE
;
501 nsWindowMediator::SetZPosition(
502 nsIXULWindow
*inWindow
,
504 nsIXULWindow
*inBelow
)
506 nsWindowInfo
*inInfo
,
509 if ((inPosition
!= nsIWindowMediator::zLevelTop
&&
510 inPosition
!= nsIWindowMediator::zLevelBottom
&&
511 inPosition
!= nsIWindowMediator::zLevelBelow
) ||
513 return NS_ERROR_INVALID_ARG
;
516 if (mSortingZOrder
) // don't fight SortZOrder()
519 NS_ENSURE_STATE(mReady
);
520 MutexAutoLock
lock(mListLock
);
522 /* Locate inWindow and unlink it from the z-order list.
523 It's important we look for it in the age list, not the z-order list.
524 This is because the former is guaranteed complete, while
525 now may be this window's first exposure to the latter. */
526 inInfo
= GetInfoFor(inWindow
);
528 return NS_ERROR_INVALID_ARG
;
530 // locate inBelow, place inWindow behind it
531 if (inPosition
== nsIWindowMediator::zLevelBelow
) {
532 belowInfo
= GetInfoFor(inBelow
);
533 // it had better also be in the z-order list
535 belowInfo
->mYounger
!= belowInfo
&& belowInfo
->mLower
== belowInfo
) {
540 return NS_ERROR_INVALID_ARG
;
542 inPosition
= nsIWindowMediator::zLevelTop
;
545 if (inPosition
== nsIWindowMediator::zLevelTop
||
546 inPosition
== nsIWindowMediator::zLevelBottom
)
547 belowInfo
= mTopmostWindow
? mTopmostWindow
->mHigher
: nullptr;
549 if (inInfo
!= belowInfo
) {
550 inInfo
->Unlink(false, true);
551 inInfo
->InsertAfter(nullptr, belowInfo
);
553 if (inPosition
== nsIWindowMediator::zLevelTop
)
554 mTopmostWindow
= inInfo
;
560 nsWindowMediator::GetZLevel(nsIXULWindow
*aWindow
, uint32_t *_retval
)
562 NS_ENSURE_ARG_POINTER(_retval
);
563 *_retval
= nsIXULWindow::normalZ
;
564 nsWindowInfo
*info
= GetInfoFor(aWindow
);
566 *_retval
= info
->mZLevel
;
568 NS_WARNING("getting z level of unregistered window");
569 // this goes off during window destruction
575 nsWindowMediator::SetZLevel(nsIXULWindow
*aWindow
, uint32_t aZLevel
)
577 NS_ENSURE_STATE(mReady
);
578 MutexAutoLock
lock(mListLock
);
580 nsWindowInfo
*info
= GetInfoFor(aWindow
);
581 NS_ASSERTION(info
, "setting z level of unregistered window");
583 return NS_ERROR_FAILURE
;
585 if (info
->mZLevel
!= aZLevel
) {
586 bool lowered
= info
->mZLevel
> aZLevel
;
587 info
->mZLevel
= aZLevel
;
589 SortZOrderFrontToBack();
591 SortZOrderBackToFront();
596 /* Fix potentially out-of-order windows by performing an insertion sort
597 on the z-order list. The method will work no matter how broken the
598 list, but its assumed usage is immediately after one window's z level
599 has been changed, so one window is potentially out of place. Such a sort
600 is most efficiently done in a particular direction. Use this one
601 if a window's z level has just been reduced, so the sort is most efficiently
602 done front to back. Assumes caller has locked mListLock.
603 Note it's hardly worth going to all the trouble to write two versions
604 of this method except that if we choose the inefficient sorting direction,
605 on slow systems windows could visibly bubble around the window that
609 nsWindowMediator::SortZOrderFrontToBack()
611 nsWindowInfo
*scan
, // scans list looking for problems
612 *search
, // searches for correct placement for scan window
613 *prev
, // previous search element
614 *lowest
; // bottom-most window in list
617 if (!mTopmostWindow
) // early during program execution there's no z list yet
618 return; // there's also only one window, so this is not dangerous
620 mSortingZOrder
= true;
622 /* Step through the list from top to bottom. If we find a window which
623 should be moved down in the list, move it to its highest legal position. */
626 lowest
= mTopmostWindow
->mHigher
;
627 scan
= mTopmostWindow
;
628 while (scan
!= lowest
) {
629 uint32_t scanZ
= scan
->mZLevel
;
630 if (scanZ
< scan
->mLower
->mZLevel
) { // out of order
631 search
= scan
->mLower
;
634 search
= search
->mLower
;
635 } while (prev
!= lowest
&& scanZ
< search
->mZLevel
);
637 // reposition |scan| within the list
638 if (scan
== mTopmostWindow
)
639 mTopmostWindow
= scan
->mLower
;
640 scan
->Unlink(false, true);
641 scan
->InsertAfter(nullptr, prev
);
643 // fix actual window order
644 nsCOMPtr
<nsIBaseWindow
> base
;
645 nsCOMPtr
<nsIWidget
> scanWidget
;
646 nsCOMPtr
<nsIWidget
> prevWidget
;
647 base
= do_QueryInterface(scan
->mWindow
);
649 base
->GetMainWidget(getter_AddRefs(scanWidget
));
650 base
= do_QueryInterface(prev
->mWindow
);
652 base
->GetMainWidget(getter_AddRefs(prevWidget
));
654 scanWidget
->PlaceBehind(eZPlacementBelow
, prevWidget
, false);
663 mSortingZOrder
= false;
666 // see comment for SortZOrderFrontToBack
668 nsWindowMediator::SortZOrderBackToFront()
670 nsWindowInfo
*scan
, // scans list looking for problems
671 *search
, // searches for correct placement for scan window
672 *lowest
; // bottom-most window in list
675 if (!mTopmostWindow
) // early during program execution there's no z list yet
676 return; // there's also only one window, so this is not dangerous
678 mSortingZOrder
= true;
680 /* Step through the list from bottom to top. If we find a window which
681 should be moved up in the list, move it to its lowest legal position. */
684 lowest
= mTopmostWindow
->mHigher
;
686 while (scan
!= mTopmostWindow
) {
687 uint32_t scanZ
= scan
->mZLevel
;
688 if (scanZ
> scan
->mHigher
->mZLevel
) { // out of order
691 search
= search
->mHigher
;
692 } while (search
!= lowest
&& scanZ
> search
->mZLevel
);
694 // reposition |scan| within the list
695 if (scan
!= search
&& scan
!= search
->mLower
) {
696 scan
->Unlink(false, true);
697 scan
->InsertAfter(nullptr, search
);
699 if (search
== lowest
)
700 mTopmostWindow
= scan
;
702 // fix actual window order
703 nsCOMPtr
<nsIBaseWindow
> base
;
704 nsCOMPtr
<nsIWidget
> scanWidget
;
705 nsCOMPtr
<nsIWidget
> searchWidget
;
706 base
= do_QueryInterface(scan
->mWindow
);
708 base
->GetMainWidget(getter_AddRefs(scanWidget
));
709 if (mTopmostWindow
!= scan
) {
710 base
= do_QueryInterface(search
->mWindow
);
712 base
->GetMainWidget(getter_AddRefs(searchWidget
));
715 scanWidget
->PlaceBehind(eZPlacementBelow
, searchWidget
, false);
719 scan
= scan
->mHigher
;
723 mSortingZOrder
= false;
726 NS_IMPL_ISUPPORTS3(nsWindowMediator
,
729 nsISupportsWeakReference
)
732 nsWindowMediator::AddListener(nsIWindowMediatorListener
* aListener
)
734 NS_ENSURE_ARG_POINTER(aListener
);
736 mListeners
.AppendObject(aListener
);
742 nsWindowMediator::RemoveListener(nsIWindowMediatorListener
* aListener
)
744 NS_ENSURE_ARG_POINTER(aListener
);
746 mListeners
.RemoveObject(aListener
);
752 nsWindowMediator::Observe(nsISupports
* aSubject
,
754 const PRUnichar
* aData
)
756 if (!strcmp(aTopic
, "xpcom-shutdown") && mReady
) {
757 // Unregistering a window may cause its destructor to run, causing it to
758 // call into the window mediator, try to acquire mListLock, and deadlock.
759 // Our solution is to hold strong refs to all windows until we release
761 nsTArray
<nsCOMPtr
<nsIXULWindow
> > windows
;
764 MutexAutoLock
lock(mListLock
);
765 while (mOldestWindow
) {
766 windows
.AppendElement(mOldestWindow
->mWindow
);
767 UnregisterWindow(mOldestWindow
);
776 notifyOpenWindow(nsIWindowMediatorListener
*aListener
, void* aData
)
778 WindowTitleData
* winData
= static_cast<WindowTitleData
*>(aData
);
779 aListener
->OnOpenWindow(winData
->mWindow
);
785 notifyCloseWindow(nsIWindowMediatorListener
*aListener
, void* aData
)
787 WindowTitleData
* winData
= static_cast<WindowTitleData
*>(aData
);
788 aListener
->OnCloseWindow(winData
->mWindow
);
794 notifyWindowTitleChange(nsIWindowMediatorListener
*aListener
, void* aData
)
796 WindowTitleData
* titleData
= reinterpret_cast<WindowTitleData
*>(aData
);
797 aListener
->OnWindowTitleChange(titleData
->mWindow
, titleData
->mTitle
);