Android 在GLSurfaceView.Renderer中添加png纹理

Android 在GLSurfaceView.Renderer中添加png纹理,android,opengl-es,opengl-es-2.0,live-wallpaper,glsurfaceview,Android,Opengl Es,Opengl Es 2.0,Live Wallpaper,Glsurfaceview,我想从PNG图像中添加另一个纹理,它更像一个徽标,因此我希望它位于中间,背景中显示GLSurfaceView及其所有效果和模型。请看我精心制作的插图 --------------------------- | GLSurfaceView * | | | | | | | | * ----

我想从PNG图像中添加另一个纹理,它更像一个徽标,因此我希望它位于中间,背景中显示
GLSurfaceView
及其所有效果和模型。请看我精心制作的插图

    ---------------------------
    |      GLSurfaceView  *   |
    |                         |
    |                         |
    |                         |
    |  *   -------------      |
    |      |           |      |
    |      |    PNG    |      |
    |      |  Texture  |    * |
    |  *   |           |      |
    |      -------------      |
    |        *                |
    |                         |
    |                         |
    |    *             *      |
    ---------------------------

LEGEND: * = some good effects :D (pweew! pweew!)
我正在尝试使用
wallperservice
制作一张实时墙纸,它有一个扩展引擎类的子类,该类有一个扩展GLSurfaceView的子类,到目前为止,我拥有的是GLSurfaceView,它工作得很好

-添加-FlashWallperService

public class FlashWallpaperService extends WallpaperService {

    @Override
    public Engine onCreateEngine() {
        return new GLEngine();
    }

    public class GLEngine extends Engine {
        private FlashGLSurfaceView flashGLSurfaceView;

        @Override
        public void onCreate(SurfaceHolder surfaceHolder) {
            super.onCreate(surfaceHolder);
            flashGLSurfaceView = new FlashGLSurfaceView(FlashWallpaperService.this);
        }

        @Override
        public void onVisibilityChanged(boolean visible) {
            super.onVisibilityChanged(visible);
            if (visible) {
                flashGLSurfaceView.onResume();
            } else {
                flashGLSurfaceView.onPause();
            }
        }

        @Override
        public void onDestroy() {
            super.onDestroy();
            flashGLSurfaceView.onDestroy();
        }

        class FlashGLSurfaceView extends GLSurfaceView {
            private ActivityManager activityManager;
            private ConfigurationInfo configurationInfo;
            private boolean supportsEs2;
            public FlashGLSurfaceView(Context context) {
                super(context);
                if (!isInEditMode()) {
                    activityManager = (ActivityManager) context.getSystemService(Context.ACTIVITY_SERVICE);
                    configurationInfo = activityManager.getDeviceConfigurationInfo();
                    supportsEs2 = configurationInfo.reqGlEsVersion >= 0x20000;
                    if (supportsEs2) {
                        // Request an OpenGL ES 2.0 compatible context.
                        this.setEGLContextClientVersion(2);
                        // Set the renderer to our demo renderer, defined below.
                        FlashSystemRenderer mRenderer = new FlashSystemRenderer(this);
                        this.setRenderer(mRenderer);
                        this.setRenderMode(GLSurfaceView.RENDERMODE_CONTINUOUSLY);
                    } else {
                        if (!isInEditMode()) throw new UnsupportedOperationException();
                    }
                }
            }

            public FlashGLSurfaceView(Context context, AttributeSet attrs) {
                super(context, attrs);
                this.setEGLContextClientVersion(2);
                this.setEGLConfigChooser(8, 8, 8, 8, 16, 0);
                this.getHolder().setFormat(PixelFormat.TRANSLUCENT);
                this.setZOrderOnTop(false);
                if (!isInEditMode()) {
                    activityManager = (ActivityManager) context.getSystemService(Context.ACTIVITY_SERVICE);
                    configurationInfo = activityManager.getDeviceConfigurationInfo();
                    supportsEs2 = configurationInfo.reqGlEsVersion >= 0x20000;
                    if (supportsEs2) {
                        // Request an OpenGL ES 2.0 compatible context.
                        this.setEGLContextClientVersion(2);

                        // Set the renderer to our demo renderer, defined below.
                        FlashSystemRenderer mRenderer = new FlashSystemRenderer(this);
                        this.setRenderer(mRenderer);
                        this.setRenderMode(GLSurfaceView.RENDERMODE_CONTINUOUSLY);
                    } else {
                        if (!isInEditMode()) throw new UnsupportedOperationException();
                    }
                }
            }

            @Override
            public SurfaceHolder getHolder() {
                return getSurfaceHolder();
            }

            public void onDestroy() {
                super.onDetachedFromWindow();
            }

        }
    }
}
-添加-渲染器类

