--- /dev/null
+
+$fn = 100;
+axis_diameter = 6;
+axis_clearance = 0.5;
+wheel_diameter_middle = 32;
+wheel_diameter_edge = 31;
+wheel_width = 22;
+wheel_inner_diameter = axis_diameter + axis_clearance;
+quarter_pin_height = (wheel_diameter_edge - wheel_inner_diameter) / 2 / 2 / 5;
+halfpin_length = wheel_diameter_edge / 2 / 2;
+wheel_pin_space_width = wheel_width * 0.7;
+pin_clearance = 1;
+pin_width = wheel_pin_space_width - pin_clearance;
+pin_space_height = quarter_pin_height;
+pin_head_height = pin_space_height / 2 * 0.9;
+pin_head_length = halfpin_length / 3;
+pin_spacer_length = halfpin_length * 0.2;
+
+module quarter_pin_profile()
+{
+ height = quarter_pin_height;
+ length = halfpin_length;
+ square([height, length], center = false);
+ polygon([[height, length], [height + pin_head_height, length - pin_head_length], [height, length - pin_head_length]]);
+}
+
+module half_pin_profile()
+{
+ translate([pin_space_height / 2, 0])
+ quarter_pin_profile();
+ mirror([1, 0])
+ translate([pin_space_height / 2, 0])
+ quarter_pin_profile();
+ translate([0, pin_spacer_length / 2])
+ square([pin_space_height, pin_spacer_length], center = true);
+}
+
+module pin()
+{
+ translate([0, 0, -pin_width / 2])
+ {
+ linear_extrude(pin_width, v = [0, 0, 1])
+ {
+ half_pin_profile();
+ mirror([0, 1])
+ half_pin_profile();
+ }
+ }
+}
+
+module pin_full()
+{
+ translate([0, 0, -wheel_pin_space_width / 2])
+ {
+ linear_extrude(wheel_pin_space_width, v = [0, 0, 1])
+ {
+ half_pin_profile();
+ mirror([0, 1])
+ half_pin_profile();
+ }
+ }
+ cube([pin_space_height, 2 * halfpin_length, wheel_pin_space_width], center = true);
+}
+
+module half_wheel()
+{
+ difference()
+ {
+ cylinder(d1 = wheel_diameter_middle, d2 = wheel_diameter_edge, h = wheel_width / 2, center = false);
+ cylinder(d = wheel_inner_diameter, h = wheel_width / 2, center = false);
+ }
+}
+
+module wheel()
+{
+ half_wheel();
+ mirror([0, 0, 1])
+ half_wheel();
+}
+
+module pinned_half_wheel()
+{
+ difference()
+ {
+ wheel();
+ translate([0, 50, 0])
+ cube([100, 100, 100], center = true);
+ translate([(wheel_diameter_edge + wheel_inner_diameter) / 2 / 2, 0, 0])
+ pin_full();
+ translate([-(wheel_diameter_edge + wheel_inner_diameter) / 2 / 2, 0, 0])
+ pin_full();
+ }
+}
+
+difference()
+{
+ pinned_half_wheel();
+ translate([0, 0, 50])
+ cube([100, 100, 100], center = true);
+}
+
+translate([(wheel_diameter_edge + wheel_inner_diameter) / 2 / 2, halfpin_length * 1.2, 0])
+ pin();