webgl学习笔记五-纹理
写在前面
建议先阅读下前面我的三篇文章。
术语 :
- 纹理 :图像
- 图形装配区域 :顶点着色器顶点坐标信息
- 装配图形 : 片元着色器装配
- 光栅化 :显示在屏幕上的三角形是由片元(像素)组成的,所以还需要将图形转化为片元,这个过程被称为光栅化。
- 纹理图像:映射的这个图像称为纹理图像
- 纹素 : 组成纹理图像的像素称为纹素
- 纹理坐标 : 是纹理图像上的坐标,通过纹理坐标可以在纹理图像上获取纹素颜色;
纹理绘图流程
重点介绍纹理的流程。
- 创建纹理对象
- 加载纹理图像
- 配置属性
demo
- html
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<title>Title</title>
</head>
<body>
<canvas id="canvas" width="200px" height="200px"></canvas>
</body>
</html>
- JavaScript
<script>
window.onload = function () {
//顶点着色器程序
var VSHADER_SOURCE =
"attribute vec4 a_Position;" +
"attribute vec2 a_TextCoord;" + // 接受纹理坐标
"varying vec2 v_TexCoord;" + // 传递纹理坐标
"void main() {" +
//设置坐标
"gl_Position = a_Position; " + // 设置坐标
//设置纹素
"v_TexCoord = a_TextCoord; " + // 设置纹理坐标
"} ";
//片元着色器
var FSHADER_SOURCE =
"precision mediump float;" + //需要声明浮点数精度,否则报错No precision specified for (float)
"uniform sampler2D u_Sampler;" + // 取样器
"varying vec2 v_TexCoord;" + // 接受纹理坐标
"void main() {" +
//设置颜色
"gl_FragColor = texture2D(u_Sampler, v_TexCoord);" + // 设置颜色
"}";
//获取canvas元素
var canvas = document.getElementById('canvas');
//获取绘制webgl绘图上下文
var gl = canvas.getContext('webgl');
if (!gl) {
console.log("Failed");
return;
}
//编译着色器
// (1)创建Shader(着色器)对象
// (2)将着色器程序附加到Shader上
// (3)编译程序
var vertShader = gl.createShader(gl.VERTEX_SHADER);
gl.shaderSource(vertShader, VSHADER_SOURCE);
gl.compileShader(vertShader);
var fragShader = gl.createShader(gl.FRAGMENT_SHADER);
gl.shaderSource(fragShader, FSHADER_SOURCE);
gl.compileShader(fragShader);
//合并程序
// (1)创建一个程序对象
// (2)附加着色器
// (3)链接着色器
// (4)使用程序
var shaderProgram = gl.createProgram();
gl.attachShader(shaderProgram, vertShader);
gl.attachShader(shaderProgram, fragShader);
gl.linkProgram(shaderProgram);
gl.useProgram(shaderProgram);
gl.clearColor(0.0, 0.0, 0.0, 1.0);
var n = initBuffers(gl, shaderProgram);
initTexture(gl, shaderProgram, n);
gl.clear(gl.COLOR_BUFFER_BIT);
//绘制一个点
gl.drawArrays(gl.POINTS, 0, 1);
}
// 使用缓冲区对象向顶点传入多个顶点数据
function initBuffers(gl, shaderProgram) {
//顶点坐标和颜色
var vertices = new Float32Array([
-0.5, 0.5, 0.0, 1.0,
-0.5, -0.5, 0.0, 0.0,
0.5, 0.5, 1.0, 1.0,
0.5, -0.5, 1.0, 0.0
]);
var n = 4;//点的个数
//创建缓冲区对象
var vertexBuffer = gl.createBuffer();
//将缓冲区对象绑定到目标
gl.bindBuffer(gl.ARRAY_BUFFER, vertexBuffer);
//向缓冲区写入数据
gl.bufferData(gl.ARRAY_BUFFER, vertices, gl.STATIC_DRAW);
var FSIZE = vertices.BYTES_PER_ELEMENT;
//获取坐标点
var a_Position = gl.getAttribLocation(shaderProgram, "a_Position");
//将缓冲区对象分配给a_Position变量
gl.vertexAttribPointer(a_Position, 2, gl.FLOAT, false, FSIZE * 4, 0);
//连接a_Position变量与分配给它的缓冲区对象
gl.enableVertexAttribArray(a_Position);
//获取Color坐标点
var a_TextCoord = gl.getAttribLocation(shaderProgram, "a_TextCoord");
//将缓冲区对象分配给a_Position变量
gl.vertexAttribPointer(a_TextCoord, 2, gl.FLOAT, false, FSIZE * 4, FSIZE * 2);
//连接a_Position变量与分配给它的缓冲区对象
gl.enableVertexAttribArray(a_TextCoord);
return n;
}
// 初始创建纹理,创建image对象
function initTexture(gl, shaderProgram, n) {
//创建纹理对象
var texture = gl.createTexture();
//获取u_Sampler的存储位置
var u_Sampler = gl.getUniformLocation(shaderProgram, 'u_Sampler');
//创建image对象
var image = new Image();
//加载纹理
image.onload = function () {
loadTexture(gl, n, texture, u_Sampler, image);
};
// 浏览器开始加载图片 注意:一定是2^mx2^n尺寸的图片
image.src = "../../resources/st2_256*128.png";
return true;
}
// 加载纹理图像,配置属性
function loadTexture(gl, n, texture, u_Sampler, image) {
//1.对纹理图像进行Y轴反转
gl.pixelStorei(gl.UNPACK_FLIP_Y_WEBGL, 1);
//2.开启0号纹理单元
gl.activeTexture(gl.TEXTURE0);
//3.向target绑定纹理对象
gl.bindTexture(gl.TEXTURE_2D, texture);
//4.配置纹理参数
gl.texParameteri(gl.TEXTURE_2D, gl.TEXTURE_MIN_FILTER, gl.LINEAR);
//5.配置纹理图像
gl.texImage2D(gl.TEXTURE_2D, 0, gl.RGB, gl.RGB, gl.UNSIGNED_BYTE, image);
//6.将0号纹理图像传递给着色器
gl.uniform1i(u_Sampler, 0);
// 清空 <canvas>
gl.clear(gl.COLOR_BUFFER_BIT);
//绘制矩形
gl.drawArrays(gl.TRIANGLE_STRIP, 0, n);
}
</script>
webgl学习笔记五-纹理的更多相关文章
- WebGL学习笔记五
本章主要是对纹理的进一步讲解,我们很多时候需要将现实中已有 的图片在网页中展示出来而不是去创造图片,通过纹理 我们可以将光栅化的图形和图片纹理形成映射并且将图片在图形 中显示出来.基本过程与前几章一致 ...
- C#可扩展编程之MEF学习笔记(五):MEF高级进阶
好久没有写博客了,今天抽空继续写MEF系列的文章.有园友提出这种系列的文章要做个目录,看起来方便,所以就抽空做了一个,放到每篇文章的最后. 前面四篇讲了MEF的基础知识,学完了前四篇,MEF中比较常用 ...
- (转)Qt Model/View 学习笔记 (五)——View 类
Qt Model/View 学习笔记 (五) View 类 概念 在model/view架构中,view从model中获得数据项然后显示给用户.数据显示的方式不必与model提供的表示方式相同,可以与 ...
- java之jvm学习笔记五(实践写自己的类装载器)
java之jvm学习笔记五(实践写自己的类装载器) 课程源码:http://download.csdn.net/detail/yfqnihao/4866501 前面第三和第四节我们一直在强调一句话,类 ...
- Learning ROS for Robotics Programming Second Edition学习笔记(五) indigo computer vision
中文译著已经出版,详情请参考:http://blog.csdn.net/ZhangRelay/article/category/6506865 Learning ROS for Robotics Pr ...
- Typescript 学习笔记五:类
中文网:https://www.tslang.cn/ 官网:http://www.typescriptlang.org/ 目录: Typescript 学习笔记一:介绍.安装.编译 Typescrip ...
- ES6学习笔记<五> Module的操作——import、export、as
import export 这两个家伙对应的就是es6自己的 module功能. 我们之前写的Javascript一直都没有模块化的体系,无法将一个庞大的js工程拆分成一个个功能相对独立但相互依赖的小 ...
- muduo网络库学习笔记(五) 链接器Connector与监听器Acceptor
目录 muduo网络库学习笔记(五) 链接器Connector与监听器Acceptor Connector 系统函数connect 处理非阻塞connect的步骤: Connetor时序图 Accep ...
- python3.4学习笔记(五) IDLE显示行号问题,插件安装和其他开发工具介绍
python3.4学习笔记(五) IDLE显示行号问题,插件安装和其他开发工具介绍 IDLE默认不能显示行号,使用ALT+G 跳到对应行号,在右下角有显示光标所在行.列.pycharm免费社区版.Su ...
随机推荐
- 20155330 2016-2017-2 《Java程序设计》第四周学习总结
20155330 2016-2017-2 <Java程序设计>第四周学习总结 教材学习内容总结 学习目标 理解封装.继承.多态的关系 理解抽象类与接口的区别 掌握S.O.L.I.D原则 了 ...
- 微信小程序标签页切换
WXML中: <view class="swiper-tab"> <view class="swiper-tab-list {{currentTab== ...
- WPF ControllTemplate Triggers小记 - 简书
原文:WPF ControllTemplate Triggers小记 - 简书 WPF中,样式模板中如果定义EventTrigger事件方式实现动画.那么需要注意两点: 1.对于绑定的属性的Event ...
- linux下order by 报出ORDER BY clause is not in SELECT list
一.问题: 在程序执行查询的时候,order by 不能找到要排序的列 二.解决: 在linux环境下,程序之前连接其他库可以正常运行,但是换了一个库后数据就不能正常的显示了,查看后台报出排序列找不到 ...
- MySql访客连接设置
步骤: 1 . 打开命令窗口,切换到mysql安装目录 可以在控制台目录切换,也可以打开所在安装目录后再打开控制台 2 . 执行命令:mysql -u root -p 3 . 无法访问的话,查看防火墙 ...
- hive 日志
hive中日志分为两种: 1 系统日志,记录hive运行情况,错误状态 2 job日志 , 记录hive中 job执行的历史过程 系统日志存储位置: 配置在 hive/conf/hive-log4j. ...
- 远程连接ejabberd的mnesia数据库
由于服务器是server版本,所以很难直观的看到mnesia的数据.所以对于初学者来说非常的困惑. 特地在qq群中请教了别人.别人说只要pong通了就行,就能通过rpc去操作远程的mnesia数据库. ...
- Windows网络通信(二):socket异步编程
简述 这里使用的API和同步编程的API是差不多的,只多了一个ioctlsocket和select函数.这里面涉及一个很重要的结构体fd_set.这里用到的API大部分都是windows和linux通 ...
- vue cli 3 +jquery
const webpack = require('webpack')module.exports = { // baseUrl type:{string} default:'/' // 将部署应用程序 ...
- springMVC 第一章
springMVC 第一章 一.分层结构的项目 组成方式: 表示层:页面,Servlet 业务层:业务逻辑类(service) 持久层:与数据库交互的类(dao) 程序执行的过程:表示层->se ...