def __init__(self): ui_path = os.path.join(CfdTools.getModulePath(), 'Gui', "CfdPreferencePage.ui") self.form = FreeCADGui.PySideUic.loadUi(ui_path) self.form.tb_choose_foam_dir.clicked.connect(self.chooseFoamDir) self.form.le_foam_dir.textChanged.connect(self.foamDirChanged) self.form.tb_choose_paraview_path.clicked.connect( self.chooseParaviewPath) self.form.le_paraview_path.textChanged.connect( self.paraviewPathChanged) self.form.tb_choose_gmsh_path.clicked.connect(self.chooseGmshPath) self.form.le_gmsh_path.textChanged.connect(self.gmshPathChanged) self.form.pb_run_dependency_checker.clicked.connect( self.runDependencyChecker) self.form.pb_download_install_openfoam.clicked.connect( self.downloadInstallOpenFoam) self.form.tb_pick_openfoam_file.clicked.connect(self.pickOpenFoamFile) self.form.pb_download_install_paraview.clicked.connect( self.downloadInstallParaview) self.form.tb_pick_paraview_file.clicked.connect(self.pickParaviewFile) self.form.pb_download_install_cfMesh.clicked.connect( self.downloadInstallCfMesh) self.form.tb_pick_cfmesh_file.clicked.connect(self.pickCfMeshFile) self.form.pb_download_install_hisa.clicked.connect( self.downloadInstallHisa) self.form.tb_pick_hisa_file.clicked.connect(self.pickHisaFile) self.form.le_openfoam_url.setText(OPENFOAM_URL) self.form.le_paraview_url.setText(PARAVIEW_URL) self.form.tb_choose_output_dir.clicked.connect(self.chooseOutputDir) self.form.le_output_dir.textChanged.connect(self.outputDirChanged) self.ev_filter = CloseDetector(self.form, self.cleanUp) self.form.installEventFilter(self.ev_filter) self.thread = None self.install_process = None self.console_message = "" self.foam_dir = "" self.initial_foam_dir = "" self.paraview_path = "" self.initial_paraview_path = "" self.gmsh_path = "" self.initial_gmsh_path = "" self.output_dir = "" self.form.gb_openfoam.setVisible(platform.system() == 'Windows') self.form.gb_paraview.setVisible(platform.system() == 'Windows')
def Activated(self): FreeCAD.Console.PrintMessage("Set fluid properties \n") FreeCAD.ActiveDocument.openTransaction("Set CfdFluidMaterialProperty") FreeCADGui.doCommand("from CfdOF import CfdTools") FreeCADGui.doCommand("from CfdOF.Solve import CfdFluidMaterial") editing_existing = False analysis_object = CfdTools.getActiveAnalysis() if analysis_object is None: CfdTools.cfdErrorBox("No active analysis object found") return False physics_model = CfdTools.getPhysicsModel(analysis_object) if not physics_model or physics_model.Phase == 'Single': members = analysis_object.Group for i in members: if isinstance(i.Proxy, CfdMaterial): FreeCADGui.activeDocument().setEdit(i.Name) editing_existing = True if not editing_existing: FreeCADGui.doCommand( "CfdTools.getActiveAnalysis().addObject(CfdFluidMaterial.makeCfdFluidMaterial('FluidProperties'))") FreeCADGui.ActiveDocument.setEdit(FreeCAD.ActiveDocument.ActiveObject.Name)
def loadSettings(self): # Don't set the autodetected location, since the user might want to allow that to vary according # to WM_PROJECT_DIR setting prefs = CfdTools.getPreferencesLocation() self.foam_dir = FreeCAD.ParamGet(prefs).GetString( "InstallationPath", "") self.initial_foam_dir = str(self.foam_dir) self.form.le_foam_dir.setText(self.foam_dir) self.paraview_path = CfdTools.getParaviewPath() self.initial_paraview_path = str(self.paraview_path) self.form.le_paraview_path.setText(self.paraview_path) self.gmsh_path = CfdTools.getGmshPath() self.initial_gmsh_path = str(self.gmsh_path) self.form.le_gmsh_path.setText(self.gmsh_path) self.output_dir = CfdTools.getDefaultOutputPath() self.form.le_output_dir.setText(self.output_dir) self.setDownloadURLs()
def doubleClicked(self, vobj): if FreeCADGui.activeWorkbench().name() != 'CfdOFWorkbench': FreeCADGui.activateWorkbench("CfdOFWorkbench") doc = FreeCADGui.getDocument(vobj.Object.Document) if not CfdTools.getActiveAnalysis(): analysis_obj = CfdTools.getParentAnalysisObject(self.Object) if analysis_obj: CfdTools.setActiveAnalysis(analysis_obj) else: FreeCAD.Console.PrintError( 'No Active Analysis detected from Solver object in the active Document\n' ) if not doc.getInEdit(): if CfdTools.getActiveAnalysis().Document is FreeCAD.ActiveDocument: if self.Object in CfdTools.getActiveAnalysis().Group: doc.setEdit(vobj.Object.Name) else: FreeCAD.Console.PrintError( 'Please activate the Analysis this solver belongs to.\n' ) else: FreeCAD.Console.PrintError( 'Active Analysis is not in active Document\n') else: FreeCAD.Console.PrintError('Task dialog already active\n') FreeCADGui.Control.showTaskView() return True
def lineDirectionChanged(self, value): selection = value.split(':') # See if entered face actually exists and is planar try: selected_object = self.obj.Document.getObject(selection[0]) if hasattr(selected_object, "Shape"): elt = selected_object.Shape.getElement(selection[1]) if elt.ShapeType == 'Face' and CfdTools.isPlanar(elt): return except SystemError: pass FreeCAD.Console.PrintMessage(value + " is not a valid, planar face\n")
def GetResources(self): icon_path = os.path.join(CfdTools.getModulePath(), "Gui", "Icons", "scalartransport.svg") return { 'Pixmap': icon_path, 'MenuText': QtCore.QT_TRANSLATE_NOOP("Cfd_ScalarTransportFunction", "Cfd scalar transport function"), 'ToolTip': QtCore.QT_TRANSLATE_NOOP("Cfd_ScalarTransportFunction", "Create a scalar transport function") }
def __init__(self, obj): FreeCADGui.Selection.clearSelection() self.obj = obj self.form = FreeCADGui.PySideUic.loadUi( os.path.join(CfdTools.getModulePath(), 'Gui', "TaskPanelCfdDynamicMeshRefinement.ui")) self.load() FreeCADGui.Selection.addObserver(self) self.updateUI()
def GetResources(self): icon_path = os.path.join(CfdTools.getModulePath(), "Gui", "Icons", "mesh.svg") return { 'Pixmap': icon_path, 'MenuText': QtCore.QT_TRANSLATE_NOOP("Cfd_MeshFromShape", "CFD mesh"), 'ToolTip': QtCore.QT_TRANSLATE_NOOP( "Cfd_MeshFromShape", "Create a mesh using cfMesh, snappyHexMesh or gmsh") }
def __init__(self, solver_runner_obj): ui_path = os.path.join(CfdTools.getModulePath(), 'Gui', "TaskPanelCfdSolverControl.ui") self.form = FreeCADGui.PySideUic.loadUi(ui_path) self.analysis_object = CfdTools.getActiveAnalysis() self.solver_runner = solver_runner_obj self.solver_object = solver_runner_obj.solver # update UI self.console_message = '' self.solver_object.Proxy.solver_process = CfdConsoleProcess( finished_hook=self.solverFinished, stdout_hook=self.gotOutputLines, stderr_hook=self.gotErrorLines) self.Timer = QtCore.QTimer() self.Timer.setInterval(1000) self.Timer.timeout.connect(self.updateText) self.form.terminateSolver.clicked.connect(self.killSolverProcess) self.form.terminateSolver.setEnabled(False) self.open_paraview = QtCore.QProcess() self.working_dir = CfdTools.getOutputPath(self.analysis_object) self.updateUI() # Connect Signals and Slots self.form.pb_write_inp.clicked.connect(self.write_input_file_handler) self.form.pb_edit_inp.clicked.connect(self.editSolverInputFile) self.form.pb_run_solver.clicked.connect(self.runSolverProcess) self.form.pb_paraview.clicked.connect(self.openParaview) self.Start = time.time() self.Timer.start()
def GetResources(self): icon_path = os.path.join(CfdTools.getModulePath(), "Gui", "Icons", "mesh_region.svg") return { 'Pixmap': icon_path, 'MenuText': QtCore.QT_TRANSLATE_NOOP("Cfd_MeshRegion", "Mesh refinement"), 'Accel': "M, R", 'ToolTip': QtCore.QT_TRANSLATE_NOOP("Cfd_MeshRegion", "Creates a mesh refinement") }
def GetResources(self): icon_path = os.path.join(CfdTools.getModulePath(), "Gui", "Icons", "physics.svg") return { 'Pixmap': icon_path, 'MenuText': QtCore.QT_TRANSLATE_NOOP("Cfd_PhysicsModel", "Select models"), 'Accel': "", 'ToolTip': QtCore.QT_TRANSLATE_NOOP("Cfd_PhysicsModel", "Select the physics model") }
def createInletBoundary(self): self.inlet_boundary = CfdFluidBoundary.makeCfdFluidBoundary('inlet') self.analysis.addObject(self.inlet_boundary) bc_set = self.inlet_boundary bc_set.BoundaryType = 'inlet' bc_set.BoundarySubType = 'uniformVelocityInlet' bc_set.Ux = 1 bc_set.Uy = 0 bc_set.Uz = 0 # Test addSelection and rebuild_list_references doc = FreeCAD.getDocument(self.__class__.__doc_name) obj = doc.getObject('inlet') vobj = obj.ViewObject from CfdOF.Solve import TaskPanelCfdFluidBoundary physics_model = CfdTools.getPhysicsModel(self.analysis) material_objs = CfdTools.getMaterials(self.analysis) taskd = TaskPanelCfdFluidBoundary.TaskPanelCfdFluidBoundary(obj, physics_model, material_objs) taskd.selecting_references = True taskd.faceSelector.addSelection(doc.Name, self.__class__.__part_name, 'Face1') # Give scheduled recompute a chance to happen FreeCADGui.updateGui() taskd.accept()
def GetResources(self): icon_path = os.path.join(CfdTools.getModulePath(), "Gui", "Icons", "monitor.svg") return { 'Pixmap': icon_path, 'MenuText': QtCore.QT_TRANSLATE_NOOP("Cfd_ReportingFunctions", "Reporting function"), 'ToolTip': QtCore.QT_TRANSLATE_NOOP( "Cfd_ReportingFunctions", "Create a reporting function for the current case") }
def constructAncillaryPlotters(self): reporting_functions = CfdTools.getReportingFunctionsGroup( CfdTools.getActiveAnalysis()) if reporting_functions is not None: for rf in reporting_functions: if rf.ReportingFunctionType == "Force": self.forces[rf.Label] = {} if rf.Label not in self.solver.Proxy.forces_plotters: self.solver.Proxy.forces_plotters[rf.Label] = \ TimePlot(title=rf.Label, y_label="Force [N]", is_log=False) elif rf.ReportingFunctionType == "ForceCoefficients": self.force_coeffs[rf.Label] = {} if rf.Label not in self.solver.Proxy.force_coeffs_plotters: self.solver.Proxy.force_coeffs_plotters[rf.Label] = \ TimePlot(title=rf.Label, y_label="Coefficient", is_log=False) elif rf.ReportingFunctionType == 'Probes': self.probes[rf.Label] = { 'field': rf.SampleFieldName, 'points': [rf.ProbePosition] } if rf.Label not in self.solver.Proxy.probes_plotters: self.solver.Proxy.probes_plotters[rf.Label] = \ TimePlot(title=rf.Label, y_label=rf.SampleFieldName, is_log=False)
def GetResources(self): icon_path = os.path.join(CfdTools.getModulePath(), "Gui", "Icons", "boundary.svg") return { 'Pixmap': icon_path, 'MenuText': QtCore.QT_TRANSLATE_NOOP("Cfd_FluidBoundary", "Fluid boundary"), 'Accel': "C, W", 'ToolTip': QtCore.QT_TRANSLATE_NOOP("Cfd_FluidBoundary", "Creates a CFD fluid boundary") }
def GetResources(self): icon_path = os.path.join(CfdTools.getModulePath(), "Gui", "Icons", "mesh_dynamic.svg") return { 'Pixmap': icon_path, 'MenuText': QtCore.QT_TRANSLATE_NOOP("Cfd_DynamicMesh", "Dynamic mesh refinement"), 'Accel': "M, D", 'ToolTip': QtCore.QT_TRANSLATE_NOOP("Cfd_DynamicMesh", "Defines dynamic mesh behaviour") }
def __init__(self, analysis=None, solver=None): super(CfdRunnable, self).__init__() if analysis and isinstance(analysis.Proxy, CfdAnalysis.CfdAnalysis): self.analysis = analysis else: if FreeCAD.GuiUp: self.analysis = CfdTools.getActiveAnalysis() self.solver = None if solver: self.solver = solver else: if analysis: self.solver = CfdTools.getSolver(self.analysis) if not self.solver: FreeCAD.Console.printMessage( "Solver object is missing from Analysis Object") if self.analysis: self.results_present = False self.result_object = None else: raise Exception('No active analysis found')
def GetResources(self): icon_path = os.path.join(CfdTools.getModulePath(), "Gui", "Icons", "solver.svg") return { 'Pixmap': icon_path, 'MenuText': QtCore.QT_TRANSLATE_NOOP("Cfd_SolverControl", "Solver job control"), 'Accel': "S, C", 'ToolTip': QtCore.QT_TRANSLATE_NOOP("Cfd_SolverControl", "Edit properties and run solver") }
def GetResources(self): icon_path = os.path.join(CfdTools.getModulePath(), "Gui", "Icons", "cfd_analysis.svg") return { 'Pixmap': icon_path, 'MenuText': QtCore.QT_TRANSLATE_NOOP("Cfd_Analysis", "Analysis container"), 'Accel': "N, C", 'ToolTip': QtCore.QT_TRANSLATE_NOOP( "Cfd_Analysis", "Creates an analysis container with a CFD solver") }
def processPorousZoneProperties(self): settings = self.settings settings['porousZonesPresent'] = True porousZoneSettings = settings['porousZones'] for po in self.porous_zone_objs: pd = {'PartNameList': tuple(r[0].Name for r in po.ShapeRefs)} po = CfdTools.propsToDict(po) if po['PorousCorrelation'] == 'DarcyForchheimer': pd['D'] = (po['D1'], po['D2'], po['D3']) pd['F'] = (po['F1'], po['F2'], po['F3']) pd['e1'] = tuple(po['e1']) pd['e3'] = tuple(po['e3']) elif po['PorousCorrelation'] == 'Jakob': # Calculate effective Darcy-Forchheimer coefficients # This is for equilateral triangles arranged with the triangles pointing in BundleLayerNormal # direction (direction of greater spacing - sqrt(3)*triangleEdgeLength) pd['e1'] = tuple(po['SpacingDirection'] ) # OpenFOAM modifies to be orthog to e3 pd['e3'] = tuple(po['TubeAxis']) spacing = po['TubeSpacing'] d0 = po['OuterDiameter'] u0 = po['VelocityEstimate'] aspectRatio = po['AspectRatio'] kinVisc = self.settings['fluidProperties'][ 'KinematicViscosity'] if kinVisc == 0.0: raise ValueError( "Viscosity must be set for Jakob correlation") if spacing < d0: raise ValueError( "Tube spacing may not be less than diameter") D = [0, 0, 0] F = [0, 0, 0] for (i, Sl, St) in [(0, aspectRatio * spacing, spacing), (1, spacing, aspectRatio * spacing)]: C = 1.0 / St * 0.5 * (1.0 + 0.47 / (Sl / d0 - 1)**1.06) * ( 1.0 / (1 - d0 / Sl))**(2.0 - 0.16) Di = C / d0 * 0.5 * (u0 * d0 / kinVisc)**(1.0 - 0.16) Fi = C * (u0 * d0 / kinVisc)**(-0.16) D[i] = Di F[i] = Fi pd['D'] = tuple(D) pd['F'] = tuple(F) # Currently assuming zero drag parallel to tube bundle (3rd principal dirn) else: raise RuntimeError( "Unrecognised method for porous baffle resistance") porousZoneSettings[po['Label']] = pd
def GetResources(self): icon_path = os.path.join(CfdTools.getModulePath(), "Gui", "Icons", "initialise.svg") return { 'Pixmap': icon_path, 'MenuText': QtCore.QT_TRANSLATE_NOOP("Cfd_InitialiseInternal", "Initialise"), 'Accel': "", 'ToolTip': QtCore.QT_TRANSLATE_NOOP( "Cfd_InitialiseInternal", "Initialise internal flow variables based on the selected physics model" ) }
def setEdit(self, vobj, mode): analysis_object = CfdTools.getParentAnalysisObject(self.Object) if analysis_object is None: CfdTools.cfdErrorBox("No parent analysis object found") return False physics_model = CfdTools.getPhysicsModel(analysis_object) if not physics_model: CfdTools.cfdErrorBox("Analysis object must have a physics object") return False boundaries = CfdTools.getCfdBoundaryGroup(analysis_object) material_objs = CfdTools.getMaterials(analysis_object) import importlib importlib.reload(TaskPanelCfdInitialiseInternalFlowField) self.taskd = TaskPanelCfdInitialiseInternalFlowField.TaskPanelCfdInitialiseInternalFlowField( self.Object, physics_model, boundaries, material_objs) self.taskd.obj = vobj.Object FreeCADGui.Control.showDialog(self.taskd) return True
def initProperties(self, obj): # Not currently used, but required for parent class addObjectProperty(obj, "References", [], "App::PropertyLinkSubList", "Material", "List of material shapes") # Compatibility with FEM material object if addObjectProperty( obj, "Category", ["Solid", "Fluid"], "App::PropertyEnumeration", "Material", "Type of material"): obj.Category = "Fluid" # 'Material' PropertyMap already present in MaterialObjectPython if not obj.Material: mats, name_path_list = CfdTools.importMaterials() # Load a default to initialise the values for each type obj.Material = mats[name_path_list[[np[0] for np in name_path_list].index('AirIsothermal')][1]] elif not obj.Material.get('Type'): mat = obj.Material mat['Type'] = 'Isothermal' obj.Material = mat
def Activated(self): is_present = False members = CfdTools.getActiveAnalysis().Group for i in members: if isinstance(i.Proxy, CfdSolverFoam): FreeCADGui.activeDocument().setEdit(i.Name) is_present = True # Allowing user to re-create if CFDSolver was deleted. if not is_present: FreeCADGui.doCommand("from CfdOF import CfdTools") FreeCADGui.doCommand("from CfdOF.Solve import CfdSolverFoam") FreeCADGui.doCommand( "CfdTools.getActiveAnalysis().addObject(CfdSolverFoam.makeCfdSolverFoam())" ) FreeCADGui.doCommand( "Gui.activeDocument().setEdit(App.ActiveDocument.ActiveObject.Name)" )
def __init__(self, obj): FreeCADGui.Selection.clearSelection() self.sel_server = None self.obj = obj self.form = FreeCADGui.PySideUic.loadUi(os.path.join(CfdTools.getModulePath(), 'Gui', "TaskPanelPhysics.ui")) self.form.radioButtonSteady.toggled.connect(self.updateUI) self.form.radioButtonTransient.toggled.connect(self.updateUI) self.form.radioButtonSinglePhase.toggled.connect(self.updateUI) self.form.radioButtonFreeSurface.toggled.connect(self.updateUI) self.form.radioButtonIncompressible.toggled.connect(self.updateUI) self.form.radioButtonCompressible.toggled.connect(self.updateUI) self.form.viscousCheckBox.stateChanged.connect(self.updateUI) self.form.radioButtonLaminar.toggled.connect(self.updateUI) self.form.radioButtonRANS.toggled.connect(self.updateUI) self.form.radioButtonDES.toggled.connect(self.updateUI) self.form.radioButtonLES.toggled.connect(self.updateUI) self.load()
def Activated(self): FreeCAD.ActiveDocument.openTransaction( "Choose appropriate physics model") is_present = False members = CfdTools.getActiveAnalysis().Group for i in members: if isinstance(i.Proxy, CfdPhysicsModel): FreeCADGui.activeDocument().setEdit(i.Name) is_present = True # Allow to re-create if deleted if not is_present: FreeCADGui.doCommand("") FreeCADGui.doCommand("from CfdOF.Solve import CfdPhysicsSelection") FreeCADGui.doCommand("from CfdOF import CfdTools") FreeCADGui.doCommand( "CfdTools.getActiveAnalysis().addObject(CfdPhysicsSelection.makeCfdPhysicsSelection())" ) FreeCADGui.ActiveDocument.setEdit( FreeCAD.ActiveDocument.ActiveObject.Name)
def Activated(self): FreeCAD.ActiveDocument.openTransaction( "Initialise the internal flow variables") isPresent = False members = CfdTools.getActiveAnalysis().Group for i in members: if "InitialiseFields" in i.Name: FreeCADGui.activeDocument().setEdit(i.Name) isPresent = True # Allow to re-create if deleted if not isPresent: FreeCADGui.doCommand("from CfdOF import CfdTools") FreeCADGui.doCommand( "from CfdOF.Solve import CfdInitialiseFlowField") FreeCADGui.doCommand( "CfdTools.getActiveAnalysis().addObject(CfdInitialiseFlowField.makeCfdInitialFlowField())" ) FreeCADGui.ActiveDocument.setEdit( FreeCAD.ActiveDocument.ActiveObject.Name)
def writeMesh(self): self.setupMeshCaseDir() CfdTools.cfdMessage("Exporting mesh refinement data ...\n") if self.progressCallback: self.progressCallback("Exporting mesh refinement data ...") self.processRefinements() self.processExtrusions() CfdTools.cfdMessage("Exporting the part surfaces ...\n") if self.progressCallback: self.progressCallback("Exporting the part surfaces ...") self.writePartFile() self.writeMeshCase() CfdTools.cfdMessage("Wrote mesh case to {}\n".format(self.meshCaseDir)) if self.progressCallback: self.progressCallback("Mesh case written successfully")
def setEdit(self, vobj, mode): analysis_object = CfdTools.getParentAnalysisObject(self.Object) if analysis_object is None: CfdTools.cfdErrorBox("No parent analysis object found") return False physics_model = CfdTools.getPhysicsModel(analysis_object) if not physics_model: CfdTools.cfdErrorBox("Analysis object must have a physics object") return False import importlib importlib.reload(TaskPanelCfdFluidProperties) self.taskd = TaskPanelCfdFluidProperties.TaskPanelCfdFluidProperties(self.Object, physics_model) self.taskd.obj = vobj.Object FreeCADGui.Control.showDialog(self.taskd) return True
def __init__(self, obj, physics_obj): self.obj = obj self.physics_obj = physics_obj self.form = FreeCADGui.PySideUic.loadUi(os.path.join(CfdTools.getModulePath(), 'Gui', "TaskPanelCfdFluidProperties.ui")) self.material = self.obj.Material self.form.compressibleCheckBox.setVisible(self.physics_obj.Flow == "Compressible") # Make sure it is checked in the default case since object was initialised with Isothermal self.form.compressibleCheckBox.setChecked(self.material.get('Type') != "Incompressible") self.form.compressibleCheckBox.stateChanged.connect(self.compressibleCheckBoxChanged) self.text_boxes = {} self.fields = [] if self.physics_obj.Flow == 'Incompressible': material_type = 'Isothermal' else: if self.physics_obj.Flow == "Compressible" and not self.form.compressibleCheckBox.isChecked(): material_type = 'Incompressible' else: material_type = 'Compressible' self.material['Type'] = material_type self.createUIBasedOnPhysics() self.populateMaterialsList() self.form.PredefinedMaterialLibraryComboBox.currentIndexChanged.connect(self.selectPredefined) self.selecting_predefined = True try: idx = self.form.PredefinedMaterialLibraryComboBox.findText(self.material['Name']) if idx == -1: # Select first one if not found idx = 0 self.form.PredefinedMaterialLibraryComboBox.setCurrentIndex(idx) self.selectPredefined() finally: self.selecting_predefined = False self.form.material_name.setText(self.obj.Label)