OSDN Git Service

Remove the global button lock
authorJohn Reck <jreck@google.com>
Mon, 7 Nov 2011 21:53:18 +0000 (13:53 -0800)
committerJohn Reck <jreck@google.com>
Mon, 7 Nov 2011 22:40:06 +0000 (14:40 -0800)
 Bug: 5558699
 Bug: 5572238

Change-Id: Ic199ffda5bc4aa09d39ee54221c6fcce6a91ca05

Source/WebCore/platform/android/RenderThemeAndroid.cpp
Source/WebCore/platform/graphics/android/GLWebViewState.cpp
Source/WebCore/platform/graphics/android/GLWebViewState.h
Source/WebCore/platform/graphics/android/GraphicsLayerAndroid.cpp
Source/WebCore/platform/graphics/android/PlatformGraphicsContext.cpp
Source/WebCore/platform/graphics/android/PlatformGraphicsContext.h
Source/WebCore/platform/graphics/android/android_graphics.cpp
Source/WebKit/android/jni/WebCoreJniOnLoad.cpp
Source/WebKit/android/jni/WebViewCore.cpp
Source/WebKit/android/jni/WebViewCore.h
Source/WebKit/android/nav/WebView.cpp

index 7ef814e..481ecbf 100644 (file)
@@ -234,17 +234,18 @@ bool RenderThemeAndroid::paintButton(RenderObject* obj, const PaintInfo& info, c
     // If it is a disabled button, simply paint it to the master picture.
     Node* node = obj->node();
     Element* formControlElement = static_cast<Element*>(node);
-    if (formControlElement && !formControlElement->isEnabledFormControl()) {
+    if (formControlElement) {
         android::WebFrame* webFrame = getWebFrame(node);
         if (webFrame) {
             RenderSkinAndroid* skins = webFrame->renderSkins();
-            if (skins)
-                skins->renderSkinButton()->draw(getCanvasFromInfo(info), rect,
-                                                RenderSkinAndroid::kDisabled);
+            if (skins) {
+                RenderSkinAndroid::State state = RenderSkinAndroid::kNormal;
+                if (!formControlElement->isEnabledFormControl())
+                    state = RenderSkinAndroid::kDisabled;
+                skins->renderSkinButton()->draw(getCanvasFromInfo(info), rect, state);
+            }
         }
-    } else
-        // Store all the important information in the platform context.
-        info.context->platformContext()->storeButtonInfo(node, rect);
+    }
 
     // We always return false so we do not request to be redrawn.
     return false;
index a1766d0..a44a743 100644 (file)
@@ -69,7 +69,7 @@ namespace WebCore {
 
 using namespace android;
 
-GLWebViewState::GLWebViewState(android::Mutex* buttonMutex)
+GLWebViewState::GLWebViewState()
     : m_zoomManager(this)
     , m_paintingBaseLayer(0)
     , m_currentBaseLayer(0)
@@ -78,7 +78,6 @@ GLWebViewState::GLWebViewState(android::Mutex* buttonMutex)
     , m_usePageA(true)
     , m_frameworkInval(0, 0, 0, 0)
     , m_frameworkLayersInval(0, 0, 0, 0)
-    , m_globalButtonMutex(buttonMutex)
     , m_baseLayerUpdate(true)
     , m_backgroundColor(SK_ColorWHITE)
     , m_isScrolling(false)
@@ -241,9 +240,7 @@ unsigned int GLWebViewState::paintBaseLayerContent(SkCanvas* canvas)
     SkSafeRef(base);
     m_baseLayerLock.unlock();
     if (base) {
-        m_globalButtonMutex->lock();
         base->drawCanvas(canvas);
-        m_globalButtonMutex->unlock();
     }
     SkSafeUnref(base);
     return m_currentPictureCounter;
index b2aab88..5f7ca71 100644 (file)
@@ -165,7 +165,7 @@ class LayerAndroid;
 
 class GLWebViewState {
 public:
-    GLWebViewState(android::Mutex* globalButtonMutex);
+    GLWebViewState();
     ~GLWebViewState();
 
     ZoomManager* zoomManager() { return &m_zoomManager; }
@@ -254,7 +254,6 @@ private:
     IntRect m_lastInval;
     IntRect m_frameworkInval;
     IntRect m_frameworkLayersInval;
-    android::Mutex* m_globalButtonMutex;
 
     bool m_baseLayerUpdate;
     SkRegion m_invalidateRegion;
index 6cb9288..05a0fdc 100644 (file)
@@ -652,7 +652,7 @@ bool GraphicsLayerAndroid::paintContext(SkPicture* context,
     if (!canvas)
         return false;
 
-    PlatformGraphicsContext platformContext(canvas, 0);
+    PlatformGraphicsContext platformContext(canvas);
     GraphicsContext graphicsContext(&platformContext);
 
     paintGraphicsLayerContents(graphicsContext, rect);
index fcdcce9..098534c 100644 (file)
 
 namespace WebCore {
 
-PlatformGraphicsContext::PlatformGraphicsContext(SkCanvas* canvas, WTF::Vector<Container>* buttons)
-        : mCanvas(canvas), m_deleteCanvas(false), m_buttons(buttons)
+PlatformGraphicsContext::PlatformGraphicsContext(SkCanvas* canvas)
+        : mCanvas(canvas), m_deleteCanvas(false)
 {
 }
 
 PlatformGraphicsContext::PlatformGraphicsContext()
-        : mCanvas(new SkCanvas), m_deleteCanvas(true), m_buttons(0)
+        : mCanvas(new SkCanvas), m_deleteCanvas(true)
 {
 }
 
@@ -48,27 +48,4 @@ PlatformGraphicsContext::~PlatformGraphicsContext()
     }
 }
 
-void PlatformGraphicsContext::storeButtonInfo(Node* node, const IntRect& r)
-{
-    if (m_buttons == NULL)
-        return;
-    // Check to see if we already have a Container for this node.  If so, update
-    // it with the new rectangle and make the new recording canvas reference
-    // its picture.
-    Container* end = m_buttons->end();
-    for (Container* ptr = m_buttons->begin(); ptr != end; ptr++) {
-        if (ptr->matches(node)) {
-            mCanvas->drawPicture(*(ptr->picture()));
-            ptr->setRect(r);
-            return;
-        }
-    }
-    // We did not have a Container representing this node, so create a new one.
-    Container container(node, r);
-    // Place a reference to our subpicture in the Picture.
-    mCanvas->drawPicture(*(container.picture()));
-    // Keep track of the information about the button.
-    m_buttons->append(container);
-}
-
 }   // WebCore
index 6d08d44..d22dbd8 100644 (file)
 
 class SkCanvas;
 
-class Container {
-public:
-    Container(WebCore::Node* node, const WebCore::IntRect& r) 
-        : m_node(node), m_rect(r), m_state(WebCore::RenderSkinAndroid::kDisabled)
-    { 
-        m_picture = new SkPicture; 
-    }
-    
-    ~Container() 
-    { 
-        m_picture->unref(); 
-    }
-
-    Container& operator=(const Container& src) 
-    {
-        if (this != &src) {
-            m_node = src.m_node;
-            if (m_picture)
-                m_picture->unref();
-            m_picture = src.m_picture;
-            m_picture->ref();
-            m_rect = src.m_rect;
-            m_state = WebCore::RenderSkinAndroid::kDisabled;
-        }
-        return *this;
-    }
-    
-    Container(const Container& src) 
-    { 
-        m_node = src.m_node;
-        m_picture = src.m_picture;
-        m_picture->ref();
-        m_rect = src.m_rect;
-        m_state = WebCore::RenderSkinAndroid::kDisabled;
-    }
-
-    // m_picture has a ref count of 1 to begin with.  It will increase each time
-    // m_picture is referenced by another picture.  When the other pictures are
-    // deleted, the ref count gets decremented.  If the ref count is one, then
-    // no other pictures reference this one, so the button is no longer being
-    // used, and therefore can be removed.
-    bool canBeRemoved()
-    {
-        return m_picture->getRefCnt() == 1;
-    }
-    
-    bool matches(const WebCore::Node* match) { return m_node == match; }
-
-    const WebCore::Node* node() const { return m_node; }
-
-    // Provide a pointer to our SkPicture.
-    SkPicture* picture() { return m_picture; }
-
-    WebCore::IntRect rect() { return m_rect; }
-
-    // Update the rectangle with a new rectangle, as the positioning of this
-    // button may have changed due to a new layout.  If it is a new rectangle,
-    // set its state to disabled, so that it will be redrawn when we cycle
-    // through the list of buttons.
-    void setRect(WebCore::IntRect r)
-    {
-        if (m_rect != r) {
-            m_rect = r; 
-            m_state = WebCore::RenderSkinAndroid::kDisabled;
-        }
-    }
-    
-    // Update the focus state of this button, depending on whether it 
-    // corresponds to the focused node passed in.  If its state has changed,
-    // re-record to the subpicture, so the master picture will reflect the
-    // change.
-    void updateFocusState(WebCore::RenderSkinAndroid::State state,
-                          WebCore::RenderSkinButton* buttonSkin)
-    {
-        if (state == m_state)
-            return;
-        // If this button is being told to draw focused, but it is already in a
-        // pressed state, leave it in the pressed state, to show that it is
-        // being followed.
-        if (m_state == WebCore::RenderSkinAndroid::kPressed &&
-                state == WebCore::RenderSkinAndroid::kFocused)
-            return;
-        m_state = state;
-        SkCanvas* canvas = m_picture->beginRecording(m_rect.maxX(), m_rect.maxY());
-        buttonSkin->draw(canvas, m_rect, state);
-        m_picture->endRecording();
-    }
-private:
-    // Only used for comparison, since after it is stored it will be transferred
-    // to the UI thread.
-    WebCore::Node*                      m_node;
-    // The rectangle representing the bounds of the button.
-    WebCore::IntRect                    m_rect;
-    // An SkPicture that, thanks to storeButtonInfo, is pointed to by the master
-    // picture, so that we can rerecord this button without rerecording the 
-    // world.
-    SkPicture*                          m_picture;
-    // The state of the button - Currently kFocused or kNormal (and kDisabled
-    // as an initial value), but could be expanded to include other states.
-    WebCore::RenderSkinAndroid::State   m_state;
-};
-
 namespace WebCore {
 
     class GraphicsContext;
@@ -146,19 +44,14 @@ public:
     PlatformGraphicsContext();
     // Pass in a recording canvas, and an array of button information to be 
     // updated.
-    PlatformGraphicsContext(SkCanvas* canvas, WTF::Vector<Container>* buttons);
+    PlatformGraphicsContext(SkCanvas* canvas);
     ~PlatformGraphicsContext();
     
     SkCanvas*                   mCanvas;
     
     bool deleteUs() const { return m_deleteCanvas; }
-    // If our graphicscontext has a button list, add a new container for the
-    // nod/rect, and record a new subpicture for this node/button in the current
-    // mCanvas
-    void storeButtonInfo(Node* node, const IntRect& r);
 private:
     bool                     m_deleteCanvas;
-    WTF::Vector<Container>*    m_buttons;
 };
 
 }
index e255d29..e88c65d 100644 (file)
@@ -112,22 +112,6 @@ void CursorRing::draw(SkCanvas* canvas, LayerAndroid* layer, IntRect* inval)
 void CursorRing::setIsButton(const CachedNode* node)
 {
     m_isButton = false;
-    m_viewImpl->gButtonMutex.lock();
-    // If this is a button drawn by us (rather than webkit) do not draw the
-    // cursor ring, since its cursor will be shown by a change in what we draw.
-    // Should be in sync with recordButtons, since that will be called
-    // before this.
-    if (m_viewImpl->m_buttons.size() > 0) {
-        WebCore::Node* cursorPointer = (WebCore::Node*) node->nodePointer();
-        Container* end = m_viewImpl->m_buttons.end();
-        for (Container* ptr = m_viewImpl->m_buttons.begin(); ptr != end; ptr++) {
-            if (ptr->matches(cursorPointer)) {
-                m_isButton = true;
-                break;
-            }
-        }
-    }
-    m_viewImpl->gButtonMutex.unlock();
 }
 
 bool CursorRing::setup()
index e9d7bc3..bb71bf5 100644 (file)
@@ -304,7 +304,7 @@ EXPORT void benchmark(const char* url, int reloadCount, int width, int height) {
     bmp.setConfig(SkBitmap::kARGB_8888_Config, width, height);
     bmp.allocPixels();
     SkCanvas canvas(bmp);
-    PlatformGraphicsContext ctx(&canvas, NULL);
+    PlatformGraphicsContext ctx(&canvas);
     GraphicsContext gc(&ctx);
     frame->view()->paintContents(&gc, IntRect(0, 0, width, height));
 
index d7a61aa..0708d5c 100644 (file)
@@ -336,7 +336,6 @@ static jmethodID GetJMethod(JNIEnv* env, jclass clazz, const char name[], const
 }
 
 Mutex WebViewCore::gFrameCacheMutex;
-Mutex WebViewCore::gButtonMutex;
 Mutex WebViewCore::gCursorBoundsMutex;
 
 WebViewCore::WebViewCore(JNIEnv* env, jobject javaWebViewCore, WebCore::Frame* mainframe)
@@ -560,19 +559,10 @@ void WebViewCore::recordPicture(SkPicture* picture)
                             view->contentsHeight(), PICT_RECORD_FLAGS);
     SkAutoMemoryUsageProbe mup(__FUNCTION__);
 
-    // Copy m_buttons so we can pass it to our graphics context.
-    gButtonMutex.lock();
-    WTF::Vector<Container> buttons(m_buttons);
-    gButtonMutex.unlock();
-
-    WebCore::PlatformGraphicsContext pgc(arp.getRecordingCanvas(), &buttons);
+    WebCore::PlatformGraphicsContext pgc(arp.getRecordingCanvas());
     WebCore::GraphicsContext gc(&pgc);
     view->platformWidget()->draw(&gc, WebCore::IntRect(0, 0,
         view->contentsWidth(), view->contentsHeight()));
-
-    gButtonMutex.lock();
-    updateButtonList(&buttons);
-    gButtonMutex.unlock();
 }
 
 void WebViewCore::recordPictureSet(PictureSet* content)
