import static uk.co.nickthecoder.foocad.along.v2.Along.* /** Uses standard, old fashioned razor blades to make a knife. The blade is held in place by a tapered "slug" which goes through the blade's hole. The taper keeps the rod in place, but can be released if you push it. The blade can be slid further into the body, so that the blade is hidden. The slug goes into the 2nd hole (flip it round by 180 degrees). In the UK, this style of knife is often called a "stanley" knife (a brand name). However, this version is trickier to retract and extend the blade. */ class RazorBladeKnife : Model { // The length of the blade (ish) // Anything less that 95, and the slot begins to appear. @Custom var length = 120 @Custom var thickness = 12 // Ideally your thumb should be on the same side as the slot, so that your thumb // prevents the "slug" from coming out. @Custom var leftHanded = false // This is the size of the slot at the end of the cover. The slot is tapered, // so that the cover is wedged in place. @Custom var bladeT = 0.2 var height = 23 var roundRadius = 2 // The diameter of the middle of the slug (should be smaller than the hole // in the razor blade. var slugD = 6 var taper = 0.5 var slack = 0.5 fun bladeProfile() : Shape2d { return PolygonBuilder().apply { moveTo( 16, 0 ) lineTo( 30, 19 ) lineTo(-30, 19 ) lineTo(-16, 0 ) }.build() - Circle( 3.5 ).translateY( 9 ) } fun sideProfile() : Shape2d { val height = this.height - roundRadius * 2 return PolygonBuilder().apply { moveTo( length - height*1.4, 0 ) radius( height * 0.15 ) lineTo( length - height*0.5, height * 0.2 ) lineTo( length - height*0.5, height * 0.5 ) lineTo( 72, height ) lineTo( height*0.6, height ) radius(2) lineTo(0,0) }.build() } fun frontProfile() : Shape2d { return PolygonBuilder().apply { moveTo( 0.1, 0 ) lineTo( thickness/2-roundRadius, height - roundRadius*2 ) lineTo(-thickness/2+roundRadius, height - roundRadius*2 ) lineTo(-0.1, 0 ) }.build() } fun topProfile() : Shape2d { return PolygonBuilder().apply { //radius(1) moveTo( 0, -thickness/2 + roundRadius ) lineTo( length, -0.1 ) lineTo( length, 0.1 ) lineTo( 0, thickness/2 - roundRadius ) }.build() } @Piece fun knife() : Shape3d { val extrudeFront = frontProfile().extrude( length ) .alongX2().centerY() val extrudeSide = sideProfile().extrude( height - roundRadius * 2 ) .rotateX(90).centerY() val extrudeTop = topProfile().extrude( height ) val knife = extrudeSide / extrudeFront / extrudeTop val slot = Cube( 74, 1, 20 ).centerY() .translateZ(1.5) .translateX(-2) val hole = Cylinder( thickness + 0.1, slugD/2 + taper + slack, slugD/2 - taper + slack ) .sides(16) .rotateX(90) .centerY() .translate( 14, 0, 11 ) .color("Red") val holes = hole.translateX(27).also() val slide = Hull3d( holes ) - Cube( 100 ).center().backTo(0) .color("Red") return knife.minkowski( Sphere( roundRadius ).sides(10) ).bottomTo(0) - slot - slide - holes } @Piece fun slug() : Shape3d { val cylinder = Cylinder( thickness * 0.7, slugD/2 + taper, slugD/2 - taper*0.7 ) .sides(16) val a = Cylinder( thickness * 0.25 ,slugD/2 ) val rod = a.hull(a.translateX(27) ) return cylinder + rod } override fun build() : Shape3d { val blade = bladeProfile().extrude(bladeT) .rotateX(90).centerY() .translateX(14) .translateZ(2) .previewOnly() return knife() + slug().translate(14,thickness/2+slugD/2+1,0) + blade.translateX(27) } }