include include include function i_points(s1,s2)= [for(i=[0:len(s1)-2]) for(j=[0:len(s1[i])-2]) for(k=[0:len(s2)-2]) for(l=[0:len(s2[k])-2]) let( p1=s1[i][j], p2=s1[i][j+1], p3=s1[i+1][j], p4=s1[i+1][j+1], list=[p1,p2,p3,p4], v1=p2-p1, v2=p3-p1, v3=cross(v1,v2), pa=s2[k][l], pb=s2[k+1][l], v4=pb-pa, t=v3*(p1-pa)/(v3*v4)==undef?0:v3*(p1-pa)/(v3*v4), pt=pa+v4*t ) if(t>0 && t<=1 && pt.x>=min(list*[1,0,0]) && pt.x<=max (list*[1,0,0]) && pt.y>=min(list*[0,1,0]) && pt.y<=max (list*[0,1,0]) && pt.z>=min(list*[0,0,1]) && pt.z<=max (list*[0,0,1]) )pt ]; function prism(sec,path)=[for(p=path)[for(p1=bijection_offset(sec,p.x))[p1.x,p1.y,p.y]]]; function surf(sec,path)=[for(p=path)[for(p1=sec)[p.x,p1.y,p.y]]]; function add_p(p,p1=[0,0],n,i=0)= n==0?p1:add_p(p,[p[i].x+p1.x,p[i].y+p1.y],n-1,i+1); function pts(p)=[for(n=[1:len(p)])add_p(p=p,p1=[0,0],n=n,i=0)]; function add_p1(p,p1=[0,0,0],n,i=0)= n==0?p1:add_p1(p,[p[i].x+p1.x,p[i].y+p1.y,p[i].z],n-1,i+1); function pts1(p)=[for(n=[1:len(p)])add_p1(p=p,p1=[0,0,0],n=n,i=0)]; function near(sec,p)=let( a=[for(i=[0:len(sec)-1])[norm(p-[sec[i].x,sec[i].y]),i]], b=min(a*[1,0]), c=lookup(b,a))sec[c]; function q(vector=[1,0,0],point=[0,5,0],theta=0)= [ let( v=vector/norm(vector), p=[cos(theta/2),v*sin(theta/2)], p1=[p.x,-p.y], q=[0,point], pq=[p.x*q.x-p.y*q.y,p.x*q.y+p.y*q.x+cross(p.y,q.y)], pqp1=[pq.x*p1.x-pq.y*p1.y,pq.x*p1.y+pq.y*p1.x+cross(pq.y,p1.y)], transformation=pqp1.y )each transformation ]; module sec_hull(sec) for(i=[0:len(sec)-2]) for(j=[0:len(sec[i])-2]) let( i_plus=i+1, j_plus=j+1){ hull(){ translate(sec[i][j])cube(.01,true); translate(sec[i][j_plus])cube(.01,true); translate(sec[i_plus][j])cube(.01,true);} hull(){ translate(sec[i_plus][j_plus])cube(.01,true); translate(sec[i][j_plus])cube(.01,true); translate(sec[i_plus][j])cube(.01,true);} } sec00=[for(i=[0:5:360])[20*cos(i),20*sin(i)]]; path00=[[0,0],[-5,25]]; surf00=prism(sec00,path00); loft(surf00); sec01=[[0,-25],[0,25]]; path01=polyRound(pts1([[-25,5,0],[10,8,20],[10,-5,10],[10,8,20],[10,-9,20],[10,5,0]]),10); surf01=surf(sec01,path01); loft(surf01); path02=i_points(surf01,surf00); //for(p=path02)translate(p)cube(.5,true); path03=[[2,0],[-5+2,25]]; surf02=prism(sec00,path03); path04=i_points(surf01,surf02); //%loft(surf02); //color("magenta") //for(p=path04)translate(p)cube(.5,true); path05=[for(p=path01)p+[0,2]]; surf03=surf(sec01,path05); //%loft(surf03); path06=i_points(surf03,surf00); //color("blue") //for(p=path06)translate(p)cube(.5,true); path07=[for(p=sec00)near(path02,p)]; path08=[for(p=sec00)near(path04,p)]; path09=[for(p=sec00)near(path06,p)]; sec04=[for(i=[0:len(path08)-1])[path08[i],path09[i]]]; //color([.1,.7,.2,1]) //loft(sec04); //fillet sec05=[for(i=[0:len(path07)-1]) let(r=3, p0=path07[i],p1=path08[i],p2=path09[i], v1=p2-p1, p3=p1+v1/2, theta=asin(norm(p2-p3)/r), v2=p3-p0,u2=v2/norm(v2), p4=p3+u2*r*cos(theta), nv=cross(p1-p4,p2-p4), list=[for(i=[0:10:2*theta])p4+q(nv,p1-p4,i),p0] )list]; color("magenta") for(i=[0:len(sec05)-1]) for(p=sec05[i]) translate(p)cube(.2,true); sec_hull(sec05);