Android-NDK:native-media
項目目錄
CMakeLists.txt
cmake_minimum_required(VERSION 3.4.1)set(CMAKE_C_FLAGS "${CMAKE_C_FLAGS} -Wall -UNDEBUG")add_library(native-media-jni SHAREDandroid_fopen.cnative-media-jni.c)# Include libraries needed for native-media-jni lib target_link_libraries(native-media-jniandroidlogOpenMAXAL)鏈接了OpenMaxAL的庫。
android_fopen.c
return funopen(asset, android_read, android_write, android_seek, android_close); The calling conventions of readfn, writefn, seekfn and closefn must matchthose, respectively, of read(2), write(2), lseek(2), and close(2) withthe single exception that they are passed the cookie argument specifiedto funopen() in place of the traditional file descriptor argument.MySurfaceView.java
1)定義GLsurface的渲染器
class MyRenderer implements GLSurfaceView.Renderer, SurfaceTexture.OnFrameAvailableListener2)構造方法
分配本地Direct buffer,可以減少內存的復制。
那么為什么創建DirectByteBuffer比HeapByteBuffer性能差卻還使用DirectByteBuffer呢?
答:創建DirectByteBuffer的確不如HeapByteBuffer快,但是本地IO(從操作系統本地獲取數據,比如FileChannel、SocketChannel網絡數據)時,使用DirectByteBuffer比HeapByteBuffer少復制一次(java堆內存復制到操作系統內存,具體請繼續看)
————————————————
版權聲明:本文為CSDN博主「我叫周利東」的原創文章,遵循CC 4.0 BY-SA版權協議,轉載請附上原文出處鏈接及本聲明。
原文鏈接:https://blog.csdn.net/qq_36951116/article/details/87185240
3)onSurfaceCreated方法
public void onSurfaceCreated(GL10 glUnused, EGLConfig config) { /* Set up alpha blending and an Android background color */ GLES20.glEnable(GLES20.GL_BLEND);//啟動混合,實現半透明的效果 /* GL_ONE:??????表示使用1.0作為因子,實際上相當于完全的使用了這種顏色參與混合運算。 GL_SRC_ALPHA:表示使用源顏色的alpha值來作為因子。 GL_DST_ALPHA:表示使用目標顏色的alpha值來作為因子。 GL_ONE_MINUS_SRC_ALPHA:表示用1.0減去源顏色的alpha值來作為因子(1-alpha)。 GL_ONE_MINUS_DST_ALPHA:表示用1.0減去目標顏色的alpha值來作為因子。 除 此以外,還有GL_SRC_COLOR(把源顏色的四個分量分別作為因子的四個分量)、GL_ONE_MINUS_SRC_COLOR、 GL_DST_COLOR、GL_ONE_MINUS_DST_COL */ GLES20.glBlendFunc(GLES20.GL_SRC_ALPHA, GLES20.GL_ONE_MINUS_SRC_ALPHA); //改變背景顏色 GLES20.glClearColor(0.643f, 0.776f, 0.223f, 1.0f);//創建著色器的程序
{
? ?//首先,加載定點著色器
? {
private int loadShader(int shaderType, String source) {int shader = GLES20.glCreateShader(shaderType);if (shader != 0) { //加載著色器程序GLES20.glShaderSource(shader, source); //編譯著色器GLES20.glCompileShader(shader);int[] compiled = new int[1];GLES20.glGetShaderiv(shader, GLES20.GL_COMPILE_STATUS, compiled, 0);if (compiled[0] == 0) {Log.e(TAG, "Could not compile shader " + shaderType + ":");Log.e(TAG, GLES20.glGetShaderInfoLog(shader));GLES20.glDeleteShader(shader);shader = 0;}}return shader; }}
int vertexShader = loadShader(GLES20.GL_VERTEX_SHADER, vertexSource); if (vertexShader == 0) {return 0; } //然后,加載片元著色器 int pixelShader = loadShader(GLES20.GL_FRAGMENT_SHADER, fragmentSource); if (pixelShader == 0) {return 0; }//創建程序
int program = GLES20.glCreateProgram(); if (program != 0) { //程序綁定,定點著色器GLES20.glAttachShader(program, vertexShader);checkGlError("glAttachShader"); //綁定片元這著色器GLES20.glAttachShader(program, pixelShader);checkGlError("glAttachShader"); //連接GLES20.glLinkProgram(program);int[] linkStatus = new int[1];GLES20.glGetProgramiv(program, GLES20.GL_LINK_STATUS, linkStatus, 0);if (linkStatus[0] != GLES20.GL_TRUE) {Log.e(TAG, "Could not link program: ");Log.e(TAG, GLES20.glGetProgramInfoLog(program));GLES20.glDeleteProgram(program);program = 0;} }}
mProgram = createProgram(mVertexShader, mFragmentShader); if (mProgram == 0) { return; }
//獲取定點位置
maPositionHandle = GLES20.glGetAttribLocation(mProgram, "aPosition"); checkGlError("glGetAttribLocation aPosition"); if (maPositionHandle == -1) {throw new RuntimeException("Could not get attrib location for aPosition"); }//獲取紋理坐標
maTextureHandle = GLES20.glGetAttribLocation(mProgram, "aTextureCoord"); checkGlError("glGetAttribLocation aTextureCoord"); if (maTextureHandle == -1) {throw new RuntimeException("Could not get attrib location for aTextureCoord"); }分別獲取相應的矩陣
muMVPMatrixHandle = GLES20.glGetUniformLocation(mProgram, "uMVPMatrix"); muSTMatrixHandle = GLES20.glGetUniformLocation(mProgram, "uSTMatrix"); int[] textures = new int[1]; // glGenTextures函數根據紋理參數返回n個紋理索引 GLES20.glGenTextures(1, textures, 0);mTextureID = textures[0]; //紋理進行綁定 GLES20.glBindTexture(GL_TEXTURE_EXTERNAL_OES, mTextureID); checkGlError("glBindTexture mTextureID");//設置紋理放大縮小和邊界的方式
GLES20.glTexParameterf(GL_TEXTURE_EXTERNAL_OES, GLES20.GL_TEXTURE_MIN_FILTER,GLES20.GL_NEAREST);創建了一個surface
mSurface = new SurfaceTexture(mTextureID); mSurface.setOnFrameAvailableListener(this); /* void setLookAtM (float[] rm , int rmOffset ,float eyeX , float eyeY , float eyeZ , float centerX,float centerY , float centerZ , float upX , float upY , float upZ )在世界坐標系下,設置眼鏡觀察點的位置,設置視圖中心的位置,設置某個坐標軸方向為屏幕豎直向上的向量(不清楚可見第3節)。 參數rm是待設定的矩陣數組,它應為4×4的矩陣,即大小為16的數組;參數rmOffset為啟用數組的偏移量,一般設為0;參數eyeX,eyeY和eyeZ為人眼在世界坐標系的位置。參數centerX,centerY和centerZ為模型中心在世界坐標系中的位置;eyeX,eyeY和eyeZ所確定的點與centerX,centerY和centerZ所確定的點構成了視線;參數upX,upY和upZ決定哪個坐標軸豎直向上,且該向量與視線是垂直的,可理解為人正常平視物體時,頭頂所指方向為豎直向上向量,視線此刻與該向量垂直的 ———————————————— 版權聲明:本文為CSDN博主「lyzirving」的原創文章,遵循CC 4.0 BY-SA版權協議,轉載請附上原文出處鏈接及本聲明。 原文鏈接:https://blog.csdn.net/lyzirving/article/details/79022445 */Matrix.setLookAtM(mVMatrix, 0, 0, 0, 4f, 0f, 0f, 0f, 0f, 1.0f, 0.0f);synchronized(this) {updateSurface = false; }4) 定點和片元著色器
private final String mVertexShader ="uniform mat4 uMVPMatrix;\n" +"uniform mat4 uSTMatrix;\n" +"attribute vec4 aPosition;\n" +"attribute vec4 aTextureCoord;\n" +"varying vec2 vTextureCoord;\n" +"void main() {\n" +" gl_Position = uMVPMatrix * aPosition;\n" +" vTextureCoord = (uSTMatrix * aTextureCoord).xy;\n" +"}\n";private final String mFragmentShader ="#extension GL_OES_EGL_image_external : require\n" +"precision mediump float;\n" +"varying vec2 vTextureCoord;\n" +"uniform samplerExternalOES sTexture;\n" +"void main() {\n" +" gl_FragColor = texture2D(sTexture, vTextureCoord);\n" +"}\n";5)當onFrameAvaliable時,進行onDrawFrame
public void onDrawFrame(GL10 glUnused)//更新texImagehttps://blog.csdn.net/lyzirving/article/details/79051437
synchronized(this) {if (updateSurface) {mSurface.updateTexImage(); //獲取紋理坐標mSurface.getTransformMatrix(mSTMatrix);updateSurface = false;} }GLES會情況深度緩沖
GLES20.glClear( GLES20.GL_DEPTH_BUFFER_BIT | GLES20.GL_COLOR_BUFFER_BIT); GLES20.glUseProgram(mProgram); checkGlError("glUseProgram"); GLES20.glActiveTexture(GLES20.GL_TEXTURE0); GLES20.glBindTexture(GL_TEXTURE_EXTERNAL_OES, mTextureID); mVertices.position(VERTICES_DATA_POS_OFFSET); GLES20.glVertexAttribPointer(maPositionHandle, 3, GLES20.GL_FLOAT, false,VERTICES_DATA_STRIDE_BYTES, mVertices); checkGlError("glVertexAttribPointer maPosition"); GLES20.glEnableVertexAttribArray(maPositionHandle); checkGlError("glEnableVertexAttribArray maPositionHandle");mVertices.position(VERTICES_DATA_UV_OFFSET); GLES20.glVertexAttribPointer(maTextureHandle, 3, GLES20.GL_FLOAT, false,VERTICES_DATA_STRIDE_BYTES, mVertices); checkGlError("glVertexAttribPointer maTextureHandle"); GLES20.glEnableVertexAttribArray(maTextureHandle); checkGlError("glEnableVertexAttribArray maTextureHandle");Matrix.multiplyMM(mMVPMatrix, 0, mVMatrix, 0, mMMatrix, 0); Matrix.multiplyMM(mMVPMatrix, 0, mProjMatrix, 0, mMVPMatrix, 0);GLES20.glUniformMatrix4fv(muMVPMatrixHandle, 1, false, mMVPMatrix, 0); GLES20.glUniformMatrix4fv(muSTMatrixHandle, 1, false, mSTMatrix, 0);//矩形渲染 GLES20.glDrawArrays(GLES20.GL_TRIANGLE_STRIP, 0, 4); checkGlError("glDrawArrays");?
?
總結
以上是生活随笔為你收集整理的Android-NDK:native-media的全部內容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: Android-NDK-hello-jn
- 下一篇: Android-NDK-audio-ec