# -*- coding: utf-8 -*-

import FreeCAD
from FreeCAD import Placement, Rotation, Vector
import matplotlib
from io import StringIO

doc=FreeCAD.newDocument("Gehäuse")

# Konfigurationsparameter

W_Dicke = 2.0           # Wandstärke
B_Dicke = 4.0           # Bodenstärke
Dim_X = 80.0            # Länge
Dim_Y = 50.0            # Breite
Dim_Z = 30.0            # Höhe
Deckel_H = 10.0         # Höhe des Deckels
D_Dicke = 4.0           # Stärke des Deckels
Rad = 5.0               # Radius außen zum Abrunden der Kanten
Noppen_AD = 8.0         # Außendurchmesser der Noppen
Noppen_ID = 2.4         # Innendurchmesser der Noppen
Noppen_H = 5.0          # Höhe der Noppen
D_Schraube = 3.0        # Durchmesser der Schraube für den Deckel
D_SchraubenKopf = 6.0   # Durchmesser des Schraubenkopfes für den Deckel
H_SchraubenKopf = 4.0   # Höhe des Schraubenkopfes für den Deckel
D_Stuetze = 8.0         # Durchmesser der Stütze für die Deckelschraube
T_Stuetze = 15.0        # Tiefe der Bohrung in der Stütze für die Deckelschraube

vec0=Vector(0,0,0)      # Nullvektor
vecx=Vector(1,0,0)      # Drehachse x
vecy=Vector(0,1,0)      # Drehachse y
vecz=Vector(0,0,1)      # Drehachse z

# Farben
Farbe_Gehäuse = matplotlib.colors.to_rgb('cyan')
Farbe_Deckel  = matplotlib.colors.to_rgb('bisque')

# Position der Noppen
Noppen_Pos =     [Vector(15,15,B_Dicke/2),
                  Vector(Dim_X-15,15,B_Dicke/2),
                  Vector(Dim_X/2,Dim_Y/2,B_Dicke/2),
                  Vector(15,Dim_Y-15,B_Dicke/2),
                  Vector(Dim_X-15,Dim_Y-15,B_Dicke/2)]

# Position der Stützen im Gehäuse für die Verschraubung
Stuetzen_Pos =   [Vector((D_Stuetze+W_Dicke)/2,(D_Stuetze+W_Dicke)/2,B_Dicke/2),
                  Vector(Dim_X-(D_Stuetze+W_Dicke)/2,(D_Stuetze+W_Dicke)/2,B_Dicke/2),
                  Vector((D_Stuetze+W_Dicke)/2,Dim_Y-(D_Stuetze+W_Dicke)/2,B_Dicke/2),
                  Vector(Dim_X-(D_Stuetze+W_Dicke)/2,Dim_Y-(D_Stuetze+W_Dicke)/2,B_Dicke/2)]

# Position der Stützen im Deckel für die Verschraubung
Stuetzen_Pos_D = [Vector((D_Stuetze+W_Dicke)/2,(D_Stuetze+W_Dicke)/2,D_Dicke/2),
                  Vector(Dim_X-(D_Stuetze+W_Dicke)/2,(D_Stuetze+W_Dicke)/2,D_Dicke/2),
                  Vector((D_Stuetze+W_Dicke)/2,Dim_Y-(D_Stuetze+W_Dicke)/2,D_Dicke/2),
                  Vector(Dim_X-(D_Stuetze+W_Dicke)/2,Dim_Y-(D_Stuetze+W_Dicke)/2,D_Dicke/2)]

# Position der Bohrungen im Deckel für die Verschraubung
Stuetzen_Pos_B = [Vector((D_Stuetze+W_Dicke)/2,(D_Stuetze+W_Dicke)/2,0),
                  Vector(Dim_X-(D_Stuetze+W_Dicke)/2,(D_Stuetze+W_Dicke)/2,0),
                  Vector((D_Stuetze+W_Dicke)/2,Dim_Y-(D_Stuetze+W_Dicke)/2,0),
                  Vector(Dim_X-(D_Stuetze+W_Dicke)/2,Dim_Y-(D_Stuetze+W_Dicke)/2,0)]

