Exemple #1
0
 def check_prerequisites(self):
     from FreeCAD import Units
     message = ""
     # analysis
     if not self.analysis:
         message += "No active Analysis\n"
     if not self.working_dir:
         message += "Working directory not set\n"
     import os
     if not (os.path.isdir(self.working_dir)):
         message += "Working directory \'{}\' doesn't exist.".format(
             self.working_dir)
     # solver
     if not self.solver:
         message += "No solver object defined in the analysis\n"
     else:
         if self.solver.AnalysisType not in self.known_analysis_types:
             message += "Unknown analysis type: {}\n".format(
                 self.solver.AnalysisType)
         if self.solver.AnalysisType == "frequency":
             if not hasattr(self.solver, "EigenmodeHighLimit"):
                 message += "Frequency analysis: Solver has no EigenmodeHighLimit.\n"
             elif not hasattr(self.solver, "EigenmodeLowLimit"):
                 message += "Frequency analysis: Solver has no EigenmodeLowLimit.\n"
             elif not hasattr(self.solver, "EigenmodesCount"):
                 message += "Frequency analysis: Solver has no EigenmodesCount.\n"
         if hasattr(self.solver, "MaterialNonlinearity"
                    ) and self.solver.MaterialNonlinearity == "nonlinear":
             if not self.materials_nonlinear:
                 message += "Solver is set to nonlinear materials, but there is no nonlinear material in the analysis.\n"
             if self.solver.Proxy.Type == 'Fem::FemSolverCalculixCcxTools' and self.solver.GeometricalNonlinearity != "nonlinear":
                 # nonlinear geometry --> should be set https://forum.freecadweb.org/viewtopic.php?f=18&t=23101&p=180489#p180489
                 message += "Solver CalculiX triggers nonlinear geometry for nonlinear material, thus it should to be set too.\n"
     # mesh
     if not self.mesh:
         message += "No mesh object defined in the analysis\n"
     if self.mesh:
         if self.mesh.FemMesh.VolumeCount == 0 and self.mesh.FemMesh.FaceCount > 0 and not self.shell_thicknesses:
             message += "FEM mesh has no volume elements, either define a shell thicknesses or provide a FEM mesh with volume elements.\n"
         if self.mesh.FemMesh.VolumeCount == 0 and self.mesh.FemMesh.FaceCount == 0 and self.mesh.FemMesh.EdgeCount > 0 and not self.beam_sections and not self.fluid_sections:
             message += "FEM mesh has no volume and no shell elements, either define a beam/fluid section or provide a FEM mesh with volume elements.\n"
         if self.mesh.FemMesh.VolumeCount == 0 and self.mesh.FemMesh.FaceCount == 0 and self.mesh.FemMesh.EdgeCount == 0:
             message += "FEM mesh has neither volume nor shell or edge elements. Provide a FEM mesh with elements!\n"
     # material linear and nonlinear
     if not self.materials_linear:
         message += "No material object defined in the analysis\n"
     has_no_references = False
     for m in self.materials_linear:
         if len(m['Object'].References) == 0:
             if has_no_references is True:
                 message += "More than one material has an empty references list (Only one empty references list is allowed!).\n"
             has_no_references = True
     mat_ref_shty = ''
     for m in self.materials_linear:
         ref_shty = femutils.get_refshape_type(m['Object'])
         if not mat_ref_shty:
             mat_ref_shty = ref_shty
         if mat_ref_shty and ref_shty and ref_shty != mat_ref_shty:
             # mat_ref_shty could be empty in one material, only the not empty ones should have the same shape type
             message += (
                 'Some material objects do not have the same reference shape type '
                 '(all material objects must have the same reference shape type, at the moment).\n'
             )
     for m in self.materials_linear:
         mat_map = m['Object'].Material
         mat_obj = m['Object']
         if mat_obj.Category == 'Solid':
             if 'YoungsModulus' in mat_map:
                 # print(Units.Quantity(mat_map['YoungsModulus']).Value)
                 if not Units.Quantity(mat_map['YoungsModulus']).Value:
                     message += "Value of YoungsModulus is set to 0.0.\n"
             else:
                 message += "No YoungsModulus defined for at least one material.\n"
             if 'PoissonRatio' not in mat_map:
                 message += "No PoissonRatio defined for at least one material.\n"  # PoissonRatio is allowed to be 0.0 (in ccx), but it should be set anyway.
         if self.solver.AnalysisType == "frequency" or self.selfweight_constraints:
             if 'Density' not in mat_map:
                 message += "No Density defined for at least one material.\n"
         if self.solver.AnalysisType == "thermomech":
             if 'ThermalConductivity' in mat_map:
                 if not Units.Quantity(
                         mat_map['ThermalConductivity']).Value:
                     message += "Value of ThermalConductivity is set to 0.0.\n"
             else:
                 message += "Thermomechanical analysis: No ThermalConductivity defined for at least one material.\n"
             if 'ThermalExpansionCoefficient' not in mat_map and mat_obj.Category == 'Solid':
                 message += "Thermomechanical analysis: No ThermalExpansionCoefficient defined for at least one material.\n"  # allowed to be 0.0 (in ccx)
             if 'SpecificHeat' not in mat_map:
                 message += "Thermomechanical analysis: No SpecificHeat defined for at least one material.\n"  # allowed to be 0.0 (in ccx)
     for m in self.materials_linear:
         has_nonlinear_material = False
         for nlm in self.materials_nonlinear:
             if nlm['Object'].LinearBaseMaterial == m['Object']:
                 if has_nonlinear_material is False:
                     has_nonlinear_material = True
                 else:
                     message += (
                         "At least two nonlinear materials use the same linear base material. "
                         "Only one nonlinear material for each linear material allowed.\n"
                     )
     # which analysis needs which constraints
     # no check in the regard of loads existence (constraint force, pressure, self weight) is done
     # because an analysis without loads at all is an valid analysis too
     if self.solver.AnalysisType == "static":
         if not (self.fixed_constraints or self.displacement_constraints):
             message += "Static analysis: Neither constraint fixed nor constraint displacement defined.\n"
     if self.solver.AnalysisType == "thermomech":
         if not self.initialtemperature_constraints:
             if not self.fluid_sections:
                 message += "Thermomechanical analysis: No initial temperature defined.\n"
         if len(self.initialtemperature_constraints) > 1:
             message += "Thermomechanical analysis: Only one initial temperature is allowed.\n"
     # constraints
     # fixed
     if self.fixed_constraints:
         for c in self.fixed_constraints:
             if len(c['Object'].References) == 0:
                 message += "At least one constraint fixed has an empty reference.\n"
     # displacement
     if self.displacement_constraints:
         for di in self.displacement_constraints:
             if len(di['Object'].References) == 0:
                 message += "At least one constraint displacement has an empty reference.\n"
     # plane rotation
     if self.planerotation_constraints:
         for c in self.planerotation_constraints:
             if len(c['Object'].References) == 0:
                 message += "At least one constraint plane rotation has an empty reference.\n"
     # contact
     if self.contact_constraints:
         for c in self.contact_constraints:
             if len(c['Object'].References) == 0:
                 message += "At least one constraint contact has an empty reference.\n"
     # transform
     if self.transform_constraints:
         for c in self.transform_constraints:
             if len(c['Object'].References) == 0:
                 message += "At least one constraint transform has an empty reference.\n"
     # pressure
     if self.pressure_constraints:
         for c in self.pressure_constraints:
             if len(c['Object'].References) == 0:
                 message += "At least one constraint pressure has an empty reference.\n"
     # force
     if self.force_constraints:
         for c in self.force_constraints:
             if len(c['Object'].References) == 0:
                 message += "At least one constraint force has an empty reference.\n"
     # temperature
     if self.temperature_constraints:
         for c in self.temperature_constraints:
             if len(c['Object'].References) == 0:
                 message += "At least one constraint temperature has an empty reference.\n"
     # heat flux
     if self.heatflux_constraints:
         for c in self.heatflux_constraints:
             if len(c['Object'].References) == 0:
                 message += "At least one constraint heat flux has an empty reference.\n"
     # beam section
     if self.beam_sections:
         if self.shell_thicknesses:
             # this needs to be checked only once either here or in shell_thicknesses
             message += "Beam sections and shell thicknesses in one analysis is not supported at the moment.\n"
         if self.fluid_sections:
             # this needs to be checked only once either here or in shell_thicknesses
             message += "Beam sections and fluid sections in one analysis is not supported at the moment.\n"
         has_no_references = False
         for b in self.beam_sections:
             if len(b['Object'].References) == 0:
                 if has_no_references is True:
                     message += "More than one beam section has an empty references list (Only one empty references list is allowed!).\n"
                 has_no_references = True
         if self.mesh:
             if self.mesh.FemMesh.FaceCount > 0 or self.mesh.FemMesh.VolumeCount > 0:
                 message += "Beam sections defined but FEM mesh has volume or shell elements.\n"
             if self.mesh.FemMesh.EdgeCount == 0:
                 message += "Beam sections defined but FEM mesh has no edge elements.\n"
         if len(self.beam_rotations) > 1:
             message += "Multiple beam rotations in one analysis are not supported at the moment.\n"
     # beam rotations
     if self.beam_rotations and not self.beam_sections:
         message += "Beam rotations in the analysis but no beam sections defined.\n"
     # shell thickness
     if self.shell_thicknesses:
         has_no_references = False
         for s in self.shell_thicknesses:
             if len(s['Object'].References) == 0:
                 if has_no_references is True:
                     message += "More than one shell thickness has an empty references list (Only one empty references list is allowed!).\n"
                 has_no_references = True
         if self.mesh:
             if self.mesh.FemMesh.VolumeCount > 0:
                 message += "Shell thicknesses defined but FEM mesh has volume elements.\n"
             if self.mesh.FemMesh.FaceCount == 0:
                 message += "Shell thicknesses defined but FEM mesh has no shell elements.\n"
     # fluid section
     if self.fluid_sections:
         if not self.selfweight_constraints:
             message += "A fluid network analysis requires self weight constraint to be applied"
         if self.solver.AnalysisType != "thermomech":
             message += "A fluid network analysis can only be done in a thermomech analysis"
         has_no_references = False
         for f in self.fluid_sections:
             if len(f['Object'].References) == 0:
                 if has_no_references is True:
                     message += "More than one fluid section has an empty references list (Only one empty references list is allowed!).\n"
                 has_no_references = True
         if self.mesh:
             if self.mesh.FemMesh.FaceCount > 0 or self.mesh.FemMesh.VolumeCount > 0:
                 message += "Fluid sections defined but FEM mesh has volume or shell elements.\n"
             if self.mesh.FemMesh.EdgeCount == 0:
                 message += "Fluid sections defined but FEM mesh has no edge elements.\n"
     return message
