Loft not working as expected

lofting the two top curves will result in a polysurface, while sweep2 on the bottom curves will return a single surface as desired (using the arcs as rails and two lines as sweep shapes). The four curves have the same CV-stucture. I guess it has something to do with weighted CVs of the arc-like curves. The whole thing was baked from Grasshopper, but the original gh-definition produces the exact same results and I need the curves to stay unrebuilt.

Any explanations or workarounds?

loft_vs_sweep.3dm (94.6 KB)

Hi, I tries Loft with the rebuild option( 5 control points) and Normal. That made a single surface. —Mark

as I said:

Then you have to live with the result (from loft). Your curves have kinks, so with loft you’ll get several sub-surfaces (from the sub-curves) that are joined into a BRep.

Hallo Lagom,

thanks for contributing to the discussion!

Please tell me how you know that there are kinks in the curves? I tried to check this by:

1 running “explode” on the curves (…“Cannot explode single curve segments.”)

2 running curvature graph, which looks like constant curvature. I had assumed this because the curves were generated by slicing through a sphere and and a cylinder:

Also interesting:

I did a “Loft” between curve “1” and “3” which worked as expected, … unlike lofting between curve “1” and “2” … although all the curves share the same CV-structure. (See attached file)

thanks in advance for your feedback!

loft_vs_sweep03.3dm (139.9 KB)

Move the centre CP of each curve and you’ll see. Your curves are arcs (measure their radius, it is constant). Curve 1 and 3 seem concentric, you get a single surface, albeit with a kink also (move the CPs on the isocurve).

@Lagom When you use “kink” do you mean a discontinuity in the tangency of the curve, or do you mean a multi-knot? A fully multiple multi-knot will cause a discontinuity in the tangency of the curve unless the control points are located so that the curves have tangency continuity.

These curves have fully multiple multi-knots but the control point locations are such that the tangency and curvature are continuous. Split the curves at the multi-knots and GCon reports G2 continuity.

Multi-knots can cause Loft to create a polysurface rather than a single surface.

hi david and lagom,

thanks for the interesting insight! This might help adress the problem in Grasshopper.

btw: the grasshopper “CrvKinky” component detects “no kinks”.

I now changed all the CV-weights to the same value which made the loft work as a single surface (when moving the center CV, it stll shows as a “kink”.

But shouldn´t opting for “loose” instead of “straight” or “developable” in the loft settings produce a single surface anyhow in this case, even with different CV weights?

Well, I’m just a surface modelling/CAS person, not a grasshopperer, so others are better qualified to explain what happens there.

No that’s not what those settings are about. They’re about how the surface behaves between the curves, not the input curves themselves…look it up in the help. Frankly “loft” is a primitive tool I never actually use.

The loft command is perfect in many situations, for example when i need a quick “fill” for a 4-sided hole. It works the same in rhino and in grasshopper (except for the “developable” option" which is not there in rhino). So please keep on commenting on the way loft works in rhino, especially on how curves and CV-structure influences the surface generation. I posted the rhino file instead of the grasshopper definition to reach more people.

thats exactly what the discussion is about ; )

and if you don´t like the loft command, then maybe this thread is not for you ; )

_Loft converts non-NurbsCurves to NurbsCurves, then creates a merged knot vector for the output surface by taking the union of all the individual knot vectors. Even if the continuities at these knots are > G1, unequal weights trigger Rhino to split _Loft’s output at these knots.

In the case of your provided model, the 2 larger curves are already NurbsCurves with unequal non-zero knot spans. _Loft converts the ArcCurves to NurbsCurves with equal non-zero knot spans, takes the union of the knot vectors, and produces a surface with 2 fully-multiple knots. The face is split at both of those knots, resulting in 3 faces, when the Brep is added to the document.

A robust solution is to convert the input curves to NurbsCurves with similar knot vectors (so no changes occur after the knot union) and feed those into _Loft. To obtain a single surface, convert the arc-shaped curves (both ArcCurves and NurbsCurves) to rational, single-spanned NurbsCurves. These are not rebuilds, but exact NURBS equivalents of ArcCurves.

spb_Crv_ConvertArcToExactNurbs.py

hi steven,

thanks a lot for the comprehensive and understandable explanation!

I tried to put your script to a grasshopper component, which seems to work quite well. As I dont have and py skills I used Google AI.

I attached a definition with two variations of the py component. In the more complex one the “SplitSpans”-option for the “Angle LimitAction”-Input makes an error if “TargetDegree” is set to 3. In the simpler solution i erased the “Angle LimitAction” and “MaxAngleDeg2”-Inputs. Could this cause problems?

ConvertArcToExactNurbs.gh (25.8 KB)

The more complex Python component can be used by just modifying the input components:

  1. TargetDegree Should only be set to 2, 3, or 5.
  2. MaxAngleDeg2 Set Min to 90 and Max to 150.
  3. MaxAngleDeg3 Set Min to 180 and Max to 210.

The max. angle upper limits are not hard stops, but they result in reasonable CP locations and weight values.

Skipping inputs other than InCurves doesn’t cause problems because default values are then used.

thanks again!

I’m trying to understand the function of “MaxAngle…”. When setting TargetDegree to 3, dragging the slider for “MaxAngleDeg3” does not change anything. Just to get some clear understanding: is there some information in the Rhino help and in what command(s) context should this be searched for?

ConvertArcToExactNurbs2.gh (25.2 KB)

The output can only be single-span if the arc angle (as reported by _What) is below the MaxAngle value for the target degree. In the case of your provided model, two of the arcs are 104.4° and the other two are 115.4°. Since all the angles are below MaxAngleDeg3 when the Min of the input is set to 180°, the output is single-span.

I’m not aware of published documentation for this, but to study the way the Rhino UI converts ArcCurves to NurbsCurves, create arcs with angles as shown below and use _PointsOn to review their NURBS representations or use _ToNURBS to actually convert the arcs to NurbsCurves.

  • A 90.0° arc has 1 span
  • 90.1° has 2
  • 180.0° has 2
  • 180.1° has 4
  • 360.0° has 4

The closest the script can duplicate this behavior is to set the inputs as so:

  • TargetDegree to 2
  • AngleLimitAction to SplitSpans
  • MaxAngleDeg2 to 90

Rhino UI and the script differ when the angle is > 180.0 and <=270; the script outputs 3-span curves instead of 4.

thanks again for the explanations. to fully understand I have to dig deeper. for the moment and the running project your script is super usefull!

I have some problems running the py-component reliably in grasshopper. sometimes it produces no output. the misbehaviour may be related to how the py-component is structured, as i dont have any scripting skills and also dont know exactly how to integrate a script into a component.

renewing the py-component sometimes helps, also copying all the relevant components from my complex definition to a fresh one.

i attach the component in three variations: in this case, the full version with all the parameters exposed is working, the two simplyfied, relying pn the fallback values, don´t.

maybe someone experienced can check on them.

ConvertArcToExactNurbs3.gh (42.5 KB)

We have come to the same conclusion.