public class FlashSystemRenderer implements GLSurfaceView.Renderer {
public float ratio;
public int mvpMatrixHandle;
public int mvMatrixHandle = -1;
public int positionHandle;
public int normalHandle;
public int textureCoordinateHandle;
public int programHandle;
public int miscHandle;
public int sizeX = 35;
public int sizeY = 70;
public float mTime;
private GLSurfaceView mGlSurfaceView;
/**
 * Store the model matrix. This matrix is used to move models from object space (where each model can be thought
 * of being located at the center of the universe) to world space.
 */
private float[] mModelMatrix = new float[16];
/**
 * Store the view matrix. This can be thought of as our camera. This matrix transforms world space to eye space;
 * it positions things relative to our eye.
 */
private float[] mViewMatrix = new float[16];
/** Store the projection matrix. This is used to project the scene onto a 2D viewport. */
private float[] mProjectionMatrix = new float[16];
/** Allocate storage for the final combined matrix. This will be passed into the shader program. */
private float[] mMVPMatrix = new float[16];
private float[] mTemporaryMatrix = new float[16];
private int timeHandle;
private long mStartTime;
private int frames;
private long startTime;
private boolean mStart;
private long timePassed;
private float dt;
private long t_current;
private long t_prev;
private float dt_prev = 1;
private ValueAnimator animator;
private Bitmap mBitmap;
private FlashSystem mFlashSystem;
private Context context;
private int resolutionHandle;
private int mWidth;
private int mHeight;
private int timesRepeated;
private float delta;
private ExecutorService mExecutor = Executors.newSingleThreadExecutor();
public FlashSystemRenderer(GLSurfaceView glSurfaceView) {
    mGlSurfaceView = glSurfaceView;
    context = glSurfaceView.getContext();
}
@Override
public void onSurfaceCreated(GL10 gl10, EGLConfig eglConfig) {
    GLES20.glClearColor(0.0f, 0.0f, 0.0f, 0.0f);
    // Use culling to remove back faces.
    GLES20.glEnable(GLES20.GL_CULL_FACE);
    GLES20.glFrontFace(GLES20.GL_CW);
    // Enable depth testing
    GLES20.glEnable(GLES20.GL_DEPTH_TEST);
    // Position the eye in front of the origin.
    final float eyeX =  0.0f;
    final float eyeY =  0.0f;
    final float eyeZ =  0.0f;
    // We are looking toward the distance
    final float lookX =  0.0f;
    final float lookY =  0.0f;
    final float lookZ =  1.0f;
    // Set our up vector. This is where our head would be pointing were we holding the camera.
    final float upX = 0.0f;
    final float upY = 1.0f;
    final float upZ = 0.0f;
    Matrix.setLookAtM(mViewMatrix, 0, eyeX, eyeY, eyeZ, lookX, lookY, lookZ, upX, upY, upZ);
    final String vertexShader = RawResourceReader.readTextFileFromRawResource(context, R.raw.flash_vert);
    final String fragmentShader = RawResourceReader.readTextFileFromRawResource(context, R.raw.flash_frag);
    final int vertexShaderHandle = ShaderHelper.compileShader(GLES20.GL_VERTEX_SHADER, vertexShader);
    final int fragmentShaderHandle = ShaderHelper.compileShader(GLES20.GL_FRAGMENT_SHADER, fragmentShader);
    programHandle = ShaderHelper.createAndLinkProgram(vertexShaderHandle, fragmentShaderHandle,
            new String[]{"a_Position", "a_TexCoordinate", "a_TileXY"});
}
@Override
public void onSurfaceChanged(GL10 unused, int width, int height) {
    // Set the OpenGL viewport to the same size as the surface.
    GLES20.glViewport(0, 0, width, height);
    mWidth = width;
    mHeight = height;
    // Create a new perspective projection matrix. The height will stay the same
    // while the width will vary as per aspect ratio.
    final float ratio = (float) width / height;
    final float left = -ratio;
    @SuppressWarnings("UnnecessaryLocalVariable")
    final float right = ratio;
    final float bottom = -1.0f;
    final float top = 1.0f;
    final float near = 1.0f;
    final float far = 10.0f;
    this.ratio = ratio;
    Matrix.frustumM(mProjectionMatrix, 0, left, right, bottom, top, near, far);
    mStartTime = System.currentTimeMillis();
    mExecutor.execute(new FlashsGenerator(this));
}
@Override
public void onDrawFrame(GL10 gl10) {
    logFrame();
    drawGl();
    if (mFlashSystem != null) {
        mFlashSystem.render();
    }
}

private void drawGl() {
    GLES20.glClear(GLES20.GL_COLOR_BUFFER_BIT | GLES20.GL_DEPTH_BUFFER_BIT);
    GLES20.glUseProgram(programHandle);
    // Set program handles
    mvpMatrixHandle = GLES20.glGetUniformLocation(programHandle, "u_MVPMatrix");
    mvMatrixHandle = GLES20.glGetUniformLocation(programHandle, "u_MVMatrix");
    timeHandle = GLES20.glGetUniformLocation(programHandle, "u_Time");
    resolutionHandle = GLES20.glGetUniformLocation(programHandle, "u_Resolution");
    positionHandle = GLES20.glGetAttribLocation(programHandle, "a_Position");
    normalHandle = GLES20.glGetAttribLocation(programHandle, "a_Normal");
    textureCoordinateHandle = GLES20.glGetAttribLocation(programHandle, "a_TexCoordinate");
    miscHandle = GLES20.glGetAttribLocation(programHandle, "a_Misc");
    Matrix.setIdentityM(mModelMatrix, 0);
    Matrix.translateM(mModelMatrix, 0, 0.0f, 0.0f, 5f);
    Matrix.multiplyMM(mMVPMatrix, 0, mViewMatrix, 0, mModelMatrix, 0);
    // Pass in the modelview matrix.
    GLES20.glUniformMatrix4fv(mvMatrixHandle, 1, false, mMVPMatrix, 0);
    Matrix.multiplyMM(mTemporaryMatrix, 0, mProjectionMatrix, 0, mMVPMatrix, 0);
    System.arraycopy(mTemporaryMatrix, 0, mMVPMatrix, 0, 16);
    // Pass in the combined matrix.
    GLES20.glUniformMatrix4fv(mvpMatrixHandle, 1, false, mMVPMatrix, 0);
    // Pass in u_Time
    GLES20.glUniform1f(timeHandle, (System.currentTimeMillis() - mStartTime) / 3500f);
    // u_Resolution
    GLES20.glUniform2f(resolutionHandle, mWidth, mHeight);
    GLES20.glBlendFunc(GLES20.GL_SRC_ALPHA, GLES20.GL_ONE_MINUS_SRC_ALPHA);
    GLES20.glEnable(GLES20.GL_BLEND);
}
public void logFrame() {
    frames++;
    timePassed = (System.nanoTime() - startTime) / 1_000_000;
    if(timePassed >= 10_000) {
        frames = 0;
        startTime = System.nanoTime();
    }
}

public void onTouchEvent() {
    if (mStart) {
        reset();
    }
    mStart = !mStart;
    mStartTime = System.nanoTime();
}

private void reset() {
    if (animator != null) {
        animator.cancel();
    }
    mStartTime = 0;
    dt = 0;
    t_prev = 0;
}


public FlashSystem getFlashSystem() {
    return mFlashSystem;
}

public void setFlashSystem(final FlashSystem flashSystem) {
    mFlashSystem = flashSystem;
}

public void queue(Runnable runnable) {
    mGlSurfaceView.queueEvent(runnable);
}
}

