Преобразуйте это изображение в растровое изображение и нарисуйте его на GLSurfaceView
. Вы можете проверить условие в коде шейдера следующим образом.
vec4 color = texture2D(uTexture, vTexPosition);
if(color.r == 0.0 && color.g == 0.0 && color.b == 0.0)
color = vec4(1.0,0.5,0.5,1.0);
gl_FragColor = color;
Это полный GLRenderer
public class GLRenderer implements GLSurfaceView.Renderer {
private static final String TAG = "MyGLRenderer";
private float[] vertices = {
-1f, -1f,
1f, -1f,
-1f, 1f,
1f, 1f
};
private float[] textureVertices = {
0f, 1f,
1f, 1f,
0f, 0f,
1f, 0f
};
private final String vertexShaderCode =
"attribute vec4 aPosition;" +
"attribute vec2 aTexPosition;" +
"varying vec2 vTexPosition;" +
"void main() {" +
" gl_Position = aPosition;" +
" vTexPosition = aTexPosition;" +
"}";
private final String fragmentShaderCode =
"precision mediump float;" +
"uniform sampler2D uTexture;" +
"varying vec2 vTexPosition;" +
"void main() {\n" +
"vec4 color = texture2D(uTexture, vTexPosition);\n"+
"if(color.r == 0.0 && color.g == 0.0 && color.b == 0.0)\n"+
"color = vec4(1.0,0.5,0.5,1.0);"+
" gl_FragColor = color;" +
"}";
private FloatBuffer verticesBuffer;
private FloatBuffer textureBuffer;
private int vertexShader;
private int fragmentShader;
private int program;
private Bitmap bmp;
private int textures[] = new int[2];
// mMVPMatrix is an abbreviation for "Model View Projection Matrix"
private final float[] mMVPMatrix = new float[16];
private final float[] mProjectionMatrix = new float[16];
private final float[] mViewMatrix = new float[16];
private final float[] mRotationMatrix = new float[16];
public GLRenderer() {
bmp=Bitmap.createBitmap(513,912, Bitmap.Config.ARGB_8888);
}
@Override
public void onSurfaceCreated(GL10 gl, EGLConfig config) {
GLES20.glClearColor(0.0f, 0.0f, 0.0f, 1.0f);
checkGlError("glClearColor");
setup();
}
@Override
public void onSurfaceChanged(GL10 gl, int width, int height) {
GLES20.glViewport(0, 0, width, height);
float ratio = (float) width / height;
Matrix.frustumM(mProjectionMatrix, 0, -ratio, ratio, -1, 1, 3, 7);
}
@Override
public void onDrawFrame(GL10 gl) {
Log.d("Drawing_Frame","Working");
float[] scratch = new float[16];
// Draw background color
GLES20.glClear(GLES20.GL_COLOR_BUFFER_BIT | GLES20.GL_DEPTH_BUFFER_BIT);
// Set the camera position (View matrix)
Matrix.setLookAtM(mViewMatrix, 0, 0, 0, -3, 0f, 0f, 0f, 0f, 1.0f, 0.0f);
// Calculate the projection and view transformation
Matrix.multiplyMM(mMVPMatrix, 0, mProjectionMatrix, 0, mViewMatrix, 0);
// Draw Bitmap
drawBinaryImage(bmp,textures[0]);
Matrix.setRotateM(mRotationMatrix, 0, 0, 0, 0, 1.0f);
Matrix.multiplyMM(scratch, 0, mMVPMatrix, 0, mRotationMatrix, 0);
}
private void setup(){
GLES20.glGenTextures(2, textures, 0);
GLES20.glBindTexture(GLES20.GL_TEXTURE_2D, textures[0]);
GLES20.glTexParameteri(GLES20.GL_TEXTURE_2D, GLES20.GL_TEXTURE_MIN_FILTER, GLES20.GL_LINEAR);
GLES20.glTexParameteri(GLES20.GL_TEXTURE_2D, GLES20.GL_TEXTURE_MAG_FILTER, GLES20.GL_LINEAR);
GLES20.glTexParameteri(GLES20.GL_TEXTURE_2D, GLES20.GL_TEXTURE_WRAP_S, GLES20.GL_CLAMP_TO_EDGE);
GLES20.glTexParameteri(GLES20.GL_TEXTURE_2D, GLES20.GL_TEXTURE_WRAP_T, GLES20.GL_CLAMP_TO_EDGE);
GLUtils.texImage2D(GLES20.GL_TEXTURE_2D, 0, bmp, 0);
//GLES20.glBindTexture(GL);
initializeBuffers();
initializeProgram();
}
private void initializeBuffers() {
ByteBuffer buff = ByteBuffer.allocateDirect(vertices.length * 4);
buff.order(ByteOrder.nativeOrder());
verticesBuffer = buff.asFloatBuffer();
verticesBuffer.put(vertices);
verticesBuffer.position(0);
buff = ByteBuffer.allocateDirect(textureVertices.length * 4);
buff.order(ByteOrder.nativeOrder());
textureBuffer = buff.asFloatBuffer();
textureBuffer.put(textureVertices);
textureBuffer.position(0);
}
private void initializeProgram() {
vertexShader = GLES20.glCreateShader(GLES20.GL_VERTEX_SHADER);
GLES20.glGetShaderInfoLog(vertexShader);
checkGlError("glCreateShader");
GLES20.glShaderSource(vertexShader, vertexShaderCode);
GLES20.glCompileShader(vertexShader);
fragmentShader = GLES20.glCreateShader(GLES20.GL_FRAGMENT_SHADER);
GLES20.glShaderSource(fragmentShader, fragmentShaderCode);
GLES20.glCompileShader(fragmentShader);
program = GLES20.glCreateProgram();
GLES20.glAttachShader(program, vertexShader);
GLES20.glAttachShader(program, fragmentShader);
GLES20.glLinkProgram(program);
checkGlError("glLinkProgram");
}
public void updateTexture(Bitmap bmp){
GLUtils.texImage2D(GLES20.GL_TEXTURE_2D, 0, bmp, 0);
}
private void drawBinaryImage(Bitmap bmp,int texture){
GLES20.glBindFramebuffer(GLES20.GL_FRAMEBUFFER, 0);
GLES20.glUseProgram(program);
//Changes Here original Line GLES20.glDisable(GLES20.GL_BLEND);
GLES20.glDisable(GLES20.GL_CULL_FACE);
GLES20.glDisable(GLES20.GL_DEPTH_TEST);
GLES20.glEnable(GLES20.GL_BLEND);
GLES20.glBlendFunc(GLES20.GL_ONE, GLES20.GL_ONE);
int positionHandle = GLES20.glGetAttribLocation(program, "aPosition");
int textureHandle = GLES20.glGetUniformLocation(program, "uTexture");
int texturePositionHandle = GLES20.glGetAttribLocation(program, "aTexPosition");
//Log.d("GL_SETUP",positionHandle+" , "+textureHandle);
GLES20.glVertexAttribPointer(texturePositionHandle, 2, GLES20.GL_FLOAT, false, 0, textureBuffer);
GLES20.glEnableVertexAttribArray(texturePositionHandle);
GLES20.glActiveTexture(GLES20.GL_TEXTURE0);
GLES20.glBindTexture(GLES20.GL_TEXTURE_2D, texture);
Log.d("FILTER_APPLY","Applying");
GLES20.glTexParameteri(GLES20.GL_TEXTURE_2D, GLES20.GL_TEXTURE_MAG_FILTER,GLES20.GL_LINEAR);
GLES20.glUniform1i(textureHandle, 0);
GLES20.glVertexAttribPointer(positionHandle, 2, GLES20.GL_FLOAT, false, 0, verticesBuffer);
GLES20.glEnableVertexAttribArray(positionHandle);
GLES20.glClear(GLES20.GL_COLOR_BUFFER_BIT);
GLES20.glDrawArrays(GLES20.GL_TRIANGLE_STRIP, 0, 4);
checkGlError("glDrawArrays");
}
public void setBitmap(Bitmap bitmap){
updateTexture(bitmap);
this.bmp = bitmap;
}
public static void checkGlError(String glOperation) {
int error;
while ((error = GLES20.glGetError()) != GLES20.GL_NO_ERROR) {
Log.e(TAG, glOperation + ": glError " + error);
throw new RuntimeException(glOperation + ": glError " + error);
}
}
}
Используйте этот рендерер с GlSurfaceView
Вот основная активность класс
public class MainActivity extends AppCompatActivity {
FrameLayout glView;
private GLRenderer renderer;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
glView = findViewById(R.id.glview);
setupGL();
}
private void setupGL(){
renderer = new GLRenderer();
//MyGlSurfaceView glSurfaceView = new MyGlSurfaceView(this,renderer);
GLSurfaceView glSurfaceView = new GLSurfaceView(this);
glSurfaceView.setEGLContextClientVersion(2);
glSurfaceView.setRenderer(renderer);
glView.addView(glSurfaceView);
produceFrame();
}
private void produceFrame(){
Bitmap bmp = BitmapFactory.decodeResource(getResources(),R.drawable.sample);
renderer.setBitmap(bmp);
}
Вы можете проверить этот для полного проекта.