#--------------------------------------------------------------------------- iritstate("EchoSource", FALSE); iritstate("InterCrv", FALSE); RESOLUTION = 15; BODY_WIDTH = 13.6; COLUMN_WIDTH = 1; BASE_WIDTH = BODY_WIDTH + 2 * 0.2 + 2 * COLUMN_WIDTH + 2 * 0.1; FLOOR = -3.6; EPS = 0.0001; #--------------------------------------------------------------------------- roundRect = function(xMin, xMax, yMin, yMax, radius): curve = arc(vector(xMin, yMax - radius, 0), vector(xMin + radius, yMax - radius, 0), vector(xMin + radius, yMax, 0)) + arc(vector(xMax - radius, yMax, 0), vector(xMax - radius, yMax - radius, 0), vector(xMax, yMax - radius, 0)) + arc(vector(xMax, yMin + radius, 0), vector(xMax - radius, yMin + radius, 0), vector(xMax - radius, yMin, 0)) + arc(vector(xMin + radius, yMin, 0), vector(xMin + radius, yMin + radius, 0), vector(xMin, yMin + radius, 0)): if(yMax - radius == yMin + radius, return = curve, return = curve + ctlpt(E2, xMin, yMax-radius)); #--------------------------------------------------------------------------- makePoly = function(closedCurve): return = gpolygon(boolone(closedCurve), off); #--------------------------------------------------------------------------- continue = function(curve, length): tMax = nth(pdomain(curve), 2): cPt = ceval(curve, tMax): pt = vector(coord(cPt, 1), coord(cPt, 2), coord(cPt, 3)): return = pt + ctangent(curve, tMax) * length; #--------------------------------------------------------------------------- makeBody = function(final): middleProfile = roundRect(-2, 4, -2, 2, 2): sideProfile = roundRect(-2, 3, -2, 2, 2): return = sfromcrvs(list(sideProfile * trans(vector(0, 0, BODY_WIDTH/2)), middleProfile * trans(vector(0, 0, BODY_WIDTH/4)), middleProfile, middleProfile * trans(vector(0, 0, -BODY_WIDTH/4)), sideProfile * trans(vector(0, 0, -BODY_WIDTH/2))), 4): if(final == TRUE, cut = roundRect(2, 6, -2, 2, 1) * rotx(90) * trans(vector(0, -3, 0)): cut = extrude(cut, vector(0, 6, 0)): return = return * -cut: side = makePoly(sideProfile): return = mergepoly(list(return, -side * trans(vector(0, 0, BODY_WIDTH/2 )), side * trans(vector(0, 0, -BODY_WIDTH/2 )))): color(return, GREEN), return); #--------------------------------------------------------------------------- makeCap = function(): body = makeBody(FALSE): return = roundRect(1.25, 6.25, -2.5, 2.5, 1) * rotx(90) * trans(vector(0.5, -4, 0)): return = extrude(return, vector(-1, 8, 0)): return = return * -body: body = offset(body, -0.1, 0.1, off): return = body * return: color(return, RED); #--------------------------------------------------------------------------- makeBase = function(): pt1 = ctlpt(E3, 0, 0.5, 0): pt2 = ctlpt(E3, 0, 0.7, 0): pt3 = ctlpt(E3, 0.2, 0.75, 0): c = ctlpt(E3, 0, 0, 0) + cbezier(list(pt1, pt2, pt3)): pt4 = continue(c, 2.5): pt5 = ctlpt(E3, 5, 0.15, 0): c = c + cbezier(list(pt3, pt4, pt5)): pt6 = continue(c, 0.1): pt7 = ctlpt(E3, 5.1, 0, 0): sideProfile = c + cbezier(list(pt5, pt6, pt7)) + ctlpt(E3, 0, 0, 0): koeff = 5.7/5: middleProfile = sideProfile * scale(vector(koeff, koeff, koeff)): return = sfromcrvs(list(sideProfile * trans(vector(0, 0, BASE_WIDTH/2)), middleProfile * trans(vector(0, 0, BASE_WIDTH/4)), middleProfile, middleProfile * trans(vector(0, 0, -BASE_WIDTH/4)), sideProfile * trans(vector(0, 0, -BASE_WIDTH/2))), 4): return = return * trans(vector(-2.3, FLOOR, 0)); #--------------------------------------------------------------------------- makeColumn = function(): # |(x, y)| = r # ((p - (x, y)) * (x, y) = 0 pX = 2.25: pY = FLOOR + 0.1: radius = 1.9: a = sqr(pX) + sqr(pY): b = -2 * sqr(radius) * pX: c = sqr(sqr(radius)) - sqr(pY) * sqr(radius): x = (-b + sqrt(sqr(b) - 4 * a * c)) / (2 * a): y = sqrt(sqr(radius) - sqr(x)): profile = ctlpt(E2, pX, pY) + arc(vector( x, y, 0), vector( 0, 0, 0), vector(-x, y, 0)) + ctlpt(E2, -pX, pY) + ctlpt(E2, pX, pY): return = extrude(profile, vector(0, 0, 1)): profile = makePoly(profile): return = mergepoly(list(-profile, profile * trans(vector(0, 0, COLUMN_WIDTH)), gpolygon(return, off))): return = return * trans(vector(0, 0, BODY_WIDTH/2 + 0.2)); #--------------------------------------------------------------------------- makeSide = function(): sin25 = sin(25 * PI / 180): cos25 = cos(25 * PI / 180): radius = (BASE_WIDTH - 0.2) / 2: return = arc(vector(-radius * sin25, FLOOR - 0.1, radius * cos25), vector( 0, FLOOR - 0.1, 0), vector( radius * sin25, FLOOR - 0.1, radius * cos25)): return = extrude(return, vector(0, 5.7, -0.4)); #--------------------------------------------------------------------------- makeSupport = function(): column = makeColumn(): side = makeSide(): base = makeBase(): return = (base + column) * side: column = column * roty(180): side = side * roty(180): return = (return + column) * side: color(return, MAGENTA); #--------------------------------------------------------------------------- makeLeg = function(): profile = ctlpt(E1, 2) + arc(vector( 2, 0, 0.8), vector( 1.4, 0, 0.8), vector( 1.4, 0, 1.4)) + arc(vector(-1.4, 0, 1.4), vector(-1.4, 0, 0.8), vector(-2, 0, 0.8)) + ctlpt(E1, -2) + ctlpt(E1, 2): profile = profile * trans(vector(0, FLOOR + 0.2, BODY_WIDTH / 2 - 0.8)): leg = extrude(profile, vector(0, -0.4, 0)): profile = makePoly(profile): leg = leg ^ (profile * trans(vector(0, -0.4, 0))): return = list(leg, leg * roty(180)): color(return, WHITE); #--------------------------------------------------------------------------- makeStopper = function(): stopper = box(vector(-0.8, -1.5, 2.6), 1.6, -1.5, 0.2): return = list(stopper, stopper * roty(180)): color(return, YELLOW); #--------------------------------------------------------------------------- makeSpindel = function(): spindel = extrude(circle(vector(0, 0, BODY_WIDTH / 2 - 0.1), 1.5), vector(0, 0, 0.4)): return = list(spindel, spindel * roty(180)): color(return, YELLOW); #--------------------------------------------------------------------------- makeTube = function(): return = surfrev(ctlpt(E3, 0, EPS, 0) + ctlpt(E3, 0, 0.5, 0) + ctlpt(E3, 0, 0.5, 1) + ctlpt(E3, 0, 0.8, 1) + ctlpt(E3, 0, 0.8, 1.3) + ctlpt(E3, 0, 0.9, 1.3) + ctlpt(E3, 0, 0.9, 1.75) + ctlpt(E3, 0, 0.85, 1.8) + ctlpt(E3, 0, EPS, 1.8)) * roty(90) * trans(vector(1.6,0,0)): color(return, BLUE); #--------------------------------------------------------------------------- makeTail = function(): return = list( con2(vector(-1.5, 0, 0), vector(-1, 0, 0), 0.5, 0.4), sweepsrf(circle(vector(0, 0, 0), 0.2), ctlpt(E1, -2) + cbezier(list(ctlpt(E2, -3, 0), ctlpt(E2, -5, 0), ctlpt(E2, -5, FLOOR + 0.2), ctlpt(E2, -7, FLOOR + 0.2))), off)): color(return, CYAN); #--------------------------------------------------------------------------- makeHolder = function(): curve = arc(vector(0, 0, 0.4), vector(0, 0, 0), vector(0, 0.4 * sin(120 * PI / 180), 0.4 * cos(120 * PI / 180))): profile = ctlpt(E2, 0.1, 0.15) + ctlpt(E2, -0.1, 0.15) + ctlpt(E2, -0.1, -0.15) + ctlpt(E2, 0.1, -0.15) + ctlpt(E2, 0.1, 0.15): holder = sweepsrf(profile, curve, off): holder = holder ^ makePoly(csurface(holder, ROW, 1)): return = list(holder, holder * rotz(180) * trans(vector( 0.35, 0, 0)), holder * rotz(180) * trans(vector(-0.35, 0, 0))): return = return * trans(vector(0, FLOOR + 0.6, -BASE_WIDTH / 2 - 0.1)); #--------------------------------------------------------------------------- makeMicro = function(): return = surfrev(ctlpt(E3, 0, EPS, -1.4) + ctlpt(E3, 0, 0.15, -1.4) + ctlpt(E3, 0, 0.2, -0.6) + ctlpt(E3, 0, 0.3, -0.6) + ctlpt(E3, 0, 0.3, 0.5) + ctlpt(E3, 0, 0.35, 0.6) + ctlpt(E3, 0, 0.35, 1.4) + ctlpt(E3, 0, EPS, 1.4)) * roty(90) * trans(vector(0, FLOOR + 0.6, -BASE_WIDTH / 2 - 0.1)): color(return, BLUE); #--------------------------------------------------------------------------- makeWire = function(): return = sweepsrf(circle(vector(0, 0, 0), 0.1), ctlpt(E1, -1) + cbezier(list(ctlpt(E2, -1.4, 0), ctlpt(E2, -3, 0), ctlpt(E2, -5, -0.5), ctlpt(E2, -7, -0.5))), off): return = return * trans(vector(0, FLOOR + 0.6, -BASE_WIDTH / 2 - 0.1)): color(return, CYAN); #--------------------------------------------------------------------------- makeView = function(): return = roty(-130) * scale(vector(0.1, 0.1, 0.1)) * rotx(25); #--------------------------------------------------------------------------- makeBack = function(): return = poly(list(vector(-BASE_WIDTH, 3 * BASE_WIDTH, 3 * BASE_WIDTH), vector(-BASE_WIDTH, 3 * BASE_WIDTH, -3 * BASE_WIDTH), vector(-BASE_WIDTH, -3 * BASE_WIDTH, -3 * BASE_WIDTH), vector(-BASE_WIDTH, -3 * BASE_WIDTH, 3 * BASE_WIDTH)), FALSE): attrib(return, "rgb", "64,0,0"); #--------------------------------------------------------------------------- moveCap = function(cap, n): body = makeBody(FALSE): domain = pdomain(body): path = csurface(body, COL, (nth(domain, 1) + nth(domain, 2)) / 2): domain = pdomain(path): endT = nth(domain, 2): middleT = (nth(domain, 1) + endT) / 2: p = ceval(path, middleT): return = cap * trans(-vector(coord(p, 1), coord(p, 2), coord(p, 3))): t = (100 - n) * middleT / 100 + n * endT/ 100: alpha = acos(ctangent(path, t) * ctangent(path, middleT)) * 180 / PI: return = return * roty(alpha): p = ceval(path, t): return = return * trans(vector(coord(p, 1), coord(p, 2), coord(p, 3))); #--------------------------------------------------------------------------- iritstate("EchoSource", TRUE); #--------------------------------------------------------------------------- view_mat = makeView(); dark = list(makeTube(), makeMicro()); camera = list( makeBody(TRUE), makeSupport(), moveCap(makeCap(), 75), makeLeg(), makeStopper(), makeSpindel(), makeTail(), makeHolder(), makeWire(), dark, view_mat); view(camera, TRUE); attrib(camera, "rgb", "128,128,128"); attrib(dark, "rgb", "32,32,32"); snoc(makeBack(), camera); #save("/tmp/camera.dat", camera);