Discuz! Board

标题: GUI系统之SurfaceFlinger(6)BufferQueue中的缓冲区分配 [打印本页]

作者: zangcf    时间: 2016-4-27 18:37
标题: GUI系统之SurfaceFlinger(6)BufferQueue中的缓冲区分配
这个系列文章包括地址:GUI系统之SurfaceFlinger(1)OpenGLES与EGLhttp://blog.csdn.net/xuesen_lin/article/details/8954553
GUI系统之SurfaceFlinger(2)Gralloc与Framebufferhttp://blog.csdn.net/xuesen_lin/article/details/8954585
GUI系统之SurfaceFlinger(3)Android中的本地窗口FramebufferNativewindowhttp://blog.csdn.net/xuesen_lin/article/details/8954748
GUI系统之SurfaceFlinger(4)opengl es本地窗口SurfaceTextureClient:http://blog.csdn.net/xuesen_lin/article/details/8954782

GUI系统之SurfaceFlinger(5)BufferQueue内部原理:http://blog.csdn.net/xuesen_lin/article/details/8954803
GUI系统之SurfaceFlinger(6)BufferQueue中的缓冲区分配:http://blog.csdn.net/xuesen_lin/article/details/8954834
..........................
等等等等






作者: zangcf    时间: 2016-4-27 18:40
下面的思路,我们还是从surface进行入手考虑:
1,当系统申请生成一个surface的时候,我们顺便生成一个影子surface
2,当系统对surface进行画图的时候,我们同时也对影子surface进行画图。
3,当系统对surface进行提交的时候,我们也对影子surface进行提交。
4,但是需要修改yi影子surface的参数,使得其下一到后半个屏幕
作者: zangcf    时间: 2016-4-27 19:19
    public int relayoutWindow(Session session, IWindow client, int seq,
            WindowManager.LayoutParams attrs, int requestedWidth,
            int requestedHeight, int viewVisibility, int flags,
            Rect outFrame, Rect outOverscanInsets, Rect outContentInsets,
            Rect outVisibleInsets, Rect outStableInsets, Configuration outConfig,
            Surface outSurface) {
中会调用::
                try {
                    if (!win.mHasSurface) {
                        surfaceChanged = true;
                    }
                    SurfaceControl surfaceControl = winAnimator.createSurfaceLocked();
                    if (surfaceControl != null) {
                        outSurface.copyFrom(surfaceControl);
                        if (SHOW_TRANSACTIONS) Slog.i(TAG,
                                "  OUT SURFACE " + outSurface + ": copied");
                    } else {
                        // For some reason there isn't a surface.  Clear the
                        // caller's object so they see the same state.
                        outSurface.release();
                    }

作者: zangcf    时间: 2016-4-27 19:20
    SurfaceControl createSurfaceLocked() {
        final WindowState w = mWin;
        if (mSurfaceControl == null) {
            if (WindowManagerService.DEBUG_ANIM || WindowManagerService.DEBUG_ORIENTATION) Slog.i(TAG,
                    "createSurface " + this + ": mDrawState=DRAW_PENDING");
            mDrawState = DRAW_PENDING;
            if (w.mAppToken != null) {
                if (w.mAppToken.mAppAnimator.animation == null) {
                    w.mAppToken.allDrawn = false;
                    w.mAppToken.deferClearAllDrawn = false;
                } else {
                    // Currently animating, persist current state of allDrawn until animation
                    // is complete.
                    w.mAppToken.deferClearAllDrawn = true;
                }
            }

            mService.makeWindowFreezingScreenIfNeededLocked(w);

            int flags = SurfaceControl.HIDDEN;
            final WindowManager.LayoutParams attrs = w.mAttrs;

            if ((attrs.flags&WindowManager.LayoutParams.FLAG_SECURE) != 0) {
                flags |= SurfaceControl.SECURE;
            }

            if (mService.isScreenCaptureDisabledLocked(UserHandle.getUserId(mWin.mOwnerUid))) {
                flags |= SurfaceControl.SECURE;
            }

            int width;
            int height;
            if ((attrs.flags & LayoutParams.FLAG_SCALED) != 0) {
                // for a scaled surface, we always want the requested
                // size.
                width = w.mRequestedWidth;
                height = w.mRequestedHeight;
            } else {
                width = w.mCompatFrame.width();
                height = w.mCompatFrame.height();
            }

            // Something is wrong and SurfaceFlinger will not like this,
            // try to revert to sane values
            if (width <= 0) {
                width = 1;
            }
            if (height <= 0) {
                height = 1;
            }

            float left = w.mFrame.left + w.mXOffset;
            float top = w.mFrame.top + w.mYOffset;

            // Adjust for surface insets.
            width += attrs.surfaceInsets.left + attrs.surfaceInsets.right;
            height += attrs.surfaceInsets.top + attrs.surfaceInsets.bottom;
            left -= attrs.surfaceInsets.left;
            top -= attrs.surfaceInsets.top;

            if (DEBUG_VISIBILITY) {
                Slog.v(TAG, "Creating surface in session "
                        + mSession.mSurfaceSession + " window " + this
                        + " w=" + width + " h=" + height
                        + " x=" + left + " y=" + top
                        + " format=" + attrs.format + " flags=" + flags);
            }

            // We may abort, so initialize to defaults.
            mSurfaceShown = false;
            mSurfaceLayer = 0;
            mSurfaceAlpha = 0;
            mSurfaceX = 0;
            mSurfaceY = 0;
            w.mLastSystemDecorRect.set(0, 0, 0, 0);
            mLastClipRect.set(0, 0, 0, 0);

            // Set up surface control with initial size.
            try {
                mSurfaceW = width;
                mSurfaceH = height;

                final boolean isHwAccelerated = (attrs.flags &
                        WindowManager.LayoutParams.FLAG_HARDWARE_ACCELERATED) != 0;
                final int format = isHwAccelerated ? PixelFormat.TRANSLUCENT : attrs.format;
                if (!PixelFormat.formatHasAlpha(attrs.format)
                        && attrs.surfaceInsets.left == 0
                        && attrs.surfaceInsets.top == 0
                        && attrs.surfaceInsets.right == 0
                        && attrs.surfaceInsets.bottom  == 0) {
                    flags |= SurfaceControl.OPAQUE;
                }

                if (WindowManagerService.DEBUG_SURFACE_TRACE) {
                    mSurfaceControl = new SurfaceTrace(
                            mSession.mSurfaceSession,
                            attrs.getTitle().toString(),
                            width, height, format, flags);
                } else {
                    mSurfaceControl = new SurfaceControl(
                        mSession.mSurfaceSession,
                        attrs.getTitle().toString(),
                        width, height, format, flags);
                }

                w.mHasSurface = true;

                if (!WindowManagerService.IS_USER_BUILD || WindowManagerService.SHOW_TRANSACTIONS || WindowManagerService.SHOW_SURFACE_ALLOC) {
                    Slog.i(TAG, "  CREATE SURFACE "
                            + mSurfaceControl + " IN SESSION "
                            + mSession.mSurfaceSession
                            + ": pid=" + mSession.mPid + " format="
                            + attrs.format + " flags=0x"
                            + Integer.toHexString(flags)
                            + " / " + this);
                }
            } catch (OutOfResourcesException e) {
                w.mHasSurface = false;
                Slog.w(TAG, "OutOfResourcesException creating surface");
                mService.reclaimSomeSurfaceMemoryLocked(this, "create", true);
                mDrawState = NO_SURFACE;
                return null;
            } catch (Exception e) {
                w.mHasSurface = false;
                Slog.e(TAG, "Exception creating surface", e);
                mDrawState = NO_SURFACE;
                return null;
            }

            if (WindowManagerService.localLOGV) {
                Slog.v(TAG, "Got surface: " + mSurfaceControl
                        + ", set left=" + w.mFrame.left + " top=" + w.mFrame.top
                        + ", animLayer=" + mAnimLayer);
            }

            if (WindowManagerService.SHOW_LIGHT_TRANSACTIONS) {
                Slog.i(TAG, ">>> OPEN TRANSACTION createSurfaceLocked");
                WindowManagerService.logSurface(w, "CREATE pos=("
                        + w.mFrame.left + "," + w.mFrame.top + ") ("
                        + w.mCompatFrame.width() + "x" + w.mCompatFrame.height()
                        + "), layer=" + mAnimLayer + " HIDE", null);
            }

            // Start a new transaction and apply position & offset.
            SurfaceControl.openTransaction();
            try {
                mSurfaceX = left;
                mSurfaceY = top;

                try {
                    mSurfaceControl.setPosition(left, top);
                    mSurfaceLayer = mAnimLayer;
                    final DisplayContent displayContent = w.getDisplayContent();
                    if (displayContent != null) {
                        mSurfaceControl.setLayerStack(displayContent.getDisplay().getLayerStack());
                    }
                    mSurfaceControl.setLayer(mAnimLayer);
                    mSurfaceControl.setAlpha(0);
                    mSurfaceShown = false;
                } catch (RuntimeException e) {
                    Slog.w(TAG, "Error creating surface in " + w, e);
                    mService.reclaimSomeSurfaceMemoryLocked(this, "create-init", true);
                }
                mLastHidden = true;
            } finally {
                SurfaceControl.closeTransaction();
                if (WindowManagerService.SHOW_LIGHT_TRANSACTIONS) Slog.i(TAG,
                        "<<< CLOSE TRANSACTION createSurfaceLocked");
            }
            if (WindowManagerService.localLOGV) Slog.v(
                    TAG, "Created surface " + this);
        }
        return mSurfaceControl;
    }
作者: zangcf    时间: 2016-4-28 08:08
如果在主窗体生成一个影子surface,那么硬件绘图的时候,如何使用这个surface的呢?看看几个人的文章。
作者: zangcf    时间: 2016-4-28 10:29
必须构建两个surface,然后画图的时候,也需要在两个surface上面画图




欢迎光临 Discuz! Board (http://47.89.242.157:9000/bbs/discuz/) Powered by Discuz! X3.2