吴晓亮,黄襄念(西华大学计算机与软件工程学院,成都 610039)
Unity中使用贝塞尔曲线对三维物体进行弯曲
吴晓亮,黄襄念
(西华大学计算机与软件工程学院,成都610039)
三维物体在三维制作软件中进行弯曲,是很常见的。但是当导出模型到游戏引擎后就无法再改变形状,而现在一些虚拟现实的软件中,经常需要对三维物体进行实时的弯曲,如管道等。要想在游戏引擎中对三维物体进行变形,就只有通过算法编程进行实现[1]。而管道等这些长条型物体,可以看成一条粗的线,只不过这条线主要靠的是网格,而形成网格的基础就是网格点,通过使用贝塞尔曲线控制网格点,就可以控制三维物体的形状,达到弯曲变形的目的。
贝塞尔曲线是一种应用于二维图形应用程序的数学曲线。贝塞尔曲线由线段与节点组成,节点是可拖动的支点,线段像可伸缩的皮筋。通过拖动节点,可以改变线段的弯曲程度和弯曲方向。贝塞尔曲线有线性公式、二次方公式、三次方公式和一般参数公式,分别对应两个节点、三个节点、四个节点和任意节点的贝塞尔曲线。由于这里只会用到四个节点,所以只叙述三次方公式。
贝塞尔曲线的定义有四个点:起始点、终止点(也称锚点)以及两个相互分离的中间点。滑动两个中间点,贝塞尔曲线的形状会发生变化。
如图1,定义四个顶点P0、P1、P2、P3,曲线从P0走向P3,并不会经P1、P2两点。这两个点只是在那里提供方向信息。P0和P1之间的间距,决定了曲线在趋进P3之前,走向P2方向的长度有多长。
贝塞尔曲线公式[2]:
B(t)=P0(1-t)3+3P1t(1-t)3+3P2t2(1-t)+P3t3,t∈[0,1]
上述公式中,参数t可看做是线段百分比所在的位置,如图2所示。
三维物体的形成,主要靠的就是网格,而网格的形成则需要网格顶点。如图3-1所示的,就是一个圆柱体的网格,在建模的时候,都会看见模型上有着密密麻麻的网格,在网格的边相交的地方就是网格顶点,通过改变这些网格顶点的位置,相应的网格就会发生形状变化,从而让模型的形状发生改变。
图1 贝塞尔曲线效果图
图2 生成示意图
在Unity中,模型导入后形状就会固定,达不到想要弯曲变形的目的。要想在Unity中对模型实时操作变形,就需要通过算法来实现。
Unity中的网格信息是通过 GameObject的 Mesh-Filter组件中的mesh属性来获取。所以想要进行网格操作,必须为游戏对象添加一个MeshFiler游戏组件,而MeshFiler中的mesh属性中包含了三维游戏模型的法线、UV坐标、三角形和vertices顶点数组属性。三角形属性并不是单独保存,而是通过顶点数组间接保存。数组不使用特殊类表示三角形,而只是一个简单的整数指数列表。每一个三角形都是以三个点为一组,因此,前三个元素定义为第一个三角形,之后的三个元素定义为第二个三角形,并依此类推。
图3 三维网格
要对三维物体进行变形,只需要获得这组顶点数组,将每一个顶点的位置通过贝塞尔曲线算法进行计算,重新定位即可。具体算法如下[3]:
(1)将三维物体导入Unity引擎中,为其添加Mesh-Filer组件,通过它获取物体的mesh属性,再通过mesh获取物体的网格顶点vertices属性。
(2)为物体创建一条贝塞尔曲线。在三维物体的两端加入两个子物体,对应好位置,通过引擎提供的In-verseTransformPoint()函数将两个子物体的坐标点转化为三维物体的本地坐标点,并将此两点作为三阶贝塞尔曲线的两个端点。再在此两点中间任取两点,将其作为贝塞尔曲线的锚点。有了这四个顶点,就可以根据三阶贝塞尔曲线公式计算出一条适用于这个三维物体的一条曲线。
(3)将获取到的mesh属性的vertices数组取出,根据自己的物体要弯曲的轴向,选择相应的X、Y、Z轴,并找出相应轴的最大值和最小值,相减获得物体的总长,再将每个点对应的值和最小值相减并除以总长,得到每一个网格顶点在物体中的百分比。
(4)将百分比值传给贝塞尔曲线,计算出贝塞尔曲线对应的百分比所在点,并计算出此百分比对应的前一个点和后一个点。
(5)通过叉乘,计算出这个百分比所在的贝塞尔曲线上的切线方向和垂直方向的偏移量。
(6)将此切线偏移量和垂直偏移量和三维物体的vertices属性中对应百分比的点相加,得到新的网格顶点。
(7)重复上述(3)到(6)的操作步骤,计算出每一个网格顶点的值。如此得到一个新的网格顶点数组,将此数组赋给vertices得到新的vertices顶点属性,就改变了三维物体网格顶点的位置,从而使物体发生弯曲(如下图)。
图4 三维物体弯曲
本文给出了利用贝塞尔曲线对三维物体进行弯曲的实现算法,并且对Unity中的网格属性进行了简单的说明,使大家对网格有简单的认识,在实现算法时有一定的帮助。但是在Unity中实现此算法,需要掌握一些Unity3D的API[4],使用这些API进行计算,可以减少许多不必要的实现代码,可以大大地简化此算法的实现。
此算法扩大了贝塞尔曲线的应用,不只是局限于应用在二维平面中的线条,如今也可以应用于三维的条形状物体,具有一定的创新性。
[1]丁德红,方逵,饶大鹏,敬松.三维植物花朵动态仿真模型技术研究与实现[J].农机化研究,2014(5)
[2]王竹溪,郭敦仁著.特殊函数概论[M].北京:北京大学出版社,2012.
[3]陈江.VC实现贝塞尔曲线绘制[J].科技经济市场,2011(5)
[4]陈泉宏著.Unity API详解[M].北京:人民邮电出版社,2014.
[5]克利福德·彼得斯(Clifford Peters),斯特·奈·斯瑞(Thet Naing Swe)著.Unity 3D人工智能编程[M].李秉义译.北京:机械工业出版社,2015.
Bezier Curve;3D Object;Mesh Vertex;Bend
Using Bezier Curve to Bend 3D Objects in Unity
WU Xiao-liang,HUANG Xiang-nian
(School of Computer and Software Engineering,Xihua University,Chengdu610039)
1007-1423(2016)07-0057-03
10.3969/j.issn.1007-1423.2016.07.013
吴晓亮(1994-),男,四川简阳人,本科,研究方向为Unity开发
2016-01-26
2016-02-26
随着虚拟现实的发展,在游戏引擎中对三维物体进行弯曲效果的模拟越来越重要。在三维游戏引擎中,需要对一些三维的物体进行弯曲,以达到游戏操作中实时模拟物体弯曲。贝塞尔曲线算法是一个在计算机图形中常用的算法,被用于各类图形制作软件中,如Photoshop等软件,但多限于二维线条的应用,在三维物体上的应用较少。通过贝塞尔曲线算法结合三维物体的网格顶点,可以实现对条形三维物体进行弯曲变化。
贝塞尔曲线;三维物体;网格顶点;弯曲
2014年国家级大学生创新训练项目(No.201410623012)
黄襄念(1964-),男,四川人,教授,研究方向为图像/文字识别技术与系统、智能视频监控技术与系统、三维游戏图形引擎技术与系统、体感交互技术与虚拟现实系统
With the development of virtual reality,it’s increasingly important to simulate bending effect of 3D objects in game engine.In order to re-al-time simulate the bending of object in the 3D game engine,it needs to bend some 3D objects.Bezier curve algorithm is one of the common algorithms in computer graphics,which is used in all kinds of graphics software,such as Photoshop and so on.It is usually used in 2D lines while rarely in 3D objects.By combining Bezier curve algorithm with mesh vertex of the 3D objects,it can achieve to bend the bar 3D objects.