@@ -786,43 +776,6 @@ void WebViewCore::recordPictureSet(PictureSet* content)
     }
 }
 
-void WebViewCore::updateButtonList(WTF::Vector<Container>* buttons)
-{
-    // All the entries in buttons are either updates of previous entries in
-    // m_buttons or they need to be added to it.
-    Container* end = buttons->end();
-    for (Container* updatedContainer = buttons->begin();
-            updatedContainer != end; updatedContainer++) {
-        bool updated = false;
-        // Search for a previous entry that references the same node as our new
-        // data
-        Container* lastPossibleMatch = m_buttons.end();
-        for (Container* possibleMatch = m_buttons.begin();
-                possibleMatch != lastPossibleMatch; possibleMatch++) {
-            if (updatedContainer->matches(possibleMatch->node())) {
-                // Update our record, and skip to the next one.
-                possibleMatch->setRect(updatedContainer->rect());
-                updated = true;
-                break;
-            }
-        }
-        if (!updated) {
-            // This is a brand new button, so append it to m_buttons
-            m_buttons.append(*updatedContainer);
-        }
-    }
-    size_t i = 0;
-    // count will decrease each time one is removed, so check count each time.
-    while (i < m_buttons.size()) {
-        if (m_buttons[i].canBeRemoved()) {
-            m_buttons[i] = m_buttons.last();
-            m_buttons.removeLast();
-        } else {
-            i++;
-        }
-    }
-}
-
 // note: updateCursorBounds is called directly by the WebView thread
 // This needs to be called each time we call CachedRoot::setCursor() with
 // non-null CachedNode/CachedFrame, since otherwise the WebViewCore's data
