| OLD | NEW |
| 1 /* | 1 /* |
| 2 * Copyright (C) 2013 Google Inc. All rights reserved. | 2 * Copyright (C) 2013 Google Inc. All rights reserved. |
| 3 * | 3 * |
| 4 * Redistribution and use in source and binary forms, with or without | 4 * Redistribution and use in source and binary forms, with or without |
| 5 * modification, are permitted provided that the following conditions are | 5 * modification, are permitted provided that the following conditions are |
| 6 * met: | 6 * met: |
| 7 * | 7 * |
| 8 * * Redistributions of source code must retain the above copyright | 8 * * Redistributions of source code must retain the above copyright |
| 9 * notice, this list of conditions and the following disclaimer. | 9 * notice, this list of conditions and the following disclaimer. |
| 10 * * Redistributions in binary form must reproduce the above | 10 * * Redistributions in binary form must reproduce the above |
| (...skipping 19 matching lines...) Expand all Loading... |
| 30 | 30 |
| 31 #include "web/FullscreenController.h" | 31 #include "web/FullscreenController.h" |
| 32 | 32 |
| 33 #include "core/dom/Document.h" | 33 #include "core/dom/Document.h" |
| 34 #include "core/dom/Fullscreen.h" | 34 #include "core/dom/Fullscreen.h" |
| 35 #include "core/frame/FrameView.h" | 35 #include "core/frame/FrameView.h" |
| 36 #include "core/frame/LocalFrame.h" | 36 #include "core/frame/LocalFrame.h" |
| 37 #include "core/frame/PageScaleConstraintsSet.h" | 37 #include "core/frame/PageScaleConstraintsSet.h" |
| 38 #include "core/html/HTMLMediaElement.h" | 38 #include "core/html/HTMLMediaElement.h" |
| 39 #include "core/html/HTMLVideoElement.h" | 39 #include "core/html/HTMLVideoElement.h" |
| 40 #include "core/layout/LayoutFullScreen.h" | |
| 41 #include "platform/RuntimeEnabledFeatures.h" | |
| 42 #include "public/platform/WebLayerTreeView.h" | 40 #include "public/platform/WebLayerTreeView.h" |
| 43 #include "public/web/WebFrameClient.h" | 41 #include "public/web/WebFrameClient.h" |
| 44 #include "web/WebLocalFrameImpl.h" | 42 #include "web/WebLocalFrameImpl.h" |
| 45 #include "web/WebSettingsImpl.h" | 43 #include "web/WebSettingsImpl.h" |
| 46 #include "web/WebViewImpl.h" | 44 #include "web/WebViewImpl.h" |
| 47 | 45 |
| 48 namespace blink { | 46 namespace blink { |
| 49 | 47 |
| 50 FullscreenController* FullscreenController::create(WebViewImpl* webViewImpl) { | 48 FullscreenController* FullscreenController::create(WebViewImpl* webViewImpl) { |
| 51 return new FullscreenController(webViewImpl); | 49 return new FullscreenController(webViewImpl); |
| 52 } | 50 } |
| 53 | 51 |
| 54 FullscreenController::FullscreenController(WebViewImpl* webViewImpl) | 52 FullscreenController::FullscreenController(WebViewImpl* webViewImpl) |
| 55 : m_webViewImpl(webViewImpl), | 53 : m_webViewImpl(webViewImpl), |
| 56 m_haveEnteredFullscreen(false), | 54 m_haveEnteredFullscreen(false), |
| 57 m_exitFullscreenPageScaleFactor(0), | 55 m_exitFullscreenPageScaleFactor(0), |
| 58 m_needsScrollAndScaleRestore(false), | 56 m_needsScrollAndScaleRestore(false), |
| 59 m_isCancelingFullscreen(false) {} | 57 m_isCancelingFullscreen(false) {} |
| 60 | 58 |
| 61 void FullscreenController::didEnterFullscreen() { | 59 void FullscreenController::didEnterFullscreen() { |
| 62 if (!m_provisionalFullscreenElement) | 60 if (m_pendingFullscreenElements.isEmpty()) |
| 63 return; | |
| 64 | |
| 65 Element* element = m_provisionalFullscreenElement.release(); | |
| 66 Document& document = element->document(); | |
| 67 m_fullscreenFrame = document.frame(); | |
| 68 | |
| 69 if (!m_fullscreenFrame) | |
| 70 return; | 61 return; |
| 71 | 62 |
| 72 if (!m_haveEnteredFullscreen) { | 63 if (!m_haveEnteredFullscreen) { |
| 73 updatePageScaleConstraints(false); | 64 updatePageScaleConstraints(false); |
| 74 m_webViewImpl->setPageScaleFactor(1.0f); | 65 m_webViewImpl->setPageScaleFactor(1.0f); |
| 75 if (m_webViewImpl->mainFrame()->isWebLocalFrame()) | 66 if (m_webViewImpl->mainFrame()->isWebLocalFrame()) |
| 76 m_webViewImpl->mainFrame()->setScrollOffset(WebSize()); | 67 m_webViewImpl->mainFrame()->setScrollOffset(WebSize()); |
| 77 m_webViewImpl->setVisualViewportOffset(FloatPoint()); | 68 m_webViewImpl->setVisualViewportOffset(FloatPoint()); |
| 78 m_haveEnteredFullscreen = true; | 69 m_haveEnteredFullscreen = true; |
| 79 } | 70 } |
| 80 | 71 |
| 81 Fullscreen::from(document).didEnterFullscreenForElement(element); | 72 // TODO(foolip): Unprefixed requests |
| 82 DCHECK_EQ(Fullscreen::currentFullScreenElementFrom(document), element); | 73 HeapVector<Member<Element>> pendingFullscreenElements; |
| 74 pendingFullscreenElements.swap(m_pendingFullscreenElements); |
| 83 | 75 |
| 84 if (isHTMLVideoElement(element)) { | 76 for (Element* element : pendingFullscreenElements) { |
| 85 HTMLVideoElement* videoElement = toHTMLVideoElement(element); | 77 Fullscreen::didEnterFullscreenForElement(*element, |
| 86 if (videoElement->usesOverlayFullscreenVideo() && | 78 Fullscreen::PrefixedRequest); |
| 87 m_webViewImpl->layerTreeView()) | 79 |
| 88 m_webViewImpl->layerTreeView()->setHasTransparentBackground(true); | 80 // TODO(foolip): this and the exit stuff has to be synced with animation |
| 81 // frames tasks too |
| 82 if (isHTMLVideoElement(element)) { |
| 83 HTMLVideoElement* videoElement = toHTMLVideoElement(element); |
| 84 if (videoElement->usesOverlayFullscreenVideo() && |
| 85 m_webViewImpl->layerTreeView()) |
| 86 m_webViewImpl->layerTreeView()->setHasTransparentBackground(true); |
| 87 } |
| 89 } | 88 } |
| 90 } | 89 } |
| 91 | 90 |
| 92 void FullscreenController::didExitFullscreen() { | 91 void FullscreenController::didExitFullscreen() { |
| 93 if (!m_fullscreenFrame) | 92 if (!m_fullscreenFrame) |
| 94 return; | 93 return; |
| 95 | 94 |
| 96 if (m_haveEnteredFullscreen) | 95 if (m_haveEnteredFullscreen) |
| 97 updatePageScaleConstraints(true); | 96 updatePageScaleConstraints(true); |
| 98 | 97 |
| 99 if (Document* document = m_fullscreenFrame->document()) { | 98 if (Document* document = m_fullscreenFrame->document()) { |
| 100 if (Fullscreen* fullscreen = Fullscreen::fromIfExists(*document)) { | 99 if (Element* element = Fullscreen::fullscreenElement(*document)) { |
| 101 Element* element = fullscreen->currentFullScreenElement(); | 100 // When the client exits from full screen we have to call |
| 102 if (element) { | 101 // fullyExitFullscreen to notify the document. While doing that, suppress |
| 103 // When the client exits from full screen we have to call | 102 // notifications back to the client. |
| 104 // fullyExitFullscreen to notify the document. While doing that, | 103 m_isCancelingFullscreen = true; |
| 105 // suppress notifications back to the client. | 104 Fullscreen::fullyExitFullscreen(*document); |
| 106 m_isCancelingFullscreen = true; | 105 m_isCancelingFullscreen = false; |
| 107 Fullscreen::fullyExitFullscreen(*document); | |
| 108 m_isCancelingFullscreen = false; | |
| 109 | 106 |
| 110 // If the video used overlay fullscreen mode, the background was made | 107 // If the video used overlay fullscreen mode, the background was made |
| 111 // transparent. Restore the transparency. | 108 // transparent. Restore the transparency. |
| 112 if (isHTMLVideoElement(element) && m_webViewImpl->layerTreeView()) | 109 if (isHTMLVideoElement(element) && m_webViewImpl->layerTreeView()) { |
| 113 m_webViewImpl->layerTreeView()->setHasTransparentBackground( | 110 m_webViewImpl->layerTreeView()->setHasTransparentBackground( |
| 114 m_webViewImpl->isTransparent()); | 111 m_webViewImpl->isTransparent()); |
| 112 } |
| 115 | 113 |
| 116 // We need to wait until style and layout are updated in order | 114 // We need to wait until style and layout are updated in order |
| 117 // to propertly restore scroll offsets since content may not be | 115 // to propertly restore scroll offsets since content may not be |
| 118 // overflowing in the same way until they do. | 116 // overflowing in the same way until they do. |
| 119 if (m_haveEnteredFullscreen) | 117 if (m_haveEnteredFullscreen) |
| 120 m_needsScrollAndScaleRestore = true; | 118 m_needsScrollAndScaleRestore = true; |
| 121 | 119 |
| 122 fullscreen->didExitFullscreen(); | 120 Fullscreen::didExitFullscreen(*document); |
| 123 } | |
| 124 } | 121 } |
| 125 } | 122 } |
| 126 | 123 |
| 127 m_haveEnteredFullscreen = false; | 124 m_haveEnteredFullscreen = false; |
| 128 m_fullscreenFrame.clear(); | 125 m_fullscreenFrame.clear(); |
| 129 } | 126 } |
| 130 | 127 |
| 131 void FullscreenController::enterFullscreenForElement(Element* element) { | 128 void FullscreenController::enterFullscreenForElement(Element* element) { |
| 132 // We are already transitioning to fullscreen for a different element. | 129 m_pendingFullscreenElements.append(element); |
| 133 if (m_provisionalFullscreenElement) { | |
| 134 m_provisionalFullscreenElement = element; | |
| 135 return; | |
| 136 } | |
| 137 | 130 |
| 138 // We are already in fullscreen mode. | 131 // We are already in fullscreen mode. |
| 139 if (m_fullscreenFrame) { | 132 if (m_fullscreenFrame) { |
| 140 m_provisionalFullscreenElement = element; | |
| 141 didEnterFullscreen(); | 133 didEnterFullscreen(); |
| 142 return; | 134 return; |
| 143 } | 135 } |
| 144 | 136 |
| 145 // We need to store these values here rather than didEnterFullscreen since | 137 // We need to store these values here rather than didEnterFullscreen since |
| 146 // by the time the latter is called, a Resize has already occured, clamping | 138 // by the time the latter is called, a Resize has already occured, clamping |
| 147 // the scroll offset. Don't save values if we're still waiting to restore | 139 // the scroll offset. Don't save values if we're still waiting to restore |
| 148 // a previous set. This can happen if we exit and quickly reenter fullscreen | 140 // a previous set. This can happen if we exit and quickly reenter fullscreen |
| 149 // without performing a layout. | 141 // without performing a layout. |
| 150 if (!m_haveEnteredFullscreen && !m_needsScrollAndScaleRestore) { | 142 if (!m_haveEnteredFullscreen && !m_needsScrollAndScaleRestore) { |
| 151 m_exitFullscreenPageScaleFactor = m_webViewImpl->pageScaleFactor(); | 143 m_exitFullscreenPageScaleFactor = m_webViewImpl->pageScaleFactor(); |
| 152 m_exitFullscreenScrollOffset = | 144 m_exitFullscreenScrollOffset = |
| 153 m_webViewImpl->mainFrame()->isWebLocalFrame() | 145 m_webViewImpl->mainFrame()->isWebLocalFrame() |
| 154 ? m_webViewImpl->mainFrame()->scrollOffset() | 146 ? m_webViewImpl->mainFrame()->scrollOffset() |
| 155 : WebSize(); | 147 : WebSize(); |
| 156 m_exitFullscreenVisualViewportOffset = | 148 m_exitFullscreenVisualViewportOffset = |
| 157 m_webViewImpl->visualViewportOffset(); | 149 m_webViewImpl->visualViewportOffset(); |
| 158 } | 150 } |
| 159 | 151 |
| 160 // We need to transition to fullscreen mode. | 152 // We need to transition to fullscreen mode. |
| 161 WebLocalFrameImpl* frame = | 153 WebLocalFrameImpl* frame = |
| 162 WebLocalFrameImpl::fromFrame(element->document().frame()); | 154 WebLocalFrameImpl::fromFrame(element->document().frame()); |
| 163 if (frame && frame->client()) { | 155 if (frame && frame->client()) { |
| 164 if (!Fullscreen::from(element->document()).forCrossProcessDescendant()) | 156 frame->client()->enterFullscreen(); |
| 165 frame->client()->enterFullscreen(); | 157 } else { |
| 166 m_provisionalFullscreenElement = element; | 158 // TODO(foolip): now what? |
| 159 DCHECK(0); |
| 167 } | 160 } |
| 168 } | 161 } |
| 169 | 162 |
| 170 void FullscreenController::exitFullscreenForElement(Element* element) { | 163 void FullscreenController::exitFullscreenForElement(Element* element) { |
| 171 DCHECK(element); | 164 DCHECK(element); |
| 172 | 165 |
| 166 // TODO(dsinclair): This should not be needed because we addToTopLayer |
| 167 // in Fullscreen::popFullscreenElementStack but, the WebView code doesn't |
| 168 // call Fullscreen::requestFullscreen() and, instead, just enters and |
| 169 // exists itself. This should be unified so there is one way to go |
| 170 // fullscreen. crbug.com/538158 |
| 171 element->document().removeFromTopLayer(element); |
| 172 |
| 173 // The client is exiting full screen, so don't send a notification. | 173 // The client is exiting full screen, so don't send a notification. |
| 174 if (m_isCancelingFullscreen) | 174 if (m_isCancelingFullscreen) |
| 175 return; | 175 return; |
| 176 | 176 |
| 177 WebLocalFrameImpl* frame = | 177 WebLocalFrameImpl* frame = |
| 178 WebLocalFrameImpl::fromFrame(element->document().frame()); | 178 WebLocalFrameImpl::fromFrame(element->document().frame()); |
| 179 if (frame && frame->client()) | 179 if (frame && frame->client()) |
| 180 frame->client()->exitFullscreen(); | 180 frame->client()->exitFullscreen(); |
| 181 } | 181 } |
| 182 | 182 |
| 183 void FullscreenController::updateSize() { | 183 void FullscreenController::updateSize() { |
| 184 if (!isFullscreen()) | 184 if (!isFullscreen()) |
| 185 return; | 185 return; |
| 186 | 186 |
| 187 updatePageScaleConstraints(false); | 187 updatePageScaleConstraints(false); |
| 188 | 188 |
| 189 LayoutFullScreen* layoutObject = | 189 Document* document = m_fullscreenFrame->document(); |
| 190 Fullscreen::from(*m_fullscreenFrame->document()).fullScreenLayoutObject(); | 190 if (Element* fullscreenElement = Fullscreen::fullscreenElement(*document)) |
| 191 if (layoutObject) | 191 Fullscreen::didUpdateSize(*fullscreenElement); |
| 192 layoutObject->updateStyle(); | |
| 193 } | 192 } |
| 194 | 193 |
| 195 void FullscreenController::didUpdateLayout() { | 194 void FullscreenController::didUpdateLayout() { |
| 196 if (!m_needsScrollAndScaleRestore) | 195 if (!m_needsScrollAndScaleRestore) |
| 197 return; | 196 return; |
| 198 | 197 |
| 199 // If we re-entered fullscreen before we could restore the scroll and scale | 198 // If we re-entered fullscreen before we could restore the scroll and scale |
| 200 // don't try restoring them yet. | 199 // don't try restoring them yet. |
| 201 if (isFullscreen()) | 200 if (isFullscreen()) |
| 202 return; | 201 return; |
| (...skipping 25 matching lines...) Expand all Loading... |
| 228 // contents size. | 227 // contents size. |
| 229 m_webViewImpl->didChangeContentsSize(); | 228 m_webViewImpl->didChangeContentsSize(); |
| 230 if (m_webViewImpl->mainFrameImpl() && | 229 if (m_webViewImpl->mainFrameImpl() && |
| 231 m_webViewImpl->mainFrameImpl()->frameView()) | 230 m_webViewImpl->mainFrameImpl()->frameView()) |
| 232 m_webViewImpl->mainFrameImpl()->frameView()->setNeedsLayout(); | 231 m_webViewImpl->mainFrameImpl()->frameView()->setNeedsLayout(); |
| 233 | 232 |
| 234 m_webViewImpl->updateMainFrameLayoutSize(); | 233 m_webViewImpl->updateMainFrameLayoutSize(); |
| 235 } | 234 } |
| 236 | 235 |
| 237 DEFINE_TRACE(FullscreenController) { | 236 DEFINE_TRACE(FullscreenController) { |
| 238 visitor->trace(m_provisionalFullscreenElement); | 237 visitor->trace(m_pendingFullscreenElements); |
| 239 visitor->trace(m_fullscreenFrame); | 238 visitor->trace(m_fullscreenFrame); |
| 240 } | 239 } |
| 241 | 240 |
| 242 } // namespace blink | 241 } // namespace blink |
| OLD | NEW |