discuss@lists.openscad.org

OpenSCAD general discussion Mailing-list

View all threads

Re: Export to .STL / .3MF for later 3D-printing.

MM
Michael Möller
Fri, May 6, 2022 12:06 PM

OpenSCAD code - is a description of your model in terms of a few
cylinder/cubes added and cut out
difference() {
cylinder(d=5,h=10);
translate([0,10,0]) cube([4,6,2]) ;
}

STL file is a list of triangles which make the same outer shell as your
model. OpenSCAD makes this complicated transform from shapes to triangles.
solid OpenSCAD_Model
facet normal 0.92388 0.382682 0
outer loop
vertex 2.5 0 3
vertex 1.76777 1.76777 0
vertex 1.76777 1.76777 3
endloop
endfacet
facet normal 0.92388 0.382682 0
outer loop
vertex 1.76777 1.76777 0
vertex 2.5 0 3
vertex 2.5 0 0
endloop
endfacet
: (and so on for 300 lines) There is a binary/compressed version, but the
description is still just triangles.

Gcode is what a 3D printer understands - it is the exact list of moves that
the head has to do with how much plastic to squeeze to trace the outline of
your shape, layer, by layer. It will optionally create moves for filling
the inside or support for overhangs. Such a program is called a SLICER and
the printer will come with one.
G92 E0 ; reset extrusion distance
G1 Z2.330 F6600.000 ; lift Z
G1 X-0.000 Y1.505 F6600.000 ; move to first perimeter point
G1 Z0.330 F6600.000 ; restore layer Z
G1 E3.00000 F2400.00000 ; unretract extruder 0
G1 F1500
G1 X-1.064 Y1.064 E3.09259 ; perimeter
G1 X-1.505 Y0.000 E3.18517 ; perimeter
: (many similar lines)
G1 X1.515 Y1.515 E4.65860 ; perimeter
G1 X0.055 Y2.120 E4.78559 ; perimeter
G1 X-0.000 Y2.143 F6600.000 ; move inwards before travel
G1 X0.384 Y0.843 F6600.000 ; move to first infill point
G1 F1500
G1 X0.843 Y0.384 E4.84815 ; infill
G1 X1.097 Y-0.229 E4.91215 ; infill
:
(and so on for thousands of lines)

The 3MF still basically deals in triangles, and attributes (surface, infill
material, picture, ticket info ... ) which probably are not used by your
slicer/printer.

On Fri, 6 May 2022 at 12:37, Jan Öhman via Discuss <
discuss@lists.openscad.org> wrote:

---------- Forwarded message ----------
From: "Jan Öhman" jan_ohman@yahoo.com
To: OpenSCAD General Discussion discuss@lists.openscad.org
Cc:
Bcc:
Date: Fri, 6 May 2022 10:38:46 +0000 (UTC)
Subject: [OpenSCAD] Export to .STL / .3MF for later 3D-printing.
Hi!

Thought to create some objects in openSCAD, to print later.
I do not have my own 3D printer (yet).

One I talked to, wanted to get the drawings in .STL or .3MF. (I don't know
the difference).

If I had my own printer, have I been able to print directly from openSCAD?
(Without some export?)

In the openSCAD, no errors or problems occur.
but
The drawings I tested to export from openSCAD have given one or another
error message.
One message .:
WARNING: Object may not be a valid 2-manifold and may need repair!

Another message .:
WARNING: No top level geometry to render

What to do?

---------- Forwarded message ----------
From: "Jan Öhman via Discuss" discuss@lists.openscad.org
To: OpenSCAD General Discussion discuss@lists.openscad.org
Cc: "Jan Öhman" jan_ohman@yahoo.com
Bcc:
Date: Fri, 6 May 2022 10:38:46 +0000 (UTC)
Subject: [OpenSCAD] Export to .STL / .3MF for later 3D-printing.


OpenSCAD mailing list
To unsubscribe send an email to discuss-leave@lists.openscad.org

