From c18c0d1387fdef1693a2e2dc00101a52aa4cd162 Mon Sep 17 00:00:00 2001 From: Wilfried Hortschitz Date: Fri, 1 Dec 2017 19:43:50 +0100 Subject: [PATCH] FEM: elmer, add electrostatic equation --- src/Mod/Fem/App/CMakeLists.txt | 1 + src/Mod/Fem/CMakeLists.txt | 1 + src/Mod/Fem/Gui/Resources/Fem.qrc | 1 + .../icons/fem-equation-electrostatic.svg | 287 ++++++++++++++++++ src/Mod/Fem/Gui/Workbench.cpp | 2 + src/Mod/Fem/PyGui/_CommandFemEquation.py | 14 + .../elmer/equations/electrostatic.py | 70 +++++ src/Mod/Fem/femsolver/elmer/solver.py | 2 + src/Mod/Fem/femsolver/elmer/writer.py | 54 ++++ src/Mod/Fem/femsolver/equationbase.py | 10 + 10 files changed, 442 insertions(+) create mode 100644 src/Mod/Fem/Gui/Resources/icons/fem-equation-electrostatic.svg create mode 100644 src/Mod/Fem/femsolver/elmer/equations/electrostatic.py diff --git a/src/Mod/Fem/App/CMakeLists.txt b/src/Mod/Fem/App/CMakeLists.txt index eb43721e65..886479d0a5 100644 --- a/src/Mod/Fem/App/CMakeLists.txt +++ b/src/Mod/Fem/App/CMakeLists.txt @@ -143,6 +143,7 @@ SET(FemEquationsElmer_SRCS femsolver/elmer/equations/linear.py femsolver/elmer/equations/nonlinear.py femsolver/elmer/equations/elasticity.py + femsolver/elmer/equations/electrostatic.py femsolver/elmer/equations/heat.py femsolver/elmer/equations/flow.py ) diff --git a/src/Mod/Fem/CMakeLists.txt b/src/Mod/Fem/CMakeLists.txt index 59fc866371..6545f33160 100755 --- a/src/Mod/Fem/CMakeLists.txt +++ b/src/Mod/Fem/CMakeLists.txt @@ -102,6 +102,7 @@ INSTALL( femsolver/elmer/equations/linear.py femsolver/elmer/equations/nonlinear.py femsolver/elmer/equations/elasticity.py + femsolver/elmer/equations/electrostatic.py femsolver/elmer/equations/heat.py femsolver/elmer/equations/flow.py DESTINATION diff --git a/src/Mod/Fem/Gui/Resources/Fem.qrc b/src/Mod/Fem/Gui/Resources/Fem.qrc index 0f774c2d76..a75c89940a 100755 --- a/src/Mod/Fem/Gui/Resources/Fem.qrc +++ b/src/Mod/Fem/Gui/Resources/Fem.qrc @@ -35,6 +35,7 @@ icons/fem-DataAlongLine.svg icons/fem-data.svg icons/fem-elmer.png + icons/fem-equation-electrostatic.svg icons/fem-equation-elasticity.svg icons/fem-equation-flow.svg icons/fem-equation-heat.svg diff --git a/src/Mod/Fem/Gui/Resources/icons/fem-equation-electrostatic.svg b/src/Mod/Fem/Gui/Resources/icons/fem-equation-electrostatic.svg new file mode 100644 index 0000000000..3de5b639df --- /dev/null +++ b/src/Mod/Fem/Gui/Resources/icons/fem-equation-electrostatic.svg @@ -0,0 +1,287 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + image/svg+xml + + + + + [Alexander Gryson] + + + fem-warp + 2017-03-11 + http://www.freecadweb.org/wiki/index.php?title=Artwork + + + FreeCAD + + + FreeCAD/src/Mod/ + + + FreeCAD LGPL2+ + + + https://www.gnu.org/copyleft/lesser.html + + + [agryson] Alexander Gryson + + + + + + + + + + + + + + + + + + + + + diff --git a/src/Mod/Fem/Gui/Workbench.cpp b/src/Mod/Fem/Gui/Workbench.cpp index e37e020d51..158575b9d9 100755 --- a/src/Mod/Fem/Gui/Workbench.cpp +++ b/src/Mod/Fem/Gui/Workbench.cpp @@ -116,6 +116,7 @@ Gui::ToolBarItem* Workbench::setupToolBars() const << "Separator" << "FEM_AddEquationHeat" << "FEM_AddEquationElasticity" + << "FEM_AddEquationElectrostatic" << "FEM_AddEquationFlow" << "Separator" << "FEM_SolverControl" @@ -218,6 +219,7 @@ Gui::MenuItem* Workbench::setupMenuBar() const << "Separator" << "FEM_AddEquationHeat" << "FEM_AddEquationElasticity" + << "FEM_AddEquationElectrostatic" << "FEM_AddEquationFlow" << "Separator" << "FEM_SolverControl" diff --git a/src/Mod/Fem/PyGui/_CommandFemEquation.py b/src/Mod/Fem/PyGui/_CommandFemEquation.py index 259b0b569f..3451853e09 100644 --- a/src/Mod/Fem/PyGui/_CommandFemEquation.py +++ b/src/Mod/Fem/PyGui/_CommandFemEquation.py @@ -84,6 +84,19 @@ class Elasticity(_Base): } +class Electrostatic(_Base): + + def getSpecifier(self): + return "Electrostatic" + + def GetResources(self): + return { + 'Pixmap': 'fem-equation-electrostatic', + 'MenuText': "Electrostatic Equation", + 'ToolTip': "Creates a FEM equation for electrostatic" + } + + class Flow(_Base): def getSpecifier(self): @@ -99,4 +112,5 @@ class Flow(_Base): Gui.addCommand('FEM_AddEquationHeat', Heat()) Gui.addCommand('FEM_AddEquationElasticity', Elasticity()) +Gui.addCommand('FEM_AddEquationElectrostatic', Electrostatic()) Gui.addCommand('FEM_AddEquationFlow', Flow()) diff --git a/src/Mod/Fem/femsolver/elmer/equations/electrostatic.py b/src/Mod/Fem/femsolver/elmer/equations/electrostatic.py new file mode 100644 index 0000000000..98f543ec92 --- /dev/null +++ b/src/Mod/Fem/femsolver/elmer/equations/electrostatic.py @@ -0,0 +1,70 @@ +# *************************************************************************** +# * * +# * Copyright (c) 2017 - Markus Hovorka * +# * * +# * This program is free software; you can redistribute it and/or modify * +# * it under the terms of the GNU Lesser General Public License (LGPL) * +# * as published by the Free Software Foundation; either version 2 of * +# * the License, or (at your option) any later version. * +# * for detail see the LICENCE text file. * +# * * +# * This program is distributed in the hope that it will be useful, * +# * but WITHOUT ANY WARRANTY; without even the implied warranty of * +# * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * +# * GNU Library General Public License for more details. * +# * * +# * You should have received a copy of the GNU Library General Public * +# * License along with this program; if not, write to the Free Software * +# * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 * +# * USA * +# * * +# *************************************************************************** + + +__title__ = "Electrostatic" +__author__ = "Markus Hovorka" +__url__ = "http://www.freecadweb.org" + + +import FemUtils +from ... import equationbase +from . import linear + + +def create(doc, name="Electrostatic"): + return FemUtils.createObject( + doc, name, Proxy, ViewProxy) + + +class Proxy(linear.Proxy, equationbase.ElectrostaticProxy): + + Type = "Fem::FemEquationElmerElectrostatic" + + def __init__(self, obj): + super(Proxy, self).__init__(obj) + obj.addProperty( + "App::PropertyBool", "CalculateElectricField", + "Electrostatic", "Select type of solver for linear system") + obj.addProperty( + "App::PropertyBool", "CalculateElectricFlux", + "Electrostatic", "Select type of solver for linear system") + obj.addProperty( + "App::PropertyBool", "CalculateElectricEnergy", + "Electrostatic", "Select type of solver for linear system") + obj.addProperty( + "App::PropertyBool", "CalculateSurfaceCharge", + "Electrostatic", "Select type of solver for linear system") + ''' + #obj.addProperty( + #"App::PropertyBool", "CalculateCapacitanceMatrix", + #"Electrostatic", "Select type of solver for linear system") + #obj.addProperty( + #"App::PropertyInteger", "CapacitanceBodies", + #"Electrostatic", "Select type of solver for linear system") + ''' + + obj.Priority = 10 + + +class ViewProxy(linear.ViewProxy, equationbase.ElectrostaticViewProxy): + pass diff --git a/src/Mod/Fem/femsolver/elmer/solver.py b/src/Mod/Fem/femsolver/elmer/solver.py index 18078dd9ef..7ab369e63f 100644 --- a/src/Mod/Fem/femsolver/elmer/solver.py +++ b/src/Mod/Fem/femsolver/elmer/solver.py @@ -34,6 +34,7 @@ from . import tasks from .equations import heat from .equations import elasticity +from .equations import electrostatic from .equations import flow @@ -50,6 +51,7 @@ class Proxy(solverbase.Proxy): _EQUATIONS = { "Heat": heat, "Elasticity": elasticity, + "Electrostatic": electrostatic, "Flow": flow, } diff --git a/src/Mod/Fem/femsolver/elmer/writer.py b/src/Mod/Fem/femsolver/elmer/writer.py index b585286b44..ecc6a56f59 100644 --- a/src/Mod/Fem/femsolver/elmer/writer.py +++ b/src/Mod/Fem/femsolver/elmer/writer.py @@ -106,6 +106,7 @@ class Writer(object): self._handleSimulation() self._handleHeat() self._handleElasticity() + self._handleElectrostatic() self._handleFlow() self._addOutputSolver() @@ -280,6 +281,59 @@ class Writer(object): name, "Heat Capacity", convert(m["SpecificHeat"], "L^2/(T^2*O)")) + def _handleElectrostatic(self): + activeIn = [] + for equation in self.solver.Group: + if FemUtils.isOfType(equation, "Fem::FemEquationElmerElectrostatic"): + if equation.References: + activeIn = equation.References[0][1] + else: + activeIn = self._getAllBodies() + solverSection = self._getElectrostaticSolver(equation) + for body in activeIn: + self._addSolver(body, solverSection) + if activeIn: + self._handleElectrostaticConstants() + #self._handleElectrostaticBndConditions() + #self._handleElectrostaticInitial(activeIn) + #self._handleElectrostaticBodyForces(activeIn) + self._handleElectrostaticMaterial(activeIn) + + def _getElectrostaticSolver(self, equation): + s = self._createLinearSolver(equation) + s["Equation"] = "Stat Elec Solver" # equation.Name + s["Procedure"] = sifio.FileAttr("StatElecSolve/StatElecSolver") + s["Variable"] = self._getUniqueVarName("Potential") + s["Variable DOFs"] = 1 + s["Calculate Electric Field"] = equation.CalculateElectricField + s["Calculate Electric Flux"] = equation.CalculateElectricFlux + s["Calculate Electric Energy"] = equation.CalculateElectricEnergy + s["Calculate Surface Charge"] = equation.CalculateSurfaceCharge + s["Displace mesh"] = False + s["Exec Solver"] = "Always" + s["Stabilize"] = equation.Stabilize + s["Bubbles"] = equation.Bubbles + s["Optimize Bandwidth"] = True + return s + + def _handleElectrostaticConstants(self): + self._constant( + "Permittivity Of Vacuum", + getConstant("PermittivityOfVacuum", "T^4*I^2/(L*M)")) + + def _handleElectrostaticMaterial(self, bodies): + for obj in self._getMember("App::MaterialObject"): + m = obj.Material + refs = ( + obj.References[0][1] + if obj.References + else self._getAllBodies()) + for name in (n for n in refs if n in bodies): + if "RelativePermittivity" in m: + self._material( + name, "Relative Permittivity", + float(m["RelativePermittivity"])) + def _handleElasticity(self): activeIn = [] for equation in self.solver.Group: diff --git a/src/Mod/Fem/femsolver/equationbase.py b/src/Mod/Fem/femsolver/equationbase.py index e95f4fc4b1..8d8eee77b5 100644 --- a/src/Mod/Fem/femsolver/equationbase.py +++ b/src/Mod/Fem/femsolver/equationbase.py @@ -86,6 +86,16 @@ class ElasticityViewProxy(BaseViewProxy): return ":/icons/fem-equation-elasticity.svg" +class ElectrostaticViewProxy(BaseViewProxy): + + def getIcon(self): + return ":/icons/fem-equation-electrostatic.svg" + + +class ElectrostaticProxy(BaseProxy): + pass + + class FlowProxy(BaseProxy): pass