`
flyfox1982
  • 浏览: 81225 次
  • 性别: Icon_minigender_1
  • 来自: 上海
社区版块
存档分类
最新评论

WebGL 绘制Line的bug(二)

阅读更多

基本思路

上一篇文章简单介绍了WebGL绘制Line的bug,这一篇文章会讲述解决这个问题的work around。

上一篇文章结尾简单提了下解决的思路,就是通过三角形来模拟线条。

以两个端点组成的线段为例,绘制line的时候只用指定两个端点,如果通过三角形来模拟一条线段,则至少需要两个三角形,如下图:


两个三角形模拟的线段

因此要绘制一条线段,则需要六个顶点,两个三角形;当时从上图中,可以看出有些顶点是共享,实际上只需要四个顶点,然后通过索引的方式绘制两个三角形,相信熟悉WebGL的同学都理解这种通过索引来绘制的方式,此处不详细说明。

如果要绘制两条相连的线段呢,则需要增加两个顶点,也就是6个顶点,绘制四个三角形,依次类推,绘制三条相连的线段需要8个顶点,绘制6个三角形;由此可以得出一个结论,绘制有n个端点的Line,需要:2 * n 个顶点, (n-1) * 2个三角形。

对于一条线段而言,控制的参数实际上只有两个端点的坐标和线的宽度。 

从上面的分析,我们知道了给定一系列点(n个)和线的宽度,绘制一条线段需要的顶点数是n * 2. 

如何计算顶点

两个端点的情况

当时 n个顶点数据应该如何计算得到呢? 先举个简单的2维绘图的例子,现在假设给定了两个端点:

(-50,0)和(50,0),要绘制一条宽度为2的线条,那么总共是四个顶点,第一个顶点是从第一个端点 + 线宽造成的偏移量,线宽为2,所以偏移量的基数应该是2 / 2 = 1;

第二个顶点是从第一个端点 + 线宽造成的偏移量 * (-1),同样线宽为2,所以偏移量的基数应该是2 /2 * (-1) = -1;

依次类推,那么应该如何偏移呢? 这个与线段的走向有关,示例中 线段的走向可以用第二个端点 - 第一个端点计算出来:

(50,0) - (-50,0) = (100,0) ,归一化之后就是(1,0),此为线段的方向向量,表示的线段的走向的是沿x轴正方向,对于第一顶点,偏移的方向应该是(1,0)逆时针旋转90度,即和线段走向垂直的方向(与线段垂直的方向有两个,此处基于右手法则,选择逆时针旋转90度的一个),旋转90度之后,向量编程了(0,-1)

从图形学里面的数学知识可以得知,向量(x,y)逆时针旋转90度变成(-y,x);

 对于第二个顶点,偏移的方向应该是(1,0)顺时针旋转90度,但是前面,我们已经把偏移的基数变成-1了,所以可以认为偏移的方向还是(1,0)逆时针旋转90度,如图:

 


基于线段方向计算顶点偏移方向

由此,可以得出第一个顶点的位置是:

(-50,0) - (0,-1)* 1 = (-50,-1),

第二个顶点的位置是:

(-50,0)-(0,-1) * 1 = (-50,1)

对于第三,第四个顶点的计算也是类似的。

 

多个端点的情况

上面讨论的是只有两个端点的情况,事实上,如果是多个端点,以上讨论的情况只适合多个端点中第一个端点和最后一个端点的情况,对于中间的端点,偏移的方向要综合考虑这个端点连接的两条线段的情况,同样举例说明:

假设三个端点的情况,三个端点 分别是 (-50,0),(0,0),(0,50),现在要计算第二个端点(0,0)对应的两个顶点(第三、第四个),如图:

 


三个端点

此时要计算中间的端点的两个顶点位置,则需要考虑改端点连接的两天线段的方向:

 


线段方向计算偏移方向

计算的大致思路,通过该端点的和前一个端点相减 计算出第一条线段的方向:

(0,0) - (-50,0) = (50,0) = (1,0)(归一化)

在通过该该端点的下一个端点减去该端点计算出第二条线段的方向:

(0,50) - (0,0) = (0,50) = (0,1)(归一化)

然后两个方向向量相加,在旋转逆时针旋转90度,可以得到偏移的方向:

(1,0) + (0,1) = (1,1) = (0.707,0.707)(归一化)

旋转之后,偏移方向编程了(-0.707,0.707),

需要注意的是,此时的的偏移基数其实也是发生了变化的,拐角处的偏移量此时应该变成大了,即有了一个放大因子。 可以通过 1 / 偏移方向 点乘 第一条线段的方向 来获取这个放大因子,不过如果两条线段夹角很小,点乘的值也很小,放大因子很大,为了拐角处的尖角不显得是否大,我们一般限定放大因子不超过2. 因此公式可以变成:

1 / max(偏移方向 .  第一条线段的方向,0.5)

如何组织顶点数据

上面大量篇幅讲述了如何计算顶点坐标,事实上,前面文字所述的一切计算方法都是发生在顶点着色器中的,而且也只能在着色器中计算,因为最终显示到屏幕上的顶点与镜头相关,上文中只是简单的用了2维的情况模拟,如果在js端计算,将极大消耗性能。 (那你不是瞎扯吗,我们都还没搞清楚如何计算出要传递给顶点着色器的数据呢),其实不是瞎扯,因为只有搞清楚了在着色器中如何计算最终的顶点,才知道如何向顶点着色器中组织数据,

以上文中“多个端点的情况”的为例,我们可以总结出计算出一个顶点需要哪些数据:

端点坐标,偏移量,前一个端点坐标,后一个端点坐标

因此在着色器中需要定义四个attribute变量 position,offset,positionPrev,positionNext,分别用来接收端点坐标,偏移量,前一个端点坐标,后一个端点坐标。

对于前面两顶点,其端点没有前一个端点,此时前一个端点就取端点坐标,然后在着色器中判断 如果前一个端点点坐标 == 端点坐标,则表明是第一个端点;使用两个端点的情况计算。

低于后面两个顶点,其端点没有后一个端点,此时后一个端点就取端点坐标,然后在着色器中判断 如果后一个端点点坐标 == 端点坐标,则表明是最后一个端点;使用两个端点的情况计算。

对于中间的顶点,既存在端点坐标,也存在前一个端点的坐标,和后一个端点的坐标,就使用前面多个端点的情况计算。

还是以之前三个端点的例子为例,三个端点的(50,0,0),(0,0,0),(0,50,0),线宽为2(注意此时已经是三维坐标了,之前模拟的情况是用屏幕上的2维坐标来模拟顶点在着色器中通过透视变换变成了二维坐标的情况)

那么第一个顶点的四个变量的数据分别是:

端点坐标,      偏移量,  前一个端点坐标,后一个端点坐标

(50,0,0),2/2,       (50,0,0)                  (0,0,0)

第二个顶点的四个变量的数据分别是:

端点坐标,      偏移量,  前一个端点坐标,后一个端点坐标

(50,0,0),-2/2,       (50,0,0)                  (0,0,0)

 

第三个顶点的四个变量的数据分别是:

端点坐标,      偏移量,  前一个端点坐标,后一个端点坐标

(0,0,0),2/2,       (50,0,0)                  (0,50,0)

第四个顶点的四个变量的数据分别是:

端点坐标,      偏移量,  前一个端点坐标,后一个端点坐标

(0,0,0),-2/2,       (50,0,0)                  (0,50,0)

第五个顶点的四个变量的数据分别是:

端点坐标,      偏移量,  前一个端点坐标,后一个端点坐标

(0,50,0),2/2,       (0,0,0)                  (0,50,0)

第六个顶点的四个变量的数据分别是:

端点坐标,      偏移量,  前一个端点坐标,后一个端点坐标

(0,50,0),-2/2,       (0,0,0)                  (0,50,0)

到此为止,我们知道了如何组织绘制需要的顶点的数据。

下一篇将贴上相关代码说明。

更多精彩内容,请关注公众号。

 

ITman彪叔公众号
ITman彪叔公众号

 

 

0
0
分享到:
评论

相关推荐

    WebGL之绘制三维地球.docx

    编写着色器是绘制三维地球的第二步,我们需要编写顶点着色器和片段着色器。顶点着色器用来处理模型的几何信息,如顶点坐标、法线、贴图坐标等,而片段着色器用来处理模型的颜色信息,如颜色、光照等。 在本例中,...

    通过js底层获取H264的数据,然后通过webgl绘制出来

    看的懂,需要自己具备对js有自己的理解,原型链,this的指向,c++,webgl的基本理解和使用,ip地址是不能看的,因为播放的流量都是收费的,如果你们有ip,可以连接你们自己的ip地址,逻辑就是这样的逻辑,你让我分析...

    网页动画素材 WebGL基于canvas画布绘制3D噪音线条酷炫动画特效。(抖音资料)

    网页动画素材 WebGL基于canvas画布绘制3D噪音线条酷炫动画特效。(抖音资料)网页动画素材 WebGL基于canvas画布绘制3D噪音线条酷炫动画特效。(抖音资料)网页动画素材 WebGL基于canvas画布绘制3D噪音线条酷炫动画...

    html5 webgl绘制3D洞穴穿越无限延伸动画特效.zip

    这个“html5 webgl绘制3D洞穴穿越无限延伸动画特效.zip”文件包含了一套完整的实现3D洞穴穿越效果的代码示例,对于学习和应用WebGL的开发者来说,这是一个非常实用的学习资源。 首先,我们要理解WebGL的基本概念。...

    WebGL-water

    在Web环境中,WebGL通过JavaScript与GPU进行交互,绘制复杂的3D场景。开发者可以通过顶点着色器和片段着色器来定义物体的形状和颜色,这些着色器是用类似于C的语言GLSL(OpenGL Shading Language)编写的。 在WebGL...

    image3D::tangerine: 使用webGL绘制三维图片。:bar_chart::chart_increasing::party_popper:Drawing three-dimensional images using webGL

    :tangerine: image3D使用webGL绘制三维图片。:bar_chart::chart_increasing::party_popper: Drawing three-dimensional images using webGL.鉴于当前浏览器支持情况,本项目只支持webGL 1上下文,更高级版本未来会...

    webgl 实现的炫酷地球 基于three.js

    WebGL是一种在网页上实现3D图形渲染的技术,它允许开发者在浏览器中创建交互式的、图形丰富的应用程序,而无需任何插件。Three.js是基于WebGL的JavaScript库,它简化了WebGL的复杂性,提供了丰富的功能和易用的API,...

    WebGLVolumeRendering, WebGL体绘制容易.zip

    WebGLVolumeRendering, WebGL体绘制容易 WebGL体绘制容易一个非常简单的步骤介绍像素着色器体渲染使用和 ThreeJS 。转到 http://lebarba.com/blog/ 一步教程中的步骤在 GitHub http://www.lebarba.com/WebGL/

    WebGL 3D雪花飘落动画特效.zip

    【WebGL 3D雪花飘落动画特效】是一种利用JavaScript和WebGL技术在网页上实现的视觉效果。WebGL(Web Graphics Library)是基于OpenGL标准的JavaScript API,它允许开发者在浏览器环境中创建交互式的3D图形,无需插件...

    WebGL+鼠标响应+如何绘制爱心.rar

    这个项目特别关注的是鼠标响应,这意味着它将利用JavaScript事件处理程序来监听用户的鼠标动作,并根据这些动作在WebGL画布上绘制图形。 首先,要实现这个功能,你需要一个HTML文件来设置页面结构,引入JavaScript...

    HTML5 javascript调用WebGL实现 下雪闪电打雷下雪天气效果天气现象 太逼真了,这其实就是游戏开发了.zip

    HTML5 javascript调用webgl实现 下雪闪电打雷下雪天气效果天气现象 太逼真了,这其实就是游戏开发了.zip

    一种基于WebGL技术的网页端大量二维文字绘画技术_大量二维文字_webgl_three.js_

    一种可以在基于WebGL技术的主流浏览器上显示巨量二维矢量文本文字而不会明显增加浏览内存消耗和明显增加前端网页转化文本矢量数据所需时间的技术。通过此技术可以在一些低配置的设备上展示WebGL时当展示内容含有巨量...

    WEBGL_webgl_

    WebGL是一种基于OpenGL标准的JavaScript API,用于在任何兼容的Web浏览器中实现交互式的2D和3D图形渲染。这个“WEBGL_webgl_”很可能是一份教程或教材,旨在帮助初学者掌握WebGL技术,并随着学习者的进步不断更新...

    webgl入门-基础矩形绘制

    webgl入门-基础矩形绘制

    webgl入门-基础三角形绘制

    webgl入门-基础三角形绘制

    webgl-debug.js

    4. 绘制调用优化:通过分析绘制调用,"webgl-debug.js"可以帮助开发者发现潜在的性能瓶颈,比如不必要的状态更改或过度绘制。 5. 纹理与缓冲区检查:WebGL依赖于纹理和缓冲区来存储数据。"webgl-debug.js"可以确保...

    使用webGL绘制三维图片

    这个“使用WebGL绘制三维图片”的主题涵盖了多个关键知识点,包括WebGL的基本概念、工作原理、以及如何利用JavaScript来创建和操作三维场景。 1. **WebGL基础**: WebGL是WebGLRenderingContext接口的实现,它允许...

    WebGL 开发介绍.zip

    二、WebGL的工作原理 1. 渲染管线:WebGL遵循OpenGL的渲染管线模型,包括顶点处理、几何变换、光栅化和像素操作等阶段。 2. 着色器语言:WebGL使用GLSL(OpenGL Shading Language)编写着色器程序,控制顶点和像素的...

    Unity通用WebGL模板Universal WebGL Template 1.2.1

    Unity通用WebGL模板Universal WebGL Template 1.2.1是一个专为开发WebGL游戏或应用程序设计的工具。Unity是一款强大的跨平台游戏引擎,它允许开发者创建高质量的3D和2D游戏,并将其发布到多种设备上,包括浏览器。...

Global site tag (gtag.js) - Google Analytics