目录
在上一篇的基础上实现共享纹理。
MainActivity
private void initView() {
picGlSurfaceView = (PicGlSurfaceView) findViewById(R.id.picGlSurfaceView);
llContent = (LinearLayout) findViewById(R.id.llContent);
//
picGlSurfaceView.getPicRender().setOnRenderCreateListener(new PicRender.OnRenderCreateListener() {
@Override
public void onCreate(final int textureId) {
//需要在主线程中
runOnUiThread(new Runnable() {
@Override
public void run() {
if (llContent.getChildCount() > 0) {
llContent.removeAllViews();
}
//动态添加
for (int i = 0; i < 3; i++) {
PicGlSurfaceViewMulti picSurface = new PicGlSurfaceViewMulti(MediaCodecTestActivity.this);
//设置共享的纹理
picSurface.setTextureId(textureId);
//使用自己的surface所以传入null,使用共享的eglcontext
picSurface.setSurfaceAndEglContext(null, picGlSurfaceView.getEglContext());
LinearLayout.LayoutParams layoutParams = new LinearLayout.LayoutParams(0, 300);
layoutParams.weight = 1;
layoutParams.topMargin = 10;
layoutParams.leftMargin = 10;
layoutParams.rightMargin = 10;
llContent.addView(picSurface, layoutParams);
}
}
});
}
});
}
PicGlSurfaceViewMulti
package com.example.opengl.eglpic;
import android.content.Context;
import android.util.AttributeSet;
import com.example.opengl.egl.MyGlSurfaceView;
public class PicGlSurfaceViewMulti extends MyGlSurfaceView {
private PicRenderMulti picRenderMulti;
public PicGlSurfaceViewMulti(Context context) {
this(context,null);
}
public PicGlSurfaceViewMulti(Context context, AttributeSet attrs) {
this(context, attrs,0);
}
public PicGlSurfaceViewMulti(Context context, AttributeSet attrs, int defStyleAttr) {
super(context, attrs, defStyleAttr);
picRenderMulti = new PicRenderMulti(context);
setRender(picRenderMulti);
}
public void setTextureId(int textureId){
if (picRenderMulti != null) {
picRenderMulti.setTextureId(textureId);
}
}
}
PicRenderMulti
package com.example.opengl.eglpic;
import android.content.Context;
import android.opengl.GLES20;
import com.example.opengl.R;
import com.example.opengl.egl.MyGlSurfaceView;
import com.example.opengl.egl.ShaderUtil;
import java.nio.ByteBuffer;
import java.nio.ByteOrder;
import java.nio.FloatBuffer;
public class PicRenderMulti implements MyGlSurfaceView.EGLRender {
private Context context;
private float[] vertexData = {
-1f, -1f,
1f, -1f,
-1f, 1f,
1f, 1f
};
private FloatBuffer vertexBuffer;
private float[] fragmentData = {
0f, 1f,
1f, 1f,
0f, 0f,
1f, 0f
};
private FloatBuffer fragmentBuffer;
private int program;
private int vPosition;
private int fPosition;
private int sampler;
private int vboId;
private int textureId;
private int index;
public void setTextureId(int textureId) {
this.textureId = textureId;
this.index = index;
}
public PicRenderMulti(Context context) {
this.context = context;
vertexBuffer = ByteBuffer.allocateDirect(vertexData.length * 4)
.order(ByteOrder.nativeOrder())
.asFloatBuffer()
.put(vertexData);
vertexBuffer.position(0);
fragmentBuffer = ByteBuffer.allocateDirect(fragmentData.length * 4)
.order(ByteOrder.nativeOrder())
.asFloatBuffer()
.put(fragmentData);
fragmentBuffer.position(0);
}
@Override
public void onSurfaceCreated() {
String vertexSource = ShaderUtil.readRawTxt(context, R.raw.vertex_shader);
String fragmentSource = ShaderUtil.readRawTxt(context, R.raw.fragment_shader);
program = ShaderUtil.createProgram(vertexSource, fragmentSource);
vPosition = GLES20.glGetAttribLocation(program, "v_Position");
fPosition = GLES20.glGetAttribLocation(program, "f_Position");
sampler = GLES20.glGetUniformLocation(program, "sTexture");
int[] vbos = new int[1];
GLES20.glGenBuffers(1, vbos, 0);
vboId = vbos[0];
GLES20.glBindBuffer(GLES20.GL_ARRAY_BUFFER, vboId);
GLES20.glBufferData(GLES20.GL_ARRAY_BUFFER, vertexData.length * 4 + fragmentData.length * 4, null, GLES20.GL_STATIC_DRAW);
GLES20.glBufferSubData(GLES20.GL_ARRAY_BUFFER, 0, vertexData.length * 4, vertexBuffer);
GLES20.glBufferSubData(GLES20.GL_ARRAY_BUFFER, vertexData.length * 4, fragmentData.length * 4, fragmentBuffer);
GLES20.glBindBuffer(GLES20.GL_ARRAY_BUFFER, 0);
}
@Override
public void onSurfaceChanged(int width, int height) {
GLES20.glViewport(0, 0, width, height);
}
@Override
public void onDrawFrame() {
GLES20.glClear(GLES20.GL_COLOR_BUFFER_BIT);
GLES20.glClearColor(1f, 0f, 0f, 1f);
GLES20.glUseProgram(program);
GLES20.glBindTexture(GLES20.GL_TEXTURE_2D, textureId);
GLES20.glBindBuffer(GLES20.GL_ARRAY_BUFFER, vboId);
GLES20.glEnableVertexAttribArray(vPosition);
GLES20.glVertexAttribPointer(vPosition, 2, GLES20.GL_FLOAT, false, 8,
0);
GLES20.glEnableVertexAttribArray(fPosition);
GLES20.glVertexAttribPointer(fPosition, 2, GLES20.GL_FLOAT, false, 8,
vertexData.length * 4);
GLES20.glDrawArrays(GLES20.GL_TRIANGLE_STRIP, 0, 4);
GLES20.glBindTexture(GLES20.GL_TEXTURE_2D, 0);
GLES20.glBindBuffer(GLES20.GL_ARRAY_BUFFER, 0);
}
}