## Wednesday, December 19, 2012

### An End to Captive Nuts

I've been using 3D printed gears and timing pulleys for a while now, but have been very disappointed with the captive nuts that are used by most scripts available on Thingiverse. Generally I've found that the material being printed isn't stiff enough to allow the set screws to be tightened enough to secure to the shaft without deforming. This causes the pulley or gear to deform out of true.

To get around this I've started using clamping hubs.  They're not too much larger than the captive nut hubs but deform uniformly so the pulley/gear run true.

The picture above shows an example gear.  I've used an M3 screw in the clamping hub.  It ends up fixing very securely to the 8mm shaft and has the additional advantage of not marking the shaft.

I printed the gear above after using my Python Involute Gear Script to generate the involute profile, followed by the Python Constructive Solid Geometry Library to generate the hub and 3D model. The full source of the script that I used is shown below:

import gears
import pyPolyCSG as csg

def make_clamp_hub( B ):
thickness = 9
hub = csg.cylinder( B/2.0+6, thickness, True )
hub = hub + csg.cylinder( 4.0, B+10, True ).rotate( 90.0, 0.0, 0.0 ).translate( B/2+3, 0, 0 )
hub = hub - csg.cylinder( 2.0, 100, True ).rotate( 90.0, 0.0, 0.0 ).translate( B/2+3, 0, 0 )
hub = hub - csg.box( B/2+6, thickness, 2, True ).translate( B/2+3.5, 0, 0 )
return hub.rotate(90,0,0).translate( 0, 0, thickness/2-0.01 )

def make_gear( pressure_angle, pitch, teeth, thickness, bore ):
px, py = gears.gears_make_gear( pressure_angle, teeth, pitch )
coords = []
for i in range( 0, len(px) ):
coords.append( ( px[i], py[i] ) )
gear = csg.extrusion( coords, thickness ) + make_clamp_hub( bore ).translate( 0, 0, thickness )
gear = gear - csg.cylinder( bore/2.0, thickness*100, True ).rotate( 90.0, 0.0, 0.0 )
return gear

pressure_angle = 20.0
pitch          = 0.8
N1             = 12
B1             = 8.0+0.7
T1             = 10.0

gear1 = make_gear( pressure_angle, pitch, N1, T1, B1 )
gear1.save_mesh("gear_%gdeg_P%g_%d_tooth.obj" % ( pressure_angle, pitch, N1 ))


I've found that being able to use Python is much more convenient than OpenSCAD, mostly because its possible to define (real) variables and functions/classes.  As a result I've pretty much switched to using the Python CSG library from OpenSCAD.