该楼层疑似违规已被系统折叠 隐藏此楼查看此楼
本人自己的转载:
http://alicexybbs.blog.163.com/blog/static/238024070201461652749707/
使用QT开发应用程序,可以在windows linux 86 armlinux 下工作。如何才能做到opengl opengles2.0 兼容的方式编程,在不同的平台上都能编译通过呢?
1、opengles2.0 使用了可变管线。比gles1.0更进一步,但是使用难度大了许多。但是使用一种叫做 glsl的语言。QT里面有对这块的支持类 QGLShader 该类可以帮助你轻松使用gles2.0
同时,使用shader的写法代替固定管线,关键是你要先理解shader 的作用。这个可以google。
下面时候一个我修改的shader
void GLShader::GLShader_init()
{
//glGenTextures(1, &m_uiTexture);
//m_uiTexture = bindTexture(QImage(":/qt.png"));
QGLShader *vshader1 = new QGLShader(QGLShader::Vertex);
const char *vsrc1 =
"attribute highp vec4 vertex;\n"
"attribute mediump vec3 normal;\n"
"attribute mediump vec4 colorin;\n"
"uniform mediump bool colorflag;\n"
"uniform mediump vec4 color_next;\n"
"uniform mediump bool highlightflag;\n"
"uniform mediump bool normalflag;\n"
"uniform mediump vec3 normal_next;\n"
"uniform mediump mat4 mModelMatrix;\n"
"uniform mediump mat4 mViewMatrix;\n"
"uniform mediump mat4 mProjectionMatrix;\n"
"varying mediump vec4 color;\n"
"void main(void)\n"
"{\n"
" vec3 toLight = normalize(vec3(0.0, 0.3, 1.0));\n"//设置灯的位置
"vec4 normal4; if(normalflag==true){normal4=vec4(normal,0.0);}else{normal4=vec4(normal_next,0.0);}\n" //是否在绘制点的时候使用法线,要求每一个点输入法线,也可以使用统一的法线 normal_next
" float angle;if(highlightflag==true){angle=1.0;}else {angle=max(dot(normalize(vec3(mModelMatrix * normal4)), toLight), 0.0);}\n"//hightlightflag等同于 glEnable(GL_LIGHTING) 因为没有开灯,就是使用顶点颜色纯色,不会混合光照颜色
"vec4 col; if(colorflag==true){col=colorin;}else{col =color_next;}\n"//是否为每一个顶点设置颜色,可以使用color_next 这样不用每一个点设置颜色,而是下面的点用 color_next 颜色 vec4
" color = col * 0.2 + col * 0.8 * angle;\n"
" color = clamp(color, 0.0, 1.0);\n"
" gl_Position = mProjectionMatrix *mViewMatrix * mModelMatrix * vertex;\n"
"}\n";
vshader1->compileSourceCode(vsrc1);
QGLShader *fshader1 = new QGLShader(QGLShader::Fragment);
const char *fsrc1 =
"varying mediump vec4 color;\n"
"void main(void)\n"
"{\n"
" gl_FragColor = color;\n"
"}\n";
fshader1->compileSourceCode(fsrc1);
program1.addShader(vshader1);
program1.addShader(fshader1);
program1.link();
vertexAttr1 = program1.attributeLocation("vertex");
normalAttr1 = program1.attributeLocation("normal");
colorflagh1 = program1.uniformLocation("colorflag");
colorinh1 = program1.attributeLocation("colorin");
color_nexth1 = program1.uniformLocation("color_next");
normalflagh1 = program1.uniformLocation("normalflag");
normal_nexth1 = program1.uniformLocation("normal_next");
highlightflagh1 =program1.uniformLocation("highlightflag");
mModelMatrixh = program1.uniformLocation("mModelMatrix");
mViewMatrixh = program1.uniformLocation("mViewMatrix");
mProjectionMatrixh = program1.uniformLocation("mProjectionMatrix");
}
ModelMatrix ViewMatrix ProjectionMatrix 三个矩阵用来 综合 最后呈现在屏幕上的内容。 模型矩阵描述模型的位置的变化,这个一定要先移动,再旋转的形式设置。记得初始化矩阵位单位阵。 视图矩阵用来设置眼睛的位置,默认的情况下,眼睛的位置在 0, 0, 0 所以要看到,必须要物体的位置在这个后面。 当然你使用正交投影的方式,就不用管这个眼睛的位置了。 正交投影就是 完全按照物体尺寸投影到屏幕上,不会近大远小。可以用来画一些你不希望受距离影响的东西,比如二维的内容。 投影矩阵 可以被设置成 透视的,不过要用lookat设置眼睛的位置。也可以设置成正交的。这三个矩阵最后会按顺序 乘顶点坐标 这个顺序就是 ProjectionMatrix *ViewMatrix * ModelMatrix * vertex ,这样,顶点就会投影到屏幕上合适的位置。 这个过程在显卡里面完成的。
gle2.0 不支持 gllist 所以,你要是用gldrawarray的方式,效率并不会低多少。完全可以把要画的内容放到一个数组里面,代替gllist。