Exemple #2
0
 def check_prerequisites(self):
     from FreeCAD import Units
     message = ""
     # analysis
     if not self.analysis:
         message += "No active Analysis\n"
     if not self.working_dir:
         message += "Working directory not set\n"
     if not (os.path.isdir(self.working_dir)):
             message += "Working directory \'{}\' doesn't exist.".format(self.working_dir)
     # solver
     if not self.solver:
         message += "No solver object defined in the analysis\n"
     else:
         if self.solver.AnalysisType not in self.known_analysis_types:
             message += "Unknown analysis type: {}\n".format(self.solver.AnalysisType)
         if self.solver.AnalysisType == "frequency":
             if not hasattr(self.solver, "EigenmodeHighLimit"):
                 message += "Frequency analysis: Solver has no EigenmodeHighLimit.\n"
             elif not hasattr(self.solver, "EigenmodeLowLimit"):
                 message += "Frequency analysis: Solver has no EigenmodeLowLimit.\n"
             elif not hasattr(self.solver, "EigenmodesCount"):
                 message += "Frequency analysis: Solver has no EigenmodesCount.\n"
         if hasattr(self.solver, "MaterialNonlinearity") and self.solver.MaterialNonlinearity == "nonlinear":
             if not self.materials_nonlinear:
                 message += "Solver is set to nonlinear materials, but there is no nonlinear material in the analysis.\n"
             if self.solver.Proxy.Type == 'Fem::FemSolverCalculixCcxTools' and self.solver.GeometricalNonlinearity != "nonlinear":
                 # nonlinear geometry --> should be set https://forum.freecadweb.org/viewtopic.php?f=18&t=23101&p=180489#p180489
                 message += "Solver CalculiX triggers nonlinear geometry for nonlinear material, thus it should to be set too.\n"
     # mesh
     if not self.mesh:
         message += "No mesh object defined in the analysis\n"
     if self.mesh:
         if self.mesh.FemMesh.VolumeCount == 0 and self.mesh.FemMesh.FaceCount > 0 and not self.shell_thicknesses:
             message += "FEM mesh has no volume elements, either define a shell thicknesses or provide a FEM mesh with volume elements.\n"
         if self.mesh.FemMesh.VolumeCount == 0 and self.mesh.FemMesh.FaceCount == 0 and self.mesh.FemMesh.EdgeCount > 0 and not self.beam_sections and not self.fluid_sections:
             message += "FEM mesh has no volume and no shell elements, either define a beam/fluid section or provide a FEM mesh with volume elements.\n"
         if self.mesh.FemMesh.VolumeCount == 0 and self.mesh.FemMesh.FaceCount == 0 and self.mesh.FemMesh.EdgeCount == 0:
             message += "FEM mesh has neither volume nor shell or edge elements. Provide a FEM mesh with elements!\n"
     # material linear and nonlinear
     if not self.materials_linear:
         message += "No material object defined in the analysis\n"
     has_no_references = False
     for m in self.materials_linear:
         if len(m['Object'].References) == 0:
             if has_no_references is True:
                 message += "More than one material has an empty references list (Only one empty references list is allowed!).\n"
             has_no_references = True
     mat_ref_shty = ''
     for m in self.materials_linear:
         ref_shty = femutils.get_refshape_type(m['Object'])
         if not mat_ref_shty:
             mat_ref_shty = ref_shty
         if mat_ref_shty and ref_shty and ref_shty != mat_ref_shty:
             # mat_ref_shty could be empty in one material, only the not empty ones should have the same shape type
             message += (
                 'Some material objects do not have the same reference shape type '
                 '(all material objects must have the same reference shape type, at the moment).\n'
             )
     for m in self.materials_linear:
         mat_map = m['Object'].Material
         mat_obj = m['Object']
         if mat_obj.Category == 'Solid':
             if 'YoungsModulus' in mat_map:
                 # print(Units.Quantity(mat_map['YoungsModulus']).Value)
                 if not Units.Quantity(mat_map['YoungsModulus']).Value:
                     message += "Value of YoungsModulus is set to 0.0.\n"
             else:
                 message += "No YoungsModulus defined for at least one material.\n"
             if 'PoissonRatio' not in mat_map:
                 message += "No PoissonRatio defined for at least one material.\n"  # PoissonRatio is allowed to be 0.0 (in ccx), but it should be set anyway.
         if self.solver.AnalysisType == "frequency" or self.selfweight_constraints:
             if 'Density' not in mat_map:
                 message += "No Density defined for at least one material.\n"
         if self.solver.AnalysisType == "thermomech":
             if 'ThermalConductivity' in mat_map:
                 if not Units.Quantity(mat_map['ThermalConductivity']).Value:
                     message += "Value of ThermalConductivity is set to 0.0.\n"
             else:
                 message += "Thermomechanical analysis: No ThermalConductivity defined for at least one material.\n"
             if 'ThermalExpansionCoefficient' not in mat_map and mat_obj.Category == 'Solid':
                 message += "Thermomechanical analysis: No ThermalExpansionCoefficient defined for at least one material.\n"  # allowed to be 0.0 (in ccx)
             if 'SpecificHeat' not in mat_map:
                 message += "Thermomechanical analysis: No SpecificHeat defined for at least one material.\n"  # allowed to be 0.0 (in ccx)
     if len(self.materials_linear) == 1:
         mobj = self.materials_linear[0]['Object']
         if hasattr(mobj, 'References') and mobj.References:
             FreeCAD.Console.PrintError('Only one material object, but this one has a reference shape. The reference shape will be ignored.\n')
     for m in self.materials_linear:
         has_nonlinear_material = False
         for nlm in self.materials_nonlinear:
             if nlm['Object'].LinearBaseMaterial == m['Object']:
                 if has_nonlinear_material is False:
                     has_nonlinear_material = True
                 else:
                     message += (
                         "At least two nonlinear materials use the same linear base material. "
                         "Only one nonlinear material for each linear material allowed.\n"
                     )
     # which analysis needs which constraints
     # no check in the regard of loads existence (constraint force, pressure, self weight) is done
     # because an analysis without loads at all is an valid analysis too
     if self.solver.AnalysisType == "static":
         if not (self.fixed_constraints or self.displacement_constraints):
             message += "Static analysis: Neither constraint fixed nor constraint displacement defined.\n"
     if self.solver.AnalysisType == "thermomech":
         if not self.initialtemperature_constraints:
             if not self.fluid_sections:
                 message += "Thermomechanical analysis: No initial temperature defined.\n"
         if len(self.initialtemperature_constraints) > 1:
             message += "Thermomechanical analysis: Only one initial temperature is allowed.\n"
     # constraints
     # fixed
     if self.fixed_constraints:
         for c in self.fixed_constraints:
             if len(c['Object'].References) == 0:
                 message += "At least one constraint fixed has an empty reference.\n"
     # displacement
     if self.displacement_constraints:
         for di in self.displacement_constraints:
             if len(di['Object'].References) == 0:
                 message += "At least one constraint displacement has an empty reference.\n"
     # plane rotation
     if self.planerotation_constraints:
         for c in self.planerotation_constraints:
             if len(c['Object'].References) == 0:
                 message += "At least one constraint plane rotation has an empty reference.\n"
     # contact
     if self.contact_constraints:
         for c in self.contact_constraints:
             if len(c['Object'].References) == 0:
                 message += "At least one constraint contact has an empty reference.\n"
     # transform
     if self.transform_constraints:
         for c in self.transform_constraints:
             if len(c['Object'].References) == 0:
                 message += "At least one constraint transform has an empty reference.\n"
     # pressure
     if self.pressure_constraints:
         for c in self.pressure_constraints:
             if len(c['Object'].References) == 0:
                 message += "At least one constraint pressure has an empty reference.\n"
     # force
     if self.force_constraints:
         for c in self.force_constraints:
             if len(c['Object'].References) == 0:
                 message += "At least one constraint force has an empty reference.\n"
     # temperature
     if self.temperature_constraints:
         for c in self.temperature_constraints:
             if len(c['Object'].References) == 0:
                 message += "At least one constraint temperature has an empty reference.\n"
     # heat flux
     if self.heatflux_constraints:
         for c in self.heatflux_constraints:
             if len(c['Object'].References) == 0:
                 message += "At least one constraint heat flux has an empty reference.\n"
     # beam section
     if self.beam_sections:
         if self.shell_thicknesses:
             # this needs to be checked only once either here or in shell_thicknesses
             message += "Beam sections and shell thicknesses in one analysis is not supported at the moment.\n"
         if self.fluid_sections:
             # this needs to be checked only once either here or in shell_thicknesses
             message += "Beam sections and fluid sections in one analysis is not supported at the moment.\n"
         has_no_references = False
         for b in self.beam_sections:
             if len(b['Object'].References) == 0:
                 if has_no_references is True:
                     message += "More than one beam section has an empty references list (Only one empty references list is allowed!).\n"
                 has_no_references = True
         if self.mesh:
             if self.mesh.FemMesh.FaceCount > 0 or self.mesh.FemMesh.VolumeCount > 0:
                 message += "Beam sections defined but FEM mesh has volume or shell elements.\n"
             if self.mesh.FemMesh.EdgeCount == 0:
                 message += "Beam sections defined but FEM mesh has no edge elements.\n"
         if len(self.beam_rotations) > 1:
             message += "Multiple beam rotations in one analysis are not supported at the moment.\n"
     # beam rotations
     if self.beam_rotations and not self.beam_sections:
         message += "Beam rotations in the analysis but no beam sections defined.\n"
     # shell thickness
     if self.shell_thicknesses:
         has_no_references = False
         for s in self.shell_thicknesses:
             if len(s['Object'].References) == 0:
                 if has_no_references is True:
                     message += "More than one shell thickness has an empty references list (Only one empty references list is allowed!).\n"
                 has_no_references = True
         if self.mesh:
             if self.mesh.FemMesh.VolumeCount > 0:
                 message += "Shell thicknesses defined but FEM mesh has volume elements.\n"
             if self.mesh.FemMesh.FaceCount == 0:
                 message += "Shell thicknesses defined but FEM mesh has no shell elements.\n"
     # fluid section
     if self.fluid_sections:
         if not self.selfweight_constraints:
             message += "A fluid network analysis requires self weight constraint to be applied"
         if self.solver.AnalysisType != "thermomech":
             message += "A fluid network analysis can only be done in a thermomech analysis"
         has_no_references = False
         for f in self.fluid_sections:
             if len(f['Object'].References) == 0:
                 if has_no_references is True:
                     message += "More than one fluid section has an empty references list (Only one empty references list is allowed!).\n"
                 has_no_references = True
         if self.mesh:
             if self.mesh.FemMesh.FaceCount > 0 or self.mesh.FemMesh.VolumeCount > 0:
                 message += "Fluid sections defined but FEM mesh has volume or shell elements.\n"
             if self.mesh.FemMesh.EdgeCount == 0:
                 message += "Fluid sections defined but FEM mesh has no edge elements.\n"
     return message