csharp [WIP] Unity Bezier
Posted
tags:
篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了csharp [WIP] Unity Bezier相关的知识,希望对你有一定的参考价值。
using System.Collections;
using System.Collections.Generic;
using UnityEngine;
public static class Bezier
{
public static Vector2 Calc(float t, Vector2[] pts)
{
return Calc(t, pts[0], pts[1], pts[2], pts[3]);
}
public static Vector2 Calc(float t, Vector2 pt0, Vector2 pt1, Vector2 pt2, Vector2 pt3)
{
t = Mathf.Clamp01(t);
return (1f - t) * (1f - t) * (1f - t) * pt0
+ 3f * (1f - t) * (1f - t) * t * pt1
+ 3f * (1f - t) * t * t * pt2 +
t * t * t * pt3;
}
}
using System.Collections;
using System.Collections.Generic;
using UnityEngine;
[RequireComponent(typeof(MeshFilter))]
[RequireComponent(typeof(MeshRenderer))]
public class BrushMesh : MonoBehaviour
{
struct VertexData
{
public Vector3[] vertices;
public int[] indices;
}
private MeshFilter _filter;
private MeshFilter Filter => _filter ?? (_filter = GetComponent<MeshFilter>());
[SerializeField]
private List<Vector3> _vertices = new List<Vector3>();
[SerializeField]
private List<int> _indices = new List<int>();
[SerializeField]
private float _radius = 0.1f;
private bool _isInit;
private int _offsetIndex = 0;
private bool _isMouseDown;
private Mesh _mesh;
[SerializeField]
private Camera _cam;
[SerializeField]
private Vector3 _mousePos;
void Awake()
{
// 筆跡を滑らかにするためにfps60にする
Application.targetFrameRate = 60;
}
void Update()
{
_isMouseDown = Input.GetMouseButton(0);
if (_isMouseDown)
{
_mousePos = Input.mousePosition;
// マウス座標をワールド座標に変換
_mousePos.z = -_cam.transform.position.z;
var pos = _cam.ScreenToWorldPoint(_mousePos);
Draw(pos);
}
}
public void Draw(Vector3 pos)
{
var data = CreateVertex(pos);
if (_mesh == null)
{
_mesh = new Mesh();
}
_mesh.vertices = data.vertices;
_mesh.SetIndices(data.indices, MeshTopology.Triangles, 0);
_mesh.RecalculateNormals();
Filter.mesh = _mesh;
}
VertexData CreateVertex(Vector3 pos)
{
if (_isInit == false)
{
// 初回処理
_isInit = true;
var pt0 = new Vector3(pos.x - _radius * 0.5f, pos.y, 0);
var pt1 = new Vector3(pos.x + _radius * 0.5f, pos.y, 0);
var pt2 = new Vector3(pos.x - _radius * 0.5f, pos.y, 0);
var pt3 = new Vector3(pos.x + _radius * 0.5f, pos.y, 0);
_vertices.Add(pt0);
_vertices.Add(pt1);
_vertices.Add(pt2);
_vertices.Add(pt3);
}
else
{
// 2回目以降
var pt2 = new Vector3(pos.x - _radius * 0.5f, pos.y, 0);
var pt3 = new Vector3(pos.x + _radius * 0.5f, pos.y, 0);
_vertices.Add(pt2);
_vertices.Add(pt3);
}
_indices.Add(_offsetIndex);
_indices.Add(_offsetIndex + 1);
_indices.Add(_offsetIndex + 3);
_indices.Add(_offsetIndex);
_indices.Add(_offsetIndex + 3);
_indices.Add(_offsetIndex + 2);
// 変数更新処理
_offsetIndex += 2;
return new VertexData()
{
vertices = _vertices.ToArray(),
indices = _indices.ToArray()
};
}
}
using System.Collections;
using System.Collections.Generic;
using UnityEngine;
public class DrawBezier : MonoBehaviour
{
[SerializeField]
private Vector2[] pts;
void Start()
{
var brush = GetComponent<BrushMesh>();
int len = 10;
for (int i = 0; i < len; i++)
{
var pt = Bezier.Calc((float) i / (float) len, pts);
brush.Draw(new Vector3(pt.x, pt.y));
}
Bezier.Calc(0, pts);
}
}
以上是关于csharp [WIP] Unity Bezier的主要内容,如果未能解决你的问题,请参考以下文章
csharp [WIP] NGUIのDOTween対応したエクステンション
Bezier Curve 贝塞尔曲线 - 在Unity中实现路径编辑
玩转贝塞尔曲线,教你在Unity中画Bezier贝塞尔曲线(二阶三阶),手把手教你推导公式