sghr / iGeo

iGeo: Computational Design and 3D Modeling Library for Processing
http://igeo.jp
GNU Lesser General Public License v3.0
146 stars 34 forks source link

How to sample ICurveGeo evenly based on the curve length? not the u coordinates #21

Open chatyan opened 5 years ago

chatyan commented 5 years ago

Hi, I am new to this great library. Currently, I want to get sampling points evenly on the ICurveGeo. I have tried to use pt(double u) function and got some points based on evenly sampling the u coordination. I just wonder if there is a way to let the user sampling points based on the arc-length of the curve, so the user can get those sampling points accurately.

Thanks a lot. Again great library for 3D modeling in Java

sghr commented 5 years ago

Thank you for the comment. Unfortunately I don't have a method to sample NURBS curves evenly by the length in the XYZ space with mathematically accurate inverse calculation from XYZ to U. What I would do is just approximate it by lengths of line segments like the code below. You could replace the length calculation with arc-length calculation by 3 points or 2 points + tangent vectors to make it more accurate, or simply increase resolution of the line segment approximation depending on how much accuracy you need. Thanks! Satoru

` import igeo.*; size(1000,800,IG.GL); ICurve crv = new ICurve(IG.v(0,0,0, 100,0,0, 110,50,0, 120,0,0, 50,-50,0),3);

int div = 10; double len = 0; // you could also use len() method, which is also linear approximation. //double len = crv.len(); int res = 1000; IVec prevPt = crv.pt(0); for(int i=1; i<=res; i++){ IVec pt = crv.pt(i*1./res); len += pt.dist(prevPt); prevPt = pt; }

int idx = 0; double curlen = 0; prevPt = crv.pt(0); for(int i=1; i<=res; i++){ IVec pt = crv.pt(i1./res); curlen += prevPt.dist(pt); for(; curlen >= len/dividx; idx++){ double ratio = (curlen - len/div*idx)/ prevPt.dist(pt); double u = (i-ratio)/res; new IPoint(crv.pt(u)).clr(1.,0,0); } prevPt = pt; } `

chatyan commented 5 years ago

Your comment really helps me a lot! Many thanks!