glDrawElements 和glDrawArrays


glDrawArrays有3個參數

void glDrawArrays(
int mode,
int first,
int count
);
第一個就是繪圖的類型:
 
1.GL_TRIANGLES:每三個頂之間繪制三角形,之間不連接
 
2.GL_TRIANGLE_FAN:以V0V1V2,V0V2V3,V0V3V4,……的形式繪制三角形
 
3.GL_TRIANGLE_STRIP:順序在每三個頂點之間均繪制三角形。這個方法可以保證從相同的方向上所有三角形均被繪制。以V0V1V2,V1V2V3,V2V3V4……的形式繪制三角形
 
參數2:從數組緩存中的哪一位開始繪制,一般都定義為0
 
參數3:頂點的數量
第一個三角形是逆時針第二個是順時針,如果第二個是逆時針有時候可以畫出總之很容易出問題,同glDrawElements一樣。
 
glDrawElements 有四個參數,
void glDrawElements(
int mode,
int count,
int type,
java.nio.Buffer indices
);
第一個參數是點的類型,第二個參數是點的個數,第三個是第四個參數的類型,第四個參數是點的存儲繪制順序。
 
如正方形:0             3     ---------------->   存儲的點順序是0,1,2,3  而 繪圖的時候是每三個點就會繪制一個三角形,因此012 可以為三角形,1,2,3則與前面的三角形重復切不會覆蓋整個矩形,
                   1             2
因此就需要我們認為的設定繪圖點的順序,第四個參數的作用就是如此,我們把點的順序設置為0,1,3,2 這樣0,1,3和1,3,2 成2個三角形且剛好形成矩陣。
因此, 在利用glDrawElements時候只需記住所有定點,在第四個參數中來秒數所需面的頂點順序即可,且每取三個點繪圖一個三角形,下面的demo只記住了立方體的8個點,利用18個點的順序就可以繪圖成一個立方體,而不是4*6個點。 第一個三角形是逆時針第二個是順時針,依次循環否則不對應的就不會繪出。
package com.example.zp.myapplication;
 
import android.opengl.GLSurfaceView;
 
import java.nio.ByteBuffer;
import java.nio.FloatBuffer;
 
import javax.microedition.khronos.egl.EGLConfig;
import javax.microedition.khronos.opengles.GL10;
 
/**
* Created by lenovo on 2016/9/1.
*/
public class GLRender0 implements GLSurfaceView.Renderer
{
float rotateSpeed =5* (float) Math.PI/18;
float rotateTri = 0;
float one = 1f;
 
//正方形的4個頂點
private FloatBuffer quaterBuffer2 = BufferUtil.floatToBuffer(new float[]{
 
-one,-one,one,
one,-one,one,
one,one,one,
-one,one,one,
 
-one,-one,-one,
-one,one,-one,
one,one,-one,
one,-one,-one,
});
private FloatBuffer colorBuffer2 = BufferUtil.floatToBuffer(new float[]{
one,0,0,one,
0,one,0,one,
0,0,one,one,
});
ByteBuffer indices = ByteBuffer.wrap(new byte[]{
0,1,3,2,
5,6,4,7,
0,1,2,6,
1,7,4,0,
5,3
});
 
@Override
public void onDrawFrame(GL10 gl)
{
// 清除屏幕和深度緩存
gl.glClear(GL10.GL_COLOR_BUFFER_BIT | GL10.GL_DEPTH_BUFFER_BIT);
// 允許設置頂點
gl.glEnableClientState(GL10.GL_VERTEX_ARRAY);
 
//****************************繪制立方體***********************************//
// 重置當前的模型觀察矩陣
gl.glLoadIdentity();
//右移 1.5 單位,並移入屏幕 6.0
gl.glTranslatef(1.5f, 0.0f, -6.0f);
//旋轉矩陣
gl.glRotatef(rotateTri, 0.1f, 0.0f,0.0f);
//設置和繪制立方體
gl.glVertexPointer(3,GL10.GL_FLOAT,0,quaterBuffer2);
//單一着色
gl.glColor4f(1.0f, 0.0f, 0.0f, 1.0f);
 
gl.glDrawElements(GL10.GL_TRIANGLE_STRIP, 18, GL10.GL_UNSIGNED_BYTE, indices);
 
// gl.glDrawArrays(GL10.GL_TRIANGLE_STRIP, 0, 4);
gl.glFinish();
 
// 關閉頂點設置
gl.glDisableClientState(GL10.GL_VERTEX_ARRAY);
 
rotateTri=rotateSpeed+rotateTri;
}
 
@Override
public void onSurfaceChanged(GL10 gl, int width, int height)
{
float ratio = (float) width / height;
//設置OpenGL場景的大小
gl.glViewport(0, 0, width, height);
//設置投影矩陣
gl.glMatrixMode(GL10.GL_PROJECTION);
//重置投影矩陣
gl.glLoadIdentity();
// 設置視口的大小
gl.glFrustumf(-ratio, ratio, -1, 1, 1, 10);
// 選擇模型觀察矩陣
gl.glMatrixMode(GL10.GL_MODELVIEW);
// 重置模型觀察矩陣
gl.glLoadIdentity();
 
}
 
@Override
public void onSurfaceCreated(GL10 gl, EGLConfig config)
{
// 啟用陰影平滑
gl.glShadeModel(GL10.GL_SMOOTH);
 
// 黑色背景
gl.glClearColor(0, 0, 0, 0);
 
// 設置深度緩存
gl.glClearDepthf(1.0f);
// 啟用深度測試
gl.glEnable(GL10.GL_DEPTH_TEST);
// 所作深度測試的類型
gl.glDepthFunc(GL10.GL_LEQUAL);
 
// 告訴系統對透視進行修正
gl.glHint(GL10.GL_PERSPECTIVE_CORRECTION_HINT, GL10.GL_FASTEST);
}
 
}
 


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM