zoukankan      html  css  js  c++  java
  • 安卓高手之路之 GDI图形引擎篇

    安卓高手之路之 GDI图形引擎篇 - 修补C++ - ITeye技术网站

    1.底层C++

      SufaceFlinger类图的静态结构

     2.上层Java的调用流程。

     首先,直接从WindowManagerService入手:

      

    Java代码  收藏代码
    1. public int relayoutWindow(Session session, IWindow client, int seq,  
    2.            WindowManager.LayoutParams attrs, int requestedWidth,  
    3.            int requestedHeight, int viewVisibility, int flags,  
    4.            Rect outFrame, Rect outContentInsets, Rect outVisibleInsets,  
    5.            Configuration outConfig, Surface outSurface)   
     public int relayoutWindow(Session session, IWindow client, int seq,
                WindowManager.LayoutParams attrs, int requestedWidth,
                int requestedHeight, int viewVisibility, int flags,
                Rect outFrame, Rect outContentInsets, Rect outVisibleInsets,
                Configuration outConfig, Surface outSurface) 

    这个方法中有一句:

       Surface surface = win.createSurfaceLocked();
    创建Surface,然后继续跟下去,跟到了jni(android_view_Surface.cpp)的如下方法:
    Java代码  收藏代码
    1. static void Surface_init(  
    2.         JNIEnv* env, jobject clazz,  
    3.         jobject session,  
    4.         jint, jstring jname, jint dpy, jint w, jint h, jint format, jint flags)  
    5. {  
    6.     if (session == NULL) {  
    7.         doThrowNPE(env);  
    8.         return;  
    9.     }  
    10.   
    11.     SurfaceComposerClient* client =  
    12.             (SurfaceComposerClient*)env->GetIntField(session, sso.client);  
    13.   
    14.     sp<SurfaceControl> surface;  
    15.     if (jname == NULL) {  
    16.         surface = client->createSurface(dpy, w, h, format, flags);  
    17.     } else {  
    18.         const jchar* str = env->GetStringCritical(jname, 0);  
    19.         const String8 name(str, env->GetStringLength(jname));  
    20.         env->ReleaseStringCritical(jname, str);  
    21.         surface = client->createSurface(name, dpy, w, h, format, flags);  
    22.     }  
    23.   
    24.     if (surface == 0) {  
    25.         jniThrowException(env, OutOfResourcesException, NULL);  
    26.         return;  
    27.     }  
    28.    <span style="background-color: #ffffff; color: #ff0000;"> setSurfaceControl(env, clazz, surface);  
    29. </span>}  
    static void Surface_init(
            JNIEnv* env, jobject clazz,
            jobject session,
            jint, jstring jname, jint dpy, jint w, jint h, jint format, jint flags)
    {
        if (session == NULL) {
            doThrowNPE(env);
            return;
        }
    
        SurfaceComposerClient* client =
                (SurfaceComposerClient*)env->GetIntField(session, sso.client);
    
        sp<SurfaceControl> surface;
        if (jname == NULL) {
            surface = client->createSurface(dpy, w, h, format, flags);
        } else {
            const jchar* str = env->GetStringCritical(jname, 0);
            const String8 name(str, env->GetStringLength(jname));
            env->ReleaseStringCritical(jname, str);
            surface = client->createSurface(name, dpy, w, h, format, flags);
        }
    
        if (surface == 0) {
            jniThrowException(env, OutOfResourcesException, NULL);
            return;
        }
        setSurfaceControl(env, clazz, surface);
    }

     郁闷的是这个session又是如何初始化的,同样在android_view_Surface.cpp中:

    Java代码  收藏代码
    1. static void SurfaceSession_init(JNIEnv* env, jobject clazz)  
    2. {  
    3.     sp<SurfaceComposerClient> client = new SurfaceComposerClient;  
    4.     client->incStrong(clazz);  
    5.     <span style="color: #ff0000;">env->SetIntField(clazz, sso.client, (int)client.get());  
    6. </span>}  
    static void SurfaceSession_init(JNIEnv* env, jobject clazz)
    {
        sp<SurfaceComposerClient> client = new SurfaceComposerClient;
        client->incStrong(clazz);
        env->SetIntField(clazz, sso.client, (int)client.get());
    }
    
    非常好,那么这个client就是和java层SurfaceSession构成了一一对应关系咯?事实的确如此。看java层的
    SurfaceSession的定义,里面仅有的成员变量就是这个client:
    Java代码  收藏代码
    1. public class SurfaceSession {  
    2.     /** Create a new connection with the surface flinger. */  
    3.     public SurfaceSession() {  
    4.         init();  
    5.     }  
    6.   
    7.     /** Forcibly detach native resources associated with this object. 
    8.      *  Unlike destroy(), after this call any surfaces that were created 
    9.      *  from the session will no longer work. The session itself is destroyed. 
    10.      */  
    11.     public native void kill();  
    12.   
    13.     /* no user serviceable parts here ... */  
    14.     @Override  
    15.     protected void finalize() throws Throwable {  
    16.         destroy();  
    17.     }  
    18.       
    19.     private native void init();  
    20.     private native void destroy();  
    21.       
    22.    <span style="color: #ff0000;"private int mClient;  
    23. </span>}  
    public class SurfaceSession {
        /** Create a new connection with the surface flinger. */
        public SurfaceSession() {
            init();
        }
    
        /** Forcibly detach native resources associated with this object.
         *  Unlike destroy(), after this call any surfaces that were created
         *  from the session will no longer work. The session itself is destroyed.
         */
        public native void kill();
    
        /* no user serviceable parts here ... */
        @Override
        protected void finalize() throws Throwable {
            destroy();
        }
    
        private native void init();
        private native void destroy();
    
        private int mClient;
    }

     好了,现在回到java层继续看Surface。现在的概念应该很明确了,从本质上来说,Surface是由SurfaceSession创建的。那么SurfaceSession 又是由谁创建的呢? 既然SurfaceSession 是Session的成员变量,那么就顺藤摸瓜去看:

    Java代码  收藏代码
    1. void windowAddedLocked() {  
    2.       if (mSurfaceSession == null) {  
    3.           if (WindowManagerService.localLOGV) Slog.v(  
    4.               WindowManagerService.TAG, "First window added to " + this + ", creating SurfaceSession");  
    5.         <span style="color: #ff0000;">  mSurfaceSession = new SurfaceSession();  
    6. span>            if (WindowManagerService.SHOW_TRANSACTIONS) Slog.i(  
    7.                   WindowManagerService.TAG, "  NEW SURFACE SESSION " + mSurfaceSession);  
    8.           mService.mSessions.add(this);  
    9.       }  
    10.       mNumWindow++;  
    11.   }  
      void windowAddedLocked() {
            if (mSurfaceSession == null) {
                if (WindowManagerService.localLOGV) Slog.v(
                    WindowManagerService.TAG, "First window added to " + this + ", creating SurfaceSession");
                mSurfaceSession = new SurfaceSession();
                if (WindowManagerService.SHOW_TRANSACTIONS) Slog.i(
                        WindowManagerService.TAG, "  NEW SURFACE SESSION " + mSurfaceSession);
                mService.mSessions.add(this);
            }
            mNumWindow++;
        }

     那么windowAddedLocked又是谁调用的呢?在WIndowState.java中:

      

    Java代码  收藏代码
    1. void attach() {  
    2.        if (WindowManagerService.localLOGV) Slog.v(  
    3.            WindowManagerService.TAG, "Attaching " + this + " token=" + mToken  
    4.            + ", list=" + mToken.windows);  
    5.        mSession.windowAddedLocked();  
    6.    }  
     void attach() {
            if (WindowManagerService.localLOGV) Slog.v(
                WindowManagerService.TAG, "Attaching " + this + " token=" + mToken
                + ", list=" + mToken.windows);
            mSession.windowAddedLocked();
        }

     那么这个attach又是谁调用的呢?WindowManagerService.java的一个方法,如下:

    Java代码  收藏代码
    1. public int addWindow(Session session, IWindow client, int seq,  
    2.            WindowManager.LayoutParams attrs, int viewVisibility,  
    3.            Rect outContentInsets, InputChannel outInputChannel)  
     public int addWindow(Session session, IWindow client, int seq,
                WindowManager.LayoutParams attrs, int viewVisibility,
                Rect outContentInsets, InputChannel outInputChannel)

     由于这个方法比较长,就不贴了,只看其中最关键的地方,其中有这么一句话:

      win.attach();
    经过这么一分析,清楚了,SurfaceSession是WindowManagerService在addWindow的时候创建的。而
    Surface是在WIndowManagerService进行relayoutWindow时创建的。
  • 相关阅读:
    C4.5算法的学习笔记
    jQuery学习笔记(二)jQuery中DOM操作
    jQuery学习笔记(四)jQuery中的动画
    jQuery学习笔记(一)jQuery选择器
    编译JDK源代码,开启Debug信息[转]
    【转】如何debug没有源代码的class文件——eclipse+jad
    【转】JAVA的内省(introspector)与反射(reflection)
    Java中访问修饰符protected的权限 [转]
    [转]我是如何设计并实现一门程序设计语言——一门函数式编程语言Lucida的诞生
    不断重构
  • 原文地址:https://www.cnblogs.com/seven1979/p/4369597.html
Copyright © 2011-2022 走看看