Add gopro_mount.scad with: - Standard GoPro 3-prong interface on top for HERO 5+ compatibility - T-slot 2020 clamp with M3 thumbscrew retention (no tools required) - Tilt mechanism: 0-90° with 15° detent angles (7 positions) - Integrated T-nut slides into rail groove - Rotation axis via M5 hinge pin with index-hole angle locking - Design supports flat-face-down printing, no supports needed Includes comprehensive BOM with: - Part specifications for base clamp and camera bracket - Fastener list and torque specs - Step-by-step assembly instructions - Tilt angle reference guide - Post-print finishing notes - Cable management guidance Co-Authored-By: Claude Haiku 4.5 <noreply@anthropic.com>
257 lines
12 KiB
OpenSCAD
257 lines
12 KiB
OpenSCAD
// ============================================================
|
||
// gopro_mount.scad — GoPro 3-Prong T-Slot Sensor Rail Mount
|
||
// Issue: #195 Agent: sl-mechanical Date: 2026-03-02
|
||
// ============================================================
|
||
//
|
||
// Universal GoPro camera mount for sensor_rail.scad (T-slot 2020).
|
||
//
|
||
// Top interface: Standard GoPro 3-prong (HERO 5+)
|
||
// Prongs slide into standard GoPro accessories.
|
||
// No additional clips or fasteners needed.
|
||
//
|
||
// Bottom clamp: T-slot 20×20 mm rail system (OpenBuilds compatible).
|
||
// M3 thumbscrew retention + M5 index holes for 15° detents.
|
||
//
|
||
// Tilt mechanism: Rotating hinge bracket allows camera tilt 0°–90° from
|
||
// horizontal, locked at 15° increments via index holes.
|
||
// Rotation axis is perpendicular to rail (about Y-axis).
|
||
//
|
||
// Assembly:
|
||
// 1. Print gopro_mount_base (single part, flat-side-down, no supports)
|
||
// 2. Slide built-in T-nut into rail T-groove
|
||
// 3. Clamp with M3 thumbscrew from outside rail face
|
||
// 4. Rotate camera to desired tilt angle (0°, 15°, 30°, ... 90°)
|
||
// 5. Insert M5 alignment pin to lock tilt
|
||
//
|
||
// RENDER options:
|
||
// "mount" assembled mount view (default)
|
||
// "base_stl" base clamp for slicing (print flat)
|
||
// "camera_bracket" rotatable camera bracket for slicing
|
||
// ============================================================
|
||
|
||
RENDER = "mount";
|
||
|
||
// ── GoPro 3-prong interface (top) ──────────────────────────
|
||
// Standard GoPro HERO 5+ 3-prong attachment point.
|
||
// Overall footprint ~43×25 mm, 3 prongs slide into camera mounting slot.
|
||
|
||
GOPRO_WIDTH = 43.0; // front-to-back along camera face
|
||
GOPRO_DEPTH = 25.0; // left-to-right width
|
||
GOPRO_PRONG_H = 5.0; // height of prongs above base
|
||
GOPRO_PRONG_D = 4.0; // diameter/thickness of each prong
|
||
GOPRO_PRONG_SP = 14.0; // spacing between outer prongs (centre-to-centre)
|
||
|
||
// Centre prong is at Y=0; outer prongs at Y±GOPRO_PRONG_SP/2
|
||
// Prongs extend upward (+Z direction)
|
||
|
||
// ── T-slot clamp (bottom) ──────────────────────────────────
|
||
// Matches sensor_rail.scad T-slot 2020 dimensions.
|
||
RAIL_W = 20.0; // rail outer width/height
|
||
SLOT_INNER_W = 10.2; // T-groove inner width
|
||
SLOT_INNER_H = 5.8; // T-groove inner height (depth)
|
||
SLOT_NECK_H = 3.2; // distance from outer face to T-groove
|
||
|
||
TNUT_W = 9.8; // printable T-nut width (SLOT_INNER_W - 0.4)
|
||
TNUT_H = 5.5; // printable T-nut height (SLOT_INNER_H - 0.3)
|
||
TNUT_L = 12.0; // T-nut body length
|
||
TNUT_BOLT_D = 3.3; // M3 clearance bore through T-nut
|
||
|
||
THUMB_D = 16.0; // thumbwheel OD (visual only)
|
||
THUMB_H = 8.0; // thumbwheel height
|
||
|
||
// Index hole pitch for tilt detents
|
||
INDEX_PITCH = 25.0; // 25 mm spacing on rail
|
||
TILT_ANGLE_STEP = 15.0; // 15° tilt detents (0°, 15°, 30°, ... 90°)
|
||
M5_INDEX_D = 5.3; // M5 clearance hole diameter
|
||
|
||
// ── Rotation/tilt mechanism ───────────────────────────────
|
||
// Camera bracket rotates about Y-axis relative to base.
|
||
// Rotation axis is at the rail clamp interface (Z=0, Y=0).
|
||
// Tilt range: 0° to 90°.
|
||
|
||
MAX_TILT_DEG = 90.0; // maximum tilt angle
|
||
|
||
// Hinge pin: M5 bolt passes through base and camera bracket
|
||
HINGE_PIN_D = 5.3; // M5 bolt clearance
|
||
HINGE_PIN_L = 25.0; // pin length (accommodates rail width + brackets)
|
||
|
||
// ── General ────────────────────────────────────────────────
|
||
$fn = 64;
|
||
e = 0.01;
|
||
|
||
// ─────────────────────────────────────────────────────────────
|
||
// gopro_mount_base()
|
||
// T-slot clamp bracket with integrated T-nut.
|
||
// Mounted at bottom, rail clamp at Z=0 face.
|
||
// Hinge pin axis at Y=0, rotates camera bracket ±X.
|
||
//
|
||
// Print: flat-side-down (rail face down), no supports needed.
|
||
// ─────────────────────────────────────────────────────────────
|
||
module gopro_mount_base() {
|
||
clamp_h = RAIL_W + 8.0; // total clamp height
|
||
clamp_w = TNUT_L + 8.0; // clamp width (along rail)
|
||
clamp_d = 18.0; // clamp depth (front-to-back)
|
||
|
||
difference() {
|
||
union() {
|
||
// Main clamp body
|
||
translate([-clamp_w/2, -clamp_d/2, 0])
|
||
cube([clamp_w, clamp_d, clamp_h]);
|
||
|
||
// T-nut integration: slot to hold T-nut at rail interface
|
||
// T-nut sits in T-groove when rail is inserted from above
|
||
translate([-TNUT_L/2, -TNUT_W/2, SLOT_NECK_H])
|
||
cube([TNUT_L, TNUT_W, TNUT_H]);
|
||
|
||
// Hinge boss (supports rotation axis pin)
|
||
translate([-HINGE_PIN_L/2 - 2, -8, clamp_h - 4])
|
||
cube([HINGE_PIN_L + 4, 4, 4]);
|
||
}
|
||
|
||
// Rail bore (25.4 mm) — matches stem adapter pattern
|
||
// When rail is vertical, this bore slides onto rail extrusion
|
||
translate([0, 0, -e])
|
||
cylinder(d=RAIL_W + 0.4, h=clamp_h + 2*e);
|
||
|
||
// T-nut through-bolt (M3 thumbscrew hole)
|
||
// Bolt comes from outside rail face, through T-nut, clamping it
|
||
translate([0, 0, SLOT_NECK_H + TNUT_H/2])
|
||
rotate([90, 0, 0])
|
||
cylinder(d=TNUT_BOLT_D, h=clamp_d + 2*e);
|
||
|
||
// Hinge pin (M5) passes through base to camera bracket
|
||
translate([-HINGE_PIN_L/2, 0, clamp_h - 2])
|
||
rotate([0, 90, 0])
|
||
cylinder(d=HINGE_PIN_D, h=HINGE_PIN_L + 2*e);
|
||
|
||
// Index hole pockets for tilt angle lock (M5)
|
||
// One index hole on each side to lock camera tilt
|
||
for (angle = [0 : TILT_ANGLE_STEP : MAX_TILT_DEG]) {
|
||
// Holes are radially spaced around the hinge axis
|
||
y_offset = (HINGE_PIN_L/2 - 2) * sin(angle);
|
||
z_offset = clamp_h - 2 - (HINGE_PIN_L/2 - 2) * (1 - cos(angle));
|
||
translate([0, y_offset, z_offset])
|
||
cylinder(d=M5_INDEX_D, h=4, center=false);
|
||
}
|
||
|
||
// Vent slots (optional, aesthetic + weight reduction)
|
||
for (dz = [4, 8, 12])
|
||
translate([-clamp_w/2 + 2, -clamp_d/2 - e, dz])
|
||
cube([clamp_w - 4, 2, 1.5]);
|
||
}
|
||
}
|
||
|
||
// ─────────────────────────────────────────────────────────────
|
||
// gopro_camera_bracket()
|
||
// Rotatable bracket that holds GoPro camera via 3-prong mount.
|
||
// Rotates about Y-axis (hinge pin), tilt 0°–90°.
|
||
//
|
||
// Hinge pin (M5 bolt) enters from base and locks bracket rotation.
|
||
// Index hole on bracket aligns with base index holes at each 15° step.
|
||
//
|
||
// Print: flat-side-down (prong face down), no supports.
|
||
// ─────────────────────────────────────────────────────────────
|
||
module gopro_camera_bracket() {
|
||
bracket_h = GOPRO_WIDTH + 8.0; // height when vertical
|
||
bracket_w = GOPRO_DEPTH + 6.0; // width (left-right)
|
||
bracket_t = 4.0; // bracket thickness
|
||
|
||
difference() {
|
||
union() {
|
||
// Main bracket body
|
||
translate([-bracket_w/2, -bracket_t/2, 0])
|
||
cube([bracket_w, bracket_t, bracket_h]);
|
||
|
||
// Hinge pivot boss
|
||
translate([-HINGE_PIN_L/2 - 2, 0, bracket_h - 4])
|
||
cube([HINGE_PIN_L + 4, bracket_t, 4]);
|
||
|
||
// GoPro prong mounting boss
|
||
translate([-GOPRO_DEPTH/2, 0, bracket_h - GOPRO_WIDTH/2])
|
||
cube([GOPRO_DEPTH, bracket_t + 2, GOPRO_WIDTH]);
|
||
}
|
||
|
||
// Hinge pin bore (M5)
|
||
translate([-HINGE_PIN_L/2, 0, bracket_h - 2])
|
||
rotate([0, 90, 0])
|
||
cylinder(d=HINGE_PIN_D + 0.2, h=HINGE_PIN_L + 2*e);
|
||
|
||
// Index hole (M5) for angle lock
|
||
// Bracket has one index hole that aligns with base holes at tilt angles
|
||
translate([GOPRO_DEPTH/2 + 1, 0, bracket_h - 4])
|
||
cylinder(d=M5_INDEX_D, h=bracket_t + 2*e);
|
||
|
||
// GoPro prong socket (3 mounting prongs)
|
||
// Centre prong at Y=0, outer prongs at Y±GOPRO_PRONG_SP/2
|
||
for (dy = [0, GOPRO_PRONG_SP/2, -GOPRO_PRONG_SP/2]) {
|
||
translate([0, bracket_t + e, bracket_h - GOPRO_WIDTH/2 + 5 - dy])
|
||
rotate([90, 0, 0])
|
||
cylinder(d=GOPRO_PRONG_D + 0.4, h=4);
|
||
}
|
||
}
|
||
}
|
||
|
||
// ─────────────────────────────────────────────────────────────
|
||
// gopro_prong_interface()
|
||
// Visual representation of the 3 prongs that camera mounts to.
|
||
// Not printed; shown during assembly view.
|
||
// ─────────────────────────────────────────────────────────────
|
||
module gopro_prong_interface() {
|
||
bracket_h = GOPRO_WIDTH + 8.0;
|
||
bracket_w = GOPRO_DEPTH + 6.0;
|
||
|
||
// 3 cylindrical prongs
|
||
for (dy = [0, GOPRO_PRONG_SP/2, -GOPRO_PRONG_SP/2]) {
|
||
translate([0, bracket_w/2 + 0.5, bracket_h - GOPRO_WIDTH/2 + 5 - dy])
|
||
rotate([90, 0, 0])
|
||
cylinder(d=GOPRO_PRONG_D, h=GOPRO_PRONG_H, $fn=32);
|
||
}
|
||
}
|
||
|
||
// ─────────────────────────────────────────────────────────────
|
||
// Assembly view: base + rotatable camera bracket
|
||
// ─────────────────────────────────────────────────────────────
|
||
module gopro_mount_assembly() {
|
||
// Base clamp (fixed)
|
||
color("SteelBlue", 0.9)
|
||
gopro_mount_base();
|
||
|
||
// Camera bracket (rotatable, at 45° tilt for visualization)
|
||
color("CornflowerBlue", 0.85)
|
||
rotate([0, 45, 0])
|
||
translate([0, 0, RAIL_W + 8])
|
||
gopro_camera_bracket();
|
||
|
||
// Visual GoPro prongs
|
||
color("LightSteelBlue", 0.7)
|
||
rotate([0, 45, 0])
|
||
translate([0, 0, RAIL_W + 8])
|
||
gopro_prong_interface();
|
||
|
||
// Phantom M5 hinge pin (visual reference)
|
||
color("Silver", 0.5)
|
||
translate([-HINGE_PIN_L/2, 0, RAIL_W + 8 - 2])
|
||
rotate([0, 90, 0])
|
||
cylinder(d=5, h=HINGE_PIN_L);
|
||
}
|
||
|
||
// ─────────────────────────────────────────────────────────────
|
||
// Render selector
|
||
// ─────────────────────────────────────────────────────────────
|
||
if (RENDER == "mount") {
|
||
gopro_mount_assembly();
|
||
|
||
} else if (RENDER == "base_stl") {
|
||
// Flat print orientation: rail-facing side down
|
||
rotate([180, 0, 0])
|
||
translate([0, 0, -RAIL_W - 8])
|
||
gopro_mount_base();
|
||
|
||
} else if (RENDER == "camera_bracket") {
|
||
// Flat print orientation: prong-facing side down
|
||
rotate([0, 0, 0])
|
||
translate([0, 0, GOPRO_WIDTH + 14])
|
||
rotate([180, 0, 0])
|
||
gopro_camera_bracket();
|
||
}
|