private void generate_ordered(List <Vector3> knots, bool generate_fine = false) { OrderedPoints = new List <Vector3>(); var path = new CubicBezierPath(knots.ToArray()); var mindist = 0.06f; var spacing = 0.08f; var max = (float)(knots.Count - 1) - 0.12f; var i = 0.12f; var last = P1; while (i < max) { var pt = path.GetPoint(i); if (Vector3.Distance(pt, last) >= mindist) { OrderedPoints.Add(pt); last = pt; } i += spacing; } if (!generate_fine) { return; } OrderedFinePoints = new List <Vector3>(); mindist = 0.04f; spacing = 0.03f; max = (float)(knots.Count - 1) - 0.04f; i = 0.04f; last = P1; while (i < max) { var pt = path.GetPoint(i); if (Vector3.Distance(pt, last) >= mindist) { OrderedFinePoints.Add(pt); last = pt; } i += spacing; } var mid_start = (P1 + OrderedFinePoints[0]) * 0.5f; var mid_end = (P2 + OrderedFinePoints[OrderedFinePoints.Count - 1]) * 0.5f; OrderedFinePoints.Insert(0, mid_start); OrderedFinePoints.Add(mid_end); }
private void OnEnable() { targetScript = (CubicBezierPathComponent)target; cubicBezierPath = targetScript.Path; settings = targetScript.EditorOnlyToolSettings; if (!Safety()) { SceneView.currentDrawingSceneView.ShowNotification(new GUIContent(PathEditorUtility.EditorUnavailable)); return; } }
public void Reset() { EditorOnlyToolSettings = new ToolSettings(); CubicBezier localBezier = new CubicBezier( new Vector3(0.5f, 0f, 0f), new Vector3(1.0f, 0.5f, 0f), new Vector3(0.5f, 1.0f, 0.5f), new Vector3(0f, 0.5f, 0.5f) ); Path = new CubicBezierPath(this.transform, localBezier); }
private bool Safety() { bool safe = true; //~ Fixes first run issues if (settings == null) { targetScript.Reset(); } cubicBezierPath = targetScript.Path; settings = targetScript.EditorOnlyToolSettings; //~ Fixes deleted transform issues if (cubicBezierPath.LocalSpaceTransform == null) { cubicBezierPath.LocalSpaceTransform = null; safe = false; } return(safe); }
public void move(Vector3 pos, Quaternion rotation, float pressure = 1f) { if (!mDrawing) { return; } if (mInputPoints.Count <= 2) { mInputPoints.Add(pos); mInputRotations.Add(rotation); } else { //blend position Vector3 lastPos = mInputPoints[mInputPoints.Count - 1]; Vector3 newPos = Vector3.Lerp(lastPos, pos, .35f); float dist = Vector3.Distance(newPos, lastPos); //blend rotation Quaternion lastRot = mInputRotations[mInputRotations.Count - 1]; Quaternion newRot = rotation; //Quaternion.Lerp(lastRot, rotation, .35f); if (dist < mMinDistance) { return; } // calculate thickness float newThick = dist; float prevThick = mThickness.Count < 1 ? newThick : mThickness[mThickness.Count - 1]; float currThick = Mathf.Lerp(prevThick, newThick, 0.2f); //lerp(prevThick, newThick, 0.2); float newPressure = pressure; float prevPressure = mPressure.Count < 1 ? newThick : mPressure[mPressure.Count - 1]; float currPressure = Mathf.Lerp(prevPressure, newPressure, 0.4f); //lerp(prevThick, newThick, 0.2); // get last 3 input points Vector3 prev2 = mInputPoints[mInputPoints.Count - 2]; Vector3 prev1 = mInputPoints[mInputPoints.Count - 1]; Vector3 cur = newPos; //come back to this bit //create bezier segment with inputs as control points Vector3[] pathPnts = new Vector3[3]; pathPnts[0] = (prev2 + prev1) / 2.0f; pathPnts[1] = prev1; pathPnts[2] = (prev1 + cur) / 2.0f; CubicBezierPath path = new CubicBezierPath(pathPnts); // divide segment adaptatively depending on its length // save vertices and thickness float pathLength = path.ComputeApproxLength(); int divisions = (int)(pathLength / mMinSegmentLength); for (int i = 1; i <= divisions; i++) { float t = i / (float)divisions; float thick = Mathf.Lerp(prevThick, currThick, t); float pressureStep = Mathf.Lerp(prevPressure, currPressure, t); Vector3 sampledPoint = path.GetPointNorm(t); Quaternion sampledRot = Quaternion.Lerp(lastRot, rotation, t); Vector3 norm = Vector3.Normalize(newPos - (mSampledPoints.Count > 0 ? mSampledPoints[mSampledPoints.Count - 1] : mInputPoints[mInputPoints.Count - 1])); Vector3 perp = new Vector3(-norm.y, norm.x, norm.z); Vector3 rotatedPerp = sampledRot * perp; mSampledPoints.Add(sampledPoint); mSampledRotations.Add(sampledRot); mThickness.Add(thick); mPressure.Add(pressureStep); mOffsets.Add(rotatedPerp); } mInputPoints.Add(newPos); mInputRotations.Add(newRot); updateMesh(); } }
private List <Vector3> get_contour(PolyBorder pb, float min_lat, float max_lat) { var dist = 0.08f; var pts = new List <Vector3>(); var norm = (pb.P2 - pb.P1).normalized; var prev = pb.P1; var lateral = Vector3.zero; for (var i = 0; i < pb.OrderedPoints.Count - 1; i++) { var pt = pb.OrderedPoints[i]; if (Vector3.Distance(prev, pt) < dist) { continue; } var behind = pb.OrderedPoints[Mathf.Max(i - 1, 0)]; var forward = pb.OrderedPoints[Mathf.Min(i + 1, pb.OrderedPoints.Count - 1)]; dist = UnityEngine.Random.Range(0.04f, 0.16f); var dir = (pt - behind).normalized; var lateral1 = Vector3.Cross(dir, Vector3.forward); dir = (forward - pt).normalized; var lateral2 = Vector3.Cross(dir, Vector3.forward); var true_lat = (lateral1 + lateral2) * 0.5f; if (i == 0) { true_lat = lateral2; } else if (i == pb.OrderedPoints.Count - 1) { true_lat = lateral1; } var shift = pt + true_lat * UnityEngine.Random.Range(min_lat, max_lat); pts.Add(shift); lateral = true_lat; prev = pt; } var endpt = pb.P2 + norm * 0.04f + lateral * min_lat; var endpt2 = pb.P2 + norm * 0.04f - lateral * min_lat; pts.Add(endpt); pts.Add(endpt2); prev = endpt; dist = 0.08f; var ordered = pb.Reversed().OrderedPoints; for (var i = 0; i < ordered.Count - 1; i++) { var pt = ordered[i]; if (Vector3.Distance(prev, pt) < dist) { continue; } var behind = ordered[Mathf.Max(i - 1, 0)]; var forward = ordered[Mathf.Min(i + 1, ordered.Count - 1)]; dist = UnityEngine.Random.Range(0.04f, 0.16f); var dir = (pt - behind).normalized; var lateral1 = Vector3.Cross(dir, Vector3.forward); dir = (forward - pt).normalized; var lateral2 = Vector3.Cross(dir, Vector3.forward); var true_lat = (lateral1 + lateral2) * 0.5f; if (i == 0) { true_lat = lateral2; } else if (i == ordered.Count - 1) { true_lat = lateral1; } var shift = pt + true_lat * UnityEngine.Random.Range(min_lat, max_lat); pts.Add(shift); lateral = true_lat; prev = pt; } endpt = pb.P1 - norm * 0.04f + lateral * min_lat; endpt2 = pb.P1 - norm * 0.04f - lateral * min_lat; pts.Add(endpt); pts.Add(endpt2); pts.Add(pts[0]); var path = new CubicBezierPath(pts.ToArray()); var max = (float)(pts.Count - 1) - 0.04f; var j = 0.04f; var spacing = 0.04f; var last = pb.P1; ordered = new List <Vector3>(); while (j < max) { var pt = path.GetPoint(j); if (Vector3.Distance(pt, last) >= spacing) { ordered.Add(pt); last = pt; } j += 0.04f; } return(ordered); }