OpenSCAD code - is a description of your model in terms of a few cylinder/cubes added and cut out difference() { cylinder(d=5,h=10); translate([0,10,0]) cube([4,6,2]) ; } STL file is a list of triangles which make the same outer shell as your model. OpenSCAD makes this complicated transform from shapes to triangles. solid OpenSCAD_Model facet normal 0.92388 0.382682 0 outer loop vertex 2.5 0 3 vertex 1.76777 1.76777 0 vertex 1.76777 1.76777 3 endloop endfacet facet normal 0.92388 0.382682 0 outer loop vertex 1.76777 1.76777 0 vertex 2.5 0 3 vertex 2.5 0 0 endloop endfacet : (and so on for 300 lines) There is a binary/compressed version, but the description is still just triangles. Gcode is what a 3D printer understands - it is the exact list of moves that the head has to do with how much plastic to squeeze to trace the outline of your shape, layer, by layer. It will optionally create moves for filling the inside or support for overhangs. Such a program is called a SLICER and the printer will come with one. G92 E0 ; reset extrusion distance G1 Z2.330 F6600.000 ; lift Z G1 X-0.000 Y1.505 F6600.000 ; move to first perimeter point G1 Z0.330 F6600.000 ; restore layer Z G1 E3.00000 F2400.00000 ; unretract extruder 0 G1 F1500 G1 X-1.064 Y1.064 E3.09259 ; perimeter G1 X-1.505 Y0.000 E3.18517 ; perimeter : (many similar lines) G1 X1.515 Y1.515 E4.65860 ; perimeter G1 X0.055 Y2.120 E4.78559 ; perimeter G1 X-0.000 Y2.143 F6600.000 ; move inwards before travel G1 X0.384 Y0.843 F6600.000 ; move to first infill point G1 F1500 G1 X0.843 Y0.384 E4.84815 ; infill G1 X1.097 Y-0.229 E4.91215 ; infill : (and so on for thousands of lines) The 3MF still basically deals in triangles, and attributes (surface, infill material, picture, ticket info ... ) which probably are not used by your slicer/printer. On Fri, 6 May 2022 at 12:37, Jan Öhman via Discuss < discuss@lists.openscad.org> wrote: > > > > ---------- Forwarded message ---------- > From: "Jan Öhman" <jan_ohman@yahoo.com> > To: OpenSCAD General Discussion <discuss@lists.openscad.org> > Cc: > Bcc: > Date: Fri, 6 May 2022 10:38:46 +0000 (UTC) > Subject: [OpenSCAD] Export to .STL / .3MF for later 3D-printing. > Hi! > > Thought to create some objects in openSCAD, to print later. > I do not have my own 3D printer (yet). > > One I talked to, wanted to get the drawings in .STL or .3MF. (I don't know > the difference). > > If I had my own printer, have I been able to print directly from openSCAD? > (Without some export?) > > In the openSCAD, no errors or problems occur. > but > The drawings I tested to export from openSCAD have given one or another > error message. > One message .: > WARNING: Object may not be a valid 2-manifold and may need repair! > > Another message .: > WARNING: No top level geometry to render > > What to do? > > > > ---------- Forwarded message ---------- > From: "Jan Öhman via Discuss" <discuss@lists.openscad.org> > To: OpenSCAD General Discussion <discuss@lists.openscad.org> > Cc: "Jan Öhman" <jan_ohman@yahoo.com> > Bcc: > Date: Fri, 6 May 2022 10:38:46 +0000 (UTC) > Subject: [OpenSCAD] Export to .STL / .3MF for later 3D-printing. > _______________________________________________ > OpenSCAD mailing list > To unsubscribe send an email to discuss-leave@lists.openscad.org >
Jan Öhman
Sat, May 7, 2022 11:04 AM

Thank you!
Begins to understand how it works. (It was not easy...)
but my solution was not good ...
Here are 2 files that do not work to render (F6)

= = product 1= = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = =  - . _ . - . _ . - . _ . - . _ . - . _ . - . _ . - . _ . - . _ . - . _ . - . _ . - . _ . - . _ . - . _ . -

include <BOSL2/std.scad>fn = 150;
placering="left";// placering="right"
box(0, 0, 0, placering, "#C0C0C0", fn); // (X, Y, Z, left/right, colorName)

// Monteringsplattan// mountingPlate(0, 0, 0, placering);

// LED belysning// LEDlampa(0, 0, 0, placering);

// - - - - - - - - - - - - - - - - - - - - - - - - - - - - - // - - - - m o d u l e r - - - - - - - - - - - - - - - - - - 

//

---================//======  box 

---===module box(posX=0, posY=0, posZ=0, mountSide="left", colorName="#00FF00", fn=24){   side = mountSide == "left" ? 0       : mountSide == "right" ? 1       : assert(false,"invalid moutSide value");  // message if no case worked    color(colorName)  translate([posX, posY, posZ])  mirror([side, 0, 0])  difference()  {  union()  {  // Skapa konturer på bottenplattan - x, y, r, angles, [grader], början  // Rotation medurs - vänster lamphållare (bakant saknas)  points1 = circSect( 140,  0,   0, [0, 0], "right",  1, fn);  // böj nere till höger  points2 = circSect(  60,  5,   5, [0, 5], "bottom",  1, fn); // brytpunkt längst ned  points3 = circSect(  10, 13,  10, [0, 90], "bottom", 1, fn); // böj nere till vänster  points4 = circSect(   5, 80,   5, [0, 90], "left",   1, fn); // böj uppe till vänster  points5 = circSect( 140, 80,   5, [0, 1], "top",   1, fn);   // böj uppe till höger  edge = concat(points1, points2, points3, points4, points5);  path = path3d(reverse(edge));  section = wall();  path_sweep( section, path, closed=false);
    // Skapa bakkant lite högre och smalare i topp  bottom1 = concat(points5, points1);  polygon(bottom1);  path1 = path3d(reverse(bottom1));  section1 = wall1(); // lite högre bakvägg wall(b=4, f=8, h=15, t=3.5)  path_sweep( section1, path1, closed=false);
  // fyll upp bottenplattansbaksida  linear_extrude(4) // Bottomplate - fill up    polygon(concat(points1, points2, points3, points4, points5));      // skapa Utskjutande del under (tänk spegelvänt)  pt1 = circSect(  19.5, 85, 0, [0, 50], "top", 1, fn);  // Uppe till höger - moturs  pt2 = circSect(  39, 1.35,  .1, [-5, 90], "right", 1, fn);  // Nere till höger  pt3 = circSect(  10, 13.05,  10, [0, 90], "bottom", 1, fn);  // Nere till vänster  pt4 = circSect(   5, 80, 5, [0, 90], "left",   1, fn);  // Uppe till vänster  translate([0, 0, -2])    linear_extrude(2.1)      polygon(concat(pt1, pt2, pt3, pt4));
  // utgången för kabeln på baksidan (diam 10mm) - pekar lite nedåt  cableExit(65, 35, 0, 15, "cyan", $fn=100);  }     // skapa ett borrhål i bakkant  translate([132,60,15])  { rotate([0, 90, 0])    { cylinder(h=10, d=2, $fn=100);      cylinder(h=4, d=9, $fn=100);      }  }    // skapa en borrmarkering i bakkant  translate([139,25,15])  { rotate([0, 90, 0])      cylinder(h=2, d1=1, d2=2.5, $fn=100);  }     // ingravera årtalet på baksidan  translate([10, 80, -0.5])  { mirror([side, 0, 0])    { rotate([0, 180, 0])      { linear_extrude(3)          text("2022", size=12, direction="ttb", font="Comic Sans MS:style=Bold");      }    }  }    /*  // Markera skruvhål på bakkant  borr=3;  bredd=140;  hojd=8;  avstNed=20;  translate([bredd, avstNed, hojd])  { rotate([0,90,0])      cylinder(h=2, d1=0.5, d2=borr, center=true, $fn=50);  }  */    // borrhål  mountingHole(20, 36, 0, 7, 90.1, 15); // posX, posY, posZ, diam, dist, deep, $fn=50    }}//========  Slut box 
---=============================

//

---================//======  cableExit 
---==============================module cableExit(posX, posY, posZ, angle, colorName){ diamHole = 7;  diamHolder = 9.8;  hight = 12;  topRad = diamHolder/2;  topDiam = diamHolder/2-topRad/2;  bowRad = 7;  offs1 = 0.1;
  color(colorName)  translate([posX, posY, posZ])  {  rotate([180, 0, 180-angle])    { difference()       { hull()        { cylinder(h=hight, d=diamHolder, center=false);          translate([0, 0, hight])        // rundad topp            rotate_extrude(angle=360, convexity=2)              translate([topDiam, 0, 0])  // yttre diam topp                circle(d=topRad);         // radie topp        }                  inpHight  =  2;   // ett värde som styr var utgångshålet hamnar        translate([0, 0, -offs1])          cylinder(h=inpHight+offs1, d=diamHole, center=false); // Bottenhål              translate([-bowRad, 0, inpHight-offs1]) // böjen        { rotate([90, 0, 0])            rotate_extrude(angle=90, convexity=10)              translate([bowRad, 0, 0]) // ställ in radien på kabelböjen                circle(d=diamHole);        }      }    }  }}//======  slut cableExit 
---=========================

//

---================//======  mountingHole 
---===========================module mountingHole(posX=0, posY=0, posZ=0, diam=7, dist=90, deep=5, $fn=50){ // diam =  6;   // [mm]  // dist = 90;   // [mm]  // deep =  12;  // [mm]
  translate([posX, posY, posZ])  { translate([0, 0, -10])      cylinder(h=deep, d=diam);  // fästhål 1        //cableHold1(dist/2, 0, .2, "#D5D5D5");  // Kabelgenomföring    translate([dist/2, 0, 0])    {  hull()      { cylinder(h=5, d=6);  // fästhål 1        sphere(d=7.5);      }    }        translate([dist, 0, -10])      cylinder(h=deep, d=diam); // fästhål 2  }}//======  slut mountingHole 
---======================

//

---================//======  LEDlampa 
---===============================// module LEDlampa(posX=8, posY=10, posZ=0)module LEDlampa(posX=0, posY=0, posZ=0, mountSide="left"){ side = mountSide == "left" ? 0       : mountSide == "right" ? 1       : assert(false,"invalid moutSide value");  // message if no case worked    xpos = mountSide == "left" ? 121       : mountSide == "right" ? -10       : assert(false,"invalid moutSide value");  // message if no case worked /*   ypos = mountSide == "left" ? 10.5       : mountSide == "right" ? 10.5       : assert(false,"invalid moutSide value");  // message if no case worked    zpos = mountSide == "left" ? 5       : mountSide == "right" ? 5       : assert(false,"invalid moutSide value");  // message if no case worked*/// echo(xpos,ypos,zpos);  // translate([xpos, ypos, zpos])  translate([xpos, 10.5, 5])  mirror([1, 0, 0])  translate([posX, posY, posZ])  { LEDbottom();      translate([0, 0, 11])        LEDglas();  }}//======  Slut LEDlampa 
---==========================

//

---================//======  LEDglas 
---================================module LEDglas(){  // Variabler botten  length  = 111;   // längd mm  wideMid = 50.5;  // bredd i mitten mm    cornRad = 10;    // Radien i alla hörn  wideCorn = 48;   // Bredd i kanterna    diamHole = 6;    // håldiameter i mm    colorBot = "gray";  colorTop = "orange";    // Variabler top  cornHigh = 5;   //Höjd i ändarna  midHigh  = 8;  highTop = cornHigh + 1;  // höjd mm          p1tx = 10;      // the start value  p1ty = 49.25;      p2tx = 55.5;    // the middle value  p2ty = 50.5;  p3tx = 101;     // the end value  p3ty = p1ty;    p4tx = 101;     // the start value  p4ty = 1.25;      p5tx = 55.5;    // the middle value  p5ty = 0.0;  p6tx = 10;      // the end value  p6ty = p4ty;  // Ger ovalt glas  points1 = 3points_arc([p1tx,p1ty], [p2tx,p2ty], [p3tx,p3ty], fn=100);  points2 = 3points_arc([p4tx,p4ty], [p5tx,p5ty], [p6tx,p6ty], fn=100);        color("orange")  linear_extrude(height=cornHigh+.1)  difference()    { polygon(concat(points1, points2));            translate([length-10 , wideMid / 2, -.2])      circle(d=6);    translate([10 , wideMid / 2, -.2])      circle(d=6);  }     // Top  color(colorTop)  difference()  { hull()    { // hörn1      translate([cornRad, wideMid - ((wideMid-wideCorn)/2) - cornRad, 0]) // [10,39]        cylinder(h=cornHigh, d=cornRad2, center=false);      // hörn2      translate([cornRad, cornRad + ((wideMid-wideCorn)/2), 0])           // [10,12]        cylinder(h=cornHigh, d=cornRad2, center=false);      // hörn3      translate([length - cornRad, wideMid - ((wideMid-wideCorn)/2) - cornRad, 0]) // [101 ,39]        cylinder(h=cornHigh, d=cornRad2, center=false);         // hörn4      translate([length - cornRad, cornRad + ((wideMid-wideCorn)/2), 0])  //         cylinder(h=cornHigh, d=cornRad2, center=false);    }              union()    { // Monteringshål 1 & 2      translate([length-10 , wideMid / 2, -.2])        cylinder(d=diamHole, h=highTop+.5, center=false);      translate([10 , wideMid / 2, -.2])        cylinder(d=diamHole, h=highTop+.5, center=false);    }  }}//========  Slut LEDglas 
---=========================

//

---================//======  LEDbottom 
---==============================module LEDbottom(){ p1x = 10;      // the start value  p1y = 49.25;      p2x = 55.5;    // the middle value  p2y = 50.5;  p3x = 101;     // the end value  p3y = p1y;
  p4x = 101;     // the start value  p4y = 1.25;      p5x = 55.5;    // the middle value  p5y = 0.0;  p6x = 10;      // the end value  p6y = p4y;    // Variabler botten för borrhålen   length  = 111;   // längd mm  wideMid = 50.5;  // bredd i mitten mm  diamHole = 6;    // håldiameter i mm  cornHigh = 5;   //Höjd i ändarna  midHigh  = 8;  highTop = cornHigh + 1;  // höjd mm  // offs1 = 0.1;  heightHole = 15; //mm  height = 11; //mm    points1 = circSect(  10, 11.25,  10, [0, 90], "bottom", 1, fn); // Hörn nere till vänster  points2 = circSect(  10, 39.25,  10, [0, 90], "left",   1, fn); // Hörn uppe till vänster  points3 = 3points_arc([p1x,p1y], [p2x,p2y], [p3x,p3y], fn);  points4 = circSect( 101, 39.25,  10, [0, 90], "top",    1, fn); // Hörn uppe till höger   points5 = circSect( 101, 11.25,  10, [0, 90], "right",  1, fn); // Hörn nere till höger   points6 = 3points_arc([p4x,p4y], [p5x,p5y], [p6x,p6y], fn);
  // The base plate for the LED lamp
    difference()  { color("gray", 0.5)     linear_extrude(height=height)      polygon(concat(points1, points2, points3, points4, points5, points6));

   // union()    { // Monteringshål 1 & 2      translate([length-10 , wideMid / 2, -.2])        cylinder(d=diamHole, h=heightHole, center=false);      translate([10 , wideMid / 2, -.2])        cylinder(d=diamHole, h=heightHole, center=false);    }  }}//========  Slut LEDbottom 
---=======================

//

---================//======  circleSect 
---=============================// Create rounded corners 2D// https://openhome.cc/eGossip/OpenSCAD/SectorArc.html// ange .:  x, y, radien,//          [från, till] vinkel,//          var vinkeln startar, (left, bottom, right, top)//          vilken rotation (-1=medsol, 1=motsols)function circSect(x=0, y=0, radius=10, angles=[0,270], startRef="bottom", rotate=1, fn=24)  =    let(        startAngel  = (startRef == "left")   ?   0                    : (startRef == "bottom") ?  90                    : (startRef == "right")  ? 180                    : (startRef == "top")    ? 270                    : startRef,  // valfri vinkel                  // : assert(false,"invalid moutSide value");  // Error message if no case worked                  //: undef,        r = radius,        //r = radius / cos(180 / fn),        step = 360 / fn,        // points = [[x, y],        points = [            for(a = [angles[0]-startAngel : step : angles[1]-startAngel])                [-rotate * r * cos(a)+x, r * sin(a)+y]]    ) points;//========  Slut circleSect 
---======================

//

---================//======  3points_arc 
---============================// Create an arc with three points 2Dfunction 3points_arc(p0, p1, p2, fn=10) =  // an alternative expression for D  // D  = 2 * ( (p1-p0).x * (p2-p0).y - (p1-p0).y * (p2-p0).x )  let( D  = 2 * cross(p1-p0, (p2-p0)) )  assert( abs(D)>1e-9, "The 3 points should not be collinear." )  let(      Ux     = ( (p2-p0).y*(p1-p0)(p1-p0) - (p1-p0).y(p2-p0)(p2-p0) )/D,      Uy     = ( (p1-p0).x(p2-p0)(p2-p0) - (p2-p0).x(p1-p0)(p1-p0) )/D,      radius = norm([Ux,Uy]),      center = [Ux,Uy] + p0,      ang0   = atan2( (p0-center).y, (p0-center).x ),      ang2   = atan2( (p2-center).y, (p2-center).x ),      // the points are in a cw winding iff D<0      // the angular difference between vectors p2-center and p0-center      // measured from p0-center; dang is positive iff D is negative      dang   = D<0  ? ang2<ang0 ? ang2-ang0 : ang2-ang0-360                    : ang2>ang0 ? ang2-ang0 : ang2-ang0+360  )  [ for(i=[0:fn-1])      let( ang = ang0 + idang/(fn-1) )      center + radius*[cos(ang),sin(ang)] ];//========  Slut 3points_arc 
---=====================

//

---================//======  Wall som ett "L" 
---=======================// Normal vägghöjdfunction wall() =   let(        b =  4,     // botten - tjocklek        f =  8,     // Foten        h = 15,     // Höjd        t =  3.5,   // Top        x = (b+(t/2) - (h - ( (-h / (f-t)) *t) )) / (-h / (f-t))    )    let(        points = [[0,0], [f,0], [t,h], [0,h]] ,        top = move([t/2, h, 0], circle(d=t, $fn=20)),        sqr = square([10, b]),        diff =            difference([                  move([x, b], square([t/2, t/2])),                  move([x+(t/2), b+(t/2), 0], circle(d = t, $fn=20) ) ])        )    union([points, top, sqr, diff]);//========  Slut Wall 
---============================

//

---================//======  Wall1 som ett "L" 
---======================// En högre väggfunction wall1() =  let(    b =  4,     // botten - tjocklek    f =  7,     // Foten    h = 25,     // Höjd    t =  3,   // Top    x = (b+(t/2) - (h - ((-h / (f-t)) *t))) / (-h / (f-t))  )  let(    points = [[0,0], [f,0], [t,h], [0,h]] ,    top = move([t/2, h, 0], circle(d=t, $fn=20)),    sqr = square([10, b]),    diff =      difference([        move([x, b], square([t/2, t/2])),        move([x+(t/2), b+(t/2), 0], circle(d = t, $fn=20) ) ])    )    union([points, top, sqr, diff]);//========  Slut Wall1 
---===========================

//

---================//======  Plåt på släp 
---===========================module mountingPlate(posX=0, posY=0, posZ=0, mountSide="left", colorName="#C0C0C0", $fn=50){ // Hörnpositionerna  posX1 = 120;  posY1 = 0;  posX2 = posX1;  posY2 = -200;  posX3 = 120 - 75;  posY3 = -200;  posX4 = 0;  posY4 = 0;  thick=2;  // tjocklek    side = mountSide == "left" ? 0       : mountSide == "right" ? 1       : assert(false,"invalid moutSide value");  // message if no case worked    xpos = mountSide == "left" ? 20       : mountSide == "right" ? -20       : assert(false,"invalid moutSide value");  // message if no case worked/*    ypos = mountSide == "left" ? 85       : mountSide == "right" ? 85       : assert(false,"invalid moutSide value");  // message if no case worked    zpos = mountSide == "left" ? -thick       : mountSide == "right" ? -thick       : assert(false,"invalid moutSide value");  // message if no case worked*/    color(colorName)  {  translate([posX, posY, posZ])     translate([xpos, 85, -thick])    { mirror([side, 0, 0])      { linear_extrude(thick)        hull()        { translate([posX1, posY1, 0])            square(0.1, center = true);          translate([posX2, posY2, 0])            square(0.1, center = true);          translate([posX3, posY3, 0])            square(0.1, center = true);          translate([posX4, posY4, 0])            square(0.1, center = true);        }      }    }  }}= = END product 1= = = = = = = = = = = = = = = = = = = = = = = = = = = = = = - . _ . - . _ . - . _ . - . _ . - . _ . - . _ . - . _ . - . _ . - . _ . - . _ . - . _ . - . _ . - . _ . -

= = product 2 = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = - . _ . - . _ . - . _ . - . _ . - . _ . - . _ . - . _ . - . _ . - . _ . - . _ . - . _ . - . _ . - . _ . -
 
$fn=100;//$fn=15;
//switch();//cableHolder4(); //Switchboxen

// cableHolder3(0, 0, 0, 33.5, 23.5, 1.5, 2);// showCables();

module cableHolder4(fn=24);{ // idé från  // - https://www.thingiverse.com/thing:6400/files  // - https://ihrchive.wordpress.com/2011/02/14/openscad-tip-round-1-of-3-basic-rounding/    // mått på Switch  heightHold = 10.5;  widthHold = 33.5;  depthHold = 23.5;  spaceHold = 10.0; // utrymmet bakom switch  holdRadie = 2;  // radie i hörnen  thick = 2;  offset1=0.5;  // öka toleransen    // innermått  holeW = widthHold + offset1;  holeH = heightHold + offset1;  holeD = depthHold + spaceHold+offset1;    // yttermått  pad = 0.1;                   // Padding to maintain manifold  box_l = holeW + thick*2;   // Bredden på switchen  box_w = holeD + thick;             // Djupet på switchen  box_h = holeH + thick;  // Height  round_r = holdRadie;         // Radius of round  smooth = 45;                 // Number of facets of rounding cylinder

  difference()  { union() // Detta utförs i två steg.    { difference()  // utför fasningar och kabelmarkeringar      { mainBox(box_l, box_w, box_h, spaceHold+thick, round_r, thick, smooth, pad);
        // fasning vänster (underkant)        translate([box_l/2-0.85, spaceHold-4.3, thick-offset1])  // sidled, fram/bak , upp/ned          rotate([0,180,45])            cylinder(h=thick, d1=holeW1.414-thick-thick, d2=holeW1.414, $fn=4);            // fasning höger (underkant)        translate([box_l/2-3.65, spaceHold-4.3, thick-offset1]) // sidled, fram/bak , upp/ned          rotate([0,180,45])            cylinder(h=thick, d1=holeW1.414-thick-thick, d2=holeW1.414, $fn=4);              // kabelgenomföringar        rotate([90, 180, 90]) // Markering ena sidan (vänster under)          ovalCableHole(spaceHold/2-offset1, -1.75, -1.2);            rotate([90, 180, 180]) // Markering bakkant (vänster under)          ovalCableHole(spaceHold/2-1.55, -1.75, -spaceHold-0.85);            rotate([90, 180, 180]) // Markering bakkant (höger under)          ovalCableHole(widthHold-spaceHold/2-offset1, -1.75, -spaceHold-0.85);              rotate([90, -180, 90])  // Markering ena sidan (höger under)          ovalCableHole(3.75, -1.75, widthHold-0.1);      }    } // Slut union - kropp        translate([-offset1/2, -spaceHold+pad, -pad]) // hålet där switchen ska placeras      cube([holeW, holeD+pad, holeH+pad], center=false);
      translate([4, 12, 0])        cylinder(h=15,d=3.2);      translate([4, 12, 17.7])        sphere(r=6);          translate([29.6, 12, 0])        cylinder(h=15,d=3.2);      translate([29.6, 12, 17.7])        sphere(r=6);            /*  // Hål genom lock bak - om så önskas      translate([box_l/2-thick, -6, offset1/2])        cylinder(h=box_h+thick4+offset1, d=3.2, $fn=100);  // hål genom lock bak            translate([box_l/2-thick, -6, 17.7])        sphere(r=6);    // kona hålet bak      /  } // Slut difference() - box
    difference()    { union()      { translate([29.6, 12, heightHold-offset1
2])          cylinder(h=2,d=5.2);        // Stödhylsa för Switchskruv1        translate([4, 12, heightHold-offset1
2])          cylinder(h=2,d=5.2);        // Stödhylsa för Switchskruv2
        translate([holeW/2, -spaceHold+thick+1, holeH/2])          rotate([180,0,0])             backHole();      } // union - slut             translate([4, 12, 0])     //  Hålen i stödhylsorna        cylinder(h=15,d=3.2);            translate([29.6, 12, 0])  //  Hålen i stödhylsorna        cylinder(h=15,d=3.2);       translate([box_l/2-thick, -6, -offset1])  // hål i stödhylsa bak        cylinder(h=box_h+offset1, d=3.2, $fn=100);            // Sänk stödhylsan        translate([ widthHold/2-7, -spaceHold-offset1, -thick+offset1])  // hål i stödhylsa bak          cube([15, 8, 3]);                  // kabelmarkering      // translate([0, 0, 0])  // hål i stödhylsa bak
            }

/*      translate([4, 12, 0])        #cylinder(h=15,d=3.2);      //translate([4, 13.5, 17.3])        //#sphere(r=6);          translate([29.6, 12, 0])        #cylinder(h=15,d=3.2);      //translate([29.6, 13.5, 17.3])        //#sphere(r=6);/  
}
module backHole(){ wallH = 10.5;    wide1   = 12; // endast runt cylindern  wide2   = 35; // hela väggen  deep1    =  4;  height1  = 10.5;  cornRad1  =  2;  diam1 = 8;  opt1 = 0.1;    //rundadFot();      // Rundad stäcka mellan t.ex. vägg och tak -bakkant  translate([wide2/2, diam1/2-cornRad1/2, -height1/2])  { rotate([90, 0, -90])    { linear_extrude(wide2)      { difference()        { square([cornRad1, cornRad1]);                    translate([cornRad1, cornRad1])            circle(r=cornRad1);        }      }    }  }    // rundad stäcka1 (vänster) mellan t.ex. vägg och tak  translate([-wide2/2+0.15, deep1/2+cornRad1/2, -height1/2])  rotate([90, 0, 0])  { linear_extrude(spaceHold)    { difference()      { square([cornRad1, cornRad1]);            translate([cornRad1, cornRad1])        circle(r=cornRad1);      }    }  }
  // rundad stäcka2 mellan t.ex. vägg och tak  translate([wide2/2-0.65, deep1/2+cornRad1/2, -height1/2])  rotate([0, -90, 90])  { linear_extrude(spaceHold)    { difference()      { square([cornRad1, cornRad1]);             translate([cornRad1, cornRad1])          circle(r=cornRad1);      }    }  }    // Skapa stödfot - bak  difference()  { union()    { //själva cylindern      translate([0, 1, 0])      { cylinder(h=height1, d=diam1, center=true);        translate([0, diam1/2, 0])          cube([diam1,diam1-1,height1], center=true);      }            // Rundad fot under cylinder ovan      translate([0, 1, -height1/2])      { rotate_extrude()        { translate([diam1/2, 0, 0])          { difference()            { square([cornRad1, cornRad1]);                            translate([cornRad1, cornRad1])                circle(r=cornRad1);            }          }        }      }            // Rundad rakstäcka1 - cylinderfot - mellan t.ex. vägg och tak      translate([diam1/2, diam1, -height1/2])      { rotate([90, 0, 0])        { linear_extrude(diam1)          { difference()            { square([cornRad1, cornRad1]);                            translate([cornRad1, cornRad1])                circle(r=cornRad1);            }          }        }      }            // Rundad rakstäcka2 - cylinderfot - mellan t.ex. vägg och tak      translate([-diam1/2, diam1, -height1/2])      { rotate([0, -90, 90])        { linear_extrude(diam1)          { difference()            { square([cornRad1, cornRad1]);                        translate([cornRad1, cornRad1])                circle(r=cornRad1);            }          }        }      }
      //väggen bakom cylindern som ska rundas      translate([0, diam1/2-cornRad1, 0])        cube([wide1, cornRad1, height1], center=true);
    }
     // Avrunda hörn1 bak    translate([-wide1/2, cornRad1/2, cornRad1])    { hull()      { cylinder(h=height1+opt1, r=cornRad1, center=true);        {  translate([0, 0, -height1/2])            sphere(r=cornRad1);        }      }      }      // Avrunda hörn2 bak    translate([wide1/2, cornRad1/2, cornRad1])    { hull()      { cylinder(h=height1+opt1, r=cornRad1, center=true);        {  translate([0, 0, -height1/2])            sphere(r=cornRad1);        }      }      }
        // Plocka bort rundad fot bak samt det som sticker ut    translate([-wide1/2, diam1/2-cornRad1/2, -height1/2-opt1])      cube([wide1, diam1/2+cornRad1, height1+opt1
2], center=false);
  }}

module ovalCableHole(posX, posY, posZ){ // Hål 5.5 x 3.5 mm  pan = 0.1;  cableHi = 1.5;    translate([posX, posY, posZ])  { color("white")    { translate([0, 0, -pan])      { cylinder(h=cableHi, d=3.5);        //#translate([0, 0, 0]) cylinder(h=10, d=1);        //translate([0, 0, -1]) cylinder(h=1, d1=0, d2=1);        //translate([0, 0, 0]) sphere(d=1); // Inre kulan        //translate([0, 0, 1.5]) sphere(d=1); // Inre kulan                translate([0, 0, -1]) sphere(d=0.8); // yttre kulan        translate([0, 0, 2.5]) sphere(d=0.8); // yttre kulan              }      translate([2, 0, -pan])      { cylinder(h=cableHi, d=3.5);        // #translate([0, 0, -cableHi*2]) cylinder(h=10, d=0.5);        //translate([0, 0, 0]) sphere(d=1); // Inre kulan        //translate([0, 0, 1.5]) sphere(d=1); // Inre kulan
        translate([0, 0, -1]) sphere(d=0.8); // yttre kulan        translate([0, 0, 2.5]) sphere(d=0.8); // yttre kulan
      }      translate([-3.5/2, 0, -pan])        cube([5.5, 3.5/2, cableHi]);      translate([-0.25, -1.74, -pan])        cube([2.5, 1.75, cableHi]);    }  }}

module rundadFot(){   // specifika värden för skruvdistansen bak  wallH = 10.5;
  wide1   = 12; // endast runt cylindern  wide2   = 34; // hela väggen  deep1    =  4;  height1  = 10;  cornRad1  =  2;  diam1 = 8;  opt1 = 0.1;

  color("magenta")  { translate([0, 0, wallH])    { difference()      { union()        { // Bakgavel          translate([wide2/2, opt1, height1/2])          { rotate([90, 180, 0])              cube([wide2, height1, opt1]);          }                // Golv          translate([wide2/2, -height1+opt1, -height1/2])            rotate([0, 180, 0])              cube([wide2, height1, opt1]);                    //väggen bakom cylindern som kan rundas          translate([0, -cornRad1/2, 0])            cube([wide1, cornRad1, height1], center=true);                    //själva cylindern          translate([0, -cornRad1/2, 0])            cylinder(h=height1, d=diam1, center=true);            // Rundad fot under cylinder ovan          translate([0, -cornRad1/2, -height1/2])          { rotate_extrude()            { translate([diam1/2, 0, 0])              { difference()                { square([cornRad1, cornRad1]);                            translate([cornRad1, cornRad1])                    circle(r=cornRad1);                }              }            }          }                    // Rundad stäcka mellan t.ex. vägg och tak -bakkant          translate([wide2/2, 0, -height1/2])          { rotate([90, 0, -90])            { linear_extrude(wide2)              { difference()                { square([cornRad1, cornRad1]);                          translate([cornRad1, cornRad1])                    circle(r=cornRad1);                }              }            }          }                    // rundad stäcka mellan t.ex. vägg och tak -sida1          translate([-wide2/2, 0, -height1/2])          { rotate([90, 0, 0])            { linear_extrude(10)              { difference()                { square([cornRad1, cornRad1]);                            translate([cornRad1, cornRad1])                  circle(r=cornRad1);                }              }            }          }                    // rundad stäcka mellan t.ex. vägg och tak -sida2          translate([wide2/2, -10, -height1/2])          { rotate([90, 0, 180])            { linear_extrude(10)              { difference()                { square([cornRad1, cornRad1]);                              translate([cornRad1, cornRad1])                  circle(r=cornRad1);                }              }            }          }        } // Avsluta union = = = = = = = = = = = = = = = = = = = =                // Avrunda hörn1 bak        translate([-wide1/2+opt11.3, -deep1/2, cornRad1])        { cylinder(h=height1+opt1, r=cornRad1, center=true);            translate([0, 0, -height1/2])              sphere(r=cornRad1);        }          // Avrunda hörn2 bak        translate([wide1/2-opt11.3, -deep1/2, cornRad1])        { cylinder(h=height1+opt1, r=cornRad1, center=true);            translate([0, 0, -height1/2])              sphere(r=cornRad1);        }            // Plocka bort rundad fot bak samt det som sticker ut        translate([-wide1/2, 0, -height1/2-opt1])          cube([wide1, diam1/2+cornRad1, height1+opt1*2], center=false);      }    }  }}

module mainBox(box_l, box_w, box_h, spaceHold, round_r, thick, smooth, pad){ translate([box_l/2-thick-offset1/2, box_w/2-spaceHold, box_h/2])  {    // To fix the corners cut the main cube with smaller cubes with spheres removed    difference()    { cube([box_l, box_w, box_h], center = true);          // Kant1 - liggande      translate([0, -box_w/2+round_r, box_h/2-round_r])      { difference()        { translate([0,-round_r-pad,round_r+pad])            cube([box_l+2pad, round_r2+pad, round_r2+pad], center = true);          rotate(a=[0,90,0])            cylinder(box_l+4pad,round_r,round_r,center=true,$fn=smooth);        }      }      // Kant2 - liggande      translate([0, box_w/2-round_r, box_h/2-round_r])      { difference()        { translate([0,round_r+pad,round_r+pad])            cube([box_l+2pad, round_r2+pad, round_r2+pad], center = true);          rotate(a=[0,90,0])            cylinder(box_l+4pad,round_r,round_r,center=true,$fn=smooth);        }      }      /*      // Kant3 - liggande      translate([0, -box_w/2+round_r, -box_h/2+round_r])      { difference()        { translate([0,-round_r-pad,-round_r-pad])            cube([box_l+2pad, round_r2+pad, round_r2+pad], center = true);          rotate(a=[0,90,0])            cylinder(box_l+4pad,round_r,round_r,center=true,$fn=smooth);        }      }          // Kant4 - liggande      translate([0, box_w/2-round_r, -box_h/2+round_r])      { difference()        { translate([0,round_r+pad,-round_r-pad])            cube([box_l+2pad, round_r2+pad, round_r2+pad], center = true);          rotate(a=[0,90,0])            cylinder(box_l+4pad,round_r,round_r,center=true,$fn=smooth);        }      }    /    // ----      // Kant1 - stående      translate([-box_l/2+round_r, box_w/2-round_r, 0])      { difference()        { translate([-round_r-pad,round_r+pad,0])            cube([round_r2+pad, round_r2+pad, box_h+2pad], center = true);          cylinder(box_h+4pad,round_r,round_r,center=true,$fn=smooth);        }      }      // Kant2 - stående      translate([box_l/2-round_r, box_w/2-round_r, 0])      { difference()        { translate([round_r+pad,round_r+pad,0])            cube([round_r2+pad, round_r2+pad, box_h+2pad], center = true);          cylinder(box_h+4pad,round_r,round_r,center=true,$fn=smooth);        }      }      // Kant3 - stående      translate([-box_l/2+round_r, -box_w/2+round_r, 0])      { difference()        { translate([-round_r-pad,-round_r-pad,0])            cube([round_r2+pad, round_r2+pad, box_h+2pad], center = true);          cylinder(box_h+4pad,round_r,round_r,center=true,$fn=smooth);        }      }      // Kant4 - stående      translate([box_l/2-round_r, -box_w/2+round_r, 0])      { difference()        { translate([round_r+pad,-round_r-pad,0])            cube([round_r2+pad, round_r2+pad, box_h+2pad], center = true);          cylinder(box_h+4pad,round_r,round_r,center=true,$fn=smooth);        }      }        // ----      // Kant1 liggande (andra hållet)      translate([-box_l/2+round_r, 0, box_h/2-round_r])      { difference()        { translate([-round_r-pad, 0, round_r+pad])            cube([round_r2+pad, box_w+2pad, round_r2+pad], center = true);          rotate(a=[0,90,90])            cylinder(box_w+4pad,round_r,round_r,center=true,$fn=smooth);        }      }      // Kant2 liggande (andra hållet)      translate([box_l/2-round_r, 0, box_h/2-round_r])      { difference()        {  translate([round_r+pad, 0, round_r+pad])            cube([round_r2+pad, box_w+2pad, round_r2+pad], center = true);          rotate(a=[0,90,90])            cylinder(box_w+4pad,round_r,round_r,center=true,$fn=smooth);        }      }      /      // Kant3 liggande (andra hållet)      translate([-box_l/2+round_r, 0, -box_h/2+round_r])      { difference()        { translate([-round_r-pad, 0, -round_r-pad])            cube([round_r2+pad, box_w+2pad, round_r2+pad], center = true);          rotate(a=[0,90,90])            cylinder(box_w+4pad,round_r,round_r,center=true,$fn=smooth);        }      }        // Kant4 liggande (andra hållet)      translate([box_l/2-round_r, 0, -box_h/2+round_r])      { difference()        { translate([round_r+pad, 0, -round_r-pad])            cube([round_r2+pad, box_w+2pad, round_r2+pad], center = true);          rotate(a=[0,90,90])            cylinder(box_w+4pad,round_r,round_r,center=true,$fn=smooth);        }      }  /     // ----      // Hörn1 (övre)      translate([box_l/2-round_r, box_w/2-round_r, box_h/2-round_r])      { difference()        { translate([round_r+pad, round_r+pad, round_r+pad])            cube([round_r2+pad, round_r2+pad, round_r2+pad], center = true);          sphere(round_r,$fn=smooth);        }      }      // Hörn2 (övre)      translate([-box_l/2+round_r, box_w/2-round_r, box_h/2-round_r])      { difference()        { translate([-round_r-pad, round_r+pad, round_r+pad])            cube([round_r2+pad, round_r2+pad, round_r2+pad], center = true);          sphere(round_r,$fn=smooth);        }      }      // Hörn3 (övre)      translate([box_l/2-round_r, -box_w/2+round_r, box_h/2-round_r])      { difference()        { translate([round_r+pad, -round_r-pad, round_r+pad])            cube([round_r2+pad, round_r2+pad, round_r2+pad], center = true);          sphere(round_r,$fn=smooth);        }      }      // Hörn4 (övre)      translate([-box_l/2+round_r, -box_w/2+round_r, box_h/2-round_r])      { difference()        { translate([-round_r-pad, -round_r-pad, round_r+pad])            cube([round_r2+pad, round_r2+pad, round_r2+pad], center = true);          sphere(round_r,$fn=smooth);        }      }      /      // Hörn1 (undre)      translate([box_l/2-round_r, box_w/2-round_r, -box_h/2+round_r])      { difference()        { translate([round_r+pad, round_r+pad, -round_r-pad])            cube([round_r2+pad, round_r2+pad, round_r2+pad], center = true);          sphere(round_r,$fn=smooth);        }      }      // Hörn2 (undre)      translate([-box_l/2+round_r, box_w/2-round_r, -box_h/2+round_r])      { difference()        { translate([-round_r-pad, round_r+pad, -round_r-pad])            cube([round_r2+pad, round_r2+pad, round_r2+pad], center = true);          sphere(round_r,$fn=smooth);        }      }      // Hörn3 (undre)      translate([box_l/2-round_r, -box_w/2+round_r, -box_h/2+round_r])      { difference()        { translate([round_r+pad, -round_r-pad, -round_r-pad])            cube([round_r2+pad, round_r2+pad, round_r2+pad], center = true);          sphere(round_r,$fn=smooth);        }      }      // Hörn4 (undre)      translate([-box_l/2+round_r, -box_w/2+round_r, -box_h/2+round_r])      { difference()        { translate([-round_r-pad, -round_r-pad, -round_r-pad])            cube([round_r2+pad, round_r2+pad, round_r2+pad], center = true);          sphere(round_r,$fn=smooth);        }      }      */    }  }}//

module cableHolder3(posX, posY, posZ, length, width, height, radius){ // Skapa toppen över switchen  // mått på Switchen  fn = 96;          // upplösning (endast bågen?)  heightHold = 10.5;  widthHold = 33.5;  depthHold = 23.5;   holdRadie = 1.5;  // radie i hörnen  thick = 1.5;      // tjocklek      translate([0,-thick,0])  {     difference(0, 0, 0)    { hull()      { difference()        { translate([thick, 0, heightHold]) // vänster kant          { rotate([-90, 0, 0])            { cylinder(h=depthHold, d=thick2);              translate([0, 0, depthHold])                sphere(d=thick2);          // längst fram            }          }          translate([0, -0.1, heightHold]) // plocka bort underdelen            rotate([-90, 0, 0])              cube([thick2, thick+.1, depthHold+thick+.1]);        }                difference()        { translate([widthHold-thick, 0, heightHold]) // höger kant          { rotate([-90, 0, 0])            { cylinder(h=depthHold, d=thick2);              translate([0, 0, depthHold])                sphere(d=thick2);         // längst fram            }          }          translate([widthHold-thick2, -0.1, heightHold]) // plocka bort underdelen          { rotate([-90, 0, 0])              cube([thick2, thick+.1, depthHold+thick+.1]);          }        }      }            // öppna hålen för monteringsskruvarna uppe på plattan      translate([4, 13.5, 0])        cylinder(h=15,d=3.2);      translate([4, 13.5, 17.3])        sphere(r=6);          translate([29.6, 13.5, 0])        cylinder(h=15,d=3.2);        translate([29.6, 13.5, 17.3])        sphere(r=6);    }      // halvbåge 1 bak    translate([thick, 0, heightHold/2+thick/2])      rotate([0, 90, 180])        rotate_extrude(angle = 180, convexity=20, $fn=64)    translate([heightHold/2-thick/2, 0, 0])      circle(d=thick2);    translate([thick, 0, heightHold])      sphere(d=thick2);  // övre kulan      translate([thick, 0, thick])      sphere(d=thick2);  // undre kulan
          // halvbåge 2 bak    translate([widthHold-thick, 0, heightHold/2+thick/2])      rotate([0, 90, 180])        rotate_extrude(angle = 180, convexity=20, $fn=64)    translate([heightHold/2-thick/2, 0, 0])      circle(d=thick2);    translate([widthHold-thick, 0, heightHold])      sphere(d=thick2);  // övre kulan    translate([widthHold-thick, 0, thick])      sphere(d=thick2);  // undre kulan          // en cylinder tvärsöver längst upp    translate([thick, 0, heightHold])    { rotate([0,90,0])        cylinder(h=widthHold-thick2, r=thick);    }  }       // Halvbågen (kabelhållaren) på baksidan switchen  translate([widthHold-thick, -thick, heightHold/2+thick/2])  { rotate([0,90,180])      linear_extrude(widthHold-thick2)        arc(heightHold/2-thick/2, [0, 180], thick, fn); //radius, angles, width, fn)  }  // en cylinder tvärsöver längst ned  translate([thick, -thick, thick])  { rotate([0,90,0])      cylinder(h=widthHold-thick2, r=thick);  }   }

module switch(posX=0, posY=0, posZ=0){ buttRadie = 1.5;  height = 10.5;  width = 33.5;  depth = 23.5;  h1x = buttRadie;  h1y = buttRadie;  h2x = width-buttRadie;  h2y = buttRadie;  h3x = width-buttRadie;  h3y = depth-buttRadie;  h4x = buttRadie;  h4y = depth-buttRadie;          translate([posX, posY, posZ])  { difference()    { color("#F9F9F3")       // tryck-knappen      union()      { translate([width/2, depth+6-0.1, height/2])        { rotate([90, 0, 0])          { translate([0,0,6])                circle(d=6.8);  // skuggan runt knapp            cylinder(h=6, d=6);            sphere(d=6);          }        }                hull()  // Switchkropp        { translate([h1x, h1y])            cylinder(h=height, r=1.5);          translate([h2x, h2y])            cylinder(h=height, r=1.5);          translate([h3x, h3y])            cylinder(h=height, r=1.5);          translate([h4x, h4y])            cylinder(h=height, r=1.5);        }      }            // Skruvhålen för switchen      hole( 4, 12, 0, "#FFD700", height);      hole(29.6, 12, 0, "#FFD700", height);      // hole( 4, 12, 0, "#FFD700", 50);      // hole(29.6, 12, 0, "#FFD700", 50);      // hål för kablar bak      color("gray")      { translate([9.5, 16, height/2])        { rotate([90, 0, 0])            cylinder(h=16.5, d=4);        }        translate([24.5, 16, height/2])        {  rotate([90, 0, 0])            cylinder(h=16.5, d=4);        }      }            // hål för kabelskruvar      color("white")      { translate([29.5, 17.1, height/2])        { rotate([0, 90, 0])            cylinder(h=4.1, d=4.5);              }        translate([-0.1, 17.1, height/2])        { rotate([0, 90, 0])            cylinder(h=4.1, d=4.5);        }      }    }         // Kabelskruvar    cableScrew(3, 17, height/2, 90);    cableScrew(31, 17, height/2, -90);       }}
// Skruven som håller fast kabeln i switchenmodule cableScrew(posX=0, posY=0, posZ=0, angle=0){ color("#FFD700")  // mässing  translate([posX, posY, posZ])  { rotate([0, 0, angle])    { difference()      { // skruvskalle        translate([0, 0, 0])          rotate([90, 0, 0])            cylinder(h=2, d1=4, d2=3.5);              // stjärnan i skruven        translate([0, 1.85, -.25])          rotate([0, 0, 0])            cylinder(h=0.5, d=5);        translate([-0.25, -.6, 2.25])            rotate([0, 90, 0])            cube([4.5, 2, 0.5]);      }    }  }}

// borrhålmodule hole(posX=0, posY=0, posZ=0, colorName="yellow", height){ diamHole1 = 3;  highHole1 = height;  diamHole2 = 6;  highHole2 = 2.5;  offs=0.1;    color(colorName)  {    translate([posX, posY, posZ])    { translate([0, 0, 0])        cylinder(h=highHole1, d=diamHole1);      translate([0, 0, -offs])        cylinder(h=highHole2, d=diamHole2);      translate([0, 0, height-highHole2+offs])        cylinder(h=highHole2, d=diamHole2);    }  }}
module showCables(){ translate([-25,8,24])    rotate([80,177,90])      cable(10,10,0,"brun");  translate([-43,8,15])    rotate([90,180,90])      cable(10,10,0,"blå");}

module cable(posX=0, posY=0, posZ=0, colorName="blå", radius=1.26, width=0.62, thick=50, fn=24){ // default 1.5mm2  // radius = inner radie  // width = bredd/tjocklek på cirkeln (inte höjd)  // thick = höjd på cirken/ röret  // pin=
  colCupper = "#D7715A";  colGreen  = "#07DA63";  colYellow = "#FFCC00";      if (colorName=="gröngul")  { translate([posX, posY, posZ])    { color(colGreen)        linear_extrude(thick)          arc(radius, [0, 60], width, fn);      color(colYellow)          linear_extrude(thick)          arc(radius, [60, 180], width, fn);      color(colGreen)        linear_extrude(thick)          arc(radius, [180, 240], width, fn);      color(colYellow)          linear_extrude(thick)          arc(radius, [240, 360], width, fn); 
      color(colCupper)        linear_extrude(10, center=true, convexity=10, $fn=100)          circle(d=1.24);    }  }  else  // vanliga kablar 1.5mm2  {    cableColor = colorName == "blå" ? "#1870D5"               : colorName == "brun" ? "#9C6137"               : colorName == "svart" ? "#000000"               : assert(false,"invalid color value");  // message if no case worked                   // : nodef      translate([posX, posY, posZ])    {             //el kabel - ena änden rak - andra böjd      color(colCupper)    //kopparstump tråd rakkabel        linear_extrude(10, center=true, convexity=10, $fn=100)          circle(d=1.24);        color(cableColor)        { cylinder(h=thick, r=radius);                translate([-radius2, 0, thick])  // kabelböj        rotate([90, 0, 0])        rotate_extrude(angle=90, convexity=20)          translate([2.5, 0, 0])            circle(r=1.26);              translate([-radius2, 0, thick+radius2])          rotate([0, -90, 0])          cylinder(h=5, r=radius);      }              translate([-10, 0, thick+radius2])      { rotate([0, -90, 0])        { color(colCupper)          { linear_extrude(5, center=true, convexity=10, $fn=100)              circle(d=1.24);          }        }      }    }  }}

//

---====module arc(radius, angles, width = 1, fn = 24) {    difference() {        sector(radius + width, angles, fn); // ytterradie        sector(radius, angles, fn);         // innerradie (plockar bort invändigt    }}
module sector(radius, angles, fn = 24) {    r = radius / cos(180 / fn);    step = -360 / fn;
    points = concat([[0, 0]],        [for(a = [angles[0] : step : angles[1] - 360])             [r * cos(a), r * sin(a)]        ],        [[r * cos(angles[1]), r * sin(angles[1])]]    );
    difference() {        circle(radius, $fn = fn);        polygon(points);    }}= = END product 2 = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = - . _ . - . _ . - . _ . - . _ . - . _ . - . _ . - . _ . - . _ . - . _ . - . _ . - . _ . - . _ . - . _ . -

Den fredag 6 maj 2022 14:06:55 CEST, Michael Möller <private2michael@gmail.com> skrev:  

OpenSCAD code - is a description of your model in terms of a few cylinder/cubes added and cut outdifference() {  cylinder(d=5,h=10);  translate([0,10,0]) cube([4,6,2]) ;}
STL file is a list of triangles which make the same outer shell as your model. OpenSCAD makes this complicated transform from shapes to triangles.solid OpenSCAD_Model
  facet normal 0.92388 0.382682 0
    outer loop
      vertex 2.5 0 3
      vertex 1.76777 1.76777 0
      vertex 1.76777 1.76777 3
    endloop
  endfacet
  facet normal 0.92388 0.382682 0
    outer loop
      vertex 1.76777 1.76777 0
      vertex 2.5 0 3
      vertex 2.5 0 0
    endloop
  endfacet
  : (and so on for 300 lines) There is a binary/compressed version, but the description is still just triangles.
Gcode is what a 3D printer understands - it is the exact list of moves that the head has to do with how much plastic to squeeze to trace the outline of your shape, layer, by layer. It will optionally create moves for filling the inside or support for overhangs. Such a program is called a SLICER and the printer will come with one.G92 E0 ; reset extrusion distance
G1 Z2.330 F6600.000 ; lift Z
G1 X-0.000 Y1.505 F6600.000 ; move to first perimeter point
G1 Z0.330 F6600.000 ; restore layer Z
G1 E3.00000 F2400.00000 ; unretract extruder 0
G1 F1500
G1 X-1.064 Y1.064 E3.09259 ; perimeter
G1 X-1.505 Y0.000 E3.18517 ; perimeter
  : (many similar lines)
G1 X1.515 Y1.515 E4.65860 ; perimeter
G1 X0.055 Y2.120 E4.78559 ; perimeter
G1 X-0.000 Y2.143 F6600.000 ; move inwards before travel
G1 X0.384 Y0.843 F6600.000 ; move to first infill point
G1 F1500
G1 X0.843 Y0.384 E4.84815 ; infill
G1 X1.097 Y-0.229 E4.91215 ; infill
 :(and so on for thousands of lines)
The 3MF still basically deals in triangles, and attributes (surface, infill material, picture, ticket info ... ) which probably are not used by your slicer/printer. 
On Fri, 6 May 2022 at 12:37, Jan Öhman via Discuss discuss@lists.openscad.org wrote:

---------- Forwarded message ----------
From: "Jan Öhman" jan_ohman@yahoo.com
To: OpenSCAD General Discussion discuss@lists.openscad.org
Cc: 
Bcc: 
Date: Fri, 6 May 2022 10:38:46 +0000 (UTC)
Subject: [OpenSCAD] Export to .STL / .3MF for later 3D-printing.
Hi!

Thought to create some objects in openSCAD, to print later.I do not have my own 3D printer (yet).
One I talked to, wanted to get the drawings in .STL or .3MF. (I don't know the difference).

If I had my own printer, have I been able to print directly from openSCAD?
(Without some export?)
In the openSCAD, no errors or problems occur.butThe drawings I tested to export from openSCAD have given one or another error message.One message .:WARNING: Object may not be a valid 2-manifold and may need repair! 

Another message .:WARNING: No top level geometry to render 

What to do?

---------- Forwarded message ----------
From: "Jan Öhman via Discuss" discuss@lists.openscad.org
To: OpenSCAD General Discussion discuss@lists.openscad.org
Cc: "Jan Öhman" jan_ohman@yahoo.com
Bcc: 
Date: Fri, 6 May 2022 10:38:46 +0000 (UTC)
Subject: [OpenSCAD] Export to .STL / .3MF for later 3D-printing.


OpenSCAD mailing list
To unsubscribe send an email to discuss-leave@lists.openscad.org


OpenSCAD mailing list
To unsubscribe send an email to discuss-leave@lists.openscad.org

Thank you! Begins to understand how it works. (It was not easy...) but my solution was not good ... Here are 2 files that do not work to render (F6) = = product 1= = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = =  - . _ . - . _ . - . _ . - . _ . - . _ . - . _ . - . _ . - . _ . - . _ . - . _ . - . _ . - . _ . - . _ . - include <BOSL2/std.scad>fn = 150; placering="left";// placering="right" box(0, 0, 0, placering, "#C0C0C0", fn); // (X, Y, Z, left/right, colorName) // Monteringsplattan// mountingPlate(0, 0, 0, placering); // LED belysning// LEDlampa(0, 0, 0, placering); // - - - - - - - - - - - - - - - - - - - - - - - - - - - - - // - - - - m o d u l e r - - - - - - - - - - - - - - - - - -  //==================================================================================//======  box  =====================================================================module box(posX=0, posY=0, posZ=0, mountSide="left", colorName="#00FF00", fn=24){   side = mountSide == "left" ? 0       : mountSide == "right" ? 1       : assert(false,"invalid moutSide value");  // message if no case worked    color(colorName)  translate([posX, posY, posZ])  mirror([side, 0, 0])  difference()  {  union()  {  // Skapa konturer på bottenplattan - x, y, r, angles, [grader], början  // Rotation medurs - vänster lamphållare (bakant saknas)  points1 = circSect( 140,  0,   0, [0, 0], "right",  1, fn);  // böj nere till höger  points2 = circSect(  60,  5,   5, [0, 5], "bottom",  1, fn); // brytpunkt längst ned  points3 = circSect(  10, 13,  10, [0, 90], "bottom", 1, fn); // böj nere till vänster  points4 = circSect(   5, 80,   5, [0, 90], "left",   1, fn); // böj uppe till vänster  points5 = circSect( 140, 80,   5, [0, 1], "top",   1, fn);   // böj uppe till höger  edge = concat(points1, points2, points3, points4, points5);  path = path3d(reverse(edge));  section = wall();  path_sweep( section, path, closed=false);     // Skapa bakkant lite högre och smalare i topp  bottom1 = concat(points5, points1);  polygon(bottom1);  path1 = path3d(reverse(bottom1));  section1 = wall1(); // lite högre bakvägg wall(b=4, f=8, h=15, t=3.5)  path_sweep( section1, path1, closed=false);   // fyll upp bottenplattansbaksida  linear_extrude(4) // Bottomplate - fill up    polygon(concat(points1, points2, points3, points4, points5));      // skapa Utskjutande del under (tänk spegelvänt)  pt1 = circSect(  19.5, 85, 0, [0, 50], "top", 1, fn);  // Uppe till höger - moturs  pt2 = circSect(  39, 1.35,  .1, [-5, 90], "right", 1, fn);  // Nere till höger  pt3 = circSect(  10, 13.05,  10, [0, 90], "bottom", 1, fn);  // Nere till vänster  pt4 = circSect(   5, 80, 5, [0, 90], "left",   1, fn);  // Uppe till vänster  translate([0, 0, -2])    linear_extrude(2.1)      polygon(concat(pt1, pt2, pt3, pt4));   // utgången för kabeln på baksidan (diam 10mm) - pekar lite nedåt  cableExit(65, 35, 0, 15, "cyan", $fn=100);  }     // skapa ett borrhål i bakkant  translate([132,60,15])  { rotate([0, 90, 0])    { cylinder(h=10, d=2, $fn=100);      cylinder(h=4, d=9, $fn=100);      }  }    // skapa en borrmarkering i bakkant  translate([139,25,15])  { rotate([0, 90, 0])      cylinder(h=2, d1=1, d2=2.5, $fn=100);  }     // ingravera årtalet på baksidan  translate([10, 80, -0.5])  { mirror([side, 0, 0])    { rotate([0, 180, 0])      { linear_extrude(3)          text("2022", size=12, direction="ttb", font="Comic Sans MS:style=Bold");      }    }  }    /*  // Markera skruvhål på bakkant  borr=3;  bredd=140;  hojd=8;  avstNed=20;  translate([bredd, avstNed, hojd])  { rotate([0,90,0])      cylinder(h=2, d1=0.5, d2=borr, center=true, $fn=50);  }  */    // borrhål  mountingHole(20, 36, 0, 7, 90.1, 15); // posX, posY, posZ, diam, dist, deep, $fn=50    }}//========  Slut box  ============================================================== //==================================================================================//======  cableExit  ===============================================================module cableExit(posX, posY, posZ, angle, colorName){ diamHole = 7;  diamHolder = 9.8;  hight = 12;  topRad = diamHolder/2;  topDiam = diamHolder/2-topRad/2;  bowRad = 7;  offs1 = 0.1;   color(colorName)  translate([posX, posY, posZ])  {  rotate([180, 0, 180-angle])    { difference()       { hull()        { cylinder(h=hight, d=diamHolder, center=false);          translate([0, 0, hight])        // rundad topp            rotate_extrude(angle=360, convexity=2)              translate([topDiam, 0, 0])  // yttre diam topp                circle(d=topRad);         // radie topp        }                  inpHight  =  2;   // ett värde som styr var utgångshålet hamnar        translate([0, 0, -offs1])          cylinder(h=inpHight+offs1, d=diamHole, center=false); // Bottenhål              translate([-bowRad, 0, inpHight-offs1]) // böjen        { rotate([90, 0, 0])            rotate_extrude(angle=90, convexity=10)              translate([bowRad, 0, 0]) // ställ in radien på kabelböjen                circle(d=diamHole);        }      }    }  }}//======  slut cableExit  ========================================================== //==================================================================================//======  mountingHole  ============================================================module mountingHole(posX=0, posY=0, posZ=0, diam=7, dist=90, deep=5, $fn=50){ // diam =  6;   // [mm]  // dist = 90;   // [mm]  // deep =  12;  // [mm]   translate([posX, posY, posZ])  { translate([0, 0, -10])      cylinder(h=deep, d=diam);  // fästhål 1        //cableHold1(dist/2, 0, .2, "#D5D5D5");  // Kabelgenomföring    translate([dist/2, 0, 0])    {  hull()      { cylinder(h=5, d=6);  // fästhål 1        sphere(d=7.5);      }    }        translate([dist, 0, -10])      cylinder(h=deep, d=diam); // fästhål 2  }}//======  slut mountingHole  ======================================================= //==================================================================================//======  LEDlampa  ================================================================// module LEDlampa(posX=8, posY=10, posZ=0)module LEDlampa(posX=0, posY=0, posZ=0, mountSide="left"){ side = mountSide == "left" ? 0       : mountSide == "right" ? 1       : assert(false,"invalid moutSide value");  // message if no case worked    xpos = mountSide == "left" ? 121       : mountSide == "right" ? -10       : assert(false,"invalid moutSide value");  // message if no case worked /*   ypos = mountSide == "left" ? 10.5       : mountSide == "right" ? 10.5       : assert(false,"invalid moutSide value");  // message if no case worked    zpos = mountSide == "left" ? 5       : mountSide == "right" ? 5       : assert(false,"invalid moutSide value");  // message if no case worked*/// echo(xpos,ypos,zpos);  // translate([xpos, ypos, zpos])  translate([xpos, 10.5, 5])  mirror([1, 0, 0])  translate([posX, posY, posZ])  { LEDbottom();      translate([0, 0, 11])        LEDglas();  }}//======  Slut LEDlampa  =========================================================== //==================================================================================//======  LEDglas  =================================================================module LEDglas(){  // Variabler botten  length  = 111;   // längd mm  wideMid = 50.5;  // bredd i mitten mm    cornRad = 10;    // Radien i alla hörn  wideCorn = 48;   // Bredd i kanterna    diamHole = 6;    // håldiameter i mm    colorBot = "gray";  colorTop = "orange";    // Variabler top  cornHigh = 5;   //Höjd i ändarna  midHigh  = 8;  highTop = cornHigh + 1;  // höjd mm          p1tx = 10;      // the start value  p1ty = 49.25;      p2tx = 55.5;    // the middle value  p2ty = 50.5;  p3tx = 101;     // the end value  p3ty = p1ty;    p4tx = 101;     // the start value  p4ty = 1.25;      p5tx = 55.5;    // the middle value  p5ty = 0.0;  p6tx = 10;      // the end value  p6ty = p4ty;  // Ger ovalt glas  points1 = 3points_arc([p1tx,p1ty], [p2tx,p2ty], [p3tx,p3ty], fn=100);  points2 = 3points_arc([p4tx,p4ty], [p5tx,p5ty], [p6tx,p6ty], fn=100);        color("orange")  linear_extrude(height=cornHigh+.1)  difference()    { polygon(concat(points1, points2));            translate([length-10 , wideMid / 2, -.2])      circle(d=6);    translate([10 , wideMid / 2, -.2])      circle(d=6);  }     // Top  color(colorTop)  difference()  { hull()    { // hörn1      translate([cornRad, wideMid - ((wideMid-wideCorn)/2) - cornRad, 0]) // [10,39]        cylinder(h=cornHigh, d=cornRad*2, center=false);      // hörn2      translate([cornRad, cornRad + ((wideMid-wideCorn)/2), 0])           // [10,12]        cylinder(h=cornHigh, d=cornRad*2, center=false);      // hörn3      translate([length - cornRad, wideMid - ((wideMid-wideCorn)/2) - cornRad, 0]) // [101 ,39]        cylinder(h=cornHigh, d=cornRad*2, center=false);         // hörn4      translate([length - cornRad, cornRad + ((wideMid-wideCorn)/2), 0])  //         cylinder(h=cornHigh, d=cornRad*2, center=false);    }              union()    { // Monteringshål 1 & 2      translate([length-10 , wideMid / 2, -.2])        cylinder(d=diamHole, h=highTop+.5, center=false);      translate([10 , wideMid / 2, -.2])        cylinder(d=diamHole, h=highTop+.5, center=false);    }  }}//========  Slut LEDglas  ========================================================== //==================================================================================//======  LEDbottom  ===============================================================module LEDbottom(){ p1x = 10;      // the start value  p1y = 49.25;      p2x = 55.5;    // the middle value  p2y = 50.5;  p3x = 101;     // the end value  p3y = p1y;   p4x = 101;     // the start value  p4y = 1.25;      p5x = 55.5;    // the middle value  p5y = 0.0;  p6x = 10;      // the end value  p6y = p4y;    // Variabler botten för borrhålen   length  = 111;   // längd mm  wideMid = 50.5;  // bredd i mitten mm  diamHole = 6;    // håldiameter i mm  cornHigh = 5;   //Höjd i ändarna  midHigh  = 8;  highTop = cornHigh + 1;  // höjd mm  // offs1 = 0.1;  heightHole = 15; //mm  height = 11; //mm    points1 = circSect(  10, 11.25,  10, [0, 90], "bottom", 1, fn); // Hörn nere till vänster  points2 = circSect(  10, 39.25,  10, [0, 90], "left",   1, fn); // Hörn uppe till vänster  points3 = 3points_arc([p1x,p1y], [p2x,p2y], [p3x,p3y], fn);  points4 = circSect( 101, 39.25,  10, [0, 90], "top",    1, fn); // Hörn uppe till höger   points5 = circSect( 101, 11.25,  10, [0, 90], "right",  1, fn); // Hörn nere till höger   points6 = 3points_arc([p4x,p4y], [p5x,p5y], [p6x,p6y], fn);   // The base plate for the LED lamp     difference()  { color("gray", 0.5)     linear_extrude(height=height)      polygon(concat(points1, points2, points3, points4, points5, points6));    // union()    { // Monteringshål 1 & 2      translate([length-10 , wideMid / 2, -.2])        cylinder(d=diamHole, h=heightHole, center=false);      translate([10 , wideMid / 2, -.2])        cylinder(d=diamHole, h=heightHole, center=false);    }  }}//========  Slut LEDbottom  ======================================================== //==================================================================================//======  circleSect  ==============================================================// Create rounded corners 2D// https://openhome.cc/eGossip/OpenSCAD/SectorArc.html// ange .:  x, y, radien,//          [från, till] vinkel,//          var vinkeln startar, (left, bottom, right, top)//          vilken rotation (-1=medsol, 1=motsols)function circSect(x=0, y=0, radius=10, angles=[0,270], startRef="bottom", rotate=1, fn=24)  =    let(        startAngel  = (startRef == "left")   ?   0                    : (startRef == "bottom") ?  90                    : (startRef == "right")  ? 180                    : (startRef == "top")    ? 270                    : startRef,  // valfri vinkel                  // : assert(false,"invalid moutSide value");  // Error message if no case worked                  //: undef,        r = radius,        //r = radius / cos(180 / fn),        step = 360 / fn,        // points = [[x, y],        points = [            for(a = [angles[0]-startAngel : step : angles[1]-startAngel])                [-rotate * r * cos(a)+x, r * sin(a)+y]]    ) points;//========  Slut circleSect  ======================================================= //==================================================================================//======  3points_arc  =============================================================// Create an arc with three points 2Dfunction 3points_arc(p0, p1, p2, fn=10) =  // an alternative expression for D  // D  = 2 * ( (p1-p0).x * (p2-p0).y - (p1-p0).y * (p2-p0).x )  let( D  = 2 * cross(p1-p0, (p2-p0)) )  assert( abs(D)>1e-9, "The 3 points should not be collinear." )  let(      Ux     = ( (p2-p0).y*(p1-p0)*(p1-p0) - (p1-p0).y*(p2-p0)*(p2-p0) )/D,      Uy     = ( (p1-p0).x*(p2-p0)*(p2-p0) - (p2-p0).x*(p1-p0)*(p1-p0) )/D,      radius = norm([Ux,Uy]),      center = [Ux,Uy] + p0,      ang0   = atan2( (p0-center).y, (p0-center).x ),      ang2   = atan2( (p2-center).y, (p2-center).x ),      // the points are in a cw winding iff D<0      // the angular difference between vectors p2-center and p0-center      // measured from p0-center; dang is positive iff D is negative      dang   = D<0  ? ang2<ang0 ? ang2-ang0 : ang2-ang0-360                    : ang2>ang0 ? ang2-ang0 : ang2-ang0+360  )  [ for(i=[0:fn-1])      let( ang = ang0 + i*dang/(fn-1) )      center + radius*[cos(ang),sin(ang)] ];//========  Slut 3points_arc  ====================================================== //==================================================================================//======  Wall som ett "L"  ========================================================// Normal vägghöjdfunction wall() =   let(        b =  4,     // botten - tjocklek        f =  8,     // Foten        h = 15,     // Höjd        t =  3.5,   // Top        x = (b+(t/2) - (h - ( (-h / (f-t)) *t) )) / (-h / (f-t))    )    let(        points = [[0,0], [f,0], [t,h], [0,h]] ,        top = move([t/2, h, 0], circle(d=t, $fn=20)),        sqr = square([10, b]),        diff =            difference([                  move([x, b], square([t/2, t/2])),                  move([x+(t/2), b+(t/2), 0], circle(d = t, $fn=20) ) ])        )    union([points, top, sqr, diff]);//========  Slut Wall  ============================================================= //==================================================================================//======  Wall1 som ett "L"  =======================================================// En högre väggfunction wall1() =  let(    b =  4,     // botten - tjocklek    f =  7,     // Foten    h = 25,     // Höjd    t =  3,   // Top    x = (b+(t/2) - (h - ((-h / (f-t)) *t))) / (-h / (f-t))  )  let(    points = [[0,0], [f,0], [t,h], [0,h]] ,    top = move([t/2, h, 0], circle(d=t, $fn=20)),    sqr = square([10, b]),    diff =      difference([        move([x, b], square([t/2, t/2])),        move([x+(t/2), b+(t/2), 0], circle(d = t, $fn=20) ) ])    )    union([points, top, sqr, diff]);//========  Slut Wall1  ============================================================ //==================================================================================//======  Plåt på släp  ============================================================module mountingPlate(posX=0, posY=0, posZ=0, mountSide="left", colorName="#C0C0C0", $fn=50){ // Hörnpositionerna  posX1 = 120;  posY1 = 0;  posX2 = posX1;  posY2 = -200;  posX3 = 120 - 75;  posY3 = -200;  posX4 = 0;  posY4 = 0;  thick=2;  // tjocklek    side = mountSide == "left" ? 0       : mountSide == "right" ? 1       : assert(false,"invalid moutSide value");  // message if no case worked    xpos = mountSide == "left" ? 20       : mountSide == "right" ? -20       : assert(false,"invalid moutSide value");  // message if no case worked/*    ypos = mountSide == "left" ? 85       : mountSide == "right" ? 85       : assert(false,"invalid moutSide value");  // message if no case worked    zpos = mountSide == "left" ? -thick       : mountSide == "right" ? -thick       : assert(false,"invalid moutSide value");  // message if no case worked*/    color(colorName)  {  translate([posX, posY, posZ])     translate([xpos, 85, -thick])    { mirror([side, 0, 0])      { linear_extrude(thick)        hull()        { translate([posX1, posY1, 0])            square(0.1, center = true);          translate([posX2, posY2, 0])            square(0.1, center = true);          translate([posX3, posY3, 0])            square(0.1, center = true);          translate([posX4, posY4, 0])            square(0.1, center = true);        }      }    }  }}= = END product 1= = = = = = = = = = = = = = = = = = = = = = = = = = = = = = - . _ . - . _ . - . _ . - . _ . - . _ . - . _ . - . _ . - . _ . - . _ . - . _ . - . _ . - . _ . - . _ . - = = product 2 = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = - . _ . - . _ . - . _ . - . _ . - . _ . - . _ . - . _ . - . _ . - . _ . - . _ . - . _ . - . _ . - . _ . -   $fn=100;//$fn=15; //switch();//cableHolder4(); //Switchboxen // cableHolder3(0, 0, 0, 33.5, 23.5, 1.5, 2);// showCables(); module cableHolder4(fn=24);{ // idé från  // - https://www.thingiverse.com/thing:6400/files  // - https://ihrchive.wordpress.com/2011/02/14/openscad-tip-round-1-of-3-basic-rounding/    // mått på Switch  heightHold = 10.5;  widthHold = 33.5;  depthHold = 23.5;  spaceHold = 10.0; // utrymmet bakom switch  holdRadie = 2;  // radie i hörnen  thick = 2;  offset1=0.5;  // öka toleransen    // innermått  holeW = widthHold + offset1;  holeH = heightHold + offset1;  holeD = depthHold + spaceHold+offset1;    // yttermått  pad = 0.1;                   // Padding to maintain manifold  box_l = holeW + thick*2;   // Bredden på switchen  box_w = holeD + thick;             // Djupet på switchen  box_h = holeH + thick; // Height  round_r = holdRadie;         // Radius of round  smooth = 45;                 // Number of facets of rounding cylinder   difference()  { union() // Detta utförs i två steg.    { difference()  // utför fasningar och kabelmarkeringar      { mainBox(box_l, box_w, box_h, spaceHold+thick, round_r, thick, smooth, pad);         // fasning vänster (underkant)        translate([box_l/2-0.85, spaceHold-4.3, thick-offset1])  // sidled, fram/bak , upp/ned          rotate([0,180,45])            cylinder(h=thick, d1=holeW*1.414-thick-thick, d2=holeW*1.414, $fn=4);            // fasning höger (underkant)        translate([box_l/2-3.65, spaceHold-4.3, thick-offset1]) // sidled, fram/bak , upp/ned          rotate([0,180,45])            cylinder(h=thick, d1=holeW*1.414-thick-thick, d2=holeW*1.414, $fn=4);              // kabelgenomföringar        rotate([90, 180, 90]) // Markering ena sidan (vänster under)          ovalCableHole(spaceHold/2-offset1, -1.75, -1.2);            rotate([90, 180, 180]) // Markering bakkant (vänster under)          ovalCableHole(spaceHold/2-1.55, -1.75, -spaceHold-0.85);            rotate([90, 180, 180]) // Markering bakkant (höger under)          ovalCableHole(widthHold-spaceHold/2-offset1, -1.75, -spaceHold-0.85);              rotate([90, -180, 90])  // Markering ena sidan (höger under)          ovalCableHole(3.75, -1.75, widthHold-0.1);      }    } // Slut union - kropp        translate([-offset1/2, -spaceHold+pad, -pad]) // hålet där switchen ska placeras      cube([holeW, holeD+pad, holeH+pad], center=false);       translate([4, 12, 0])        cylinder(h=15,d=3.2);      translate([4, 12, 17.7])        sphere(r=6);          translate([29.6, 12, 0])        cylinder(h=15,d=3.2);      translate([29.6, 12, 17.7])        sphere(r=6);            /*  // Hål genom lock bak - om så önskas      translate([box_l/2-thick, -6, offset1/2])        cylinder(h=box_h+thick*4+offset1, d=3.2, $fn=100);  // hål genom lock bak            translate([box_l/2-thick, -6, 17.7])        sphere(r=6);    // kona hålet bak      */  } // Slut difference() - box     difference()    { union()      { translate([29.6, 12, heightHold-offset1*2])          cylinder(h=2,d=5.2);        // Stödhylsa för Switchskruv1        translate([4, 12, heightHold-offset1*2])          cylinder(h=2,d=5.2);        // Stödhylsa för Switchskruv2         translate([holeW/2, -spaceHold+thick+1, holeH/2])          rotate([180,0,0])             backHole();      } // union - slut             translate([4, 12, 0])     //  Hålen i stödhylsorna        cylinder(h=15,d=3.2);            translate([29.6, 12, 0])  //  Hålen i stödhylsorna        cylinder(h=15,d=3.2);       translate([box_l/2-thick, -6, -offset1])  // hål i stödhylsa bak        cylinder(h=box_h+offset1, d=3.2, $fn=100);            // Sänk stödhylsan        translate([ widthHold/2-7, -spaceHold-offset1, -thick+offset1])  // hål i stödhylsa bak          cube([15, 8, 3]);                  // kabelmarkering      // translate([0, 0, 0])  // hål i stödhylsa bak             } /*      translate([4, 12, 0])        #cylinder(h=15,d=3.2);      //translate([4, 13.5, 17.3])        //#sphere(r=6);          translate([29.6, 12, 0])        #cylinder(h=15,d=3.2);      //translate([29.6, 13.5, 17.3])        //#sphere(r=6);*/   } module backHole(){ wallH = 10.5;    wide1   = 12; // endast runt cylindern  wide2   = 35; // hela väggen  deep1    =  4;  height1  = 10.5;  cornRad1  =  2;  diam1 = 8;  opt1 = 0.1;    //rundadFot();      // Rundad stäcka mellan t.ex. vägg och tak -bakkant  translate([wide2/2, diam1/2-cornRad1/2, -height1/2])  { rotate([90, 0, -90])    { linear_extrude(wide2)      { difference()        { square([cornRad1, cornRad1]);                    translate([cornRad1, cornRad1])            circle(r=cornRad1);        }      }    }  }    // rundad stäcka1 (vänster) mellan t.ex. vägg och tak  translate([-wide2/2+0.15, deep1/2+cornRad1/2, -height1/2])  rotate([90, 0, 0])  { linear_extrude(spaceHold)    { difference()      { square([cornRad1, cornRad1]);            translate([cornRad1, cornRad1])        circle(r=cornRad1);      }    }  }   // rundad stäcka2 mellan t.ex. vägg och tak  translate([wide2/2-0.65, deep1/2+cornRad1/2, -height1/2])  rotate([0, -90, 90])  { linear_extrude(spaceHold)    { difference()      { square([cornRad1, cornRad1]);             translate([cornRad1, cornRad1])          circle(r=cornRad1);      }    }  }    // Skapa stödfot - bak  difference()  { union()    { //själva cylindern      translate([0, 1, 0])      { cylinder(h=height1, d=diam1, center=true);        translate([0, diam1/2, 0])          cube([diam1,diam1-1,height1], center=true);      }            // Rundad fot under cylinder ovan      translate([0, 1, -height1/2])      { rotate_extrude()        { translate([diam1/2, 0, 0])          { difference()            { square([cornRad1, cornRad1]);                            translate([cornRad1, cornRad1])                circle(r=cornRad1);            }          }        }      }            // Rundad rakstäcka1 - cylinderfot - mellan t.ex. vägg och tak      translate([diam1/2, diam1, -height1/2])      { rotate([90, 0, 0])        { linear_extrude(diam1)          { difference()            { square([cornRad1, cornRad1]);                            translate([cornRad1, cornRad1])                circle(r=cornRad1);            }          }        }      }            // Rundad rakstäcka2 - cylinderfot - mellan t.ex. vägg och tak      translate([-diam1/2, diam1, -height1/2])      { rotate([0, -90, 90])        { linear_extrude(diam1)          { difference()            { square([cornRad1, cornRad1]);                        translate([cornRad1, cornRad1])                circle(r=cornRad1);            }          }        }      }       //väggen bakom cylindern som ska rundas      translate([0, diam1/2-cornRad1, 0])        cube([wide1, cornRad1, height1], center=true);     }      // Avrunda hörn1 bak    translate([-wide1/2, cornRad1/2, cornRad1])    { hull()      { cylinder(h=height1+opt1, r=cornRad1, center=true);        {  translate([0, 0, -height1/2])            sphere(r=cornRad1);        }      }      }      // Avrunda hörn2 bak    translate([wide1/2, cornRad1/2, cornRad1])    { hull()      { cylinder(h=height1+opt1, r=cornRad1, center=true);        {  translate([0, 0, -height1/2])            sphere(r=cornRad1);        }      }      }         // Plocka bort rundad fot bak samt det som sticker ut    translate([-wide1/2, diam1/2-cornRad1/2, -height1/2-opt1])      cube([wide1, diam1/2+cornRad1, height1+opt1*2], center=false);   }} module ovalCableHole(posX, posY, posZ){ // Hål 5.5 x 3.5 mm  pan = 0.1;  cableHi = 1.5;    translate([posX, posY, posZ])  { color("white")    { translate([0, 0, -pan])      { cylinder(h=cableHi, d=3.5);        //#translate([0, 0, 0]) cylinder(h=10, d=1);        //translate([0, 0, -1]) cylinder(h=1, d1=0, d2=1);        //translate([0, 0, 0]) sphere(d=1); // Inre kulan        //translate([0, 0, 1.5]) sphere(d=1); // Inre kulan                translate([0, 0, -1]) sphere(d=0.8); // yttre kulan        translate([0, 0, 2.5]) sphere(d=0.8); // yttre kulan              }      translate([2, 0, -pan])      { cylinder(h=cableHi, d=3.5);        // #translate([0, 0, -cableHi*2]) cylinder(h=10, d=0.5);        //translate([0, 0, 0]) sphere(d=1); // Inre kulan        //translate([0, 0, 1.5]) sphere(d=1); // Inre kulan         translate([0, 0, -1]) sphere(d=0.8); // yttre kulan        translate([0, 0, 2.5]) sphere(d=0.8); // yttre kulan       }      translate([-3.5/2, 0, -pan])        cube([5.5, 3.5/2, cableHi]);      translate([-0.25, -1.74, -pan])        cube([2.5, 1.75, cableHi]);    }  }} module rundadFot(){   // specifika värden för skruvdistansen bak  wallH = 10.5;   wide1   = 12; // endast runt cylindern  wide2   = 34; // hela väggen  deep1    =  4;  height1  = 10;  cornRad1  =  2;  diam1 = 8;  opt1 = 0.1;   color("magenta")  { translate([0, 0, wallH])    { difference()      { union()        { // Bakgavel          translate([wide2/2, opt1, height1/2])          { rotate([90, 180, 0])              cube([wide2, height1, opt1]);          }                // Golv          translate([wide2/2, -height1+opt1, -height1/2])            rotate([0, 180, 0])              cube([wide2, height1, opt1]);                    //väggen bakom cylindern som kan rundas          translate([0, -cornRad1/2, 0])            cube([wide1, cornRad1, height1], center=true);                    //själva cylindern          translate([0, -cornRad1/2, 0])            cylinder(h=height1, d=diam1, center=true);            // Rundad fot under cylinder ovan          translate([0, -cornRad1/2, -height1/2])          { rotate_extrude()            { translate([diam1/2, 0, 0])              { difference()                { square([cornRad1, cornRad1]);                            translate([cornRad1, cornRad1])                    circle(r=cornRad1);                }              }            }          }                    // Rundad stäcka mellan t.ex. vägg och tak -bakkant          translate([wide2/2, 0, -height1/2])          { rotate([90, 0, -90])            { linear_extrude(wide2)              { difference()                { square([cornRad1, cornRad1]);                          translate([cornRad1, cornRad1])                    circle(r=cornRad1);                }              }            }          }                    // rundad stäcka mellan t.ex. vägg och tak -sida1          translate([-wide2/2, 0, -height1/2])          { rotate([90, 0, 0])            { linear_extrude(10)              { difference()                { square([cornRad1, cornRad1]);                            translate([cornRad1, cornRad1])                  circle(r=cornRad1);                }              }            }          }                    // rundad stäcka mellan t.ex. vägg och tak -sida2          translate([wide2/2, -10, -height1/2])          { rotate([90, 0, 180])            { linear_extrude(10)              { difference()                { square([cornRad1, cornRad1]);                              translate([cornRad1, cornRad1])                  circle(r=cornRad1);                }              }            }          }        } // Avsluta union = = = = = = = = = = = = = = = = = = = =                // Avrunda hörn1 bak        translate([-wide1/2+opt1*1.3, -deep1/2, cornRad1])        { cylinder(h=height1+opt1, r=cornRad1, center=true);            translate([0, 0, -height1/2])              sphere(r=cornRad1);        }          // Avrunda hörn2 bak        translate([wide1/2-opt1*1.3, -deep1/2, cornRad1])        { cylinder(h=height1+opt1, r=cornRad1, center=true);            translate([0, 0, -height1/2])              sphere(r=cornRad1);        }            // Plocka bort rundad fot bak samt det som sticker ut        translate([-wide1/2, 0, -height1/2-opt1])          cube([wide1, diam1/2+cornRad1, height1+opt1*2], center=false);      }    }  }} module mainBox(box_l, box_w, box_h, spaceHold, round_r, thick, smooth, pad){ translate([box_l/2-thick-offset1/2, box_w/2-spaceHold, box_h/2])  {    // To fix the corners cut the main cube with smaller cubes with spheres removed    difference()    { cube([box_l, box_w, box_h], center = true);          // Kant1 - liggande      translate([0, -box_w/2+round_r, box_h/2-round_r])      { difference()        { translate([0,-round_r-pad,round_r+pad])            cube([box_l+2*pad, round_r*2+pad, round_r*2+pad], center = true);          rotate(a=[0,90,0])            cylinder(box_l+4*pad,round_r,round_r,center=true,$fn=smooth);        }      }      // Kant2 - liggande      translate([0, box_w/2-round_r, box_h/2-round_r])      { difference()        { translate([0,round_r+pad,round_r+pad])            cube([box_l+2*pad, round_r*2+pad, round_r*2+pad], center = true);          rotate(a=[0,90,0])            cylinder(box_l+4*pad,round_r,round_r,center=true,$fn=smooth);        }      }      /*      // Kant3 - liggande      translate([0, -box_w/2+round_r, -box_h/2+round_r])      { difference()        { translate([0,-round_r-pad,-round_r-pad])            cube([box_l+2*pad, round_r*2+pad, round_r*2+pad], center = true);          rotate(a=[0,90,0])            cylinder(box_l+4*pad,round_r,round_r,center=true,$fn=smooth);        }      }          // Kant4 - liggande      translate([0, box_w/2-round_r, -box_h/2+round_r])      { difference()        { translate([0,round_r+pad,-round_r-pad])            cube([box_l+2*pad, round_r*2+pad, round_r*2+pad], center = true);          rotate(a=[0,90,0])            cylinder(box_l+4*pad,round_r,round_r,center=true,$fn=smooth);        }      }    */    // ----      // Kant1 - stående      translate([-box_l/2+round_r, box_w/2-round_r, 0])      { difference()        { translate([-round_r-pad,round_r+pad,0])            cube([round_r*2+pad, round_r*2+pad, box_h+2*pad], center = true);          cylinder(box_h+4*pad,round_r,round_r,center=true,$fn=smooth);        }      }      // Kant2 - stående      translate([box_l/2-round_r, box_w/2-round_r, 0])      { difference()        { translate([round_r+pad,round_r+pad,0])            cube([round_r*2+pad, round_r*2+pad, box_h+2*pad], center = true);          cylinder(box_h+4*pad,round_r,round_r,center=true,$fn=smooth);        }      }      // Kant3 - stående      translate([-box_l/2+round_r, -box_w/2+round_r, 0])      { difference()        { translate([-round_r-pad,-round_r-pad,0])            cube([round_r*2+pad, round_r*2+pad, box_h+2*pad], center = true);          cylinder(box_h+4*pad,round_r,round_r,center=true,$fn=smooth);        }      }      // Kant4 - stående      translate([box_l/2-round_r, -box_w/2+round_r, 0])      { difference()        { translate([round_r+pad,-round_r-pad,0])            cube([round_r*2+pad, round_r*2+pad, box_h+2*pad], center = true);          cylinder(box_h+4*pad,round_r,round_r,center=true,$fn=smooth);        }      }        // ----      // Kant1 liggande (andra hållet)      translate([-box_l/2+round_r, 0, box_h/2-round_r])      { difference()        { translate([-round_r-pad, 0, round_r+pad])            cube([round_r*2+pad, box_w+2*pad, round_r*2+pad], center = true);          rotate(a=[0,90,90])            cylinder(box_w+4*pad,round_r,round_r,center=true,$fn=smooth);        }      }      // Kant2 liggande (andra hållet)      translate([box_l/2-round_r, 0, box_h/2-round_r])      { difference()        {  translate([round_r+pad, 0, round_r+pad])            cube([round_r*2+pad, box_w+2*pad, round_r*2+pad], center = true);          rotate(a=[0,90,90])            cylinder(box_w+4*pad,round_r,round_r,center=true,$fn=smooth);        }      }      /*      // Kant3 liggande (andra hållet)      translate([-box_l/2+round_r, 0, -box_h/2+round_r])      { difference()        { translate([-round_r-pad, 0, -round_r-pad])            cube([round_r*2+pad, box_w+2*pad, round_r*2+pad], center = true);          rotate(a=[0,90,90])            cylinder(box_w+4*pad,round_r,round_r,center=true,$fn=smooth);        }      }        // Kant4 liggande (andra hållet)      translate([box_l/2-round_r, 0, -box_h/2+round_r])      { difference()        { translate([round_r+pad, 0, -round_r-pad])            cube([round_r*2+pad, box_w+2*pad, round_r*2+pad], center = true);          rotate(a=[0,90,90])            cylinder(box_w+4*pad,round_r,round_r,center=true,$fn=smooth);        }      }  */     // ----      // Hörn1 (övre)      translate([box_l/2-round_r, box_w/2-round_r, box_h/2-round_r])      { difference()        { translate([round_r+pad, round_r+pad, round_r+pad])            cube([round_r*2+pad, round_r*2+pad, round_r*2+pad], center = true);          sphere(round_r,$fn=smooth);        }      }      // Hörn2 (övre)      translate([-box_l/2+round_r, box_w/2-round_r, box_h/2-round_r])      { difference()        { translate([-round_r-pad, round_r+pad, round_r+pad])            cube([round_r*2+pad, round_r*2+pad, round_r*2+pad], center = true);          sphere(round_r,$fn=smooth);        }      }      // Hörn3 (övre)      translate([box_l/2-round_r, -box_w/2+round_r, box_h/2-round_r])      { difference()        { translate([round_r+pad, -round_r-pad, round_r+pad])            cube([round_r*2+pad, round_r*2+pad, round_r*2+pad], center = true);          sphere(round_r,$fn=smooth);        }      }      // Hörn4 (övre)      translate([-box_l/2+round_r, -box_w/2+round_r, box_h/2-round_r])      { difference()        { translate([-round_r-pad, -round_r-pad, round_r+pad])            cube([round_r*2+pad, round_r*2+pad, round_r*2+pad], center = true);          sphere(round_r,$fn=smooth);        }      }      /*      // Hörn1 (undre)      translate([box_l/2-round_r, box_w/2-round_r, -box_h/2+round_r])      { difference()        { translate([round_r+pad, round_r+pad, -round_r-pad])            cube([round_r*2+pad, round_r*2+pad, round_r*2+pad], center = true);          sphere(round_r,$fn=smooth);        }      }      // Hörn2 (undre)      translate([-box_l/2+round_r, box_w/2-round_r, -box_h/2+round_r])      { difference()        { translate([-round_r-pad, round_r+pad, -round_r-pad])            cube([round_r*2+pad, round_r*2+pad, round_r*2+pad], center = true);          sphere(round_r,$fn=smooth);        }      }      // Hörn3 (undre)      translate([box_l/2-round_r, -box_w/2+round_r, -box_h/2+round_r])      { difference()        { translate([round_r+pad, -round_r-pad, -round_r-pad])            cube([round_r*2+pad, round_r*2+pad, round_r*2+pad], center = true);          sphere(round_r,$fn=smooth);        }      }      // Hörn4 (undre)      translate([-box_l/2+round_r, -box_w/2+round_r, -box_h/2+round_r])      { difference()        { translate([-round_r-pad, -round_r-pad, -round_r-pad])            cube([round_r*2+pad, round_r*2+pad, round_r*2+pad], center = true);          sphere(round_r,$fn=smooth);        }      }      */    }  }}// module cableHolder3(posX, posY, posZ, length, width, height, radius){ // Skapa toppen över switchen  // mått på Switchen  fn = 96;          // upplösning (endast bågen?)  heightHold = 10.5;  widthHold = 33.5;  depthHold = 23.5;   holdRadie = 1.5;  // radie i hörnen  thick = 1.5;      // tjocklek      translate([0,-thick,0])  {     difference(0, 0, 0)    { hull()      { difference()        { translate([thick, 0, heightHold]) // vänster kant          { rotate([-90, 0, 0])            { cylinder(h=depthHold, d=thick*2);              translate([0, 0, depthHold])                sphere(d=thick*2);          // längst fram            }          }          translate([0, -0.1, heightHold]) // plocka bort underdelen            rotate([-90, 0, 0])              cube([thick*2, thick+.1, depthHold+thick+.1]);        }                difference()        { translate([widthHold-thick, 0, heightHold]) // höger kant          { rotate([-90, 0, 0])            { cylinder(h=depthHold, d=thick*2);              translate([0, 0, depthHold])                sphere(d=thick*2);         // längst fram            }          }          translate([widthHold-thick*2, -0.1, heightHold]) // plocka bort underdelen          { rotate([-90, 0, 0])              cube([thick*2, thick+.1, depthHold+thick+.1]);          }        }      }            // öppna hålen för monteringsskruvarna uppe på plattan      translate([4, 13.5, 0])        cylinder(h=15,d=3.2);      translate([4, 13.5, 17.3])        sphere(r=6);          translate([29.6, 13.5, 0])        cylinder(h=15,d=3.2);        translate([29.6, 13.5, 17.3])        sphere(r=6);    }      // halvbåge 1 bak    translate([thick, 0, heightHold/2+thick/2])      rotate([0, 90, 180])        rotate_extrude(angle = 180, convexity=20, $fn=64)    translate([heightHold/2-thick/2, 0, 0])      circle(d=thick*2);    translate([thick, 0, heightHold])      sphere(d=thick*2);  // övre kulan      translate([thick, 0, thick])      sphere(d=thick*2);  // undre kulan           // halvbåge 2 bak    translate([widthHold-thick, 0, heightHold/2+thick/2])      rotate([0, 90, 180])        rotate_extrude(angle = 180, convexity=20, $fn=64)    translate([heightHold/2-thick/2, 0, 0])      circle(d=thick*2);    translate([widthHold-thick, 0, heightHold])      sphere(d=thick*2);  // övre kulan    translate([widthHold-thick, 0, thick])      sphere(d=thick*2);  // undre kulan          // en cylinder tvärsöver längst upp    translate([thick, 0, heightHold])    { rotate([0,90,0])        cylinder(h=widthHold-thick*2, r=thick);    }  }       // Halvbågen (kabelhållaren) på baksidan switchen  translate([widthHold-thick, -thick, heightHold/2+thick/2])  { rotate([0,90,180])      linear_extrude(widthHold-thick*2)        arc(heightHold/2-thick/2, [0, 180], thick, fn); //radius, angles, width, fn)  }  // en cylinder tvärsöver längst ned  translate([thick, -thick, thick])  { rotate([0,90,0])      cylinder(h=widthHold-thick*2, r=thick);  }   } module switch(posX=0, posY=0, posZ=0){ buttRadie = 1.5;  height = 10.5;  width = 33.5;  depth = 23.5;  h1x = buttRadie;  h1y = buttRadie;  h2x = width-buttRadie;  h2y = buttRadie;  h3x = width-buttRadie;  h3y = depth-buttRadie;  h4x = buttRadie;  h4y = depth-buttRadie;          translate([posX, posY, posZ])  { difference()    { color("#F9F9F3")       // tryck-knappen      union()      { translate([width/2, depth+6-0.1, height/2])        { rotate([90, 0, 0])          { translate([0,0,6])                circle(d=6.8);  // skuggan runt knapp            cylinder(h=6, d=6);            sphere(d=6);          }        }                hull()  // Switchkropp        { translate([h1x, h1y])            cylinder(h=height, r=1.5);          translate([h2x, h2y])            cylinder(h=height, r=1.5);          translate([h3x, h3y])            cylinder(h=height, r=1.5);          translate([h4x, h4y])            cylinder(h=height, r=1.5);        }      }            // Skruvhålen för switchen      hole( 4, 12, 0, "#FFD700", height);      hole(29.6, 12, 0, "#FFD700", height);      // hole( 4, 12, 0, "#FFD700", 50);      // hole(29.6, 12, 0, "#FFD700", 50);      // hål för kablar bak      color("gray")      { translate([9.5, 16, height/2])        { rotate([90, 0, 0])            cylinder(h=16.5, d=4);        }        translate([24.5, 16, height/2])        {  rotate([90, 0, 0])            cylinder(h=16.5, d=4);        }      }            // hål för kabelskruvar      color("white")      { translate([29.5, 17.1, height/2])        { rotate([0, 90, 0])            cylinder(h=4.1, d=4.5);              }        translate([-0.1, 17.1, height/2])        { rotate([0, 90, 0])            cylinder(h=4.1, d=4.5);        }      }    }         // Kabelskruvar    cableScrew(3, 17, height/2, 90);    cableScrew(31, 17, height/2, -90);       }} // Skruven som håller fast kabeln i switchenmodule cableScrew(posX=0, posY=0, posZ=0, angle=0){ color("#FFD700")  // mässing  translate([posX, posY, posZ])  { rotate([0, 0, angle])    { difference()      { // skruvskalle        translate([0, 0, 0])          rotate([90, 0, 0])            cylinder(h=2, d1=4, d2=3.5);              // stjärnan i skruven        translate([0, 1.85, -.25])          rotate([0, 0, 0])            cylinder(h=0.5, d=5);        translate([-0.25, -.6, 2.25])            rotate([0, 90, 0])            cube([4.5, 2, 0.5]);      }    }  }} // borrhålmodule hole(posX=0, posY=0, posZ=0, colorName="yellow", height){ diamHole1 = 3;  highHole1 = height;  diamHole2 = 6;  highHole2 = 2.5;  offs=0.1;    color(colorName)  {    translate([posX, posY, posZ])    { translate([0, 0, 0])        cylinder(h=highHole1, d=diamHole1);      translate([0, 0, -offs])        cylinder(h=highHole2, d=diamHole2);      translate([0, 0, height-highHole2+offs])        cylinder(h=highHole2, d=diamHole2);    }  }} module showCables(){ translate([-25,8,24])    rotate([80,177,90])      cable(10,10,0,"brun");  translate([-43,8,15])    rotate([90,180,90])      cable(10,10,0,"blå");} module cable(posX=0, posY=0, posZ=0, colorName="blå", radius=1.26, width=0.62, thick=50, fn=24){ // default 1.5mm2  // radius = inner radie  // width = bredd/tjocklek på cirkeln (inte höjd)  // thick = höjd på cirken/ röret  // pin=   colCupper = "#D7715A";  colGreen  = "#07DA63";  colYellow = "#FFCC00";      if (colorName=="gröngul")  { translate([posX, posY, posZ])    { color(colGreen)        linear_extrude(thick)          arc(radius, [0, 60], width, fn);      color(colYellow)          linear_extrude(thick)          arc(radius, [60, 180], width, fn);      color(colGreen)        linear_extrude(thick)          arc(radius, [180, 240], width, fn);      color(colYellow)          linear_extrude(thick)          arc(radius, [240, 360], width, fn);        color(colCupper)        linear_extrude(10, center=true, convexity=10, $fn=100)          circle(d=1.24);    }  }  else  // vanliga kablar 1.5mm2  {    cableColor = colorName == "blå" ? "#1870D5"               : colorName == "brun" ? "#9C6137"               : colorName == "svart" ? "#000000"               : assert(false,"invalid color value");  // message if no case worked                   // : nodef      translate([posX, posY, posZ])    {             //el kabel - ena änden rak - andra böjd      color(colCupper)    //kopparstump tråd rakkabel        linear_extrude(10, center=true, convexity=10, $fn=100)          circle(d=1.24);        color(cableColor)        { cylinder(h=thick, r=radius);                translate([-radius*2, 0, thick])  // kabelböj        rotate([90, 0, 0])        rotate_extrude(angle=90, convexity=20)          translate([2.5, 0, 0])            circle(r=1.26);              translate([-radius*2, 0, thick+radius*2])          rotate([0, -90, 0])          cylinder(h=5, r=radius);      }              translate([-10, 0, thick+radius*2])      { rotate([0, -90, 0])        { color(colCupper)          { linear_extrude(5, center=true, convexity=10, $fn=100)              circle(d=1.24);          }        }      }    }  }} // ======================================================================module arc(radius, angles, width = 1, fn = 24) {    difference() {        sector(radius + width, angles, fn); // ytterradie        sector(radius, angles, fn);         // innerradie (plockar bort invändigt    }} module sector(radius, angles, fn = 24) {    r = radius / cos(180 / fn);    step = -360 / fn;     points = concat([[0, 0]],        [for(a = [angles[0] : step : angles[1] - 360])             [r * cos(a), r * sin(a)]        ],        [[r * cos(angles[1]), r * sin(angles[1])]]    );     difference() {        circle(radius, $fn = fn);        polygon(points);    }}= = END product 2 = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = - . _ . - . _ . - . _ . - . _ . - . _ . - . _ . - . _ . - . _ . - . _ . - . _ . - . _ . - . _ . - . _ . - Den fredag 6 maj 2022 14:06:55 CEST, Michael Möller <private2michael@gmail.com> skrev: OpenSCAD code - is a description of your model in terms of a few cylinder/cubes added and cut outdifference() {  cylinder(d=5,h=10);  translate([0,10,0]) cube([4,6,2]) ;} STL file is a list of triangles which make the same outer shell as your model. OpenSCAD makes this complicated transform from shapes to triangles.solid OpenSCAD_Model   facet normal 0.92388 0.382682 0     outer loop       vertex 2.5 0 3       vertex 1.76777 1.76777 0       vertex 1.76777 1.76777 3     endloop   endfacet   facet normal 0.92388 0.382682 0     outer loop       vertex 1.76777 1.76777 0       vertex 2.5 0 3       vertex 2.5 0 0     endloop   endfacet   : (and so on for 300 lines) There is a binary/compressed version, but the description is still just triangles. Gcode is what a 3D printer understands - it is the exact list of moves that the head has to do with how much plastic to squeeze to trace the outline of your shape, layer, by layer. It will optionally create moves for filling the inside or support for overhangs. Such a program is called a SLICER and the printer will come with one.G92 E0 ; reset extrusion distance G1 Z2.330 F6600.000 ; lift Z G1 X-0.000 Y1.505 F6600.000 ; move to first perimeter point G1 Z0.330 F6600.000 ; restore layer Z G1 E3.00000 F2400.00000 ; unretract extruder 0 G1 F1500 G1 X-1.064 Y1.064 E3.09259 ; perimeter G1 X-1.505 Y0.000 E3.18517 ; perimeter   : (many similar lines) G1 X1.515 Y1.515 E4.65860 ; perimeter G1 X0.055 Y2.120 E4.78559 ; perimeter G1 X-0.000 Y2.143 F6600.000 ; move inwards before travel G1 X0.384 Y0.843 F6600.000 ; move to first infill point G1 F1500 G1 X0.843 Y0.384 E4.84815 ; infill G1 X1.097 Y-0.229 E4.91215 ; infill  :(and so on for thousands of lines) The 3MF still basically deals in triangles, and attributes (surface, infill material, picture, ticket info ... ) which probably are not used by your slicer/printer.  On Fri, 6 May 2022 at 12:37, Jan Öhman via Discuss <discuss@lists.openscad.org> wrote: ---------- Forwarded message ---------- From: "Jan Öhman" <jan_ohman@yahoo.com> To: OpenSCAD General Discussion <discuss@lists.openscad.org> Cc:  Bcc:  Date: Fri, 6 May 2022 10:38:46 +0000 (UTC) Subject: [OpenSCAD] Export to .STL / .3MF for later 3D-printing. Hi! Thought to create some objects in openSCAD, to print later.I do not have my own 3D printer (yet). One I talked to, wanted to get the drawings in .STL or .3MF. (I don't know the difference). If I had my own printer, have I been able to print directly from openSCAD? (Without some export?) In the openSCAD, no errors or problems occur.butThe drawings I tested to export from openSCAD have given one or another error message.One message .:WARNING: Object may not be a valid 2-manifold and may need repair!  Another message .:WARNING: No top level geometry to render  What to do? ---------- Forwarded message ---------- From: "Jan Öhman via Discuss" <discuss@lists.openscad.org> To: OpenSCAD General Discussion <discuss@lists.openscad.org> Cc: "Jan Öhman" <jan_ohman@yahoo.com> Bcc:  Date: Fri, 6 May 2022 10:38:46 +0000 (UTC) Subject: [OpenSCAD] Export to .STL / .3MF for later 3D-printing. _______________________________________________ OpenSCAD mailing list To unsubscribe send an email to discuss-leave@lists.openscad.org _______________________________________________ OpenSCAD mailing list To unsubscribe send an email to discuss-leave@lists.openscad.org