📄 webnotificationcenter.cpp
字号:
/* * Copyright (C) 2006, 2007 Apple Inc. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in the * documentation and/or other materials provided with the distribution. * * THIS SOFTWARE IS PROVIDED BY APPLE COMPUTER, INC. ``AS IS'' AND ANY * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL APPLE COMPUTER, INC. OR * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY * OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */#include "config.h"#include "WebKitDLL.h"#include "WebNotificationCenter.h"#include "WebNotification.h"#pragma warning(push, 0)#include <WebCore/COMPtr.h>#include <WebCore/PlatformString.h>#include <WebCore/StringHash.h>#include <wtf/HashMap.h>#include <wtf/HashTraits.h>#include <wtf/Vector.h>#pragma warning(pop)#include <tchar.h>#include <utility>using namespace WebCore;typedef std::pair<COMPtr<IUnknown>, COMPtr<IWebNotificationObserver> > ObjectObserverPair;typedef Vector<ObjectObserverPair> ObjectObserverList;typedef ObjectObserverList::iterator ObserverListIterator;typedef HashMap<String, ObjectObserverList> MappedObservers;struct WebNotificationCenterPrivate { MappedObservers m_mappedObservers;};// WebNotificationCenter ----------------------------------------------------------------IWebNotificationCenter* WebNotificationCenter::m_defaultCenter = 0;WebNotificationCenter::WebNotificationCenter() : m_refCount(0) , d(new WebNotificationCenterPrivate){ gClassCount++; gClassNameCount.add("WebNotificationCenter");}WebNotificationCenter::~WebNotificationCenter(){ gClassCount--; gClassNameCount.remove("WebNotificationCenter");}WebNotificationCenter* WebNotificationCenter::createInstance(){ WebNotificationCenter* instance = new WebNotificationCenter(); instance->AddRef(); return instance;}// IUnknown -------------------------------------------------------------------HRESULT STDMETHODCALLTYPE WebNotificationCenter::QueryInterface(REFIID riid, void** ppvObject){ *ppvObject = 0; if (IsEqualGUID(riid, IID_IUnknown)) *ppvObject = static_cast<IWebNotificationCenter*>(this); else if (IsEqualGUID(riid, IID_IWebNotificationCenter)) *ppvObject = static_cast<IWebNotificationCenter*>(this); else return E_NOINTERFACE; AddRef(); return S_OK;}ULONG STDMETHODCALLTYPE WebNotificationCenter::AddRef(void){ return ++m_refCount;}ULONG STDMETHODCALLTYPE WebNotificationCenter::Release(void){ ULONG newRef = --m_refCount; if (!newRef) delete(this); return newRef;}IWebNotificationCenter* WebNotificationCenter::defaultCenterInternal(){ if (!m_defaultCenter) m_defaultCenter = WebNotificationCenter::createInstance(); return m_defaultCenter;}void WebNotificationCenter::postNotificationInternal(IWebNotification* notification, BSTR notificationName, IUnknown* anObject){ String name(notificationName, SysStringLen(notificationName)); MappedObservers::iterator it = d->m_mappedObservers.find(name); if (it == d->m_mappedObservers.end()) return; // Intentionally make a copy of the list to avoid the possibility of errors // from a mutation of the list in the onNotify callback. ObjectObserverList list = it->second; ObserverListIterator end = list.end(); for (ObserverListIterator it2 = list.begin(); it2 != end; ++it2) { IUnknown* observedObject = it2->first.get(); IWebNotificationObserver* observer = it2->second.get(); if (!observedObject || !anObject || observedObject == anObject) observer->onNotify(notification); }}// IWebNotificationCenter -----------------------------------------------------HRESULT STDMETHODCALLTYPE WebNotificationCenter::defaultCenter( /* [retval][out] */ IWebNotificationCenter** center){ *center = defaultCenterInternal(); (*center)->AddRef(); return S_OK;}HRESULT STDMETHODCALLTYPE WebNotificationCenter::addObserver( /* [in] */ IWebNotificationObserver* observer, /* [in] */ BSTR notificationName, /* [in] */ IUnknown* anObject){ String name(notificationName, SysStringLen(notificationName)); MappedObservers::iterator it = d->m_mappedObservers.find(name); if (it != d->m_mappedObservers.end()) it->second.append(ObjectObserverPair(anObject, observer)); else { ObjectObserverList list; list.append(ObjectObserverPair(anObject, observer)); d->m_mappedObservers.add(name, list); } return S_OK;}HRESULT STDMETHODCALLTYPE WebNotificationCenter::postNotification( /* [in] */ IWebNotification* notification){ BSTR name; HRESULT hr = notification->name(&name); if (FAILED(hr)) return hr; COMPtr<IUnknown> obj; hr = notification->getObject(&obj); if (FAILED(hr)) return hr; postNotificationInternal(notification, name, obj.get()); SysFreeString(name); return hr;}HRESULT STDMETHODCALLTYPE WebNotificationCenter::postNotificationName( /* [in] */ BSTR notificationName, /* [in] */ IUnknown* anObject, /* [optional][in] */ IPropertyBag* userInfo){ COMPtr<WebNotification> notification(AdoptCOM, WebNotification::createInstance(notificationName, anObject, userInfo)); postNotificationInternal(notification.get(), notificationName, anObject); return S_OK;}HRESULT STDMETHODCALLTYPE WebNotificationCenter::removeObserver( /* [in] */ IWebNotificationObserver* anObserver, /* [in] */ BSTR notificationName, /* [optional][in] */ IUnknown* anObject){ String name(notificationName, SysStringLen(notificationName)); MappedObservers::iterator it = d->m_mappedObservers.find(name); if (it == d->m_mappedObservers.end()) return E_FAIL; ObjectObserverList& observerList = it->second; ObserverListIterator end = observerList.end(); int i = 0; for (ObserverListIterator it2 = observerList.begin(); it2 != end; ++it2, ++i) { IUnknown* observedObject = it2->first.get(); IWebNotificationObserver* observer = it2->second.get(); if (observer == anObserver && (!anObject || anObject == observedObject)) { observerList.remove(i); break; } } if (observerList.isEmpty()) d->m_mappedObservers.remove(name); return S_OK;}
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -