#----------------------------------------------------------------------------- # Name : gear.3.rb # Description : This file creates a involute tooth gear, with or without a hole for shaft and key. # Parameters : The number of teeth, pressure angle, pitch radius, shaft radius, keyway width and depth. # Menu Item : Draw -> Involute Gear # : Draw -> Key Involute Gear # Context Menu: NONE # Usage : N/A # Date : 9/2/2006 # Author : Doug Herrmann #----------------------------------------------------------------------------- require 'sketchup.rb' #============================================================================= # Generates an Involute Tooth Gear class Gear # default values for dialog box @@teeth = 9 @@ang_pressure = 20.0 # degrees @@rad_pitch = 10.0.inch def Gear.dialog # First prompt for the dimensions. prompts = ["Number of Teeth: ", "Pressure Angle: ", "Pitch Radius: "] values = [@@teeth, @@ang_pressure, @@rad_pitch] # Display the inputbox results = inputbox prompts, values, [nil,'14.5|20.0|25.0'], "Involute Gear Parameters" return if not results # This means that the user cancelled the operation # update default settings @@teeth, @@ang_pressure, @@rad_pitch = results Gear.new end def initialize(teeth=@@teeth, ang_pressure=@@ang_pressure, rad_pitch=@@rad_pitch) @teeth = teeth @ang_pressure = ang_pressure * Math::PI / 180.0 # convert to radians @rad_pitch = rad_pitch # Constants really -- as long as the original parameters don't change @diameter = 2.0 * @rad_pitch @rad_outside = @rad_pitch + @diameter/@teeth # + 1/diametral pitch @rad_inside = @rad_pitch - @diameter/@teeth # - 1/diametral pitch @rad_root = @rad_pitch - 1.157*@diameter/@teeth # - 1.157/diametral pitch @rad_base = @rad_pitch * Math.cos(@ang_pressure) @rad_fillet = @rad_inside - @rad_root # Encapsulate into a single UNDO operation. model = Sketchup.active_model model.start_operation "Create Involute Gear" # Group the entities - And save the SketchUp Group Entities object as a class variable entities = model.active_entities group = entities.add_group @entities = group.entities drawGear model.commit_operation end private def drawGear edges = drawProfile face = @entities.add_face edges end # points on involute curve parameterized by ang (in radians) def involute(ang) x1 = @rad_base * Math.cos(ang) y1 = @rad_base * Math.sin(ang) s = ang * @rad_base x = x1 + s * Math.sin(ang) y = y1 - s * Math.cos(ang) [x, y] end def drawProfile points = [] # Fillet points on right side of tooth if @rad_inside <= @rad_base points = filletPoints @rad_inside, -@rad_fillet ang = 0 else # calc angle and coordinate involute intersects inside radius s = Math.sqrt(@rad_inside * @rad_inside - @rad_base * @rad_base) ang = s / @rad_base x0, y0 = involute(ang) points = filletPoints x0, y0 - @rad_fillet end # calc value of parameter where Involute curve intersects outside radius s_max = Math.sqrt(@rad_outside * @rad_outside - @rad_base * @rad_base) ang_max = s_max / @rad_base # calc Involute curve points along tooth's right side ang += 7 * Math::PI / 180.0 while ang < ang_max x, y = involute(ang) points.push([x, y, 0]) ang += 7 * Math::PI / 180.0 end #Compute last point where involute intersects the outside circle x, y = involute(ang_max) points.push([x, y, 0]) # Rotate profile CW so that it intersects the x-axis at the Pitch radius s = Math.sqrt(@rad_pitch**2 - @rad_base**2) delta = (s / @rad_base) - @ang_pressure t0 = Geom::Transformation.rotation [0,0,0], Z_AXIS, -delta points.collect! {|pnt| t0 * pnt} # Reflect about the x-axis t1 = Geom::Transformation.rotation [0,0,0], X_AXIS, Math::PI # Rotate CW a tooth-space t2 = Geom::Transformation.rotation [0,0,0], Z_AXIS, -Math::PI/@teeth # The left profile of the adjacent tooth t = t2 * t1 reflect = points.collect {|pnt| t * pnt} # Left profile, space, right profile points = reflect.reverse! + points # Center tooth along x-axis t3 = Geom::Transformation.rotation [0,0,0], Z_AXIS, -Math::PI/(2.0*@teeth) points.collect! {|pnt| t3 * pnt} # vertices for edge p1 = points.last p2 = [p1.x, -p1.y, 0] # Now add curves and edges outlining the gear edges = [] 0.upto(@teeth - 1) do |n| tr = Geom::Transformation.rotation [0,0,0], Z_AXIS, 2 * Math::PI * n / @teeth # add curve edges += @entities.add_curve points.collect {|pnt| tr * pnt} # add edge at top of tooth edges += @entities.add_edges tr*p1, tr*p2 end # return edges edges end def filletPoints(x0, y0) points = [] #deg = 180 downto 90 ang = Math::PI 4.times do x = x0 + @rad_fillet * Math.cos(ang) y = y0 + @rad_fillet * Math.sin(ang) points.push([x, y, 0]) ang = ang - Math::PI / 6.0 end points end end #============================================================================= # Generates an Involute Tooth Gear with hole for shaft and key class KeyGear < Gear # default values for dialog box @@rad_shaft = 4.inch @@width_key = 2.inch @@height_key = 1.5.inch def KeyGear.dialog # First prompt for the dimensions prompts = ["Number of Teeth: ", "Pressure Angle: ", "Pitch Radius: ", "Shaft Radius: ", "Keyway Width: ", "Keyway Depth: "] values = [@@teeth, @@ang_pressure, @@rad_pitch, @@rad_shaft, @@width_key, @@height_key] # Display the inputbox results = inputbox prompts, values, [nil,'14.5|20.0|25.0'], "Key Involute Gear Parameters" return if not results # This means that the user cancelled the operation # update default settings @@teeth, @@ang_pressure, @@rad_pitch, @@rad_shaft, @@width_key, @@height_key = results KeyGear.new end def initialize(teeth=@@teeth, ang_pressure=@@ang_pressure, rad_pitch=@@rad_pitch, rad_shaft=@@rad_shaft, width_key=@@width_key, height_key=@@height_key) # Class variables unique to Key Gear @rad_shaft = rad_shaft @width_keyhole = width_key @height_keyhole = height_key super(teeth, ang_pressure, rad_pitch) end private def drawGear # Draw gear face1 = super # Create interior face for shaft and keyway edges2 = drawKey face2 = @entities.add_face edges2 # knock out a hole face2.erase! end def drawKey opp = @width_keyhole / 2 adj = Math.sqrt(@rad_shaft**2 - opp**2) phi = Math.atan2(opp, adj) # Unit vectors along the X-axis and Z-axis i = Geom::Vector3d.new 1,0,0; i.normalize! k = Geom::Vector3d.new 0,0,1; k.normalize! # Draw shaft arc edges1 = @entities.add_arc [0,0,0], i, k, @rad_shaft, phi, 2*Math::PI - phi, 48 # points on keyway p1 = [adj, -opp, 0] p2 = [adj + @height_keyhole, -opp, 0] p3 = [adj + @height_keyhole, +opp, 0] p4 = [adj, +opp, 0] # edges along keyway edges2 = @entities.add_edges p1, p2, p3, p4 # Return edges edges1 + edges2 end end #============================================================================= # User Interface Stuff if( not file_loaded?("gear.3.rb") ) # This will add a separator to the menu, but only once add_separator_to_menu($exStrings.GetString("Draw")) # Add items to Draw menu UI.menu($exStrings.GetString("Draw")).add_item($exStrings.GetString("Involute Gear")) { Gear.dialog } UI.menu($exStrings.GetString("Draw")).add_item($exStrings.GetString("Key Involute Gear")) { KeyGear.dialog } end #----------------------------------------------------------------------------- file_loaded("gear.3.rb")