# Basisformen generieren
aussen =   Part.makeBox(Dim_X, Dim_Y, Dim_Z, App.Vector(0, 0, 0), App.Vector(0, 0, 1))      # Außenbox
innen =    Part.makeBox(Dim_X-2*W_Dicke, Dim_Y-2*W_Dicke, Dim_Z, App.Vector(0, 0, 0), App.Vector(0, 0, 1)).translate(Vector(W_Dicke,W_Dicke,B_Dicke))      # Innenbox
daussen =  Part.makeBox(Dim_X, Dim_Y, Deckel_H, App.Vector(0, 0, 0), App.Vector(0, 0, 1))      # Außenbox Deckel
dinnen =   Part.makeBox(Dim_X-2*W_Dicke, Dim_Y-2*W_Dicke, Deckel_H, App.Vector(0, 0, 0), App.Vector(0, 0, 1)).translate(Vector(W_Dicke,W_Dicke,D_Dicke))      # Innenbox Deckel
noppe =    Part.makeCylinder(Noppen_AD/2, Noppen_H+B_Dicke/2, vec0).cut(Part.makeCylinder(Noppen_ID/2, Noppen_H+B_Dicke/2+1, vec0))
stuetze =  Part.makeCylinder(D_Stuetze/2, Dim_Z-B_Dicke/2, vec0).cut(Part.makeCylinder(D_Schraube/2, Dim_Z-T_Stuetze+1, Vector(0,0,Dim_Z-T_Stuetze)))
dstuetze = Part.makeCylinder(D_Stuetze/2, Deckel_H-D_Dicke/2, vec0)
dbohrung = Part.makeCylinder(D_Schraube/2+0.2, Deckel_H+2, vec0).fuse(Part.makeCylinder(D_SchraubenKopf/2, H_SchraubenKopf, vec0)) # Bohrung Deckel

# vertikale Kanten der Außenseite des Gehäuses zum Abrunden auswählen
edges=[]
edgecount = len(aussen.Edges)
for i in range (0,edgecount):
      thisEdge = aussen.Edges[i]
      tan = thisEdge.tangentAt(0.0)
      if tan == Vector(0,0,1):
         edges.append(thisEdge)

# ...und abrunden
if ((len(edges) > 0) & (Rad > 0)):
   aussen = aussen.makeFillet(Rad, edges)

# vertikale Kanten der Innenseite des Gehäuses zum Abrunden auswählen
edges=[]
edgecount = len(innen.Edges)
for i in range (0,edgecount):
      thisEdge = innen.Edges[i]
      tan = thisEdge.tangentAt(0.0)
      if tan == Vector(0,0,1):
         edges.append(thisEdge)

# ...und abrunden
if ((len(edges) > 0) & (Rad > W_Dicke)):
   innen = innen.makeFillet(Rad-W_Dicke, edges)

# vertikale Kanten der Außenseite des Deckels zum Abrunden auswählen
edges=[]
edgecount = len(daussen.Edges)
for i in range (0,edgecount):
      thisEdge = daussen.Edges[i]
      tan = thisEdge.tangentAt(0.0)
      if tan == Vector(0,0,1):
         edges.append(thisEdge)

# ...und abrunden
if ((len(edges) > 0) & (Rad > 0)):
   daussen = daussen.makeFillet(Rad, edges)

# vertikale Kanten der Innenseite des Deckels zum Abrunden auswählen
edges=[]
edgecount = len(dinnen.Edges)
for i in range (0,edgecount):
      thisEdge = dinnen.Edges[i]
      tan = thisEdge.tangentAt(0.0)
      if tan == Vector(0,0,1):
         edges.append(thisEdge)

# ...und abrunden
if ((len(edges) > 0) & (Rad > W_Dicke)):
   dinnen = dinnen.makeFillet(Rad-W_Dicke, edges)

# Gehäuse
Gehäuse = aussen.cut(innen)

# Deckel
Deckel = daussen.cut(dinnen).translate(Vector(0,0,0))

# Noppen
for i in range (0,len(Noppen_Pos)):
   Gehäuse = Gehäuse.fuse(noppe.copy().translate(Noppen_Pos[i]))

# Stützen für Verschraubung
for i in range (0,len(Stuetzen_Pos)):
   Gehäuse = Gehäuse.fuse(stuetze.copy().translate(Stuetzen_Pos[i]))

# Stützen im Deckel für Verschraubung
for i in range (0,len(Stuetzen_Pos_D)):
   Deckel = Deckel.fuse(dstuetze.copy().translate(Stuetzen_Pos_D[i]))

# Bohrungen im Deckel für Verschraubung
for i in range (0,len(Stuetzen_Pos_B)):
   Deckel = Deckel.cut(dbohrung.copy().translate(Stuetzen_Pos_B[i]))

# Deckel drehen und verschieben
Deckel = Deckel.rotate(vec0, vecy, 180).translate(Vector(Dim_X, 0, Deckel_H + Dim_Z))

# Namen und Farben zuweisen
p1=doc.addObject("Part::Feature")
p1.Shape = Gehäuse
p1.ViewObject.ShapeColor=Farbe_Gehäuse
p1.Label="Gehäuse"

p1=doc.addObject("Part::Feature")
p1.Shape = Deckel
p1.ViewObject.ShapeColor=Farbe_Deckel
p1.Label="Deckel"

view = FreeCADGui.ActiveDocument.ActiveView
view.fitAll()


