簡體   English   中英

使用Android版NDK編寫OpenGL代碼

[英]using NDK for Android to write OpenGL code

所以這里是交易。 我已經在Windows [Win32]上使用OpenGL API大約3年了。 我在同一篇文章中編寫了多個着色器。

現在,我想在Android上移植我的項目。 我的問題是,如果要使用C ++ [NDK]編寫項目,並使用OpenGL ES,可以嗎?

我得到的簡短答案是“是”,但這是正確的方法嗎? 我最好使用Java嗎? 因為我基於基於VR的OpenGL應用程序性能是主要因素,所以我使用NDK是否會導致性能下降?

是的,這是多個問題,但它們指向類似的問題,將NDK用於實際項目是否可行。

取決於您使用C ++編寫多少應用程序以及使用Java編寫多少代碼。 每個JNI調用都有一個相關的開銷,因此在決定如何拆分Java代碼和本機代碼時,您可能需要牢記這一點(例如,用C ++編寫整個渲染循環將每幀只招致一個JNI調用,通過Java包裝器調用OpenGL API進行渲染循環可能會導致每幀數千個JNI調用)。 什么可能是“正確的”取決於您的特定要求。

至少,你需要得到無論是Surface (從SurfaceHolder由一個提供SurfaceView )或SurfaceTexture (從獲得TextureView ),並通過JNI傳遞到你的本地應用程序,在那里你可以使用ANativeWindow_fromSurfaceANativeWindow_fromSurfaceTexture (請參閱此處 )獲得一個本機窗口,您可以使用該窗口創建OpenGL ES表面和上下文。 您可能希望將JNI調用封裝在偵聽SurfaceHolderSurfaceTexture回調的Java類中。 例如:

public class GlSurfaceHolder {
    private SurfaceHolder mSurfaceHolder;
    private SurfaceHolder.Callback mSurfaceHolderCallback;

    public GlSurfaceHolder(SurfaceHolder surfaceHolder) {
        mSurfaceHolder = surfaceHolder;
        mSurfaceHolderCallback = new SurfaceHolder.Callback() {
            // JNI calls in here
        }

        mSurfaceHolder.addCallback(mSurfaceHolderCallback);
    }
};

如果不需要此級別的控制,則可以考慮使用GLSurfaceView ,它是一個SurfaceView ,可以管理自己的OpenGL ES曲面,上下文和渲染循環。 GLSurfaceView的缺點是,它不必要地耦合了表面上無關的事物的整個負載。 分離這些功能不僅從單一職責原則的角度來看更加整潔,而且還允許您潛在地在單獨的線程中執行渲染(這當然需要與UI線程同步,但可能會帶來性能上的好處)。

如果您甚至不關心在Java端運行的任何應用程序,則可以使用NativeActivity便利類,該類將前面提到的所有功能以及其他一些東西捆綁到Android Activity中。 這是快速而骯臟的選擇。

簡短的答案是,可以將NDK用於實際項目。 如果您使用NativeActivity,則可以擁有一個完全沒有Java代碼的應用程序。 許多游戲都是使用Unity引擎構建的,並且所有OpenGL都是以C ++編寫的,沒有任何性能抱怨。 實際上, 事實恰恰相反 ,但是在現實生活中,Java到GL包裝器的性能損失非常低。

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM