{
 "cells": [
  {
   "cell_type": "markdown",
   "id": "0",
   "metadata": {},
   "source": [
    "# 4.4.1 OpenCascade Bottle-tutorial\n",
    "\n",
    "Please consult the OCCT - documentation for more explanations:\n",
    "\n",
    "https://dev.opencascade.org/doc/overview/html/occt__tutorial.html\n"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "id": "1",
   "metadata": {},
   "outputs": [],
   "source": [
    "from netgen.occ import *\n",
    "from netgen.webgui import Draw as DrawGeo"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "id": "2",
   "metadata": {},
   "outputs": [],
   "source": [
    "myHeight = 70\n",
    "myWidth = 50\n",
    "myThickness = 30"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "id": "3",
   "metadata": {},
   "outputs": [],
   "source": [
    "pnt1 = Pnt(-myWidth / 2., 0, 0);\n",
    "pnt2 = Pnt(-myWidth / 2., -myThickness / 4., 0);\n",
    "pnt3 = Pnt(0, -myThickness / 2., 0);\n",
    "pnt4 = Pnt(myWidth / 2., -myThickness / 4., 0);\n",
    "pnt5 = Pnt(myWidth / 2., 0, 0);"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "id": "4",
   "metadata": {},
   "outputs": [],
   "source": [
    "seg1 = Segment(pnt1, pnt2)\n",
    "arc = ArcOfCircle(pnt2, pnt3, pnt4)\n",
    "seg2 = Segment(pnt4, pnt5)"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "id": "5",
   "metadata": {},
   "outputs": [],
   "source": [
    "wire = Wire ([seg1, arc, seg2])\n",
    "mirrored_wire = wire.Mirror(Axis((0,0,0), X))\n",
    "w = Wire([wire, mirrored_wire])"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "id": "6",
   "metadata": {},
   "outputs": [],
   "source": [
    "f = Face (w)\n",
    "body = f.Extrude( myHeight*Z )"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "id": "7",
   "metadata": {},
   "outputs": [],
   "source": [
    "body = body.MakeFillet (body.edges, myThickness / 12.)\n",
    "DrawGeo (body);"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "id": "8",
   "metadata": {},
   "outputs": [],
   "source": [
    "from ngsolve import Mesh\n",
    "from ngsolve.webgui import Draw"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "id": "9",
   "metadata": {},
   "outputs": [],
   "source": [
    "geo = OCCGeometry(body)\n",
    "mesh = Mesh(geo.GenerateMesh(maxh=5))"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "id": "10",
   "metadata": {},
   "outputs": [],
   "source": [
    "Draw (mesh);"
   ]
  },
  {
   "cell_type": "markdown",
   "id": "11",
   "metadata": {},
   "source": [
    "## Adding the neck:"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "id": "12",
   "metadata": {},
   "outputs": [],
   "source": [
    "neckax = Axes(body.faces.Max(Z).center, Z)"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "id": "13",
   "metadata": {},
   "outputs": [],
   "source": [
    "myNeckRadius = myThickness / 4.\n",
    "myNeckHeight = myHeight / 10\n",
    "neck = Cylinder(neckax, myNeckRadius, myNeckHeight);"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "id": "14",
   "metadata": {},
   "outputs": [],
   "source": [
    "body = body+neck\n",
    "DrawGeo (body);"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "id": "15",
   "metadata": {},
   "outputs": [],
   "source": [
    "mesh = Mesh(OCCGeometry(body).GenerateMesh(maxh=5))\n",
    "Draw (mesh);"
   ]
  },
  {
   "cell_type": "markdown",
   "id": "16",
   "metadata": {},
   "source": [
    "find face with maximal z-coordinate:"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "id": "17",
   "metadata": {},
   "outputs": [],
   "source": [
    "fmax = body.faces.Max(Z)\n",
    "thickbody = body.MakeThickSolid([fmax], -myThickness / 50, 1.e-3)\n",
    "DrawGeo (thickbody);"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "id": "18",
   "metadata": {},
   "outputs": [],
   "source": [
    "mesh = Mesh(OCCGeometry(thickbody).GenerateMesh(maxh=3))\n",
    "Draw (mesh);"
   ]
  },
  {
   "cell_type": "markdown",
   "id": "19",
   "metadata": {},
   "source": [
    "## Defining the threading"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "id": "20",
   "metadata": {},
   "outputs": [],
   "source": [
    "cyl1 = Cylinder(neckax, myNeckRadius * 0.99, 1).faces[0]\n",
    "cyl2 = Cylinder(neckax, myNeckRadius * 1.05, 1).faces[0]"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "id": "21",
   "metadata": {},
   "outputs": [],
   "source": [
    "import math\n",
    "aPnt = Pnt(2.*math.pi, myNeckHeight / 2.)\n",
    "aDir = Dir( 2.*math.pi, myNeckHeight / 4. )\n",
    "anAx2d = gp_Ax2d(aPnt, aDir)"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "id": "22",
   "metadata": {},
   "outputs": [],
   "source": [
    "aMajor = 2. * math.pi\n",
    "aMinor = myNeckHeight / 10\n",
    "arc1 = Ellipse(anAx2d, aMajor, aMinor).Trim(0, math.pi)\n",
    "arc2 = Ellipse(anAx2d, aMajor, aMinor/4).Trim(0, math.pi)"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "id": "23",
   "metadata": {},
   "outputs": [],
   "source": [
    "seg = Segment(arc1.start, arc1.end)"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "id": "24",
   "metadata": {},
   "outputs": [],
   "source": [
    "wire1 = Wire( [Edge(arc1, cyl1), Edge(seg, cyl1)] )\n",
    "wire2 = Wire( [Edge(arc2, cyl2), Edge(seg, cyl2)] )"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "id": "25",
   "metadata": {},
   "outputs": [],
   "source": [
    "threading = ThruSections ([wire1, wire2])"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "id": "26",
   "metadata": {},
   "outputs": [],
   "source": [
    "res = thickbody+threading\n",
    "DrawGeo (res);"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "id": "27",
   "metadata": {},
   "outputs": [],
   "source": [
    "# mesh = Mesh(OCCGeometry(res).GenerateMesh(maxh=3))\n",
    "# Draw (mesh);"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "id": "28",
   "metadata": {},
   "outputs": [],
   "source": []
  }
 ],
 "metadata": {
  "kernelspec": {
   "display_name": "Python 3",
   "language": "python",
   "name": "python3"
  },
  "language_info": {
   "codemirror_mode": {
    "name": "ipython",
    "version": 3
   },
   "file_extension": ".py",
   "mimetype": "text/x-python",
   "name": "python",
   "nbconvert_exporter": "python",
   "pygments_lexer": "ipython3",
   "version": "3.9.7"
  }
 },
 "nbformat": 4,
 "nbformat_minor": 5
}
