Android GUI 的更新過程

來源:互聯網
上載者:User
Android GUI 的更新過程2011-05-25 17:41

 

From:

http://www.linuxgraphics.cn/android/gui_update_flow.html

元件圖表

相關組件如所示:

  • ViewRoot

在private void draw(boolean fullRedrawNeeded)中,會調用lockCanvas,從而擷取一個Canvas對象,然後調用遞迴調用子視窗(View)的draw函數去繪製自己,最後調用unlockCanvasAndPost讓Surface把自己更新到螢幕上。

    canvas = surface.lockCanvas(dirty);    mView.draw(canvas);    surface.unlockCanvasAndPost(canvas);
  • android/view/Surface

它主要對一些native函數的封裝。

    private native Canvas lockCanvasNative(Rect dirty);    public native   void unlockCanvasAndPost(Canvas canvas);
  • android_view_Surface.cpp

這是native函數的實現。

Surface_lockCanvas它先鎖住Surface,從而擷取Surface相關的資訊,如果格式、寬度、高度和像素緩衝區。然後建立一個bitmap,這個bitmap和View共用一個像素緩衝區,這樣View就能直接把自己繪製到Surface上了。

    status_t err = surface->lock(&info, &dirtyRegion);    bitmap.setPixels(info.bits);    nativeCanvas->setBitmapDevice(bitmap);Surface_unlockCanvasAndPost它斷開SkCanvas與Surface之間的關係,然後調用Surface的unlockAndPost。
    nativeCanvas->setBitmapDevice(SkBitmap());    status_t err = surface->unlockAndPost();
  • surfaceflinger_client/Surface.cpp

Surface::lock調用dequeueBuffer擷取一個可用的Buffer,dequeueBuffer會調用SharedBufferClient::dequeue等到backbuffer可用,然後鎖住這個Buffer並填充相關資訊。

    status_t err = dequeueBuffer(&backBuffer);    err = lockBuffer(backBuffer.get());Surface::unlockAndPost先unlock Buffer,然後調queueBuffer顯示Buffer。
    status_t err = mLockedBuffer->unlock();    err = queueBuffer(mLockedBuffer.get());Surface::queueBuffer是比較有意思的,它設定更新的地區,然後通知服務端(SurfaceFlinger)。    mSharedBufferClient->setDirtyRegion(bufIdx, mDirtyRegion);    err = mSharedBufferClient->queue(bufIdx);    client->signalServer();通過binder發送請求給服務:
    virtual void signal() const    {        Parcel data, reply;        data.writeInterfaceToken(ISurfaceComposer::getInterfaceDescriptor());        remote()->transact(BnSurfaceComposer::SIGNAL, data, &reply, IBinder::FLAG_ONEWAY);    }
  • SurfaceFlinger
    BnSurfaceComposer::onTransact    case SIGNAL: {        CHECK_INTERFACE(ISurfaceComposer, data, reply);        signal();    } break;這是SurfaceFlinger中處理SIGNAL的代碼,它調用SurfaceFlinger::signal,再調用 SurfaceFlinger::signalEvent,最後調用MessageQueue::invalidate喚醒是 SurfaceFlinger的主迴圈。

在主迴圈中waitForEvent返回,再handleRepaint去合成個Layer/Surface。

    bool SurfaceFlinger::threadLoop()    {        waitForEvent();        handleRepaint();        postFramebuffer();    }SurfaceFlinger::handleRepaint會調用composeSurfaces把需要繪製各個Surface合并起來,繪製到FrameBuffer的BackBuffer上。
    for (size_t i=0 ; i<count ; ++i) {        const sp<LayerBase>& layer = layers[i];        const Region& visibleRegion(layer->visibleRegionScreen);        if (!visibleRegion.isEmpty())  {            /* broncho cy add */            #ifdef USEOVERLAY            mToppest[1] = mToppest[0];            mToppest[0] = layer->getIdentity();            #endif            /* broncho end */            const Region clip(dirty.intersect(visibleRegion));            if (!clip.isEmpty()) {                layer->draw(clip);            }        }    }SurfaceFlinger::postFramebuffer最後把FrameBuffer的BackBuffer顯示到螢幕上:
hw.flip(mInvalidRegion); -->eglSwapBuffers(dpy, surface);

 

相關文章

聯繫我們

該頁面正文內容均來源於網絡整理,並不代表阿里雲官方的觀點,該頁面所提到的產品和服務也與阿里云無關,如果該頁面內容對您造成了困擾,歡迎寫郵件給我們,收到郵件我們將在5個工作日內處理。

如果您發現本社區中有涉嫌抄襲的內容,歡迎發送郵件至: info-contact@alibabacloud.com 進行舉報並提供相關證據,工作人員會在 5 個工作天內聯絡您,一經查實,本站將立刻刪除涉嫌侵權內容。

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.