Restructured enclosure project
This commit is contained in:
179
enclosure/box.scad
Normal file
179
enclosure/box.scad
Normal file
@@ -0,0 +1,179 @@
|
|||||||
|
// Defines the box for the Fabula Open Source storyteller.
|
||||||
|
// This is the box, without any cutout nor electronics components mount.
|
||||||
|
|
||||||
|
// Global dimensions, change here
|
||||||
|
width = 180;
|
||||||
|
height = 90;
|
||||||
|
depth = 40;
|
||||||
|
screw_diameter = 3;
|
||||||
|
|
||||||
|
// Internal global variables
|
||||||
|
rounded_edge_diameter = height;
|
||||||
|
box_cut_height = 10;
|
||||||
|
flange_height = 3;
|
||||||
|
standoff_diameter=screw_diameter*3;
|
||||||
|
|
||||||
|
// Screw standoff
|
||||||
|
module standoff() {
|
||||||
|
cylinder(h = depth, d = standoff_diameter, center = true);
|
||||||
|
}
|
||||||
|
|
||||||
|
// Screw hole, to be subtracted from standoff and box
|
||||||
|
module screw_hole() {
|
||||||
|
// Hole where the screw will thread into
|
||||||
|
cylinder(h = depth - 2, d = screw_diameter, center = true);
|
||||||
|
// Hole where the screw will pass with slack, without threading (in the lid)
|
||||||
|
translate([0, 0, depth/2 - box_cut_height/2]) {
|
||||||
|
cylinder(h = box_cut_height + 12, d = screw_diameter*1.5, center = true);
|
||||||
|
}
|
||||||
|
// Screw head bevel
|
||||||
|
bevel_depth = 1;
|
||||||
|
translate([0, 0, depth/2 - bevel_depth/2 + 6]) {
|
||||||
|
cylinder(h = bevel_depth, d2 = screw_diameter * 2.5, d1 = screw_diameter*1.5, center = true);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
// Main body
|
||||||
|
module main_body() {
|
||||||
|
module half_body() {
|
||||||
|
cube([width - rounded_edge_diameter/2, height/2, depth]);
|
||||||
|
cylinder(h = depth, d = rounded_edge_diameter, $fn=256);
|
||||||
|
}
|
||||||
|
|
||||||
|
union() {
|
||||||
|
translate([-(width - rounded_edge_diameter)/2, 0, -depth/2]) {
|
||||||
|
half_body();
|
||||||
|
}
|
||||||
|
translate([(width - rounded_edge_diameter)/2, 0, -depth/2]) {
|
||||||
|
mirror([1, 0, 0]) {
|
||||||
|
mirror([0, 1, 0]) {
|
||||||
|
half_body();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// Closed Box
|
||||||
|
module closed_box() {
|
||||||
|
difference() {
|
||||||
|
union() {
|
||||||
|
// Hollow box
|
||||||
|
difference() {
|
||||||
|
// Round all edges to avoid danger for the children
|
||||||
|
minkowski() {
|
||||||
|
$fn = 64;
|
||||||
|
main_body();
|
||||||
|
sphere(6);
|
||||||
|
}
|
||||||
|
main_body();
|
||||||
|
}
|
||||||
|
|
||||||
|
// Screws standoffs near curved edges
|
||||||
|
translate([width/2 - rounded_edge_diameter/2, -height/2, 0]) {
|
||||||
|
standoff();
|
||||||
|
}
|
||||||
|
translate([-width/2 + rounded_edge_diameter/2, height/2, 0]) {
|
||||||
|
standoff();
|
||||||
|
}
|
||||||
|
// Screws standoff near sharp edges
|
||||||
|
translate([-width/2 + standoff_diameter/2, -height/2, 0]) {
|
||||||
|
standoff();
|
||||||
|
}
|
||||||
|
translate([width/2 - standoff_diameter/2, height/2, 0]) {
|
||||||
|
standoff();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
// Screw holes near curved edges
|
||||||
|
translate([width/2 - rounded_edge_diameter/2, -height/2, 0]) {
|
||||||
|
screw_hole();
|
||||||
|
}
|
||||||
|
translate([-width/2 + rounded_edge_diameter/2, height/2, 0]) {
|
||||||
|
screw_hole();
|
||||||
|
}
|
||||||
|
// Screws holes near sharp edges
|
||||||
|
translate([-width/2 + standoff_diameter/2, -height/2, 0]) {
|
||||||
|
screw_hole();
|
||||||
|
}
|
||||||
|
translate([width/2 - standoff_diameter/2, height/2, 0]) {
|
||||||
|
screw_hole();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
// Lower box
|
||||||
|
module box() {
|
||||||
|
difference() {
|
||||||
|
closed_box();
|
||||||
|
translate([0, 0, depth - box_cut_height]) {
|
||||||
|
cube([width*2, height*2, depth], true);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// Upper cap lip
|
||||||
|
module lip() {
|
||||||
|
// Lip support
|
||||||
|
translate([0, 0, box_cut_height + 5]) {
|
||||||
|
intersection() {
|
||||||
|
difference() {
|
||||||
|
main_body();
|
||||||
|
scale([0.95, 0.95, 0.95]) main_body();
|
||||||
|
}
|
||||||
|
|
||||||
|
cube([width*2, height*2, box_cut_height], true);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
// Chamfered lip
|
||||||
|
difference() {
|
||||||
|
for (i = [0:10]) {
|
||||||
|
translate([0, 0, box_cut_height - i * 0.5]) {
|
||||||
|
intersection() {
|
||||||
|
difference() {
|
||||||
|
scale_ratio = 1 - i * 0.001;
|
||||||
|
scale([scale_ratio, scale_ratio, scale_ratio]) {
|
||||||
|
main_body();
|
||||||
|
}
|
||||||
|
scale([0.95, 0.95, 0.95]) main_body();
|
||||||
|
}
|
||||||
|
|
||||||
|
cube([width*2, height*2, 0.5], true);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
// Leave space for screws standoffs near curved edges
|
||||||
|
translate([width/2 - rounded_edge_diameter/2, -height/2, 0]) {
|
||||||
|
scale([1.2, 1.2, 1]) standoff();
|
||||||
|
}
|
||||||
|
translate([-width/2 + rounded_edge_diameter/2, height/2, 0]) {
|
||||||
|
scale([1.2, 1.2, 1]) standoff();
|
||||||
|
}
|
||||||
|
// Leave space for screws standoff near sharp edges
|
||||||
|
translate([-width/2 + standoff_diameter/2, -height/2, 0]) {
|
||||||
|
scale([1.2, 1.2, 1]) standoff();
|
||||||
|
}
|
||||||
|
translate([width/2 - standoff_diameter/2, height/2, 0]) {
|
||||||
|
scale([1.2, 1.2, 1]) standoff();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// Upper cap
|
||||||
|
module cap() {
|
||||||
|
difference() {
|
||||||
|
closed_box();
|
||||||
|
translate([0, 0, - box_cut_height]) {
|
||||||
|
cube([width*2, height*2, depth], true);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
lip();
|
||||||
|
}
|
||||||
|
|
||||||
|
translate([0, -60, 0]) box();
|
||||||
|
translate([0, 60, 0]) rotate([180, 0, 0]) cap();
|
||||||
2
enclosure/cutouts.scad
Normal file
2
enclosure/cutouts.scad
Normal file
@@ -0,0 +1,2 @@
|
|||||||
|
// The cutouts to allow external components (such as buttons and connectors) to be mounted on the box
|
||||||
|
|
||||||
@@ -1,180 +1,18 @@
|
|||||||
|
use <box.scad>
|
||||||
|
use <supports.scad>
|
||||||
|
use <cutouts.scad>
|
||||||
|
|
||||||
// FABULA open source storyteller enclosure
|
// FABULA open source storyteller enclosure
|
||||||
|
|
||||||
// TODO: open hardware logo, Fabula logo, cutouts for components and buttons, tag slot with led mount
|
// TODO: open hardware logo, Fabula logo, cutouts for components and buttons, tag slot with led mount
|
||||||
|
|
||||||
// Global dimensions, change here
|
module fabula_enclosure_bottom() {
|
||||||
width = 180;
|
cap();
|
||||||
height = 90;
|
|
||||||
depth = 40;
|
|
||||||
screw_diameter = 3;
|
|
||||||
|
|
||||||
// Internal global variables
|
|
||||||
rounded_edge_diameter = height;
|
|
||||||
box_cut_height = 10;
|
|
||||||
flange_height = 3;
|
|
||||||
standoff_diameter=screw_diameter*3;
|
|
||||||
|
|
||||||
// Screw standoff
|
|
||||||
module standoff() {
|
|
||||||
cylinder(h = depth, d = standoff_diameter, center = true);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
// Screw hole, to be subtracted from standoff and box
|
module fabula_enclosure_top() {
|
||||||
module screw_hole() {
|
box();
|
||||||
// Hole where the screw will thread into
|
|
||||||
cylinder(h = depth - 2, d = screw_diameter, center = true);
|
|
||||||
// Hole where the screw will pass with slack, without threading (in the lid)
|
|
||||||
translate([0, 0, depth/2 - box_cut_height/2]) {
|
|
||||||
cylinder(h = box_cut_height + 12, d = screw_diameter*1.5, center = true);
|
|
||||||
}
|
|
||||||
// Screw head bevel
|
|
||||||
bevel_depth = 1;
|
|
||||||
translate([0, 0, depth/2 - bevel_depth/2 + 6]) {
|
|
||||||
cylinder(h = bevel_depth, d2 = screw_diameter * 2.5, d1 = screw_diameter*1.5, center = true);
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
translate([0, -60, 0]) rotate([180, 0, 0]) fabula_enclosure_bottom();
|
||||||
// Main body
|
translate([0, 60, 0]) fabula_enclosure_top();
|
||||||
module main_body() {
|
|
||||||
module half_body() {
|
|
||||||
cube([width - rounded_edge_diameter/2, height/2, depth]);
|
|
||||||
cylinder(h = depth, d = rounded_edge_diameter, $fn=256);
|
|
||||||
}
|
|
||||||
|
|
||||||
union() {
|
|
||||||
translate([-(width - rounded_edge_diameter)/2, 0, -depth/2]) {
|
|
||||||
half_body();
|
|
||||||
}
|
|
||||||
translate([(width - rounded_edge_diameter)/2, 0, -depth/2]) {
|
|
||||||
mirror([1, 0, 0]) {
|
|
||||||
mirror([0, 1, 0]) {
|
|
||||||
half_body();
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
// Closed Box
|
|
||||||
module closed_box() {
|
|
||||||
difference() {
|
|
||||||
union() {
|
|
||||||
// Hollow box
|
|
||||||
difference() {
|
|
||||||
// Round all edges to avoid danger for the children
|
|
||||||
minkowski() {
|
|
||||||
$fn = 64;
|
|
||||||
main_body();
|
|
||||||
sphere(6);
|
|
||||||
}
|
|
||||||
main_body();
|
|
||||||
}
|
|
||||||
|
|
||||||
// Screws standoffs near curved edges
|
|
||||||
translate([width/2 - rounded_edge_diameter/2, -height/2, 0]) {
|
|
||||||
standoff();
|
|
||||||
}
|
|
||||||
translate([-width/2 + rounded_edge_diameter/2, height/2, 0]) {
|
|
||||||
standoff();
|
|
||||||
}
|
|
||||||
// Screws standoff near sharp edges
|
|
||||||
translate([-width/2 + standoff_diameter/2, -height/2, 0]) {
|
|
||||||
standoff();
|
|
||||||
}
|
|
||||||
translate([width/2 - standoff_diameter/2, height/2, 0]) {
|
|
||||||
standoff();
|
|
||||||
}
|
|
||||||
}
|
|
||||||
// Screw holes near curved edges
|
|
||||||
translate([width/2 - rounded_edge_diameter/2, -height/2, 0]) {
|
|
||||||
screw_hole();
|
|
||||||
}
|
|
||||||
translate([-width/2 + rounded_edge_diameter/2, height/2, 0]) {
|
|
||||||
screw_hole();
|
|
||||||
}
|
|
||||||
// Screws holes near sharp edges
|
|
||||||
translate([-width/2 + standoff_diameter/2, -height/2, 0]) {
|
|
||||||
screw_hole();
|
|
||||||
}
|
|
||||||
translate([width/2 - standoff_diameter/2, height/2, 0]) {
|
|
||||||
screw_hole();
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
}
|
|
||||||
|
|
||||||
// Lower box
|
|
||||||
module box() {
|
|
||||||
difference() {
|
|
||||||
closed_box();
|
|
||||||
translate([0, 0, depth - box_cut_height]) {
|
|
||||||
cube([width*2, height*2, depth], true);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
// Upper cap lip
|
|
||||||
module lip() {
|
|
||||||
// Lip support
|
|
||||||
translate([0, 0, box_cut_height + 5]) {
|
|
||||||
intersection() {
|
|
||||||
difference() {
|
|
||||||
main_body();
|
|
||||||
scale([0.95, 0.95, 0.95]) main_body();
|
|
||||||
}
|
|
||||||
|
|
||||||
cube([width*2, height*2, box_cut_height], true);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
// Chamfered lip
|
|
||||||
difference() {
|
|
||||||
for (i = [0:10]) {
|
|
||||||
translate([0, 0, box_cut_height - i * 0.5]) {
|
|
||||||
intersection() {
|
|
||||||
difference() {
|
|
||||||
scale_ratio = 1 - i * 0.001;
|
|
||||||
scale([scale_ratio, scale_ratio, scale_ratio]) {
|
|
||||||
main_body();
|
|
||||||
}
|
|
||||||
scale([0.95, 0.95, 0.95]) main_body();
|
|
||||||
}
|
|
||||||
|
|
||||||
cube([width*2, height*2, 0.5], true);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
// Leave space for screws standoffs near curved edges
|
|
||||||
translate([width/2 - rounded_edge_diameter/2, -height/2, 0]) {
|
|
||||||
scale([1.2, 1.2, 1]) standoff();
|
|
||||||
}
|
|
||||||
translate([-width/2 + rounded_edge_diameter/2, height/2, 0]) {
|
|
||||||
scale([1.2, 1.2, 1]) standoff();
|
|
||||||
}
|
|
||||||
// Leave space for screws standoff near sharp edges
|
|
||||||
translate([-width/2 + standoff_diameter/2, -height/2, 0]) {
|
|
||||||
scale([1.2, 1.2, 1]) standoff();
|
|
||||||
}
|
|
||||||
translate([width/2 - standoff_diameter/2, height/2, 0]) {
|
|
||||||
scale([1.2, 1.2, 1]) standoff();
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
// Upper cap
|
|
||||||
module cap() {
|
|
||||||
difference() {
|
|
||||||
closed_box();
|
|
||||||
translate([0, 0, - box_cut_height]) {
|
|
||||||
cube([width*2, height*2, depth], true);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
lip();
|
|
||||||
}
|
|
||||||
|
|
||||||
translate([0, -60, 0]) box();
|
|
||||||
translate([0, 60, 0]) rotate([180, 0, 0]) cap();
|
|
||||||
|
|||||||
8
enclosure/supports.scad
Normal file
8
enclosure/supports.scad
Normal file
@@ -0,0 +1,8 @@
|
|||||||
|
// Supports to mount internal components in the box
|
||||||
|
|
||||||
|
module supports_speaker() {
|
||||||
|
difference() {
|
||||||
|
cylinder(d = 84, h = 2);
|
||||||
|
cylinder(d = 80, h = 2);
|
||||||
|
}
|
||||||
|
}
|
||||||
@@ -16,5 +16,4 @@ module test_fit_components() {
|
|||||||
}
|
}
|
||||||
|
|
||||||
test_fit_components();
|
test_fit_components();
|
||||||
//#closed_box();
|
translate([0, 0, 20]) rotate([0, 0, -90]) #fabula_enclosure_bottom();
|
||||||
translate([0, 0, 20]) rotate([0, 0, -90]) #box();
|
|
||||||
Reference in New Issue
Block a user