-添加-flash_vert.glsl

uniform mat4 u_MVPMatrix;       // A constant representing the combined model/view/projection matrix.
uniform mat4 u_MVMatrix;        // A constant representing the combined model/view matrix.
uniform float u_Time;
uniform vec2 u_Resolution;

attribute vec4 a_Position; //initial
attribute vec2 a_TexCoordinate;
attribute vec4 a_Misc; //initial

varying vec2 v_TexCoordinate;
varying float v_Radius;

#define RADIUS 3.5

float rand( vec2 co )
{
   return fract(sin(dot(co.xy ,vec2(12.9898,78.233))) * 43758.5453);
}

void rotate( in float angle, inout vec2 vector )
{
    mat2 rotationMatrix = mat2( cos( angle ), -sin( angle ),
                sin( angle ),  cos( angle ));
                     vector *= rotationMatrix;
}

void main()
{
    // Transform the vertex into eye space.
    //v_Position = vec3(u_MVMatrix * a_Position);

    float aspect = u_Resolution.x / u_Resolution.y;

    // Pass through the texture coordinate.
    v_TexCoordinate = a_TexCoordinate;

    vec2 centerPos = a_Position.xy;

    float f = mix(1.0, a_Misc.t, u_Time);

    centerPos *= mod(f, RADIUS);

    float size = a_Misc.s;

    size = mix(0.0, size, mod(f, RADIUS)/RADIUS);

    vec2 relativePos = vec2(
      (a_TexCoordinate.s - 0.5) * 2.0 * size,
      (a_TexCoordinate.t - 0.5) * 2.0 * size
    );

    vec2 v = vec2(0.0, 1.0);


    vec4 pos = vec4(
    relativePos + centerPos,
      0.0,
      1.0
    );


    gl_Position = u_MVPMatrix * pos;

    v_Radius = size * 2.5;
}
-添加-flash\u frag.glsl

precision mediump float;
uniform sampler2D uTexture;
varying vec2 vTexPosition;
void main() {
  gl_FragColor = texture2D(uTexture, vTexPosition);
}

如果具有透明度/alpha的PNG纹理位于所有其他对象的顶部,如何从现有渲染器添加PNG纹理以将它们一起渲染?我在搜索中找到的所有东西都不起作用,有些不起作用,但它只显示PNG纹理

听起来像是要用
glTexImage2D()
将PNG转换为纹理,并在屏幕中央渲染?@fadden是的!:D找到了一些教程并实际实现了它们,但问题是背景上的GLSURFACHEVIEW没有显示,和/或被PNG纹理覆盖。不过我不能确定。然而,我尝试了另一种方法,在Engine类中添加ImageView(是的,一个UI元素),但同样的问题GLSurfaceView看不到