润趣微游

 找回密码
 立即注册

QQ登录

只需一步,快速开始

扫一扫,访问微社区

搜索
热搜: 活动 交友 discuz
查看: 17|回复: 0

Unity创建贝塞尔曲线代码示例BezierLine

[复制链接]

67

主题

68

帖子

331

积分

管理员

Rank: 9Rank: 9Rank: 9

积分
331
发表于 2018-10-30 23:07:58 | 显示全部楼层 |阅读模式
CreateBezierLine
  1. using UnityEngine;
  2. using UnityEditor;
  3. using System.Collections;

  4. public class CreateBezierLine : ScriptableWizard {
  5.        
  6.         static public int m_iCreatedNum = 0;
  7.         public string LineName = "";
  8.         public int InterplateNumber = 4;
  9.        
  10.         [MenuItem ("GameObject/Create Bezier Line")]
  11.         static void CreateWizard () {
  12.                 ++m_iCreatedNum;
  13.                
  14.                 CreateBezierLine pBezierEditor = ScriptableWizard.DisplayWizard<CreateBezierLine>("Create Bezier", "Create");
  15.                 pBezierEditor.LineName = "Bezier" + CreateBezierLine.m_iCreatedNum.ToString();
  16.         }
  17.        
  18.         void OnWizardCreate () {
  19.                 GameObject pParentObj = new GameObject();
  20.                 pParentObj.name = LineName;
  21.                 pParentObj.transform.position = new Vector3(0.0f, 0.0f, 0.0f);
  22.                
  23.                 for (int i = 0; i < InterplateNumber; ++i) {
  24.                         GameObject pInterplateObj = GameObject.CreatePrimitive(PrimitiveType.Cube);
  25.                         pInterplateObj.name = "interplate" + i.ToString();
  26.                         pInterplateObj.transform.position = new Vector3(10.0f * i, 0.0f, 0.0f);
  27.                         pInterplateObj.transform.parent = pParentObj.transform;
  28.                        
  29.                         GameObject pControlObj = GameObject.CreatePrimitive(PrimitiveType.Cube);
  30.                         pControlObj.name = "control";
  31.                         pControlObj.transform.position = new Vector3(10.0f * i, 0.0f, 10.0f);
  32.                         pControlObj.transform.parent = pInterplateObj.transform;

  33.                 }
  34.                
  35.                 BezierLine pLine = pParentObj.AddComponent<BezierLine>();
  36.                 pLine.FixPoints(InterplateNumber);
  37.         }
  38. }
复制代码

