namespace WebCore {
-#if USE(ACCELERATED_COMPOSITING)
-class LayerAndroid;
-#endif
-
class FrameView;
class Widget;
};
static String* globalLocalizedName(rawResId resId);
-#if USE(ACCELERATED_COMPOSITING)
- // Those methods are used by the layers system
- static void setUIRootLayer(const FrameView* view, const LayerAndroid* layer);
- static void immediateRepaint(const FrameView* view);
-#endif // USE(ACCELERATED_COMPOSITING)
-
// Whether the WebView is paused.
// ANDROID
// TODO: Upstream to webkit.org. See https://bugs.webkit.org/show_bug.cgi?id=34082
--- /dev/null
+/*
+ * Copyright 2010, The Android Open Source Project
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * * Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * * 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 THE COPYRIGHT HOLDERS ``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 THE COPYRIGHT OWNER 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.
+ */
+
+#ifndef BASELAYERANDROID_H_
+#define BASELAYERANDROID_H_
+
+#include "PictureSet.h"
+#include "SkLayer.h"
+
+namespace WebCore {
+
+class BaseLayerAndroid : public SkLayer {
+
+public:
+ BaseLayerAndroid() { }
+ virtual ~BaseLayerAndroid() { }
+
+ void setContent(const android::PictureSet& src) { m_content.set(src); }
+ android::PictureSet* content() { return &m_content; }
+
+private:
+ android::PictureSet m_content;
+};
+
+} // namespace WebCore
+
+#endif /* BASELAYERANDROID_H_ */
setNeedsDisplayInRect(rect);
}
-void GraphicsLayerAndroid::setFrame(Frame* f)
-{
- m_frame = f;
-}
-
-void GraphicsLayerAndroid::sendImmediateRepaint()
-{
- LOG("(%x) sendImmediateRepaint()", this);
- GraphicsLayerAndroid* rootGraphicsLayer = this;
-
- while (rootGraphicsLayer->parent())
- rootGraphicsLayer = static_cast<GraphicsLayerAndroid*>(rootGraphicsLayer->parent());
-
- if (rootGraphicsLayer->m_frame
- && rootGraphicsLayer->m_frame->view()) {
- LayerAndroid* rootLayer = new LayerAndroid(true);
- LayerAndroid* copyLayer = new LayerAndroid(*m_contentLayer);
- rootLayer->addChild(copyLayer);
- copyLayer->unref();
- TLOG("(%x) sendImmediateRepaint, copy the layer, (%.2f,%.2f => %.2f,%.2f)",
- this, m_contentLayer->getSize().width(), m_contentLayer->getSize().height(),
- copyLayer->getSize().width(), copyLayer->getSize().height());
- PlatformBridge::setUIRootLayer(m_frame->view(), rootLayer);
- PlatformBridge::immediateRepaint(m_frame->view());
- }
-}
-
bool GraphicsLayerAndroid::repaint()
{
LOG("(%x) repaint(), gPaused(%d) m_needsRepaint(%d) m_haveContents(%d) ",
virtual void setZPosition(float);
- void askForSync();
- void syncPositionState();
- void needsSyncChildren();
- void syncChildren();
- void syncMask();
virtual void syncCompositingState();
- void setFrame(Frame*);
void notifyClientAnimationStarted();
- void sendImmediateRepaint();
LayerAndroid* contentLayer() { return m_contentLayer; }
static int instancesCount();
private:
+ void askForSync();
+ void syncPositionState();
+ void needsSyncChildren();
+ void syncChildren();
+ void syncMask();
+
void updateFixedPosition();
// with SkPicture, we always repaint the entire layer's content.
FloatPoint m_currentPosition;
- RefPtr<Frame> m_frame;
-
Vector<FloatRect> m_invalidatedRects;
LayerAndroid* m_contentLayer;
#if USE(ACCELERATED_COMPOSITING)
-void ChromeClientAndroid::layersSync()
+WebCore::GraphicsLayer* ChromeClientAndroid::layersSync()
{
- if (!m_rootGraphicsLayer)
- return;
-
- if (!m_needsLayerSync)
- return;
-
- m_needsLayerSync = false;
-
- if (m_webFrame) {
- FrameView* frameView = m_webFrame->page()->mainFrame()->view();
- if (frameView && frameView->syncCompositingStateRecursive()) {
- GraphicsLayerAndroid* androidGraphicsLayer =
- static_cast<GraphicsLayerAndroid*>(m_rootGraphicsLayer);
- if (androidGraphicsLayer) {
- androidGraphicsLayer->sendImmediateRepaint();
- androidGraphicsLayer->notifyClientAnimationStarted();
- }
- }
+ if (m_rootGraphicsLayer && m_needsLayerSync && m_webFrame) {
+ if (FrameView* frameView = m_webFrame->page()->mainFrame()->view())
+ frameView->syncCompositingStateRecursive();
}
+ m_needsLayerSync = false;
+ return m_rootGraphicsLayer;
}
void ChromeClientAndroid::scheduleCompositingLayerSync()
// This should not be needed
}
-void ChromeClientAndroid::attachRootGraphicsLayer(WebCore::Frame* frame, WebCore::GraphicsLayer* layer)
+void ChromeClientAndroid::attachRootGraphicsLayer(WebCore::Frame*, WebCore::GraphicsLayer* layer)
{
+ // frame is not used in Android as we should only get root graphics layer for the main frame
m_rootGraphicsLayer = layer;
- if (!layer) {
- WebViewCore::getWebViewCore(frame->view())->setUIRootLayer(0);
+ if (!layer)
return;
- }
- WebCore::GraphicsLayerAndroid* androidGraphicsLayer = static_cast<GraphicsLayerAndroid*>(layer);
- androidGraphicsLayer->setFrame(frame);
scheduleCompositingLayerSync();
}
virtual void attachRootGraphicsLayer(WebCore::Frame*, WebCore::GraphicsLayer* g);
virtual void setNeedsOneShotDrawingSynchronization();
virtual void scheduleCompositingLayerSync();
- void layersSync();
+ WebCore::GraphicsLayer* layersSync();
#endif
#if ENABLE(ANDROID_INSTALLABLE_WEB_APPS)
#include <wtf/android/AndroidThreading.h>
#include <wtf/MainThread.h>
-#if USE(ACCELERATED_COMPOSITING)
-#include "LayerAndroid.h"
-#endif
-
using namespace android;
namespace WebCore {
-#if USE(ACCELERATED_COMPOSITING)
-
-void PlatformBridge::setUIRootLayer(const WebCore::FrameView* view, const LayerAndroid* layer)
-{
- android::WebViewCore* core = android::WebViewCore::getWebViewCore(view);
- core->setUIRootLayer(layer);
-}
-
-void PlatformBridge::immediateRepaint(const WebCore::FrameView* view)
-{
- android::WebViewCore* core = android::WebViewCore::getWebViewCore(view);
- core->immediateRepaint();
-}
-
-#endif // USE(ACCELERATED_COMPOSITING)
-
WTF::Vector<String> PlatformBridge::getSupportedKeyStrengthList()
{
KeyGeneratorClient* client = JavaSharedClient::GetKeyGeneratorClient();
#include "WebViewCore.h"
#include "AtomicString.h"
+#include "BaseLayerAndroid.h"
#include "CachedNode.h"
#include "CachedRoot.h"
#include "Chrome.h"
jmethodID m_updateViewport;
jmethodID m_sendNotifyProgressFinished;
jmethodID m_sendViewInvalidate;
- jmethodID m_sendImmediateRepaint;
- jmethodID m_setRootLayer;
jmethodID m_updateTextfield;
jmethodID m_updateTextSelection;
jmethodID m_clearTextEntry;
Mutex WebViewCore::gFrameCacheMutex;
Mutex WebViewCore::gButtonMutex;
Mutex WebViewCore::gCursorBoundsMutex;
-Mutex WebViewCore::m_contentMutex;
WebViewCore::WebViewCore(JNIEnv* env, jobject javaWebViewCore, WebCore::Frame* mainframe)
: m_pluginInvalTimer(this, &WebViewCore::pluginInvalTimerFired)
m_javaGlue->m_updateViewport = GetJMethod(env, clazz, "updateViewport", "()V");
m_javaGlue->m_sendNotifyProgressFinished = GetJMethod(env, clazz, "sendNotifyProgressFinished", "()V");
m_javaGlue->m_sendViewInvalidate = GetJMethod(env, clazz, "sendViewInvalidate", "(IIII)V");
- m_javaGlue->m_sendImmediateRepaint = GetJMethod(env, clazz, "sendImmediateRepaint", "()V");
- m_javaGlue->m_setRootLayer = GetJMethod(env, clazz, "setRootLayer", "(I)V");
m_javaGlue->m_updateTextfield = GetJMethod(env, clazz, "updateTextfield", "(IZLjava/lang/String;I)V");
m_javaGlue->m_updateTextSelection = GetJMethod(env, clazz, "updateTextSelection", "(IIII)V");
m_javaGlue->m_clearTextEntry = GetJMethod(env, clazz, "clearTextEntry", "()V");
void WebViewCore::clearContent()
{
DBG_SET_LOG("");
- m_contentMutex.lock();
m_content.clear();
- m_contentMutex.unlock();
m_addInval.setEmpty();
m_rebuildInval.setEmpty();
}
-void WebViewCore::copyContentToPicture(SkPicture* picture)
-{
- DBG_SET_LOG("start");
- m_contentMutex.lock();
- PictureSet copyContent = PictureSet(m_content);
- m_contentMutex.unlock();
-
- int w = copyContent.width();
- int h = copyContent.height();
- copyContent.draw(picture->beginRecording(w, h, PICT_RECORD_FLAGS));
- picture->endRecording();
- DBG_SET_LOG("end");
-}
-
-bool WebViewCore::drawContent(SkCanvas* canvas, SkColor color)
-{
-#ifdef ANDROID_INSTRUMENT
- TimeCounterAuto counter(TimeCounter::WebViewUIDrawTimeCounter);
-#endif
- DBG_SET_LOG("start");
- m_contentMutex.lock();
- PictureSet copyContent = PictureSet(m_content);
- m_contentMutex.unlock();
- int sc = canvas->save(SkCanvas::kClip_SaveFlag);
- SkRect clip;
- clip.set(0, 0, copyContent.width(), copyContent.height());
- canvas->clipRect(clip, SkRegion::kDifference_Op);
- canvas->drawColor(color);
- canvas->restoreToCount(sc);
- bool tookTooLong = copyContent.draw(canvas);
- m_contentMutex.lock();
- m_content.setDrawTimes(copyContent);
- m_contentMutex.unlock();
- DBG_SET_LOG("end");
- return tookTooLong;
-}
-
bool WebViewCore::focusBoundsChanged()
{
bool result = m_focusBoundsChanged;
return result;
}
-bool WebViewCore::pictureReady()
-{
- bool done;
- m_contentMutex.lock();
- PictureSet copyContent = PictureSet(m_content);
- done = m_progressDone;
- m_contentMutex.unlock();
- DBG_NAV_LOGD("done=%s empty=%s", done ? "true" : "false",
- copyContent.isEmpty() ? "true" : "false");
- return done || !copyContent.isEmpty();
-}
-
SkPicture* WebViewCore::rebuildPicture(const SkIRect& inval)
{
WebCore::FrameView* view = m_mainFrame->view();
pictureSet->validate(__FUNCTION__);
}
-bool WebViewCore::recordContent(SkRegion* region, SkIPoint* point)
+BaseLayerAndroid* WebViewCore::recordContent(SkRegion* region, SkIPoint* point)
{
DBG_SET_LOG("start");
float progress = (float) m_mainFrame->page()->progress()->estimatedProgress();
- m_contentMutex.lock();
- PictureSet contentCopy(m_content);
m_progressDone = progress <= 0.0f || progress >= 1.0f;
- m_contentMutex.unlock();
- recordPictureSet(&contentCopy);
- if (!m_progressDone && contentCopy.isEmpty()) {
+ recordPictureSet(&m_content);
+ if (!m_progressDone && m_content.isEmpty()) {
DBG_SET_LOGD("empty (progress=%g)", progress);
- return false;
+ return 0;
}
region->set(m_addInval);
m_addInval.setEmpty();
region->op(m_rebuildInval, SkRegion::kUnion_Op);
m_rebuildInval.setEmpty();
- m_contentMutex.lock();
- contentCopy.setDrawTimes(m_content);
- m_content.set(contentCopy);
point->fX = m_content.width();
point->fY = m_content.height();
- m_contentMutex.unlock();
DBG_SET_LOGD("region={%d,%d,r=%d,b=%d}", region->getBounds().fLeft,
region->getBounds().fTop, region->getBounds().fRight,
region->getBounds().fBottom);
DBG_SET_LOG("end");
+ BaseLayerAndroid* base = new BaseLayerAndroid();
+ base->setContent(m_content);
+
#if USE(ACCELERATED_COMPOSITING)
// We update the layers
ChromeClientAndroid* chromeC = static_cast<ChromeClientAndroid*>(m_mainFrame->page()->chrome()->client());
- chromeC->layersSync();
+ GraphicsLayerAndroid* root = static_cast<GraphicsLayerAndroid*>(chromeC->layersSync());
+ if (root) {
+ root->notifyClientAnimationStarted();
+ LayerAndroid* copyLayer = new LayerAndroid(*root->contentLayer());
+ base->addChild(copyLayer);
+ copyLayer->unref();
+ }
#endif
- return true;
+
+ return base;
}
-void WebViewCore::splitContent()
+void WebViewCore::splitContent(PictureSet* content)
{
bool layoutSuceeded = layoutIfNeededRecursive(m_mainFrame);
LOG_ASSERT(layoutSuceeded, "Can never be called recursively");
- PictureSet tempPictureSet;
- m_contentMutex.lock();
- m_content.split(&tempPictureSet);
- m_contentMutex.unlock();
- rebuildPictureSet(&tempPictureSet);
- m_contentMutex.lock();
- m_content.set(tempPictureSet);
- m_contentMutex.unlock();
+ content->split(&m_content);
+ rebuildPictureSet(&m_content);
+ content->set(m_content);
}
void WebViewCore::scrollTo(int x, int y, bool animate)
checkException(env);
}
-#if USE(ACCELERATED_COMPOSITING)
-
-void WebViewCore::immediateRepaint()
-{
- LOG_ASSERT(m_javaGlue->m_obj, "A Java widget was not associated with this view bridge!");
- JNIEnv* env = JSC::Bindings::getJNIEnv();
- env->CallVoidMethod(m_javaGlue->object(env).get(),
- m_javaGlue->m_sendImmediateRepaint);
- checkException(env);
-}
-
-void WebViewCore::setUIRootLayer(const LayerAndroid* layer)
-{
- JNIEnv* env = JSC::Bindings::getJNIEnv();
- env->CallVoidMethod(m_javaGlue->object(env).get(),
- m_javaGlue->m_setRootLayer,
- reinterpret_cast<jint>(layer));
- checkException(env);
-}
-
-#endif // USE(ACCELERATED_COMPOSITING)
-
void WebViewCore::contentDraw()
{
JNIEnv* env = JSC::Bindings::getJNIEnv();
m_groupForVisitedLinks->addVisitedLink(string, length);
}
-static bool RecordContent(JNIEnv *env, jobject obj, jobject region, jobject pt)
+static jint RecordContent(JNIEnv *env, jobject obj, jobject region, jobject pt)
{
#ifdef ANDROID_INSTRUMENT
TimeCounterAuto counter(TimeCounter::WebViewCoreTimeCounter);
WebViewCore* viewImpl = GET_NATIVE_VIEW(env, obj);
SkRegion* nativeRegion = GraphicsJNI::getNativeRegion(env, region);
SkIPoint nativePt;
- bool result = viewImpl->recordContent(nativeRegion, &nativePt);
+ BaseLayerAndroid* result = viewImpl->recordContent(nativeRegion, &nativePt);
GraphicsJNI::ipoint_to_jpoint(nativePt, env, pt);
- return result;
+ return reinterpret_cast<jint>(result);
}
-static void SplitContent(JNIEnv *env, jobject obj)
+static void SplitContent(JNIEnv *env, jobject obj, jint content)
{
#ifdef ANDROID_INSTRUMENT
TimeCounterAuto counter(TimeCounter::WebViewCoreTimeCounter);
#endif
WebViewCore* viewImpl = GET_NATIVE_VIEW(env, obj);
- viewImpl->splitContent();
+ viewImpl->splitContent(reinterpret_cast<PictureSet*>(content));
}
static void SendListBoxChoice(JNIEnv* env, jobject obj, jint choice)
WebCore::SecurityOrigin::registerURLSchemeAsLocal(to_string(env, scheme));
}
-static void ClearContent(JNIEnv *env, jobject obj)
-{
-#ifdef ANDROID_INSTRUMENT
- TimeCounterAuto counter(TimeCounter::WebViewCoreTimeCounter);
-#endif
- WebViewCore* viewImpl = GET_NATIVE_VIEW(env, obj);
- viewImpl->clearContent();
-}
-
-static void CopyContentToPicture(JNIEnv *env, jobject obj, jobject pict)
-{
-#ifdef ANDROID_INSTRUMENT
- TimeCounterAuto counter(TimeCounter::WebViewCoreTimeCounter);
-#endif
- WebViewCore* viewImpl = GET_NATIVE_VIEW(env, obj);
- if (!viewImpl)
- return;
- SkPicture* picture = GraphicsJNI::getNativePicture(env, pict);
- viewImpl->copyContentToPicture(picture);
-}
-
-static bool DrawContent(JNIEnv *env, jobject obj, jobject canv, jint color)
-{
- // Note: this is called from UI thread, don't count it for WebViewCoreTimeCounter
- WebViewCore* viewImpl = GET_NATIVE_VIEW(env, obj);
- SkCanvas* canvas = GraphicsJNI::getNativeCanvas(env, canv);
- return viewImpl->drawContent(canvas, color);
-}
-
static bool FocusBoundsChanged(JNIEnv* env, jobject obj)
{
return GET_NATIVE_VIEW(env, obj)->focusBoundsChanged();
}
-static bool PictureReady(JNIEnv* env, jobject obj)
-{
- return GET_NATIVE_VIEW(env, obj)->pictureReady();
-}
-
static void Pause(JNIEnv* env, jobject obj)
{
// This is called for the foreground tab when the browser is put to the
* JNI registration.
*/
static JNINativeMethod gJavaWebViewCoreMethods[] = {
- { "nativeClearContent", "()V",
- (void*) ClearContent },
- { "nativeCopyContentToPicture", "(Landroid/graphics/Picture;)V",
- (void*) CopyContentToPicture },
- { "nativeDrawContent", "(Landroid/graphics/Canvas;I)Z",
- (void*) DrawContent } ,
{ "nativeFocusBoundsChanged", "()Z",
(void*) FocusBoundsChanged } ,
{ "nativeKey", "(IIIZZZZ)Z",
(void*) Key },
{ "nativeClick", "(II)V",
(void*) Click },
- { "nativePictureReady", "()Z",
- (void*) PictureReady } ,
{ "nativeSendListBoxChoices", "([ZI)V",
(void*) SendListBoxChoices },
{ "nativeSendListBoxChoice", "(I)V",
(void*) UpdateFrameCache },
{ "nativeGetContentMinPrefWidth", "()I",
(void*) GetContentMinPrefWidth },
- { "nativeRecordContent", "(Landroid/graphics/Region;Landroid/graphics/Point;)Z",
+ { "nativeRecordContent", "(Landroid/graphics/Region;Landroid/graphics/Point;)I",
(void*) RecordContent },
{ "setViewportSettingsFromNative", "()V",
(void*) SetViewportSettingsFromNative },
- { "nativeSplitContent", "()V",
+ { "nativeSplitContent", "(I)V",
(void*) SplitContent },
{ "nativeSetBackgroundColor", "(I)V",
(void*) SetBackgroundColor },
#if USE(ACCELERATED_COMPOSITING)
namespace WebCore {
class GraphicsLayerAndroid;
- class LayerAndroid;
}
#endif
+namespace WebCore {
+ class BaseLayerAndroid;
+}
+
struct PluginWidgetAndroid;
class SkPicture;
class SkIRect;
#if USE(ACCELERATED_COMPOSITING)
GraphicsLayerAndroid* graphicsRootLayer() const;
- void immediateRepaint();
- void setUIRootLayer(const LayerAndroid* layer);
#endif
/** Invalidate the view/screen, NOT the content/DOM, but expressed in
// reset the picture set to empty
void clearContent();
- // flatten the picture set to a picture
- void copyContentToPicture(SkPicture* );
-
- // draw the picture set with the specified background color
- bool drawContent(SkCanvas* , SkColor );
bool focusBoundsChanged();
- bool pictureReady();
// record the inval area, and the picture size
- bool recordContent(SkRegion* , SkIPoint* );
+ BaseLayerAndroid* recordContent(SkRegion* , SkIPoint* );
int textWrapWidth() const { return m_textWrapWidth; }
float scale() const { return m_scale; }
float textWrapScale() const { return m_screenWidth * m_scale / m_textWrapWidth; }
void updateFrameCacheIfLoading();
// utility to split slow parts of the picture set
- void splitContent();
+ void splitContent(PictureSet*);
void notifyWebAppCanBeInstalled();
WebCore::IntRect m_lastFocusedBounds;
int m_lastFocusedSelStart;
int m_lastFocusedSelEnd;
- static Mutex m_contentMutex; // protects ui/core thread pictureset access
- PictureSet m_content; // the set of pictures to draw (accessed by UI too)
+ PictureSet m_content; // the set of pictures to draw
SkRegion m_addInval; // the accumulated inval region (not yet drawn)
SkRegion m_rebuildInval; // the accumulated region for rebuilt pictures
// Used in passToJS to avoid updating the UI text field until after the
#include "AndroidAnimation.h"
#include "AndroidLog.h"
#include "AtomicString.h"
+#include "BaseLayerAndroid.h"
#include "CachedFrame.h"
#include "CachedNode.h"
#include "CachedRoot.h"
m_lastDx = 0;
m_lastDxTime = 0;
m_ringAnimationEnd = 0;
- m_rootLayer = 0;
+ m_baseLayer = 0;
}
~WebView()
}
delete m_frameCacheUI;
delete m_navPictureUI;
- delete m_rootLayer;
+ delete m_baseLayer;
}
WebViewCore* getWebViewCore() const {
SkRect visible;
calcOurContentVisibleRect(&visible);
#if USE(ACCELERATED_COMPOSITING)
- if (m_rootLayer) {
- m_rootLayer->updateFixedLayersPositions(visible);
- m_rootLayer->updatePositions();
- visible = m_rootLayer->subtractLayers(visible);
+ LayerAndroid* root = compositeRoot();
+ if (root) {
+ root->updateFixedLayersPositions(visible);
+ root->updatePositions();
+ visible = root->subtractLayers(visible);
}
#endif
int dx = 0;
}
}
-void drawExtras(SkCanvas* canvas, int extras)
+PictureSet* draw(SkCanvas* canvas, SkColor bgColor, int extras, bool split)
{
+ PictureSet* ret = 0;
+ if (!m_baseLayer) {
+ canvas->drawColor(bgColor);
+ return ret;
+ }
+
+ // draw the content of the base layer first
+ PictureSet* content = m_baseLayer->content();
+ int sc = canvas->save(SkCanvas::kClip_SaveFlag);
+ canvas->clipRect(SkRect::MakeLTRB(0, 0, content->width(),
+ content->height()), SkRegion::kDifference_Op);
+ canvas->drawColor(bgColor);
+ canvas->restoreToCount(sc);
+ if (content->draw(canvas))
+ ret = split ? new PictureSet(*content) : 0;
+
CachedRoot* root = getFrameCache(AllowNewer);
if (!root) {
DBG_NAV_LOG("!root");
if (extras == DrawExtrasCursorRing)
resetCursorRing();
- return;
+ return ret;
}
LayerAndroid mainPicture(m_navPictureUI);
DrawExtra* extra = 0;
if (extra)
extra->draw(canvas, &mainPicture);
#if USE(ACCELERATED_COMPOSITING)
- if (!m_rootLayer)
- return;
- m_rootLayer->setExtra(extra);
+ LayerAndroid* compositeLayer = compositeRoot();
+ if (!compositeLayer)
+ return ret;
+ compositeLayer->setExtra(extra);
SkRect visible;
calcOurContentVisibleRect(&visible);
// call this to be sure we've adjusted for any scrolling or animations
// before we actually draw
- m_rootLayer->updateFixedLayersPositions(visible);
- m_rootLayer->updatePositions();
- // We have to set the canvas' matrix on the root layer
+ compositeLayer->updateFixedLayersPositions(visible);
+ compositeLayer->updatePositions();
+ // We have to set the canvas' matrix on the base layer
// (to have fixed layers work as intended)
SkAutoCanvasRestore restore(canvas, true);
- m_rootLayer->setMatrix(canvas->getTotalMatrix());
+ m_baseLayer->setMatrix(canvas->getTotalMatrix());
canvas->resetMatrix();
- m_rootLayer->draw(canvas);
+ m_baseLayer->draw(canvas);
#endif
+ return ret;
}
m_viewImpl->m_navPictureKit = 0;
m_viewImpl->gFrameCacheMutex.unlock();
if (m_frameCacheUI)
- m_frameCacheUI->setRootLayer(m_rootLayer);
+ m_frameCacheUI->setRootLayer(compositeRoot());
#if USE(ACCELERATED_COMPOSITING)
if (layerId >= 0) {
SkRect visible;
return m_viewImpl->m_moveGeneration;
}
-LayerAndroid* rootLayer() const
+LayerAndroid* compositeRoot() const
{
- return m_rootLayer;
+ LOG_ASSERT(!m_baseLayer || m_baseLayer->countChildren() == 1,
+ "base layer can't have more than one child %s", __FUNCTION__);
+ if (m_baseLayer && m_baseLayer->countChildren() == 1)
+ return static_cast<LayerAndroid*>(m_baseLayer->getChild(0));
+ else
+ return 0;
}
-void setRootLayer(LayerAndroid* layer)
+void setBaseLayer(BaseLayerAndroid* layer)
{
- delete m_rootLayer;
- m_rootLayer = layer;
+ delete m_baseLayer;
+ m_baseLayer = layer;
CachedRoot* root = getFrameCache(DontAllowNewer);
if (!root)
return;
root->resetLayers();
- root->setRootLayer(m_rootLayer);
+ root->setRootLayer(compositeRoot());
+}
+
+void replaceBaseContent(PictureSet* set)
+{
+ if (!m_baseLayer)
+ return;
+ m_baseLayer->setContent(*set);
+ delete set;
+}
+
+void copyBaseContentToPicture(SkPicture* picture)
+{
+ if (!m_baseLayer)
+ return;
+ PictureSet* content = m_baseLayer->content();
+ content->draw(picture->beginRecording(content->width(), content->height(),
+ SkPicture::kUsePathBoundsForClip_RecordingFlag));
+ picture->endRecording();
+}
+
+bool hasContent() {
+ if (!m_baseLayer)
+ return false;
+ return !m_baseLayer->content()->isEmpty();
}
private: // local state for WebView
SelectText m_selectText;
FindOnPage m_findOnPage;
CursorRing m_ring;
- LayerAndroid* m_rootLayer;
+ BaseLayerAndroid* m_baseLayer;
}; // end of WebView class
/*
#endif
}
-static void nativeDrawExtras(JNIEnv *env, jobject obj, jobject canv, jint extras)
-{
+static jint nativeDraw(JNIEnv *env, jobject obj, jobject canv, jint color,
+ jint extras, jboolean split) {
SkCanvas* canvas = GraphicsJNI::getNativeCanvas(env, canv);
- GET_NATIVE_VIEW(env, obj)->drawExtras(canvas, extras);
+ return reinterpret_cast<jint>(GET_NATIVE_VIEW(env, obj)->draw(canvas, color, extras, split));
}
static bool nativeEvaluateLayersAnimations(JNIEnv *env, jobject obj)
{
#if USE(ACCELERATED_COMPOSITING)
- const LayerAndroid* root = GET_NATIVE_VIEW(env, obj)->rootLayer();
+ const LayerAndroid* root = GET_NATIVE_VIEW(env, obj)->compositeRoot();
if (root)
return root->evaluateAnimations();
#endif
return false;
}
-static void nativeSetRootLayer(JNIEnv *env, jobject obj, jint layer)
+static void nativeSetBaseLayer(JNIEnv *env, jobject obj, jint layer)
{
-#if USE(ACCELERATED_COMPOSITING)
- LayerAndroid* layerImpl = reinterpret_cast<LayerAndroid*>(layer);
- GET_NATIVE_VIEW(env, obj)->setRootLayer(layerImpl);
-#endif
+ BaseLayerAndroid* layerImpl = reinterpret_cast<BaseLayerAndroid*>(layer);
+ GET_NATIVE_VIEW(env, obj)->setBaseLayer(layerImpl);
+}
+
+static void nativeReplaceBaseContent(JNIEnv *env, jobject obj, jint content)
+{
+ PictureSet* set = reinterpret_cast<PictureSet*>(content);
+ GET_NATIVE_VIEW(env, obj)->replaceBaseContent(set);
+}
+
+static void nativeCopyBaseContentToPicture(JNIEnv *env, jobject obj, jobject pict)
+{
+ SkPicture* picture = GraphicsJNI::getNativePicture(env, pict);
+ GET_NATIVE_VIEW(env, obj)->copyBaseContentToPicture(picture);
+}
+
+static bool nativeHasContent(JNIEnv *env, jobject obj)
+{
+ return GET_NATIVE_VIEW(env, obj)->hasContent();
}
static jobject nativeImageURI(JNIEnv *env, jobject obj, jint x, jint y)
{
SkIRect irect = jrect_to_webrect(env, jrect);
#if USE(ACCELERATED_COMPOSITING)
- LayerAndroid* root = GET_NATIVE_VIEW(env, obj)->rootLayer();
+ LayerAndroid* root = GET_NATIVE_VIEW(env, obj)->compositeRoot();
if (root) {
SkRect rect;
rect.set(irect);
SkDumpCanvas canvas(&dumper);
// this will playback the picture into the canvas, which will
// spew its contents to the dumper
- view->getWebViewCore()->drawContent(&canvas, 0);
-#if USE(ACCELERATED_COMPOSITING)
- if (true) {
- LayerAndroid* rootLayer = view->rootLayer();
- if (rootLayer) {
- // We have to set the canvas' matrix on the root layer
- // (to have fixed layers work as intended)
- SkAutoCanvasRestore restore(&canvas, true);
- rootLayer->setMatrix(canvas.getTotalMatrix());
- canvas.resetMatrix();
- rootLayer->draw(&canvas);
- }
- }
-#endif
+ view->draw(&canvas, 0, 0, false);
// we're done with the file now
fwrite("\n", 1, 1, file);
fclose(file);
}
#if USE(ACCELERATED_COMPOSITING)
- const LayerAndroid* rootLayer = view->rootLayer();
+ const LayerAndroid* rootLayer = view->compositeRoot();
if (rootLayer) {
FILE* file = fopen(LAYERS_TREE_LOG_FILE,"w");
if (file) {
(void*) nativeDebugDump },
{ "nativeDestroy", "()V",
(void*) nativeDestroy },
- { "nativeDrawExtras", "(Landroid/graphics/Canvas;I)V",
- (void*) nativeDrawExtras },
+ { "nativeDraw", "(Landroid/graphics/Canvas;IIZ)I",
+ (void*) nativeDraw },
{ "nativeDumpDisplayTree", "(Ljava/lang/String;)V",
(void*) nativeDumpDisplayTree },
{ "nativeEvaluateLayersAnimations", "()Z",
(void*) nativeSetFollowedLink },
{ "nativeSetHeightCanMeasure", "(Z)V",
(void*) nativeSetHeightCanMeasure },
- { "nativeSetRootLayer", "(I)V",
- (void*) nativeSetRootLayer },
+ { "nativeSetBaseLayer", "(I)V",
+ (void*) nativeSetBaseLayer },
+ { "nativeReplaceBaseContent", "(I)V",
+ (void*) nativeReplaceBaseContent },
+ { "nativeCopyBaseContentToPicture", "(Landroid/graphics/Picture;)V",
+ (void*) nativeCopyBaseContentToPicture },
+ { "nativeHasContent", "()Z",
+ (void*) nativeHasContent },
{ "nativeSetSelectionPointer", "(ZFII)V",
(void*) nativeSetSelectionPointer },
{ "nativeStartSelection", "(II)Z",