diff options
author | Lorry Tar Creator <lorry-tar-importer@lorry> | 2017-06-27 06:07:23 +0000 |
---|---|---|
committer | Lorry Tar Creator <lorry-tar-importer@lorry> | 2017-06-27 06:07:23 +0000 |
commit | 1bf1084f2b10c3b47fd1a588d85d21ed0eb41d0c (patch) | |
tree | 46dcd36c86e7fbc6e5df36deb463b33e9967a6f7 /Source/WebCore/page/PointerLockController.cpp | |
parent | 32761a6cee1d0dee366b885b7b9c777e67885688 (diff) | |
download | WebKitGtk-tarball-master.tar.gz |
webkitgtk-2.16.5HEADwebkitgtk-2.16.5master
Diffstat (limited to 'Source/WebCore/page/PointerLockController.cpp')
-rw-r--r-- | Source/WebCore/page/PointerLockController.cpp | 103 |
1 files changed, 75 insertions, 28 deletions
diff --git a/Source/WebCore/page/PointerLockController.cpp b/Source/WebCore/page/PointerLockController.cpp index 5d6f5a5ea..ded552ebd 100644 --- a/Source/WebCore/page/PointerLockController.cpp +++ b/Source/WebCore/page/PointerLockController.cpp @@ -25,81 +25,109 @@ #include "config.h" #include "PointerLockController.h" +#if ENABLE(POINTER_LOCK) + #include "Chrome.h" #include "ChromeClient.h" #include "Element.h" #include "Event.h" +#include "EventNames.h" #include "Page.h" #include "PlatformMouseEvent.h" +#include "RuntimeEnabledFeatures.h" +#include "ScriptController.h" #include "VoidCallback.h" -#if ENABLE(POINTER_LOCK) namespace WebCore { -PointerLockController::PointerLockController(Page* page) +PointerLockController::PointerLockController(Page& page) : m_page(page) { } -PassOwnPtr<PointerLockController> PointerLockController::create(Page* page) -{ - return adoptPtr(new PointerLockController(page)); -} - void PointerLockController::requestPointerLock(Element* target) { - if (!target || !target->inDocument() || m_documentOfRemovedElementWhileWaitingForUnlock) { - enqueueEvent(eventNames().webkitpointerlockerrorEvent, target); + if (!target || !target->isConnected() || m_documentOfRemovedElementWhileWaitingForUnlock) { + enqueueEvent(eventNames().pointerlockerrorEvent, target); + return; + } + + if (m_documentAllowedToRelockWithoutUserGesture != &target->document() && !ScriptController::processingUserGesture()) { + enqueueEvent(eventNames().pointerlockerrorEvent, target); return; } if (target->document().isSandboxed(SandboxPointerLock)) { // FIXME: This message should be moved off the console once a solution to https://bugs.webkit.org/show_bug.cgi?id=103274 exists. - target->document().addConsoleMessage(SecurityMessageSource, ErrorMessageLevel, "Blocked pointer lock on an element because the element's frame is sandboxed and the 'allow-pointer-lock' permission is not set."); - enqueueEvent(eventNames().webkitpointerlockerrorEvent, target); + target->document().addConsoleMessage(MessageSource::Security, MessageLevel::Error, ASCIILiteral("Blocked pointer lock on an element because the element's frame is sandboxed and the 'allow-pointer-lock' permission is not set.")); + enqueueEvent(eventNames().pointerlockerrorEvent, target); return; } if (m_element) { if (&m_element->document() != &target->document()) { - enqueueEvent(eventNames().webkitpointerlockerrorEvent, target); + enqueueEvent(eventNames().pointerlockerrorEvent, target); return; } - enqueueEvent(eventNames().webkitpointerlockchangeEvent, target); m_element = target; - } else if (m_page->chrome().client().requestPointerLock()) { + enqueueEvent(eventNames().pointerlockchangeEvent, target); + } else { m_lockPending = true; m_element = target; - } else { - enqueueEvent(eventNames().webkitpointerlockerrorEvent, target); + if (!m_page.chrome().client().requestPointerLock()) { + clearElement(); + enqueueEvent(eventNames().pointerlockerrorEvent, target); + } } } void PointerLockController::requestPointerUnlock() { - return m_page->chrome().client().requestPointerUnlock(); + if (!m_element) + return; + + m_unlockPending = true; + m_page.chrome().client().requestPointerUnlock(); +} + +void PointerLockController::requestPointerUnlockAndForceCursorVisible() +{ + m_documentAllowedToRelockWithoutUserGesture = nullptr; + + if (!m_element) + return; + + m_unlockPending = true; + m_page.chrome().client().requestPointerUnlock(); + m_forceCursorVisibleUponUnlock = true; } -void PointerLockController::elementRemoved(Element* element) +void PointerLockController::elementRemoved(Element& element) { - if (m_element == element) { + if (m_element == &element) { m_documentOfRemovedElementWhileWaitingForUnlock = &m_element->document(); // Set element null immediately to block any future interaction with it // including mouse events received before the unlock completes. - clearElement(); requestPointerUnlock(); + clearElement(); } } -void PointerLockController::documentDetached(Document* document) +void PointerLockController::documentDetached(Document& document) { - if (m_element && &m_element->document() == document) { - clearElement(); + if (m_element && &m_element->document() == &document) { + m_documentOfRemovedElementWhileWaitingForUnlock = &m_element->document(); requestPointerUnlock(); + clearElement(); } } +bool PointerLockController::isLocked() const +{ + return m_element && !m_lockPending; +} + bool PointerLockController::lockPending() const { return m_lockPending; @@ -112,21 +140,32 @@ Element* PointerLockController::element() const void PointerLockController::didAcquirePointerLock() { - enqueueEvent(eventNames().webkitpointerlockchangeEvent, m_element.get()); + enqueueEvent(eventNames().pointerlockchangeEvent, m_element.get()); m_lockPending = false; + m_forceCursorVisibleUponUnlock = false; + m_documentAllowedToRelockWithoutUserGesture = &m_element->document(); } void PointerLockController::didNotAcquirePointerLock() { - enqueueEvent(eventNames().webkitpointerlockerrorEvent, m_element.get()); + enqueueEvent(eventNames().pointerlockerrorEvent, m_element.get()); clearElement(); + m_unlockPending = false; } void PointerLockController::didLosePointerLock() { - enqueueEvent(eventNames().webkitpointerlockchangeEvent, m_element ? &m_element->document() : m_documentOfRemovedElementWhileWaitingForUnlock.get()); + if (!m_unlockPending) + m_documentAllowedToRelockWithoutUserGesture = nullptr; + + enqueueEvent(eventNames().pointerlockchangeEvent, m_element ? &m_element->document() : m_documentOfRemovedElementWhileWaitingForUnlock.get()); clearElement(); - m_documentOfRemovedElementWhileWaitingForUnlock = 0; + m_unlockPending = false; + m_documentOfRemovedElementWhileWaitingForUnlock = nullptr; + if (m_forceCursorVisibleUponUnlock) { + m_forceCursorVisibleUponUnlock = false; + m_page.chrome().client().setCursorHiddenUntilMouseMoves(false); + } } void PointerLockController::dispatchLockedMouseEvent(const PlatformMouseEvent& event, const AtomicString& eventType) @@ -141,10 +180,18 @@ void PointerLockController::dispatchLockedMouseEvent(const PlatformMouseEvent& e m_element->dispatchMouseEvent(event, eventNames().clickEvent, event.clickCount()); } +void PointerLockController::dispatchLockedWheelEvent(const PlatformWheelEvent& event) +{ + if (!m_element || !m_element->document().frame()) + return; + + m_element->dispatchWheelEvent(event); +} + void PointerLockController::clearElement() { m_lockPending = false; - m_element = 0; + m_element = nullptr; } void PointerLockController::enqueueEvent(const AtomicString& type, Element* element) |