BezierLine
  1. using UnityEngine;
  2. //using UnityEditor;
  3. using System.Collections;

  4. [ExecuteInEditMode]
  5. public class BezierLine : MonoBehaviour {
  6.        
  7.         public Color m_cDrawColor = Color.white;
  8.         public Transform[] m_pInterplatePoints;
  9.         public Transform[] m_pInterplateControlPoints;
  10.         public int m_iSampleNum = 64;
  11.         public int m_iInterplatePointNum = 0;
  12.         protected bool m_bEditorMode = true;
  13.         protected bool m_bPointFix = false;
  14.        
  15.         public Vector3[] m_vInterplationPoint = null;
  16.         public Vector3[] m_vInterplationControlPoint = null;
  17.         public Vector3[] m_vSamplePoints = null;
  18.        
  19.         public void Start() {
  20.                 if (null != m_pInterplatePoints && m_pInterplatePoints.Length > 2 && m_iInterplatePointNum == m_pInterplatePoints.Length) {
  21.                         m_bPointFix = true;
  22.                 }
  23.         }
  24.        
  25.         public void FixPoints(int iPointNumber) {
  26.                 m_pInterplatePoints = new Transform[iPointNumber];
  27.                 m_pInterplateControlPoints = new Transform[iPointNumber];
  28.                 m_vInterplationPoint = new Vector3[iPointNumber];
  29.                 m_vInterplationControlPoint = new Vector3[iPointNumber];
  30.                 for (int i = 0; i < iPointNumber; ++i) {
  31.                         m_pInterplatePoints[i] = GameObject.Find(gameObject.name + "/interplate" + i.ToString()).transform;
  32.                         m_vInterplationPoint[i] = m_pInterplatePoints[i].position;
  33.                         m_pInterplateControlPoints[i] = GameObject.Find(gameObject.name + "/interplate" + i.ToString() + "/control").transform;
  34.                         m_vInterplationControlPoint[i] = m_pInterplateControlPoints[i].position;
  35.                 }
  36.                 m_iInterplatePointNum = iPointNumber;
  37.                 m_bPointFix = true;
  38.                 SampleLocations();
  39.         }
  40.        
  41.         public void UseAsGame() {
  42.                 m_bEditorMode = false;
  43.                 for (int i = 0; i < m_iInterplatePointNum; ++i) {
  44.                         GameObject.Destroy(m_pInterplatePoints[i].gameObject.renderer);
  45.                         GameObject.Destroy(m_pInterplatePoints[i].gameObject.collider);
  46.                         GameObject.Destroy(m_pInterplateControlPoints[i].gameObject.renderer);
  47.                         GameObject.Destroy(m_pInterplateControlPoints[i].gameObject.collider);                       
  48.                 }
  49.         }
  50.        
  51.         public void Update() {
  52.                 if (m_bEditorMode && m_bPointFix) {
  53.                         bool bChanged = false;
  54.                         for (int i = 0; i < m_iInterplatePointNum; ++i) {
  55.                                 if (m_vInterplationPoint[i] != m_pInterplatePoints[i].position) {
  56.                                         bChanged = true;
  57.                                         break;
  58.                                 }
  59.                                 if (m_vInterplationControlPoint[i] != m_pInterplateControlPoints[i].position) {
  60.                                         bChanged = true;
  61.                                         break;
  62.                                 }                               
  63.                         }
  64.                        
  65.                         if (bChanged) {
  66.                                 SampleLocations();
  67.                         }

  68.                         for (int i = 0; i < (m_iInterplatePointNum - 1) * m_iSampleNum - 1; ++i) {
  69.                                 Debug.DrawLine(m_vSamplePoints[i],
  70.                                                m_vSamplePoints[i + 1], m_cDrawColor);
  71.                         }                       
  72.                        
  73.                         for (int i = 0; i < m_iInterplatePointNum; ++i) {
  74.                                 Debug.DrawLine(m_pInterplateControlPoints[i].position,
  75.                                                2.0f * m_pInterplatePoints[i].position - m_pInterplateControlPoints[i].position, m_cDrawColor);
  76.                         }
  77.                 }
  78.         }
  79.        
  80.         public void SampleLocations() {
  81.                 for (int i = 0; i < m_iInterplatePointNum; ++i) {
  82.                         m_vInterplationPoint[i] = m_pInterplatePoints[i].position;
  83.                         m_vInterplationControlPoint[i] = m_pInterplateControlPoints[i].position;
  84.                 }
  85.                
  86.                 m_vSamplePoints = new Vector3[m_iSampleNum * (m_iInterplatePointNum - 1)];
  87.                 for (int i = 0; i < m_iInterplatePointNum - 1; ++i) {
  88.                         Vector3 P0 = m_vInterplationPoint[i];
  89.                         Vector3 P1 = m_vInterplationControlPoint[i];
  90.                         Vector3 P2 = 2.0f * m_vInterplationPoint[i + 1] - m_vInterplationControlPoint[i + 1];
  91.                         Vector3 P3 = m_vInterplationPoint[i + 1];
  92.                        
  93.                         float Length = 0.0f;
  94.                         float q = 1.0f/(m_iSampleNum-1.0f);
  95.                        
  96.                         Vector3 a = P0;
  97.                         Vector3 b = 3.0f * (P1 - P0);
  98.                         Vector3 c = 3.0f * (P2 - 2.0f * P1 + P0);
  99.                         Vector3 d = P3 - 3.0f * P2 + 3.0f * P1 - P0;
  100.                        
  101.                         Vector3 S  = a;                                                // the poly value
  102.                         Vector3 U  = b*q + c*q*q + d*q*q*q;        // 1st order diff (quadratic)
  103.                         Vector3 V  = 2.0f*c*q*q + 6.0f*d*q*q*q;        // 2nd order diff (linear)
  104.                         Vector3 W  = 6.0f*d*q*q*q;                                // 3rd order diff (constant)
  105.                        
  106.                         Vector3 OldPos = P0;
  107.                         m_vSamplePoints[m_iSampleNum * i] = P0;
  108.                        
  109.                         for (int j = m_iSampleNum * i + 1; j < m_iSampleNum * (i + 1); ++j) {
  110.                                 S += U;                        // update poly value
  111.                                 U += V;                        // update 1st order diff value
  112.                                 V += W;                        // update 2st order diff value
  113.                                 // 3rd order diff is constant => no update needed.
  114.        
  115.                                 // Update Length.
  116.                                 Length += (S - OldPos).magnitude;
  117.                                 OldPos  = S;
  118.                                 m_vSamplePoints[j] = S;
  119.                         }
  120.                 }
  121.         }
  122.        
  123.         public Vector3 GetLocation(float fRate) {
  124.                 fRate = Mathf.Clamp(fRate, 0.0f, 0.9999f);
  125.                
  126.                 fRate = fRate * (m_iSampleNum * (m_iInterplatePointNum - 1) - 1);//0.0f to 190.999f
  127.                 int iPreLoc = Mathf.FloorToInt(fRate);
  128.                 fRate = fRate - iPreLoc;
  129.                 return m_vSamplePoints[iPreLoc] * (1.0f - fRate) + m_vSamplePoints[iPreLoc + 1] * fRate;
  130.         }
  131. }
复制代码





回复

使用道具 举报

您需要登录后才可以回帖 登录 | 立即注册

本版积分规则

QQ|Archiver|手机版|小黑屋|南京润趣网络科技有限公司 ( 苏ICP备16029781号 )

GMT+8, 2018-11-18 18:58 , Processed in 0.737782 second(s), 19 queries .

Powered by Discuz! X3.4

© 2001-2017 Comsenz Inc.

快速回复 返回顶部 返回列表