Herramientas de usuario

Herramientas del sitio


wiki2:oglpipeline

Diferencias

Muestra las diferencias entre dos versiones de la página.

Enlace a la vista de comparación

Próxima revisión
Revisión previa
wiki2:oglpipeline [2015/11/20 19:20]
alfred creado
wiki2:oglpipeline [2020/05/09 09:25] (actual)
Línea 1: Línea 1:
 ====== OpenGL Pipeline ====== ====== OpenGL Pipeline ======
 +===== OpenGL Pipeline Básico =====
 +
 +==== Load pixels in memory ====
 +
 +=== Android version ===
 +
 +<code java>
 +float[] tableVerticesWithTriangles = {
 +        // Triangle 1
 +        0, 0.5f,
 +        -0.5f, ​ 0,
 +        0.5f,  0,
 +
 +        // Triangle 2
 +        0, 0,
 +        0.5f, -0.5f,
 +        -0.5f, ​ -0.5f
 +};
 +
 +vertexData = ByteBuffer
 +        .allocateDirect(tableVerticesWithTriangles.length * BYTES_PER_FLOAT)
 +        .order(ByteOrder.nativeOrder())
 +        .asFloatBuffer();​
 +
 +vertexData.put(tableVerticesWithTriangles);​
 +</​code>​
 +
 +==== Change the area where we are gonna render ====
 +
 +<code java>
 +@Override
 +public void onSurfaceChanged(GL10 glUnused, int width, int height) {
 +    glViewport(0,​ 0, width, height);
 +}
 +</​code>​
 +
 +==== Coding vertex shader ====
 +
 +<code java>
 +attribute vec4 a_Position;
 +void main()
 +{
 +    gl_Position = a_Position;
 +    gl_PointSize = 10.0;
 +}
 +</​code>​
 +
 +==== Coding fragment shader ====
 +
 +<​code>​
 +precision mediump float;
 +uniform vec4 u_Color;
 +void main()
 +{
 +    gl_FragColor = u_Color;
 +}
 +</​code>​
 +
 +==== Compiling shaders ====
 +
 +<code java>
 +private int compileShader(int type, String shaderCode) {
 +    final int shaderObjectId = glCreateShader(type);​
 +    if (shaderObjectId == 0) {
 +        Log.w(TAG, "Could not create new shader."​);​
 +        return 0;
 +    }
 +
 +    glShaderSource(shaderObjectId,​ shaderCode);​
 +    glCompileShader(shaderObjectId);​
 +    final int[] compileStatus = new int[1];
 +    glGetShaderiv(shaderObjectId,​ GL_COMPILE_STATUS,​ compileStatus,​ 0);
 +
 +    Log.v(TAG, "​Results of compiling source:"​ + "​\n"​ + shaderCode + "​\n:" ​ + glGetShaderInfoLog(shaderObjectId));​
 +
 +    if (compileStatus[0] == 0) {
 +        glDeleteShader(shaderObjectId);​
 +        Log.w(TAG, "​Compilation of shader failed."​);​
 +        return 0;
 +    }
 +    Log.w(TAG, "​Compilation of shader was good."​);​
 +    return shaderObjectId;​
 +}
 +</​code>​
 +
 +==== Link and use the shader program ====
 +
 +<code java>
 +public int linkProgram(int vertexShaderId,​ int fragmentShaderId) {
 +    final int programObjectId = glCreateProgram();​
 +    if (programObjectId == 0) {
 +        Log.w(TAG, "Could not create new program"​);​
 +        return 0;
 +    }
 +
 +    glAttachShader(programObjectId,​ vertexShaderId);​
 +    glAttachShader(programObjectId,​ fragmentShaderId);​
 +    glLinkProgram(programObjectId);​
 +
 +    final int[] linkStatus = new int[1];
 +    glGetProgramiv(programObjectId,​ GL_LINK_STATUS,​ linkStatus, 0);
 +    Log.v(TAG, "​Results of linking program:​\n"​ + glGetProgramInfoLog(programObjectId));​
 +    if (linkStatus[0] == 0) {
 +        glDeleteProgram(programObjectId);​
 +        Log.w(TAG, "​Linking of program failed."​);​
 +        return 0;
 +    }
 +
 +    glValidateProgram(programObjectId);​
 +    final int[] validateStatus = new int[1];
 +    glGetProgramiv(programObjectId,​ GL_VALIDATE_STATUS,​ validateStatus,​ 0);
 +    Log.v(TAG, "​Results of validating program: " + validateStatus[0]
 +            + "​\nLog:"​ + glGetProgramInfoLog(programObjectId));​
 +    if (validateStatus[0] == 0) {
 +        Log.w(TAG, "​Validation program failed."​);​
 +        return 0;
 +    }
 +
 +    return programObjectId;​
 +}
 +</​code>​
 +
 +==== Initialize values ====
 +
 +  * Set the color to clear the screen
 +  * Obtain the shaders code in string format
 +  * Link and use the shader program
 +  * As we are working with fixed triangles, assign shader variable values
 +
 +<code java>
 +glClearColor(0.0f,​ 0.0f, 0.0f, 0.0f);
 +
 +String vertexShaderSource = Utils.ResourcesReader(context,​ R.raw.vertex);​
 +String fragmentShaderSource = Utils.ResourcesReader(context,​ R.raw.fragment);​
 +
 +int vertexShader = compileShader(GL_VERTEX_SHADER,​ vertexShaderSource);​
 +int fragmentShader = compileShader(GL_FRAGMENT_SHADER,​ fragmentShaderSource);​
 +program = linkProgram(vertexShader,​ fragmentShader);​
 +glUseProgram(program);​
 +
 +uColorLocation = glGetUniformLocation(program,​ U_COLOR);
 +aPositionLocation = glGetAttribLocation(program,​ A_POSITION);​
 +vertexData.position(0);​
 +glVertexAttribPointer(aPositionLocation,​ POSITION_COMPONENT_COUNT,​ GL_FLOAT,
 +        false, 0, vertexData);​
 +glEnableVertexAttribArray(aPositionLocation);​
 +</​code>​
 +
 +==== Render ====
 +
 +
 +<code java>
 +glClear(GL_COLOR_BUFFER_BIT);​
 +
 +glUniform4f(uColorLocation,​ 1.0f, 0f, 0f, 1.0f);
 +glDrawArrays(GL_TRIANGLES,​ 0, 3);
 +
 +glUniform4f(uColorLocation,​ 0.0f, 0f, 1f, 1.0f);
 +glDrawArrays(GL_TRIANGLES,​ 3, 3);
 +</​code>​
 +
 +==== Functional examples ====
 +
 +  * {{:​wiki2:​ogl:​two-triangles.zip|}}
 +===== Color =====
 +
 +==== Define vertices, color and indexs ====
 +
 +<code java>
 +float[] tableVerticesWithTriangles = {
 +        // x, y          r,g,b
 +        0, 0.5f,         ​1,​0,​0,​
 +        -0.5f, ​ 0,       ​0,​1,​0,​
 +        0.5f,  0,        0,0,1
 +};
 +
 +vertexData = ByteBuffer
 +        .allocateDirect(tableVerticesWithTriangles.length * BYTES_PER_FLOAT)
 +        .order(ByteOrder.nativeOrder())
 +        .asFloatBuffer();​
 +vertexData.put(tableVerticesWithTriangles);​
 +
 +byte[] tableIndices = {0, 1, 2};
 +indexArray =  ByteBuffer.allocateDirect(3).put(tableIndices);​
 +</​code>​
 +
 +==== Shaders ====
 +
 +=== Vertex Shader ===
 +<​code>​
 +attribute vec4 a_Position;  ​
 +attribute vec4 a_Color;
 +
 +varying vec4 v_Color;
 +
 +void main() ​                   ​
 +{                            ​
 +    v_Color = a_Color;
 +    gl_Position = a_Position;
 +}
 +</​code>​
 +
 +=== Fragment Shader ===
 +<​code>​
 +precision mediump float;
 +varying vec4 v_Color; ​        ​
 +  ​
 +void main() ​                  
 +{                             
 +    gl_FragColor = v_Color; ​                                
 +}
 +</​code>​
 +
 +==== Render ====
 +
 +  * Obtain the attributes location for color and position.
 +  * Write color and position (in this case this step could be performed only once).
 +  * Enable them.
 +  * Draw them.
 +
 +<code java>
 +// next step is really important in java
 +vertexData.position(0);​
 +indexArray.position(0);​
 +
 +glClear(GL_COLOR_BUFFER_BIT);​
 +
 +aColorLocation = glGetAttribLocation(program,​ A_COLOR);
 +aPositionLocation = glGetAttribLocation(program,​ A_POSITION);​
 +
 +
 +glVertexAttribPointer(aPositionLocation,​ POSITION_COMPONENT_COUNT,​ GL_FLOAT,
 +        false, STRIDE, vertexData);​
 +glEnableVertexAttribArray(aPositionLocation);​
 +
 +vertexData.position(POSITION_COMPONENT_COUNT);​
 +glVertexAttribPointer(aColorLocation,​ COLOR_COMPONENT_COUNT,​ GL_FLOAT,
 +        false, STRIDE, vertexData);​
 +glEnableVertexAttribArray(aColorLocation);​
 +
 +glDrawElements(GL_TRIANGLES,​ 3, GL_UNSIGNED_BYTE,​ indexArray);​
 +
 +glDisableVertexAttribArray(aPositionLocation);​
 +glDisableVertexAttribArray(aColorLocation);​
 +</​code>​
 +
 +=== Constant values ===
 +<code java>
 +private static final int BYTES_PER_FLOAT = 4;
 +private static final int POSITION_COMPONENT_COUNT = 2;
 +private static final int COLOR_COMPONENT_COUNT = 3;
 +private static final int STRIDE = (POSITION_COMPONENT_COUNT + COLOR_COMPONENT_COUNT) * BYTES_PER_FLOAT;​
 +</​code>​
 +
 +==== Example ====
 +
 +{{:​wiki2:​ogl:​color.zip|Example}}
 +===== Transformaciones y proyecciones =====
 +
 +  * {{:​wiki2:​ogl:​tutorial_3_matrices.pdf|Explicacion de matrices y proyecciones}}
 +  * {{:​wiki2:​ogl:​objectoriented.matrix.zip|Ejemplo de matrices y orientación a objetos en OpenGL ES}}
 +
 +===== Texturas =====
 +
 +==== Cargar texturas ====
 +
 +  - Read the texture.
 +  - Bind the texture.
 +  - Set filtering: a default must be set, or the texture will be black.
 +  - Load the bitmap into the bound texture with ''​texImage2D''​.
 +  - Unbind from the texture with ''​glBindTexture(GL_TEXTURE_2D,​ 0)''​.
 +
 +<code java>
 +public static int loadTexture(Context context, int resourceId) {
 +    final int[] textureObjectIds = new int[1];
 +    glGenTextures(1,​ textureObjectIds,​ 0);
 +    if (textureObjectIds[0] == 0) {
 +        Log.w(TAG, "Could not generate a new OpenGL texture object."​);​
 +        return 0;
 +    }
 +
 +    final BitmapFactory.Options options = new BitmapFactory.Options();​
 +    options.inScaled = false;
 +    final Bitmap bitmap = BitmapFactory.decodeResource(context.getResources(),​ resourceId, options);
 +    if (bitmap == null) {
 +        Log.w(TAG, "​Resource ID " + resourceId + " could not be decoded."​);​
 +        glDeleteTextures(1,​ textureObjectIds,​ 0);
 +        return 0;
 +    }
 +    glBindTexture(GL_TEXTURE_2D,​ textureObjectIds[0]);​
 +
 +    glTexParameterf(GL_TEXTURE_2D,​ GL_TEXTURE_MIN_FILTER,​ GL_NEAREST);​
 +    glTexParameterf(GL_TEXTURE_2D,​ GL_TEXTURE_MAG_FILTER,​ GL_LINEAR);
 +    glTexParameteri(GL_TEXTURE_2D,​ GL_TEXTURE_WRAP_S,​ GL_REPEAT);
 +    glTexParameteri(GL_TEXTURE_2D,​ GL_TEXTURE_WRAP_T,​ GL_REPEAT);
 +
 +    texImage2D(GL_TEXTURE_2D,​ 0, bitmap, 0);
 +    glBindTexture(GL_TEXTURE_2D,​ 0);
 +    bitmap.recycle();​
 +
 +    Log.w(TAG, "​Texture loaded"​);​
 +
 +    return textureObjectIds[0];​
 +}
 +</​code>​
 +
 +Podríamos cargar mipmaps:
 +<code java>
 +glTexParameteri(GL_TEXTURE_2D,​ GL_TEXTURE_MIN_FILTER,​ GL_LINEAR_MIPMAP_LINEAR);​
 +glTexParameteri(GL_TEXTURE_2D,​ GL_TEXTURE_MAG_FILTER,​ GL_LINEAR);
 +glGenerateMipmap(GL_TEXTURE_2D);​
 +</​code>​
 +
 +==== Shaders ====
 +=== Vertex ===
 +<​code>​
 +attribute vec4 a_Position;
 +attribute vec2 a_TextureCoordinates;​
 +varying vec2 v_TextureCoordinates;​
 +
 +void main()
 +{
 +    v_TextureCoordinates = a_TextureCoordinates;​
 +    gl_Position = a_Position;
 +}
 +</​code>​
 +
 +=== Fragment ===
 +<​code>​
 +precision mediump float;
 +uniform sampler2D u_TextureUnit;​
 +varying vec2 v_TextureCoordinates;​
 +
 +void main()
 +{
 +    gl_FragColor = texture2D(u_TextureUnit,​ v_TextureCoordinates);​
 +}
 +</​code>​
 +
 +==== When render ====
 +<code java>
 +vertexData.position(0);​
 +indexArray.position(0);​
 +
 +glClear(GL_COLOR_BUFFER_BIT);​
 +
 +glVertexAttribPointer(aPositionLocation,​ POSITION_COMPONENT_COUNT,​ GL_FLOAT,
 +        false, STRIDE, vertexData);​
 +
 +vertexData.position(POSITION_COMPONENT_COUNT);​
 +glVertexAttribPointer(aTextCoordLocation,​ TEXTURE_COORDINATES_COMPONENT_COUNT,​ GL_FLOAT,
 +        false, STRIDE, vertexData);​
 +
 +glEnableVertexAttribArray(aPositionLocation);​
 +glEnableVertexAttribArray(aTextCoordLocation);​
 +
 +glActiveTexture(GL_TEXTURE0);​
 +glBindTexture(GL_TEXTURE_2D,​ texture);
 +glUniform1i(uTextureUnitLocation,​ 0);
 +
 +glDrawElements(GL_TRIANGLES,​ 3, GL_UNSIGNED_BYTE,​ indexArray);​
 +
 +glDisableVertexAttribArray(aPositionLocation);​
 +glDisableVertexAttribArray(aTextCoordLocation);​
 +</​code>​
 +
 +Setting these values:
 +<code java>
 +float[] tableVerticesWithTriangles = {
 +        // x, y          s,t
 +        0, 0.5f,         ​0.5f,​0,​
 +        -0.5f, ​ 0,       0,1,
 +        0.5f,  0,        1,1
 +};
 +</​code>​
 +
 +And these constants:
 +<code java>
 +private static final int BYTES_PER_FLOAT = 4;
 +private static final int POSITION_COMPONENT_COUNT = 2;
 +private static final int TEXTURE_COORDINATES_COMPONENT_COUNT = 2;
 +private static final int STRIDE = (POSITION_COMPONENT_COUNT + TEXTURE_COORDINATES_COMPONENT_COUNT) * BYTES_PER_FLOAT;​
 +</​code>​
 +
 +==== Code ====
 +  * {{:​wiki2:​ogl:​textures.zip|}}
 +===== Luces =====
  
wiki2/oglpipeline.1448047216.txt.gz · Última modificación: 2020/05/09 09:25 (editor externo)