@@ -877,11 +830,7 @@ SkPicture* WebViewCore::rebuildPicture(const SkIRect& inval)
     SkAutoMemoryUsageProbe mup(__FUNCTION__);
     SkCanvas* recordingCanvas = arp.getRecordingCanvas();
 
-    gButtonMutex.lock();
-    WTF::Vector<Container> buttons(m_buttons);
-    gButtonMutex.unlock();
-
-    WebCore::PlatformGraphicsContext pgc(recordingCanvas, &buttons);
+    WebCore::PlatformGraphicsContext pgc(recordingCanvas);
     WebCore::GraphicsContext gc(&pgc);
     recordingCanvas->translate(-inval.fLeft, -inval.fTop);
     recordingCanvas->save();
@@ -892,10 +841,6 @@ SkPicture* WebViewCore::rebuildPicture(const SkIRect& inval)
         m_rebuildInval.getBounds().fLeft, m_rebuildInval.getBounds().fTop,
         m_rebuildInval.getBounds().fRight, m_rebuildInval.getBounds().fBottom);
 
-    gButtonMutex.lock();
-    updateButtonList(&buttons);
-    gButtonMutex.unlock();
-
     return picture;
 }
 
index ea57c11..acde590 100644 (file)
@@ -595,21 +595,12 @@ namespace android {
         IntPoint m_cursorLocation;
         void* m_cursorNode;
         static Mutex gCursorBoundsMutex;
-        // These two fields go together: we use the mutex to protect access to
-        // m_buttons, so that we, and webview.cpp can look/modify the m_buttons
-        // field safely from our respective threads
-        static Mutex gButtonMutex;
-        WTF::Vector<Container> m_buttons;
         // end of shared members
 
         // internal functions
     private:
         CacheBuilder& cacheBuilder();
         WebCore::Node* currentFocus();
-        // Compare the new set of buttons to the old one.  All of the new
-        // buttons either replace our old ones or should be added to our list.
-        // Then check the old buttons to see if any are no longer needed.
-        void updateButtonList(WTF::Vector<Container>* buttons);
         // Create a set of pictures to represent the drawn DOM, driven by
         // the invalidated region and the time required to draw (used to draw)
         void recordPictureSet(PictureSet* master);
index 10f679d..64d7bbd 100644 (file)
@@ -303,58 +303,6 @@ void debugDump()
 }
 #endif
 
