opengles特效之飘扬的旗帜
原文地址: http://blog.csdn.net/hb707934728/article/details/52998569
效果图
核心代码 主要看shader中的实现
x方向飘扬shader
- uniform mat4 uMVPMatrix; //总变换矩阵
- uniform float uStartAngle;//本帧起始角度
- uniform float uWidthSpan;//横向长度总跨度
- attribute vec3 aPosition; //顶点位置
- attribute vec2 aTexCoor; //顶点纹理坐标
- varying vec2 vTextureCoord; //用于传递给片元着色器的变量
- void main()
- {
- //计算X向波浪
- float angleSpanH=4.0*3.14159265;//横向角度总跨度
- float startX=-uWidthSpan/2.0;//起始X坐标
- //根据横向角度总跨度、横向长度总跨度及当前点X坐标折算出当前点X坐标对应的角度
- float currAngle=uStartAngle+((aPosition.x-startX)/uWidthSpan)*angleSpanH;
- float tz=sin(currAngle)*0.1;
- //根据总变换矩阵计算此次绘制此顶点位置
- gl_Position = uMVPMatrix * vec4(aPosition.x,aPosition.y,tz,1);
- // gl_Position = uMVPMatrix * vec4(aPosition.x,tz,aPosition.y,1);
- vTextureCoord = aTexCoor;//将接收的纹理坐标传递给片元着色器
- }
斜向飘扬shader
- uniform mat4 uMVPMatrix; //总变换矩阵
- uniform float uStartAngle;//本帧起始角度
- uniform float uWidthSpan;//横向长度总跨度
- attribute vec3 aPosition; //顶点位置
- attribute vec2 aTexCoor; //顶点纹理坐标
- varying vec2 vTextureCoord; //用于传递给片元着色器的变量
- void main()
- {
- //计算X向角度
- float angleSpanH=4.0*3.14159265;//横向角度总跨度
- float startX=-uWidthSpan/2.0;//起始X坐标
- //根据横向角度总跨度、横向长度总跨度及当前点X坐标折算出当前点X坐标对应的角度
- float currAngleH=uStartAngle+((aPosition.x-startX)/uWidthSpan)*angleSpanH;
- //计算出随Y向发展起始角度的扰动值
- float angleSpanZ=4.0*3.14159265;//纵向角度总跨度
- float uHeightSpan=0.75*uWidthSpan;//纵向长度总跨度
- float startY=-uHeightSpan/2.0;//起始Y坐标
- //根据纵向角度总跨度、纵向长度总跨度及当前点Y坐标折算出当前点Y坐标对应的角度
- float currAngleZ=((aPosition.y-startY)/uHeightSpan)*angleSpanZ;
- //计算斜向波浪
- float tzH=sin(currAngleH-currAngleZ)*0.1;
- //根据总变换矩阵计算此次绘制此顶点位置
- gl_Position = uMVPMatrix * vec4(aPosition.x,aPosition.y,tzH,1);
- vTextureCoord = aTexCoor;//将接收的纹理坐标传递给片元着色器
- }
xy双向飘扬shader
- uniform mat4 uMVPMatrix; //总变换矩阵
- uniform float uStartAngle;//本帧起始角度
- uniform float uWidthSpan;//横向长度总跨度
- attribute vec3 aPosition; //顶点位置
- attribute vec2 aTexCoor; //顶点纹理坐标
- varying vec2 vTextureCoord; //用于传递给片元着色器的变量
- void main()
- {
- //计算X向波浪
- float angleSpanH=4.0*3.14159265;//横向角度总跨度
- float startX=-uWidthSpan/2.0;//起始X坐标
- //根据横向角度总跨度、横向长度总跨度及当前点X坐标折算出当前点X坐标对应的角度
- float currAngleH=uStartAngle+((aPosition.x-startX)/uWidthSpan)*angleSpanH;
- float tzH=sin(currAngleH)*0.1;
- //计算Y向波浪
- float angleSpanZ=4.0*3.14159265;//纵向角度总跨度
- float uHeightSpan=0.75*uWidthSpan;//纵向长度总跨度
- float startY=-uHeightSpan/2.0;//起始Y坐标
- //根据纵向角度总跨度、纵向长度总跨度及当前点Y坐标折算出当前点Y坐标对应的角度
- float currAngleZ=uStartAngle+3.14159265/3.0+((aPosition.y-startY)/uHeightSpan)*angleSpanZ;
- float tzZ=sin(currAngleZ)*0.1;
- //根据总变换矩阵计算此次绘制此顶点位置
- gl_Position = uMVPMatrix * vec4(aPosition.x,aPosition.y,tzH+tzZ,1);
- vTextureCoord = aTexCoor;//将接收的纹理坐标传递给片元着色器
- }
同时需要启动一个线程不断修改当前帧起始角度
- package test.com.opengles_1_1;
- import java.nio.ByteBuffer;
- import java.nio.ByteOrder;
- import java.nio.FloatBuffer;
- import android.annotation.SuppressLint;
- import android.opengl.GLES20;
- /**
- * Created by hbin on 2016/11/1.
- * 有波浪效果的纹理矩形
- */
- public class TextureRect {
- int[] mPrograms=new int[3];//自定义渲染管线着色器程序id
- int[] muMVPMatrixHandle=new int[3];//总变换矩阵引用
- int[] maPositionHandle=new int[3]; //顶点位置属性引用
- int[] maTexCoorHandle=new int[3]; //顶点纹理坐标属性引用
- int[] maStartAngleHandle=new int[3]; //本帧起始角度属性引用
- int[] muWidthSpanHandle=new int[3];//横向长度总跨度引用
- int currIndex=0;//当前着色器索引
- FloatBuffer mVertexBuffer;//顶点坐标数据缓冲
- FloatBuffer mTexCoorBuffer;//顶点纹理坐标数据缓冲
- int vCount=0;
- final float WIDTH_SPAN=3.3f;//2.8f;//横向长度总跨度
- float currStartAngle=0;//当前帧的起始角度0~2PI
- public TextureRect(MySurfaceView mv)
- {
- //初始化顶点坐标与着色数据
- initVertexData();
- //初始化shader
- initShader(mv,0,"vertex_tex_x.sh");
- initShader(mv,1,"vertex_tex_xie.sh");
- initShader(mv,2,"vertex_tex_xy.sh");
- //启动一个线程定时换帧
- new Thread()
- {
- public void run()
- {
- while(Constant.threadFlag)
- {
- currStartAngle+=(float) (Math.PI/16);
- try
- {
- Thread.sleep(50);
- } catch (InterruptedException e)
- {
- e.printStackTrace();
- }
- }
- }
- }.start();
- }
- private void initVertexData()
- {
- final int cols=12;//列数
- final int rows=cols*3/4;//行数
- final float UNIT_SIZE=WIDTH_SPAN/cols;//每格的单位长度
- vCount=cols*rows*6;//每个格子两个三角形,每个三角形3个顶点
- float vertices[]=new float[vCount*3];//每个顶点xyz三个坐标
- int count=0;
- for (int j=0;j<rows;j++){
- for (int i=0;i<cols;i++){
- float zsx=-UNIT_SIZE*cols/2+i*UNIT_SIZE;
- float zsy=UNIT_SIZE*rows/2-j*UNIT_SIZE;
- float zsz=0;
- vertices[count++]=zsx;
- vertices[count++]=zsy;
- vertices[count++]=zsz;
- vertices[count++]=zsx;
- vertices[count++]=zsy-UNIT_SIZE;
- vertices[count++]=zsz;
- vertices[count++]=zsx+UNIT_SIZE;
- vertices[count++]=zsy;
- vertices[count++]=zsz;
- vertices[count++]=zsx+UNIT_SIZE;
- vertices[count++]=zsy;
- vertices[count++]=zsz;
- vertices[count++]=zsx;
- vertices[count++]=zsy-UNIT_SIZE;
- vertices[count++]=zsz;
- vertices[count++]=zsx+UNIT_SIZE;
- vertices[count++]=zsy-UNIT_SIZE;
- vertices[count++]=zsz;
- }
- }
- //创建顶点坐标数据缓冲
- //vertices.length*4是因为一个整数四个字节
- ByteBuffer vbb = ByteBuffer.allocateDirect(vertices.length*4);
- vbb.order(ByteOrder.nativeOrder());//设置字节顺序
- mVertexBuffer = vbb.asFloatBuffer();//转换为Float型缓冲
- mVertexBuffer.put(vertices);//向缓冲区中放入顶点坐标数据
- mVertexBuffer.position(0);//设置缓冲区起始位置
- //顶点纹理坐标数据的初始化================begin============================
- float texCoor[]=generateTexCoor(cols,rows);
- //创建顶点纹理坐标数据缓冲
- ByteBuffer cbb = ByteBuffer.allocateDirect(texCoor.length*4);
- cbb.order(ByteOrder.nativeOrder());//设置字节顺序
- mTexCoorBuffer = cbb.asFloatBuffer();//转换为Float型缓冲
- mTexCoorBuffer.put(texCoor);//向缓冲区中放入顶点着色数据
- mTexCoorBuffer.position(0);//设置缓冲区起始位置
- }
- public void initShader(MySurfaceView mv,int index,String vertexName)
- {
- //加载顶点着色器的脚本内容
- String mVertexShader=ShaderUtil.loadFromAssetsFile(vertexName, mv.getResources());
- //加载片元着色器的脚本内容
- String mFragmentShader=ShaderUtil.loadFromAssetsFile("frag_tex.sh", mv.getResources());
- //基于顶点着色器与片元着色器创建程序
- mPrograms[index] = ShaderUtil.createProgram(mVertexShader, mFragmentShader);
- //获取程序中顶点位置属性引用
- maPositionHandle[index] = GLES20.glGetAttribLocation(mPrograms[index], "aPosition");
- //获取程序中顶点纹理坐标属性引用
- maTexCoorHandle[index]= GLES20.glGetAttribLocation(mPrograms[index], "aTexCoor");
- //获取程序中总变换矩阵引用
- muMVPMatrixHandle[index] = GLES20.glGetUniformLocation(mPrograms[index], "uMVPMatrix");
- //获取本帧起始角度属性引用
- maStartAngleHandle[index]=GLES20.glGetUniformLocation(mPrograms[index], "uStartAngle");
- //获取横向长度总跨度引用
- muWidthSpanHandle[index]=GLES20.glGetUniformLocation(mPrograms[index], "uWidthSpan");
- }
- public void drawSelf(int texId)
- {
- //制定使用某套shader程序
- GLES20.glUseProgram(mPrograms[currIndex]);
- //将最终变换矩阵传入shader程序
- GLES20.glUniformMatrix4fv(muMVPMatrixHandle[currIndex], 1, false, MatrixState.getFinalMatrix(), 0);
- //将本帧起始角度传入shader程序
- GLES20.glUniform1f(maStartAngleHandle[currIndex], currStartAngle);
- //将横向长度总跨度传入shader程序
- GLES20.glUniform1f(muWidthSpanHandle[currIndex], WIDTH_SPAN);
- //将顶点位置数据传入渲染管线
- GLES20.glVertexAttribPointer
- (
- maPositionHandle[currIndex],
- 3,
- GLES20.GL_FLOAT,
- false,
- 3*4,
- mVertexBuffer
- );
- //将顶点纹理坐标数据传入渲染管线
- GLES20.glVertexAttribPointer
- (
- maTexCoorHandle[currIndex],
- 2,
- GLES20.GL_FLOAT,
- false,
- 2*4,
- mTexCoorBuffer
- );
- //启用顶点位置、纹理坐标数据
- GLES20.glEnableVertexAttribArray(maPositionHandle[currIndex]);
- GLES20.glEnableVertexAttribArray(maTexCoorHandle[currIndex]);
- //绑定纹理
- GLES20.glActiveTexture(GLES20.GL_TEXTURE0);
- GLES20.glBindTexture(GLES20.GL_TEXTURE_2D, texId);
- GLES20.glDrawArrays(GLES20.GL_TRIANGLES, 0, vCount);
- }
- //自动切分纹理产生纹理数组的方法
- public float[] generateTexCoor(int bw,int bn)
- {
- float[] result=new float[bw*bn*6*2];
- float sizew=1.0f/bw;//列数
- float sizeh=0.75f/bn;//行数
- int c=0;
- for(int i=0;i<bn;i++)
- {
- for(int j=0;j<bw;j++)
- {
- //每行列一个矩形,由两个三角形构成,共六个点,12个纹理坐标
- float s=j*sizew;
- float t=i*sizeh;
- //第一个纹理三角形
- result[c++]=s;
- result[c++]=t;
- result[c++]=s;
- result[c++]=t+sizeh;
- result[c++]=s+sizew;
- result[c++]=t;
- //第二个纹理三角形
- result[c++]=s+sizew;
- result[c++]=t;
- result[c++]=s;
- result[c++]=t+sizeh;
- result[c++]=s+sizew;
- result[c++]=t+sizeh;
- }
- }
- return result;
- }
- }
完整代码下载地址
http://download.csdn.net/detail/hb707934728/9670345
opengles特效之飘扬的旗帜相关推荐
- C++ Opengl WaveFlag(飘扬的旗帜)源码
C++ Opengl WaveFlag飘扬的旗帜源码 项目开发环境 项目功能 项目演示 项目源码传送门 项目开发环境 开发语言:C++和IDE:VS2017,操作系统Windows版本windows ...
- 3ds Max制作一面飘扬的旗帜效果图
在大家平时建模过程中肯定会遇到很多力学作用的模型,它们有很多的不确定性,通过人工拖拽的手段很难达到理想的自然效果,这时我们就需要一些特殊的命令来完成我们模拟自然状态的效果.下面我们就一面飘扬的国旗来探 ...
- java适合舰旗_飘扬的旗帜!shader 编程实战!Cocos Creator!
> 用 shader + mesh 立个 flag 吧! 文章底部获取完整代码! 效果预览 使用方法 创建一个空节点 添加用户脚本组件 mesh-texture-flag 添加图片 修改对应属性 ...
- Android 3D游戏开发技术详解与典型案例
下载地址 <Android3D游戏开发技术详解与典型案例>主要以Android平台下3D游戏的开发为主题,并结合真实的案例向读者详细介绍了OpenGL ES的基础 知识及3D游戏程序开发的 ...
- 角色扮演游戏引擎的设计原理--转自MOVE2008
角色扮演游戏引擎的设计原理--转自MOVE2008 角色扮演游戏引擎的设计原理 角色扮演游戏(RPG)是深受广大游戏迷们喜爱的一种游戏, 它以独特的互动性和故事性吸引了无数的玩家.它向人们提供了超出现 ...
- 角色扮演游戏引擎的设计原理
角色扮演游戏引擎的设计原理 角色扮演游戏(RPG)是深受广大游戏迷们喜爱的一种游戏, 它以独特的互动性和故事性吸引了无数的玩家.它向人们提供了超出现实生活的广阔的虚拟世界,使人们能够尝试扮演不同的角色 ...
- 这么全的 Cocos Creator 3.x 学习资源,竟然是免费的!
目前 Cocos Creator 3.0 越来越成熟,使用 Cocos Creator 做游戏的小伙伴越来越多.我们在这里整理了现阶段最全面.最优质的 Cocos Creator 3.x 的学习资料, ...
- Macromedia Flash MX 2004 V7.01 简体中文版下载地址及例视频教程(swf版)
Macromedia Flash MX 2004 V7.01 简体中文版 软件大小:48.65 MB 软件语言:简体中文 软件类别:国外软件 / 动画制作 运行环境:XP, 2000, NT, Win ...
- RPG游戏引擎的设计原理
角色扮演游戏(RPG)是深受广大游戏迷们喜爱的一种游戏, 它以独特的互动性和故事性吸引了无数的玩家.它向人们提供了超出现实生活的广阔的虚拟世界,使人们能够尝试扮演不同的角色,去经历和体验各种不同的人生 ...
- 角色扮演游戏(RPG)-------之谈
角色扮演游戏(RPG)是深受广大游戏迷们喜爱的一种游戏, 它以独特的互动性和故事性吸引了无数的玩家.它向人们提供了超出现实生活的广阔的虚拟世界,使人们能够尝试扮演不同的角色,去经历和体验各种不同的人生 ...
最新文章
- WebGoat教程学习(三)--Ajax安全
- mysql autocommit 脚本_mysql autocommit的差异
- 高性能服务器架构思路「不仅是思路」
- ACM中Java输入输出
- 常用的函数式接口_Consumer接口练习_字符串拼接输出
- python3基础3--数据类型--数据运算--表达式if -else-while-for
- Java 抽象类和抽象方法
- 返回数据_多层数据返回匹配值
- Ubunut14.04安装wps最新方法
- oracle 数据的定义,oracle——数据定义
- pinia中文文档 指导文档中文翻译版 pinia指导中文翻译
- bzoj 1433: [ZJOI2009]假期的宿舍
- VS2017编译SNMP库
- adc0808温度换算公式_多路温度采集与控制(C51、ADC0808)
- 12帧跑步动画分解图_跑步动画原理讲解
- CSU oj 1681 Adjoin(dfs求树上最长路径)(搜索)
- UWB相关技术之测距定位方法
- JavaSE第04篇:Java基础语法之循环结构
- java-IOC(控制反转) 理论推导
- c++软件开发面试旋极面试题_北京旋极信息技术股份有限公司2015招聘
热门文章
- 将实时频谱分析仪与HIF输出配合使用
- HCIA-Big Data华为认证大数据工程师 习题册 含答案
- 企业上云,安全合规如何进阶 ——一文拆解亚马逊云科技云安全理念与实践
- iOS NSString,NSLog添加%百分号和引号等符号
- PYMOL-note
- GLFWError #65542 Happen, WGL: The driver does not appear to support OpenGL的问题处理经历
- MySQL慢查询,一口从天而降的锅!
- Linux远程终端工具之Xmanager-Xbrowser
- Prefix Sum —— 树状数组+懵逼的组合恒等式
- java ship_用Java对象来解答世界悖论难题“忒修斯之船”