术语pipeline(管线)常用语阐述彼此紧密联系的一系列事件。
OpenGL Application: geometry(几何图形) + texture(纹理贴图)
Vertex data(顶点数据):lighting(光照) transform(变换) scale:缩放
Geometry:rasterization(光栅) clipping(剪裁)
Fragment(段):fog(雾) + texture.
Framebufer(帧缓冲区):stecil(蒙版) z-test:深度测试 alpha:透明 blending(混合)
Eyeballs(眼球)
public class MyActivity extends Activity {
@Override
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
MyGLSurfaceView view = new MyGLSurfaceView(this);
MyRenderer render = new MyRenderer();
view.setRenderer(render);
setContentView(view);
}
class MyGLSurfaceView extends GLSurfaceView {
public MyGLSurfaceView(Context context) {
super(context);
}
public MyGLSurfaceView(Context context, AttributeSet attrs) {
super(context, attrs);
}
}
// 自定义渲染器
class MyRenderer implements android.opengl.GLSurfaceView.Renderer {
private float ratio;
// 表层创建时
@Override
public void onSurfaceCreated(GL10 gl, EGLConfig config) {
// 设置清屏色(即GLSurface背景色)
gl.glClearColor(0, 0, 0, 1);
// 启用顶点缓冲区.
gl.glEnableClientState(GL10.GL_VERTEX_ARRAY);
}
// 表层size change时
@Override
public void onSurfaceChanged(GL10 gl, int width, int height) {
// 设置视口,输出画面的区域(冲印相片的大小)
gl.glViewport(0, 0, width, height);
ratio = (float) width / (float) height;// 等比例,不失真
// 矩阵模式,投影矩阵,openGL基于状态机
gl.glMatrixMode(GL10.GL_PROJECTION);
// 加载单位矩阵
gl.glLoadIdentity();
// 平截头体(视景体)
// 参数:left,right,bottom,top,zNear,zFar
gl.glFrustumf(-1f, 1f, -ratio, ratio, 3, 7);
}
// 绘图
@Override
public void onDrawFrame(GL10 gl) {
// 清除颜色缓存区
gl.glClear(GL10.GL_COLOR_BUFFER_BIT);
// 模型视图矩阵(在视景体内绘制物体)
gl.glMatrixMode(GL10.GL_MODELVIEW);
gl.glLoadIdentity();// 加载单位矩阵
// eyex,eyey,eyez:放置眼球(相机)的坐标
// centerx,centery,centerz:眼球(相机)的观察点.
// upx,upy,upz:指定眼球(相机)向上的向量
GLU.gluLookAt(gl, 0, 0, 5, 0, 0, 0, 0, 1, 0);
// 画三角形
// 绘制数组——三角形坐标(z=2f,就在近平面上画;否则在-2~2之间会缩小不占满整屏)
float[] coords = { 0f, ratio, 2f,
-1f, -ratio, 2f,
1f, -ratio, 2f };
// 分配字节缓存区空间,存放顶点坐标数据
ByteBuffer ibb = ByteBuffer.allocateDirect(coords.length * 4);
// 设置的顺序(本地顺序)
ibb.order(ByteOrder.nativeOrder());
// 放置顶点坐标数组
FloatBuffer fbb = ibb.asFloatBuffer();
fbb.put(coords);
// 定位指针的位置,从该位置开始读取顶点数据
ibb.position(0);
// 设置绘图颜色,红色
gl.glColor4f(1f, 0f, 0f, 1f);
// 3:【3维点】,使用三个坐标值表示一个点
// type:每个点的数据类型
// stride:0,跨度(连续取值,固无跨度)
// ibb:指定顶点缓冲区
gl.glVertexPointer(3, GL10.GL_FLOAT, 0, ibb);
// 绘制三角形
// 0:起始点:
// 3:绘制点的数量
gl.glDrawArrays(GL10.GL_TRIANGLES, 0, 3);
}
}
}
通过断点调试可以知道,GLSurfaceView.Renderer的三个接口实现都是在子线程中完成的。
openGL:开放图形库,es(嵌入式系统)
openGLES:一个子集.
3D游戏:
图形处理:
openGL语言:
函数:
c:
java:
动画:
ps:
透视:
矩阵:
SurfaceView:表层视图
GLSurfaceView:
renderer:渲染器
黑色 + 白色
000 255
viewPort:视口,输出画面的区域.
openGL:matrix,矩阵.
投影:
透视投影:有深度,越远越小.
正投影:没有深度,相同大小.
GLSurfaceView:GL表层视图,输出openGL画面的控件.
GLSurfaceView.Renderer:openGL渲染器,绘制openGL的类.
gl.glMatrixMode(int n);
矩阵模式,openGL基于状态的,操纵很多矩阵,通过该函数指定使用哪个矩阵.
常用的矩阵有:
GL10.GL_PROJECTION:投影矩阵.
GL10.GL_MODELVIEW:模型视图矩阵.
指定使用哪个矩阵之后,需要先加载单位矩阵(使用gl.loadIdentity()方法,类似于矩阵归零.
frustum:平截头体,拍摄画面的一个区域,是一个棱台,对投影矩阵进行操纵.
参数:
left:左侧距离
right:右侧距离
bottom:下方距离
top:上方距离
zNear:近平面距离
zFar:远平面距离
gl.glFrustum(,,,,,,);
设置眼睛的位置.
//涉及到眼球的坐标,观察的点,向上的向量
//操纵的是模型视图矩阵,因此需要先设置gl.glMatrixMode(Gl_modelview);
GLU.gluLookat(gl,eyex,eyey,eyez,centerx,centery,centerz,upx,upy,upz);
使用openGL步骤:
1.创建GLSurfaceView对象
2.创建GLSurfaceView.renderer实现类.
3.设置activity的contentView,以及设置view的render对象.
4.实现render类的过程.
a.onSurfaceCreate()方法
1.设置清屏的颜色和启用顶点缓冲区
//设置清屏色
gl.glClearColor(0, 0, 0, 1);
//启用顶点缓冲区.
gl.glEnableClientState(GL10.GL_VERTEX_ARRAY);
b.onSurfaceChanged()方法
1.设置viewport(视口)
gl.glViewport(0, 0, width, height);
2.操纵投影矩阵,设置平截头体(比例通常和视口比例相同,否则输出画面会走样)
//矩阵模式,投影矩阵,openGL基于状态机
gl.glMatrixMode(GL10.GL_PROJECTION);
//加载单位矩阵
gl.glLoadIdentity();
//平截头体
gl.glFrustumf(-1f, 1f, -ratio, ratio, 3, 7);
c.onDrawFrame()方法
1.清除颜色缓冲区
gl.glClear(GL10.GL_COLOR_BUFFER_BIT);
2.操纵模型视图矩阵,设置眼球的参数
gl.glMatrixMode(GL10.GL_MODELVIEW);
gl.glLoadIdentity();//加载单位矩阵
GLU.gluLookAt(gl, 0, 0, 5, 0, 0, 0, 0, 1, 0);
3.定义图形顶点坐标值数组
float[] coords = {
0f,0.5f,0f,
-0.5f,-0.5f,0f,
0.5f,-0.5f,0f
};
4.将顶点坐标转换成缓冲区数据
//分配字节缓存区空间,存放顶点坐标数据
ByteBuffer ibb = ByteBuffer.allocateDirect(coords.length * 4);
//设置的顺序(本地顺序)
ibb.order(ByteOrder.nativeOrder());
//放置顶点坐标数组
FloatBuffer fbb = ibb.asFloatBuffer();
fbb.put(coords);
//定位指针的位置,从该位置开始读取顶点数据
ibb.position(0);
5.设置绘图颜色
gl.glColor4f(1f, 0f, 0f, 1f);
6.指定顶点缓冲区指针
//3:3维点,使用三个坐标值表示一个点
//type:每个点的数据类型
//stride:0,跨度.
//ibb:指定顶点缓冲区
gl.glVertexPointer(3, GL10.GL_FLOAT, 0, ibb);
7.绘图
//0:起始点:
//3:绘制点的数量
gl.glDrawArrays(GL10.GL_TRIANGLES, 0, 3);
纹理:
openGLES1.0 ---> openGL1.3
openGLES1.1 ---> openGL1.5
pipeline:管线:
opengl application: geometry(几何图形) + texture(纹理贴图)
vertex data(顶点数据):lighting(光照) transform(变换) scale:缩放
geometry:rasterization(光栅) clipping(剪裁)
fragment(段):fog(雾) + texture.
framebufer(帧缓冲区):stecil(蒙版) z-test:深度测试 alpha:透明 blending(混合)
eyeball(眼球):
屏幕坐标:原点在左上
0-------->X
|
|
|
\|/ Y
数学坐标系:原点左下角
/|\Y
|
|
0-------->X
openGL3D坐标系(笛卡尔坐标系)
/|\Y
|
|
0-------->X
/
/
/Z