-// Traverse our stored array of buttons that are in our picture, and update
-// their subpictures according to their current state.
-// Called from the UI thread.  This is the one place in the UI thread where we
-// access the buttons stored in the WebCore thread.
-// hasFocus keeps track of whether the WebView has focus && windowFocus.
-// If not, we do not want to draw the button in a selected or pressed state
-void nativeRecordButtons(bool hasFocus, bool pressed, bool invalidate)
-{
-    bool cursorIsOnButton = false;
-    const CachedFrame* cachedFrame;
-    const CachedNode* cachedCursor = 0;
-    // Lock the mutex, since we now share with the WebCore thread.
-    m_viewImpl->gButtonMutex.lock();
-    if (m_viewImpl->m_buttons.size() && m_buttonSkin) {
-        // FIXME: In a future change, we should keep track of whether the selection
-        // has changed to short circuit (note that we would still need to update
-        // if we received new buttons from the WebCore thread).
-        WebCore::Node* cursor = 0;
-        CachedRoot* root = getFrameCache(DontAllowNewer);
-        if (root) {
-            cachedCursor = root->currentCursor(&cachedFrame);
-            if (cachedCursor)
-                cursor = (WebCore::Node*) cachedCursor->nodePointer();
-        }
-
-        // Traverse the array, and update each button, depending on whether it
-        // is selected.
-        Container* end = m_viewImpl->m_buttons.end();
-        for (Container* ptr = m_viewImpl->m_buttons.begin(); ptr != end; ptr++) {
-            RenderSkinAndroid::State state = RenderSkinAndroid::kNormal;
-            if (ptr->matches(cursor)) {
-                cursorIsOnButton = true;
-                // If the WebView is out of focus/window focus, set the state to
-                // normal, but still keep track of the fact that the selected is a
-                // button
-                if (hasFocus) {
-                    if (pressed || m_ring.m_isPressed)
-                        state = RenderSkinAndroid::kPressed;
-                    else if (SkTime::GetMSecs() < m_ringAnimationEnd)
-                        state = RenderSkinAndroid::kFocused;
-                }
-            }
-            ptr->updateFocusState(state, m_buttonSkin);
-        }
-    }
-    m_viewImpl->gButtonMutex.unlock();
-    if (invalidate && cachedCursor && cursorIsOnButton) {
-        const WebCore::IntRect& b = cachedCursor->bounds(cachedFrame);
-        viewInvalidateRect(b.x(), b.y(), b.maxX(), b.maxY());
-    }
-}
-
 void scrollToCurrentMatch()
 {
     if (!m_findOnPage.currentMatchIsInLayer()) {
@@ -528,7 +476,7 @@ bool drawGL(WebCore::IntRect& viewRect, WebCore::IntRect* invalRect, WebCore::In
         return false;
 
     if (!m_glWebViewState) {
-        m_glWebViewState = new GLWebViewState(&m_viewImpl->gButtonMutex);
+        m_glWebViewState = new GLWebViewState();
         m_glWebViewState->glExtras()->setCursorRingExtra(&m_ring);
         m_glWebViewState->glExtras()->setFindOnPageExtra(&m_findOnPage);
         if (m_baseLayer->content()) {
@@ -638,8 +586,7 @@ PictureSet* draw(SkCanvas* canvas, SkColor bgColor, int extras, bool split)
             break;
         case DrawExtrasCursorRing:
             if (drawCursorPreamble(root) && m_ring.setup()) {
-                if (!m_ring.m_isButton)
-                    extra = &m_ring;
+                extra = &m_ring;
                 drawCursorPostamble();
             }
             break;
@@ -2296,14 +2243,6 @@ static bool nativeMoveCursor(JNIEnv *env, jobject obj,
     return view->moveCursor(key, count, ignoreScroll);
 }
 
-static void nativeRecordButtons(JNIEnv* env, jobject obj, jint nativeView,
-                                bool hasFocus, bool pressed, bool invalidate)
-{
-    WebView* view = (WebView*) nativeView;
-    LOG_ASSERT(view, "view not set in %s", __FUNCTION__);
-    view->nativeRecordButtons(hasFocus, pressed, invalidate);
-}
-
 static void nativeSetFindIsUp(JNIEnv *env, jobject obj, jboolean isUp)
 {
     WebView* view = GET_NATIVE_VIEW(env, obj);
@@ -2886,8 +2825,6 @@ static JNINativeMethod gJavaWebViewMethods[] = {
         (void*) nativeMoveSelection },
     { "nativePointInNavCache", "(III)Z",
         (void*) nativePointInNavCache },
-    { "nativeRecordButtons", "(IZZZ)V",
-        (void*) nativeRecordButtons },
     { "nativeResetSelection", "()V",
         (void*) nativeResetSelection },
     { "nativeSelectableText", "()Landroid/graphics/Point;",