Merge pull request #2267 from berndhahnebach/bhbdev228
FEM: femconcrete
This commit is contained in:
@@ -660,6 +660,10 @@ std::map<std::string, std::string> _getFreeCADMechResultVectorProperties() {
|
||||
// App::PropertyVectorList will be a list of vectors in vtk
|
||||
std::map<std::string, std::string> resFCVecProp;
|
||||
resFCVecProp["DisplacementVectors"] = "Displacement";
|
||||
// https://forum.freecadweb.org/viewtopic.php?f=18&t=33106&start=70#p296317
|
||||
resFCVecProp["PS1Vector"] = "Major Principal Stress";
|
||||
resFCVecProp["PS2Vector"] = "Intermediate Principal Stress";
|
||||
resFCVecProp["PS3Vector"] = "Minor Principal Stress";
|
||||
|
||||
return resFCVecProp;
|
||||
}
|
||||
@@ -686,11 +690,16 @@ std::map<std::string, std::string> _getFreeCADMechResultScalarProperties() {
|
||||
resFCScalProp["NodeStrainXZ"] = "Strain xz component";
|
||||
resFCScalProp["NodeStrainYZ"] = "Strain yz component";
|
||||
resFCScalProp["Peeq"] = "Equivalent Plastic Strain";
|
||||
resFCScalProp["PrincipalMax"] = "Major Principal Stress"; // can be plotted in Paraview as THE MAJOR PRINCIPAL STRESS MAGNITUDE
|
||||
resFCScalProp["PrincipalMed"] = "Intermediate Principal Stress"; // can be plotted in Paraview as THE INTERMEDIATE PRINCIPAL STRESS MAGNITUDE
|
||||
resFCScalProp["PrincipalMin"] = "Minor Principal Stress"; // can be plotted in Paraview as THE MINOR PRINCIPAL STRESS MAGNITUDE
|
||||
// https://forum.freecadweb.org/viewtopic.php?f=18&t=33106&start=70#p296317
|
||||
// resFCScalProp["PrincipalMax"] = "Major Principal Stress"; // can be plotted in Paraview as THE MAJOR PRINCIPAL STRESS MAGNITUDE
|
||||
// resFCScalProp["PrincipalMed"] = "Intermediate Principal Stress"; // can be plotted in Paraview as THE INTERMEDIATE PRINCIPAL STRESS MAGNITUDE
|
||||
// resFCScalProp["PrincipalMin"] = "Minor Principal Stress"; // can be plotted in Paraview as THE MINOR PRINCIPAL STRESS MAGNITUDE
|
||||
resFCScalProp["StressValues"] = "von Mises Stress";
|
||||
resFCScalProp["Temperature"] = "Temperature";
|
||||
resFCScalProp["MohrCoulomb"] = "MohrCoulomb";
|
||||
resFCScalProp["ReinforcementRatio_x"] = "ReinforcementRatio_x";
|
||||
resFCScalProp["ReinforcementRatio_y"] = "ReinforcementRatio_y";
|
||||
resFCScalProp["ReinforcementRatio_z"] = "ReinforcementRatio_z";
|
||||
|
||||
resFCScalProp["UserDefined"] = "UserDefinedMyName"; // this is empty or am I wrong ?!
|
||||
resFCScalProp["MassFlowRate"] = "Mass Flow Rate";
|
||||
|
||||
@@ -36,11 +36,13 @@ SET(FemExamples_SRCS
|
||||
femexamples/__init__.py
|
||||
femexamples/ccx_cantilever_std.py
|
||||
femexamples/manager.py
|
||||
femexamples/rc_wall_2d.py
|
||||
)
|
||||
|
||||
SET(FemExampleMeshes_SRCS
|
||||
femexamples/meshes/__init__.py
|
||||
femexamples/meshes/mesh_canticcx_tetra10.py
|
||||
femexamples/meshes/mesh_rc_wall_2d_tria6.py
|
||||
)
|
||||
|
||||
SET(FemInOut_SRCS
|
||||
@@ -206,6 +208,7 @@ SET(FemObjectsScripts_SRCS
|
||||
femobjects/_FemElementGeometry2D.py
|
||||
femobjects/_FemElementRotation1D.py
|
||||
femobjects/_FemMaterial.py
|
||||
femobjects/_FemMaterialReinforced.py
|
||||
femobjects/_FemMaterialMechanicalNonlinear.py
|
||||
femobjects/_FemMeshBoundaryLayer.py
|
||||
femobjects/_FemMeshGmsh.py
|
||||
@@ -286,6 +289,7 @@ SET(FemGuiScripts_SRCS
|
||||
femguiobjects/_ViewProviderFemElementGeometry2D.py
|
||||
femguiobjects/_ViewProviderFemElementRotation1D.py
|
||||
femguiobjects/_ViewProviderFemMaterial.py
|
||||
femguiobjects/_ViewProviderFemMaterialReinforced.py
|
||||
femguiobjects/_ViewProviderFemMaterialMechanicalNonlinear.py
|
||||
femguiobjects/_ViewProviderFemMeshBoundaryLayer.py
|
||||
femguiobjects/_ViewProviderFemMeshGmsh.py
|
||||
|
||||
@@ -401,6 +401,7 @@ SET(FemGuiPythonUI_SRCS
|
||||
Resources/ui/FlowVelocity.ui
|
||||
Resources/ui/InitialFlowVelocity.ui
|
||||
Resources/ui/Material.ui
|
||||
Resources/ui/MaterialReinforcement.ui
|
||||
Resources/ui/MeshBoundaryLayer.ui
|
||||
Resources/ui/MeshGmsh.ui
|
||||
Resources/ui/MeshGroup.ui
|
||||
|
||||
@@ -52,6 +52,7 @@
|
||||
<file>icons/fem-material.svg</file>
|
||||
<file>icons/fem-material-fluid.svg</file>
|
||||
<file>icons/fem-material-nonlinear.svg</file>
|
||||
<file>icons/fem-material-reinforced.svg</file>
|
||||
<file>icons/fem-post-data-pipline.svg</file>
|
||||
<file>icons/fem-post-filter-clip-region.svg</file>
|
||||
<file>icons/fem-post-filter-clip-scalar.svg</file>
|
||||
|
||||
686
src/Mod/Fem/Gui/Resources/icons/fem-material-reinforced.svg
Normal file
686
src/Mod/Fem/Gui/Resources/icons/fem-material-reinforced.svg
Normal file
@@ -0,0 +1,686 @@
|
||||
<?xml version="1.0" encoding="UTF-8" standalone="no"?>
|
||||
<!-- Created with Inkscape (http://www.inkscape.org/) -->
|
||||
|
||||
<svg
|
||||
xmlns:dc="http://purl.org/dc/elements/1.1/"
|
||||
xmlns:cc="http://creativecommons.org/ns#"
|
||||
xmlns:rdf="http://www.w3.org/1999/02/22-rdf-syntax-ns#"
|
||||
xmlns:svg="http://www.w3.org/2000/svg"
|
||||
xmlns="http://www.w3.org/2000/svg"
|
||||
xmlns:xlink="http://www.w3.org/1999/xlink"
|
||||
xmlns:sodipodi="http://sodipodi.sourceforge.net/DTD/sodipodi-0.dtd"
|
||||
xmlns:inkscape="http://www.inkscape.org/namespaces/inkscape"
|
||||
width="64px"
|
||||
height="64px"
|
||||
id="svg2816"
|
||||
version="1.1"
|
||||
inkscape:version="0.92.4 (5da689c313, 2019-01-14)"
|
||||
sodipodi:docname="fem-material-reinforced1.svg">
|
||||
<defs
|
||||
id="defs2818">
|
||||
<linearGradient
|
||||
inkscape:collect="always"
|
||||
id="linearGradient4432">
|
||||
<stop
|
||||
style="stop-color:#ffffff;stop-opacity:1;"
|
||||
offset="0"
|
||||
id="stop4434" />
|
||||
<stop
|
||||
style="stop-color:#ffffff;stop-opacity:0;"
|
||||
offset="1"
|
||||
id="stop4436" />
|
||||
</linearGradient>
|
||||
<linearGradient
|
||||
inkscape:collect="always"
|
||||
id="linearGradient4044">
|
||||
<stop
|
||||
style="stop-color:#000000;stop-opacity:1;"
|
||||
offset="0"
|
||||
id="stop4046" />
|
||||
<stop
|
||||
style="stop-color:#000000;stop-opacity:0;"
|
||||
offset="1"
|
||||
id="stop4048" />
|
||||
</linearGradient>
|
||||
<linearGradient
|
||||
id="linearGradient3681">
|
||||
<stop
|
||||
id="stop3697"
|
||||
offset="0"
|
||||
style="stop-color:#fff110;stop-opacity:1;" />
|
||||
<stop
|
||||
style="stop-color:#cf7008;stop-opacity:1;"
|
||||
offset="1"
|
||||
id="stop3685" />
|
||||
</linearGradient>
|
||||
<inkscape:perspective
|
||||
sodipodi:type="inkscape:persp3d"
|
||||
inkscape:vp_x="0 : 32 : 1"
|
||||
inkscape:vp_y="0 : 1000 : 0"
|
||||
inkscape:vp_z="64 : 32 : 1"
|
||||
inkscape:persp3d-origin="32 : 21.333333 : 1"
|
||||
id="perspective2824" />
|
||||
<inkscape:perspective
|
||||
id="perspective3622"
|
||||
inkscape:persp3d-origin="0.5 : 0.33333333 : 1"
|
||||
inkscape:vp_z="1 : 0.5 : 1"
|
||||
inkscape:vp_y="0 : 1000 : 0"
|
||||
inkscape:vp_x="0 : 0.5 : 1"
|
||||
sodipodi:type="inkscape:persp3d" />
|
||||
<inkscape:perspective
|
||||
id="perspective3622-9"
|
||||
inkscape:persp3d-origin="0.5 : 0.33333333 : 1"
|
||||
inkscape:vp_z="1 : 0.5 : 1"
|
||||
inkscape:vp_y="0 : 1000 : 0"
|
||||
inkscape:vp_x="0 : 0.5 : 1"
|
||||
sodipodi:type="inkscape:persp3d" />
|
||||
<inkscape:perspective
|
||||
id="perspective3653"
|
||||
inkscape:persp3d-origin="0.5 : 0.33333333 : 1"
|
||||
inkscape:vp_z="1 : 0.5 : 1"
|
||||
inkscape:vp_y="0 : 1000 : 0"
|
||||
inkscape:vp_x="0 : 0.5 : 1"
|
||||
sodipodi:type="inkscape:persp3d" />
|
||||
<inkscape:perspective
|
||||
id="perspective3675"
|
||||
inkscape:persp3d-origin="0.5 : 0.33333333 : 1"
|
||||
inkscape:vp_z="1 : 0.5 : 1"
|
||||
inkscape:vp_y="0 : 1000 : 0"
|
||||
inkscape:vp_x="0 : 0.5 : 1"
|
||||
sodipodi:type="inkscape:persp3d" />
|
||||
<inkscape:perspective
|
||||
id="perspective3697"
|
||||
inkscape:persp3d-origin="0.5 : 0.33333333 : 1"
|
||||
inkscape:vp_z="1 : 0.5 : 1"
|
||||
inkscape:vp_y="0 : 1000 : 0"
|
||||
inkscape:vp_x="0 : 0.5 : 1"
|
||||
sodipodi:type="inkscape:persp3d" />
|
||||
<inkscape:perspective
|
||||
id="perspective3720"
|
||||
inkscape:persp3d-origin="0.5 : 0.33333333 : 1"
|
||||
inkscape:vp_z="1 : 0.5 : 1"
|
||||
inkscape:vp_y="0 : 1000 : 0"
|
||||
inkscape:vp_x="0 : 0.5 : 1"
|
||||
sodipodi:type="inkscape:persp3d" />
|
||||
<inkscape:perspective
|
||||
id="perspective3742"
|
||||
inkscape:persp3d-origin="0.5 : 0.33333333 : 1"
|
||||
inkscape:vp_z="1 : 0.5 : 1"
|
||||
inkscape:vp_y="0 : 1000 : 0"
|
||||
inkscape:vp_x="0 : 0.5 : 1"
|
||||
sodipodi:type="inkscape:persp3d" />
|
||||
<inkscape:perspective
|
||||
id="perspective3764"
|
||||
inkscape:persp3d-origin="0.5 : 0.33333333 : 1"
|
||||
inkscape:vp_z="1 : 0.5 : 1"
|
||||
inkscape:vp_y="0 : 1000 : 0"
|
||||
inkscape:vp_x="0 : 0.5 : 1"
|
||||
sodipodi:type="inkscape:persp3d" />
|
||||
<inkscape:perspective
|
||||
id="perspective3785"
|
||||
inkscape:persp3d-origin="0.5 : 0.33333333 : 1"
|
||||
inkscape:vp_z="1 : 0.5 : 1"
|
||||
inkscape:vp_y="0 : 1000 : 0"
|
||||
inkscape:vp_x="0 : 0.5 : 1"
|
||||
sodipodi:type="inkscape:persp3d" />
|
||||
<inkscape:perspective
|
||||
id="perspective3806"
|
||||
inkscape:persp3d-origin="0.5 : 0.33333333 : 1"
|
||||
inkscape:vp_z="1 : 0.5 : 1"
|
||||
inkscape:vp_y="0 : 1000 : 0"
|
||||
inkscape:vp_x="0 : 0.5 : 1"
|
||||
sodipodi:type="inkscape:persp3d" />
|
||||
<inkscape:perspective
|
||||
id="perspective3806-3"
|
||||
inkscape:persp3d-origin="0.5 : 0.33333333 : 1"
|
||||
inkscape:vp_z="1 : 0.5 : 1"
|
||||
inkscape:vp_y="0 : 1000 : 0"
|
||||
inkscape:vp_x="0 : 0.5 : 1"
|
||||
sodipodi:type="inkscape:persp3d" />
|
||||
<inkscape:perspective
|
||||
id="perspective3835"
|
||||
inkscape:persp3d-origin="0.5 : 0.33333333 : 1"
|
||||
inkscape:vp_z="1 : 0.5 : 1"
|
||||
inkscape:vp_y="0 : 1000 : 0"
|
||||
inkscape:vp_x="0 : 0.5 : 1"
|
||||
sodipodi:type="inkscape:persp3d" />
|
||||
<inkscape:perspective
|
||||
id="perspective3614"
|
||||
inkscape:persp3d-origin="0.5 : 0.33333333 : 1"
|
||||
inkscape:vp_z="1 : 0.5 : 1"
|
||||
inkscape:vp_y="0 : 1000 : 0"
|
||||
inkscape:vp_x="0 : 0.5 : 1"
|
||||
sodipodi:type="inkscape:persp3d" />
|
||||
<inkscape:perspective
|
||||
id="perspective3614-8"
|
||||
inkscape:persp3d-origin="0.5 : 0.33333333 : 1"
|
||||
inkscape:vp_z="1 : 0.5 : 1"
|
||||
inkscape:vp_y="0 : 1000 : 0"
|
||||
inkscape:vp_x="0 : 0.5 : 1"
|
||||
sodipodi:type="inkscape:persp3d" />
|
||||
<inkscape:perspective
|
||||
id="perspective3643"
|
||||
inkscape:persp3d-origin="0.5 : 0.33333333 : 1"
|
||||
inkscape:vp_z="1 : 0.5 : 1"
|
||||
inkscape:vp_y="0 : 1000 : 0"
|
||||
inkscape:vp_x="0 : 0.5 : 1"
|
||||
sodipodi:type="inkscape:persp3d" />
|
||||
<inkscape:perspective
|
||||
id="perspective3643-3"
|
||||
inkscape:persp3d-origin="0.5 : 0.33333333 : 1"
|
||||
inkscape:vp_z="1 : 0.5 : 1"
|
||||
inkscape:vp_y="0 : 1000 : 0"
|
||||
inkscape:vp_x="0 : 0.5 : 1"
|
||||
sodipodi:type="inkscape:persp3d" />
|
||||
<inkscape:perspective
|
||||
id="perspective3672"
|
||||
inkscape:persp3d-origin="0.5 : 0.33333333 : 1"
|
||||
inkscape:vp_z="1 : 0.5 : 1"
|
||||
inkscape:vp_y="0 : 1000 : 0"
|
||||
inkscape:vp_x="0 : 0.5 : 1"
|
||||
sodipodi:type="inkscape:persp3d" />
|
||||
<inkscape:perspective
|
||||
id="perspective3672-5"
|
||||
inkscape:persp3d-origin="0.5 : 0.33333333 : 1"
|
||||
inkscape:vp_z="1 : 0.5 : 1"
|
||||
inkscape:vp_y="0 : 1000 : 0"
|
||||
inkscape:vp_x="0 : 0.5 : 1"
|
||||
sodipodi:type="inkscape:persp3d" />
|
||||
<inkscape:perspective
|
||||
id="perspective3701"
|
||||
inkscape:persp3d-origin="0.5 : 0.33333333 : 1"
|
||||
inkscape:vp_z="1 : 0.5 : 1"
|
||||
inkscape:vp_y="0 : 1000 : 0"
|
||||
inkscape:vp_x="0 : 0.5 : 1"
|
||||
sodipodi:type="inkscape:persp3d" />
|
||||
<inkscape:perspective
|
||||
id="perspective3701-8"
|
||||
inkscape:persp3d-origin="0.5 : 0.33333333 : 1"
|
||||
inkscape:vp_z="1 : 0.5 : 1"
|
||||
inkscape:vp_y="0 : 1000 : 0"
|
||||
inkscape:vp_x="0 : 0.5 : 1"
|
||||
sodipodi:type="inkscape:persp3d" />
|
||||
<inkscape:perspective
|
||||
id="perspective3746"
|
||||
inkscape:persp3d-origin="0.5 : 0.33333333 : 1"
|
||||
inkscape:vp_z="1 : 0.5 : 1"
|
||||
inkscape:vp_y="0 : 1000 : 0"
|
||||
inkscape:vp_x="0 : 0.5 : 1"
|
||||
sodipodi:type="inkscape:persp3d" />
|
||||
<pattern
|
||||
patternTransform="matrix(0.67643728,-0.81829155,2.4578314,1.8844554,-26.450606,18.294947)"
|
||||
id="pattern5231"
|
||||
xlink:href="#Strips1_1-4"
|
||||
inkscape:collect="always" />
|
||||
<inkscape:perspective
|
||||
id="perspective5224"
|
||||
inkscape:persp3d-origin="0.5 : 0.33333333 : 1"
|
||||
inkscape:vp_z="1 : 0.5 : 1"
|
||||
inkscape:vp_y="0 : 1000 : 0"
|
||||
inkscape:vp_x="0 : 0.5 : 1"
|
||||
sodipodi:type="inkscape:persp3d" />
|
||||
<pattern
|
||||
inkscape:stockid="Stripes 1:1"
|
||||
id="Strips1_1-4"
|
||||
patternTransform="matrix(0.66772843,-1.0037085,2.4261878,2.3114548,3.4760987,3.534923)"
|
||||
height="1"
|
||||
width="2"
|
||||
patternUnits="userSpaceOnUse"
|
||||
inkscape:collect="always">
|
||||
<rect
|
||||
id="rect4483-4"
|
||||
height="2"
|
||||
width="1"
|
||||
y="-0.5"
|
||||
x="0"
|
||||
style="fill:black;stroke:none" />
|
||||
</pattern>
|
||||
<inkscape:perspective
|
||||
id="perspective5224-9"
|
||||
inkscape:persp3d-origin="0.5 : 0.33333333 : 1"
|
||||
inkscape:vp_z="1 : 0.5 : 1"
|
||||
inkscape:vp_y="0 : 1000 : 0"
|
||||
inkscape:vp_x="0 : 0.5 : 1"
|
||||
sodipodi:type="inkscape:persp3d" />
|
||||
<pattern
|
||||
patternTransform="matrix(0.66772843,-1.0037085,2.4261878,2.3114548,39.618381,8.9692804)"
|
||||
id="pattern5231-4"
|
||||
xlink:href="#Strips1_1-6"
|
||||
inkscape:collect="always" />
|
||||
<inkscape:perspective
|
||||
id="perspective5224-3"
|
||||
inkscape:persp3d-origin="0.5 : 0.33333333 : 1"
|
||||
inkscape:vp_z="1 : 0.5 : 1"
|
||||
inkscape:vp_y="0 : 1000 : 0"
|
||||
inkscape:vp_x="0 : 0.5 : 1"
|
||||
sodipodi:type="inkscape:persp3d" />
|
||||
<pattern
|
||||
inkscape:stockid="Stripes 1:1"
|
||||
id="Strips1_1-6"
|
||||
patternTransform="matrix(0.66772843,-1.0037085,2.4261878,2.3114548,3.4760987,3.534923)"
|
||||
height="1"
|
||||
width="2"
|
||||
patternUnits="userSpaceOnUse"
|
||||
inkscape:collect="always">
|
||||
<rect
|
||||
id="rect4483-0"
|
||||
height="2"
|
||||
width="1"
|
||||
y="-0.5"
|
||||
x="0"
|
||||
style="fill:black;stroke:none" />
|
||||
</pattern>
|
||||
<pattern
|
||||
patternTransform="matrix(0.66513382,-1.0631299,2.4167603,2.4482973,-49.762569,2.9546807)"
|
||||
id="pattern5296"
|
||||
xlink:href="#pattern5231-3"
|
||||
inkscape:collect="always" />
|
||||
<inkscape:perspective
|
||||
id="perspective5288"
|
||||
inkscape:persp3d-origin="0.5 : 0.33333333 : 1"
|
||||
inkscape:vp_z="1 : 0.5 : 1"
|
||||
inkscape:vp_y="0 : 1000 : 0"
|
||||
inkscape:vp_x="0 : 0.5 : 1"
|
||||
sodipodi:type="inkscape:persp3d" />
|
||||
<pattern
|
||||
patternTransform="matrix(0.66772843,-1.0037085,2.4261878,2.3114548,-26.336284,10.887197)"
|
||||
id="pattern5231-3"
|
||||
xlink:href="#Strips1_1-4-3"
|
||||
inkscape:collect="always" />
|
||||
<pattern
|
||||
inkscape:stockid="Stripes 1:1"
|
||||
id="Strips1_1-4-3"
|
||||
patternTransform="matrix(0.66772843,-1.0037085,2.4261878,2.3114548,3.4760987,3.534923)"
|
||||
height="1"
|
||||
width="2"
|
||||
patternUnits="userSpaceOnUse"
|
||||
inkscape:collect="always">
|
||||
<rect
|
||||
id="rect4483-4-6"
|
||||
height="2"
|
||||
width="1"
|
||||
y="-0.5"
|
||||
x="0"
|
||||
style="fill:black;stroke:none" />
|
||||
</pattern>
|
||||
<pattern
|
||||
patternTransform="matrix(0.42844886,-0.62155849,1.5567667,1.431396,27.948414,13.306456)"
|
||||
id="pattern5330"
|
||||
xlink:href="#Strips1_1-9"
|
||||
inkscape:collect="always" />
|
||||
<inkscape:perspective
|
||||
id="perspective5323"
|
||||
inkscape:persp3d-origin="0.5 : 0.33333333 : 1"
|
||||
inkscape:vp_z="1 : 0.5 : 1"
|
||||
inkscape:vp_y="0 : 1000 : 0"
|
||||
inkscape:vp_x="0 : 0.5 : 1"
|
||||
sodipodi:type="inkscape:persp3d" />
|
||||
<pattern
|
||||
inkscape:stockid="Stripes 1:1"
|
||||
id="Strips1_1-9"
|
||||
patternTransform="matrix(0.66772843,-1.0037085,2.4261878,2.3114548,3.4760987,3.534923)"
|
||||
height="1"
|
||||
width="2"
|
||||
patternUnits="userSpaceOnUse"
|
||||
inkscape:collect="always">
|
||||
<rect
|
||||
id="rect4483-3"
|
||||
height="2"
|
||||
width="1"
|
||||
y="-0.5"
|
||||
x="0"
|
||||
style="fill:black;stroke:none" />
|
||||
</pattern>
|
||||
<inkscape:perspective
|
||||
id="perspective5361"
|
||||
inkscape:persp3d-origin="0.5 : 0.33333333 : 1"
|
||||
inkscape:vp_z="1 : 0.5 : 1"
|
||||
inkscape:vp_y="0 : 1000 : 0"
|
||||
inkscape:vp_x="0 : 0.5 : 1"
|
||||
sodipodi:type="inkscape:persp3d" />
|
||||
<inkscape:perspective
|
||||
id="perspective5383"
|
||||
inkscape:persp3d-origin="0.5 : 0.33333333 : 1"
|
||||
inkscape:vp_z="1 : 0.5 : 1"
|
||||
inkscape:vp_y="0 : 1000 : 0"
|
||||
inkscape:vp_x="0 : 0.5 : 1"
|
||||
sodipodi:type="inkscape:persp3d" />
|
||||
<inkscape:perspective
|
||||
id="perspective5411"
|
||||
inkscape:persp3d-origin="0.5 : 0.33333333 : 1"
|
||||
inkscape:vp_z="1 : 0.5 : 1"
|
||||
inkscape:vp_y="0 : 1000 : 0"
|
||||
inkscape:vp_x="0 : 0.5 : 1"
|
||||
sodipodi:type="inkscape:persp3d" />
|
||||
<linearGradient
|
||||
inkscape:collect="always"
|
||||
xlink:href="#linearGradient3681"
|
||||
id="linearGradient3687"
|
||||
x1="37.89756"
|
||||
y1="41.087898"
|
||||
x2="4.0605712"
|
||||
y2="40.168594"
|
||||
gradientUnits="userSpaceOnUse" />
|
||||
<linearGradient
|
||||
inkscape:collect="always"
|
||||
xlink:href="#linearGradient3681"
|
||||
id="linearGradient3695"
|
||||
x1="31.777767"
|
||||
y1="40.24213"
|
||||
x2="68.442062"
|
||||
y2="54.041203"
|
||||
gradientUnits="userSpaceOnUse"
|
||||
gradientTransform="matrix(0.25023482,-0.66040068,0.68751357,0.24036653,-8.7488565,43.149938)" />
|
||||
<radialGradient
|
||||
inkscape:collect="always"
|
||||
xlink:href="#linearGradient12512"
|
||||
id="radialGradient278"
|
||||
gradientUnits="userSpaceOnUse"
|
||||
cx="55"
|
||||
cy="125"
|
||||
fx="55"
|
||||
fy="125"
|
||||
r="14.375" />
|
||||
<linearGradient
|
||||
id="linearGradient12512">
|
||||
<stop
|
||||
style="stop-color:#ffffff;stop-opacity:1.0000000;"
|
||||
offset="0.0000000"
|
||||
id="stop12513" />
|
||||
<stop
|
||||
style="stop-color:#fff520;stop-opacity:0.89108908;"
|
||||
offset="0.50000000"
|
||||
id="stop12517" />
|
||||
<stop
|
||||
style="stop-color:#fff300;stop-opacity:0.0000000;"
|
||||
offset="1.0000000"
|
||||
id="stop12514" />
|
||||
</linearGradient>
|
||||
<radialGradient
|
||||
r="14.375"
|
||||
fy="125"
|
||||
fx="55"
|
||||
cy="125"
|
||||
cx="55"
|
||||
gradientUnits="userSpaceOnUse"
|
||||
id="radialGradient4017"
|
||||
xlink:href="#linearGradient12512"
|
||||
inkscape:collect="always" />
|
||||
<linearGradient
|
||||
inkscape:collect="always"
|
||||
xlink:href="#linearGradient4044"
|
||||
id="linearGradient4060"
|
||||
x1="15.78776"
|
||||
y1="50.394047"
|
||||
x2="27.641447"
|
||||
y2="39.95837"
|
||||
gradientUnits="userSpaceOnUse" />
|
||||
<radialGradient
|
||||
inkscape:collect="always"
|
||||
xlink:href="#linearGradient12512-2"
|
||||
id="radialGradient278-5"
|
||||
gradientUnits="userSpaceOnUse"
|
||||
cx="55"
|
||||
cy="125"
|
||||
fx="55"
|
||||
fy="125"
|
||||
r="14.375" />
|
||||
<linearGradient
|
||||
id="linearGradient12512-2">
|
||||
<stop
|
||||
style="stop-color:#ffffff;stop-opacity:1.0000000;"
|
||||
offset="0.0000000"
|
||||
id="stop12513-3" />
|
||||
<stop
|
||||
style="stop-color:#fff520;stop-opacity:0.89108908;"
|
||||
offset="0.50000000"
|
||||
id="stop12517-1" />
|
||||
<stop
|
||||
style="stop-color:#fff300;stop-opacity:0.0000000;"
|
||||
offset="1.0000000"
|
||||
id="stop12514-6" />
|
||||
</linearGradient>
|
||||
<radialGradient
|
||||
r="14.375"
|
||||
fy="125"
|
||||
fx="55"
|
||||
cy="125"
|
||||
cx="55"
|
||||
gradientUnits="userSpaceOnUse"
|
||||
id="radialGradient4078"
|
||||
xlink:href="#linearGradient12512-2"
|
||||
inkscape:collect="always" />
|
||||
<linearGradient
|
||||
inkscape:collect="always"
|
||||
xlink:href="#linearGradient3960"
|
||||
id="linearGradient3966"
|
||||
x1="37.758171"
|
||||
y1="57.301327"
|
||||
x2="21.860462"
|
||||
y2="22.615412"
|
||||
gradientUnits="userSpaceOnUse" />
|
||||
<linearGradient
|
||||
inkscape:collect="always"
|
||||
id="linearGradient3960">
|
||||
<stop
|
||||
style="stop-color:#c4a000;stop-opacity:1"
|
||||
offset="0"
|
||||
id="stop3962" />
|
||||
<stop
|
||||
style="stop-color:#fce94f;stop-opacity:1"
|
||||
offset="1"
|
||||
id="stop3964" />
|
||||
</linearGradient>
|
||||
<radialGradient
|
||||
inkscape:collect="always"
|
||||
xlink:href="#linearGradient4432"
|
||||
id="radialGradient4440"
|
||||
cx="55"
|
||||
cy="125"
|
||||
fx="55"
|
||||
fy="125"
|
||||
r="20.367043"
|
||||
gradientTransform="matrix(0.41658223,-0.00547178,0.00729572,0.55544286,-40.222685,-44.926056)"
|
||||
gradientUnits="userSpaceOnUse" />
|
||||
<linearGradient
|
||||
gradientTransform="matrix(1.383847,0,0,1.383847,-144.55537,-20.287334)"
|
||||
y2="23.429474"
|
||||
x2="36.991264"
|
||||
y1="58.615189"
|
||||
x1="18.969967"
|
||||
gradientUnits="userSpaceOnUse"
|
||||
id="linearGradient3076-5"
|
||||
xlink:href="#linearGradient3960"
|
||||
inkscape:collect="always" />
|
||||
<clipPath
|
||||
clipPathUnits="userSpaceOnUse"
|
||||
id="clipPath1070">
|
||||
<path
|
||||
style="fill:#555753;stroke:none;stroke-width:1px;stroke-linecap:butt;stroke-linejoin:miter;stroke-opacity:1"
|
||||
d="m -88.459092,0.94349885 11.448734,12.27337715 7.071068,20.05612 c 0,0 -4.242641,22.241722 -4.499771,22.884547 -0.257129,0.642824 -13.885006,11.956533 -13.885006,11.956533 l -22.755983,2.185603 -20.69894,-1.671344 -9.64237,-7.713892 z"
|
||||
id="path1072"
|
||||
inkscape:connector-curvature="0" />
|
||||
</clipPath>
|
||||
</defs>
|
||||
<sodipodi:namedview
|
||||
id="base"
|
||||
pagecolor="#ffffff"
|
||||
bordercolor="#666666"
|
||||
borderopacity="1.0"
|
||||
inkscape:pageopacity="0.0"
|
||||
inkscape:pageshadow="2"
|
||||
inkscape:zoom="5.4999999"
|
||||
inkscape:cx="-5.300599"
|
||||
inkscape:cy="18.864338"
|
||||
inkscape:current-layer="layer1"
|
||||
showgrid="true"
|
||||
inkscape:document-units="px"
|
||||
inkscape:grid-bbox="true"
|
||||
inkscape:snap-bbox="true"
|
||||
inkscape:bbox-paths="true"
|
||||
inkscape:bbox-nodes="true"
|
||||
inkscape:snap-bbox-edge-midpoints="true"
|
||||
inkscape:snap-bbox-midpoints="true"
|
||||
inkscape:object-paths="true"
|
||||
inkscape:object-nodes="true"
|
||||
inkscape:window-width="1920"
|
||||
inkscape:window-height="1051"
|
||||
inkscape:window-x="1791"
|
||||
inkscape:window-y="-9"
|
||||
inkscape:window-maximized="1"
|
||||
inkscape:snap-grids="false"
|
||||
inkscape:snap-global="false">
|
||||
<inkscape:grid
|
||||
type="xygrid"
|
||||
id="grid3051"
|
||||
empspacing="2"
|
||||
visible="true"
|
||||
enabled="true"
|
||||
snapvisiblegridlinesonly="true" />
|
||||
</sodipodi:namedview>
|
||||
<metadata
|
||||
id="metadata2821">
|
||||
<rdf:RDF>
|
||||
<cc:Work
|
||||
rdf:about="">
|
||||
<dc:format>image/svg+xml</dc:format>
|
||||
<dc:type
|
||||
rdf:resource="http://purl.org/dc/dcmitype/StillImage" />
|
||||
<dc:title />
|
||||
<dc:creator>
|
||||
<cc:Agent>
|
||||
<dc:title>[Przemo Firszt]</dc:title>
|
||||
</cc:Agent>
|
||||
</dc:creator>
|
||||
<dc:title>fem-material</dc:title>
|
||||
<dc:date>2015-07-28</dc:date>
|
||||
<dc:relation>http://www.freecadweb.org/wiki/index.php?title=Artwork</dc:relation>
|
||||
<dc:publisher>
|
||||
<cc:Agent>
|
||||
<dc:title>FreeCAD</dc:title>
|
||||
</cc:Agent>
|
||||
</dc:publisher>
|
||||
<dc:identifier>FreeCAD/src/Mod/</dc:identifier>
|
||||
<dc:rights>
|
||||
<cc:Agent>
|
||||
<dc:title>FreeCAD LGPL2+</dc:title>
|
||||
</cc:Agent>
|
||||
</dc:rights>
|
||||
<cc:license>https://www.gnu.org/copyleft/lesser.html</cc:license>
|
||||
<dc:contributor>
|
||||
<cc:Agent>
|
||||
<dc:title>[agryson] Alexander Gryson</dc:title>
|
||||
</cc:Agent>
|
||||
</dc:contributor>
|
||||
</cc:Work>
|
||||
</rdf:RDF>
|
||||
</metadata>
|
||||
<g
|
||||
id="layer1"
|
||||
inkscape:label="Layer 1"
|
||||
inkscape:groupmode="layer">
|
||||
<g
|
||||
id="g1030"
|
||||
clip-path="url(#clipPath1070)"
|
||||
transform="matrix(-1,0,0,1,-74.303836,-3.0089371)">
|
||||
<circle
|
||||
id="path4042-8"
|
||||
style="fill:url(#linearGradient3076-5);fill-opacity:1;stroke:#302b00;stroke-width:2;stroke-miterlimit:4;stroke-dasharray:none;stroke-dashoffset:0"
|
||||
cx="-106.30383"
|
||||
cy="35.008938"
|
||||
r="29" />
|
||||
<g
|
||||
id="g1006">
|
||||
<circle
|
||||
r="27"
|
||||
cy="35.008938"
|
||||
cx="-106.30383"
|
||||
style="fill:none;stroke:#fce94f;stroke-width:2;stroke-miterlimit:4;stroke-dasharray:none;stroke-dashoffset:0"
|
||||
id="path4042-0-2" />
|
||||
<circle
|
||||
r="29"
|
||||
cy="35.008938"
|
||||
cx="-106.30383"
|
||||
style="fill:none;stroke:#302b00;stroke-width:2;stroke-miterlimit:4;stroke-dasharray:none;stroke-dashoffset:0"
|
||||
id="path4042-3-2" />
|
||||
</g>
|
||||
</g>
|
||||
<ellipse
|
||||
cy="24.203362"
|
||||
cx="-16.398699"
|
||||
style="color:#000000;display:block;visibility:visible;fill:url(#radialGradient4440);fill-opacity:1;fill-rule:nonzero;stroke:none;stroke-width:0.85062206;marker:none"
|
||||
id="path12511"
|
||||
transform="matrix(-0.99872946,-0.05039302,-0.05039302,0.99872946,0,0)"
|
||||
inkscape:export-filename="/home/jimmac/ximian_art/icons/nautilus/suse93/stock_new-16.png"
|
||||
inkscape:export-xdpi="33.852203"
|
||||
inkscape:export-ydpi="33.852203"
|
||||
rx="8"
|
||||
ry="11.961311" />
|
||||
<ellipse
|
||||
ry="5.8596506"
|
||||
rx="27.434761"
|
||||
cy="-11.644531"
|
||||
cx="-45.06081"
|
||||
style="fill:#fce94f;stroke:#302b00;stroke-width:2.1268518;stroke-linecap:round;stroke-linejoin:round;stroke-miterlimit:4.5;stroke-dasharray:none;stroke-dashoffset:20.39999962;stroke-opacity:1"
|
||||
id="path2994"
|
||||
transform="matrix(-0.66077367,-0.75058521,-0.75058521,0.66077367,0,0)" />
|
||||
<g
|
||||
id="g929"
|
||||
transform="translate(1.7844006,-0.37678835)">
|
||||
<path
|
||||
sodipodi:nodetypes="ccccc"
|
||||
inkscape:connector-curvature="0"
|
||||
id="path2672"
|
||||
d="M 29.13582,18.494191 42.26632,6.9348259 47.145866,12.477594 33.796524,24.229615 C 31.270776,23.145378 29.410249,21.35914 29.13582,18.494191 Z"
|
||||
style="fill:#729fcf;stroke:#0b1521;stroke-width:2;stroke-linecap:butt;stroke-linejoin:round;stroke-miterlimit:4;stroke-dasharray:none;stroke-opacity:1" />
|
||||
<ellipse
|
||||
transform="matrix(-0.66077367,-0.75058521,-0.75058521,0.66077367,0,0)"
|
||||
ry="2.3864655"
|
||||
rx="3.6330051"
|
||||
cy="-27.219051"
|
||||
cx="-36.860275"
|
||||
id="path2725"
|
||||
style="opacity:1;fill:#729fcf;fill-opacity:1;fill-rule:nonzero;stroke:#0b1521;stroke-width:2;stroke-linejoin:round;stroke-miterlimit:4;stroke-dasharray:none" />
|
||||
<path
|
||||
inkscape:connector-curvature="0"
|
||||
id="path2727"
|
||||
d="m 38.051112,16.763386 1.269735,-4.485794 -3.928998,0.919075"
|
||||
style="fill:none;stroke:#0b1521;stroke-width:2;stroke-linecap:round;stroke-linejoin:round;stroke-miterlimit:4;stroke-dasharray:none;stroke-opacity:1" />
|
||||
<path
|
||||
inkscape:connector-curvature="0"
|
||||
id="path2727-5"
|
||||
d="m 33.289904,21.032974 1.269732,-4.485794 -3.928998,0.919076"
|
||||
style="fill:none;stroke:#0b1521;stroke-width:2;stroke-linecap:round;stroke-linejoin:round;stroke-miterlimit:4;stroke-dasharray:none;stroke-opacity:1" />
|
||||
<path
|
||||
sodipodi:nodetypes="ccccc"
|
||||
inkscape:connector-curvature="0"
|
||||
id="path2672-0"
|
||||
d="M 39.632328,28.739999 52.526725,17.388486 57.125796,22.612657 44.016493,34.153362 C 41.715452,33.03536 39.914754,31.527247 39.632328,28.739999 Z"
|
||||
style="fill:#729fcf;stroke:#0b1521;stroke-width:2;stroke-linecap:butt;stroke-linejoin:round;stroke-miterlimit:4;stroke-dasharray:none;stroke-opacity:1" />
|
||||
<ellipse
|
||||
transform="matrix(-0.66077367,-0.75058521,-0.75058521,0.66077367,0,0)"
|
||||
ry="2.330615"
|
||||
rx="3.4292362"
|
||||
cy="-27.36412"
|
||||
cx="-51.272247"
|
||||
id="path2725-7"
|
||||
style="opacity:1;fill:#729fcf;fill-opacity:1;fill-rule:nonzero;stroke:#0b1521;stroke-width:2;stroke-linejoin:round;stroke-miterlimit:4;stroke-dasharray:none" />
|
||||
<path
|
||||
inkscape:connector-curvature="0"
|
||||
id="path2727-3"
|
||||
d="m 48.267466,26.904181 1.312881,-4.330186 -3.808594,0.959064"
|
||||
style="fill:none;stroke:#0b1521;stroke-width:2;stroke-linecap:round;stroke-linejoin:round;stroke-miterlimit:4;stroke-dasharray:none;stroke-opacity:1" />
|
||||
<path
|
||||
inkscape:connector-curvature="0"
|
||||
id="path2727-5-4"
|
||||
d="m 43.59034,31.095258 1.312882,-4.330187 -3.808597,0.959067"
|
||||
style="fill:none;stroke:#0b1521;stroke-width:2;stroke-linecap:round;stroke-linejoin:round;stroke-miterlimit:4;stroke-dasharray:none;stroke-opacity:1" />
|
||||
</g>
|
||||
<path
|
||||
style="fill:none;stroke:#fce94f;stroke-width:2;stroke-linecap:butt;stroke-linejoin:miter;stroke-miterlimit:4;stroke-dasharray:none;stroke-opacity:1"
|
||||
d="M 53.432979,48.750319 C 45.75619,46.435326 23.315662,25.197958 17.744599,8.2386998"
|
||||
id="path3485"
|
||||
inkscape:connector-curvature="0"
|
||||
sodipodi:nodetypes="cc" />
|
||||
</g>
|
||||
</svg>
|
||||
|
After Width: | Height: | Size: 24 KiB |
183
src/Mod/Fem/Gui/Resources/ui/MaterialReinforcement.ui
Executable file
183
src/Mod/Fem/Gui/Resources/ui/MaterialReinforcement.ui
Executable file
@@ -0,0 +1,183 @@
|
||||
<?xml version="1.0" encoding="UTF-8"?>
|
||||
<ui version="4.0">
|
||||
<class>FemMaterial</class>
|
||||
<widget class="QWidget" name="FemMaterial">
|
||||
<property name="geometry">
|
||||
<rect>
|
||||
<x>0</x>
|
||||
<y>0</y>
|
||||
<width>396</width>
|
||||
<height>448</height>
|
||||
</rect>
|
||||
</property>
|
||||
<property name="windowTitle">
|
||||
<string>FEM material</string>
|
||||
</property>
|
||||
<property name="layoutDirection">
|
||||
<enum>Qt::LeftToRight</enum>
|
||||
</property>
|
||||
<layout class="QVBoxLayout" name="verticalLayout">
|
||||
<item>
|
||||
<widget class="QGroupBox" name="groupBox_desc">
|
||||
<property name="maximumSize">
|
||||
<size>
|
||||
<width>16777215</width>
|
||||
<height>1677215</height>
|
||||
</size>
|
||||
</property>
|
||||
<property name="title">
|
||||
<string>Matrix Material</string>
|
||||
</property>
|
||||
<layout class="QVBoxLayout" name="verticalLayout_5">
|
||||
<item>
|
||||
<layout class="QGridLayout" name="gridLayout_2">
|
||||
<item row="1" column="1">
|
||||
<widget class="QComboBox" name="cb_materials_m">
|
||||
<item>
|
||||
<property name="text">
|
||||
<string>Choose</string>
|
||||
</property>
|
||||
</item>
|
||||
</widget>
|
||||
</item>
|
||||
<item row="1" column="0">
|
||||
<widget class="QLabel" name="label_2">
|
||||
<property name="text">
|
||||
<string>Material</string>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
<item row="3" column="0">
|
||||
<widget class="QLabel" name="label_3">
|
||||
<property name="text">
|
||||
<string>Name</string>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
<item row="3" column="1">
|
||||
<widget class="QLabel" name="l_name_m">
|
||||
<property name="text">
|
||||
<string>TextLabel</string>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
<item row="2" column="1">
|
||||
<widget class="QPushButton" name="pb_edit_m">
|
||||
<property name="text">
|
||||
<string>Edit</string>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
<item row="2" column="0">
|
||||
<widget class="QLabel" name="label_4">
|
||||
<property name="text">
|
||||
<string>Properties</string>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
</layout>
|
||||
</item>
|
||||
<item>
|
||||
<widget class="QLabel" name="l_description_m">
|
||||
<property name="text">
|
||||
<string>Description</string>
|
||||
</property>
|
||||
<property name="wordWrap">
|
||||
<bool>true</bool>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
</layout>
|
||||
</widget>
|
||||
</item>
|
||||
<item>
|
||||
<widget class="QGroupBox" name="groupBox_desc_2">
|
||||
<property name="maximumSize">
|
||||
<size>
|
||||
<width>16777215</width>
|
||||
<height>1677215</height>
|
||||
</size>
|
||||
</property>
|
||||
<property name="title">
|
||||
<string>Reinforcement Material</string>
|
||||
</property>
|
||||
<layout class="QVBoxLayout" name="verticalLayout_6">
|
||||
<item>
|
||||
<layout class="QGridLayout" name="gridLayout_3">
|
||||
<item row="1" column="1">
|
||||
<widget class="QComboBox" name="cb_materials_r">
|
||||
<item>
|
||||
<property name="text">
|
||||
<string>Choose</string>
|
||||
</property>
|
||||
</item>
|
||||
</widget>
|
||||
</item>
|
||||
<item row="1" column="0">
|
||||
<widget class="QLabel" name="label_6">
|
||||
<property name="text">
|
||||
<string>Material</string>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
<item row="3" column="0">
|
||||
<widget class="QLabel" name="label_7">
|
||||
<property name="text">
|
||||
<string>Name</string>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
<item row="3" column="1">
|
||||
<widget class="QLabel" name="l_name_r">
|
||||
<property name="text">
|
||||
<string>TextLabel</string>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
<item row="2" column="1">
|
||||
<widget class="QPushButton" name="pb_edit_r">
|
||||
<property name="text">
|
||||
<string>Edit</string>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
<item row="2" column="0">
|
||||
<widget class="QLabel" name="label_8">
|
||||
<property name="text">
|
||||
<string>Properties</string>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
</layout>
|
||||
</item>
|
||||
<item>
|
||||
<widget class="QLabel" name="l_description_r">
|
||||
<property name="text">
|
||||
<string>Description</string>
|
||||
</property>
|
||||
<property name="wordWrap">
|
||||
<bool>true</bool>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
</layout>
|
||||
</widget>
|
||||
</item>
|
||||
<item>
|
||||
<spacer name="verticalSpacer_2">
|
||||
<property name="orientation">
|
||||
<enum>Qt::Vertical</enum>
|
||||
</property>
|
||||
<property name="sizeHint" stdset="0">
|
||||
<size>
|
||||
<width>20</width>
|
||||
<height>40</height>
|
||||
</size>
|
||||
</property>
|
||||
</spacer>
|
||||
</item>
|
||||
</layout>
|
||||
</widget>
|
||||
<resources/>
|
||||
<connections/>
|
||||
</ui>
|
||||
@@ -87,6 +87,7 @@ Gui::ToolBarItem* Workbench::setupToolBars() const
|
||||
<< "FEM_MaterialSolid"
|
||||
<< "FEM_MaterialFluid"
|
||||
<< "FEM_MaterialMechanicalNonlinear"
|
||||
<< "FEM_MaterialReinforced"
|
||||
<< "FEM_MaterialEditor"
|
||||
<< "Separator"
|
||||
<< "FEM_ElementGeometry1D"
|
||||
@@ -190,6 +191,7 @@ Gui::MenuItem* Workbench::setupMenuBar() const
|
||||
*material << "FEM_MaterialSolid"
|
||||
<< "FEM_MaterialFluid"
|
||||
<< "FEM_MaterialMechanicalNonlinear"
|
||||
<< "FEM_MaterialReinforced"
|
||||
<< "FEM_MaterialEditor";
|
||||
|
||||
Gui::MenuItem* elec = new Gui::MenuItem;
|
||||
|
||||
@@ -372,6 +372,21 @@ def makeMaterialMechanicalNonlinear(
|
||||
return obj
|
||||
|
||||
|
||||
def makeMaterialReinforced(
|
||||
doc,
|
||||
name="MaterialReinforced"
|
||||
):
|
||||
'''makeMaterialReinforced(document, [matrix_material], [reinforcement_material], [name]):
|
||||
creates a reinforced material object'''
|
||||
obj = doc.addObject("App::MaterialObjectPython", name)
|
||||
from femobjects import _FemMaterialReinforced
|
||||
_FemMaterialReinforced._FemMaterialReinforced(obj)
|
||||
if FreeCAD.GuiUp:
|
||||
from femguiobjects import _ViewProviderFemMaterialReinforced
|
||||
_ViewProviderFemMaterialReinforced._ViewProviderFemMaterialReinforced(obj.ViewObject)
|
||||
return obj
|
||||
|
||||
|
||||
def makeMaterialSolid(
|
||||
doc,
|
||||
name="MechanicalSolidMaterial"
|
||||
|
||||
@@ -126,7 +126,9 @@ gf()
|
||||
./bin/FreeCADCmd --run-test "femtest.testobject.TestObjectType.test_femobjects_derivedfromstd"
|
||||
./bin/FreeCADCmd --run-test "femtest.testresult.TestResult.test_read_frd_massflow_networkpressure"
|
||||
./bin/FreeCADCmd --run-test "femtest.testresult.TestResult.test_stress_von_mises"
|
||||
./bin/FreeCADCmd --run-test "femtest.testresult.TestResult.test_stress_principal"
|
||||
./bin/FreeCADCmd --run-test "femtest.testresult.TestResult.test_stress_principal_std"
|
||||
./bin/FreeCADCmd --run-test "femtest.testresult.TestResult.test_stress_principal_reinforced"
|
||||
./bin/FreeCADCmd --run-test "femtest.testresult.TestResult.test_rho"
|
||||
./bin/FreeCADCmd --run-test "femtest.testresult.TestResult.test_disp_abs"
|
||||
./bin/FreeCADCmd --run-test "femtest.testsolverframework.TestSolverFrameWork.test_solver_framework"
|
||||
|
||||
@@ -214,7 +216,13 @@ import unittest
|
||||
unittest.TextTestRunner().run(unittest.TestLoader().loadTestsFromName("femtest.testresult.TestResult.test_stress_von_mises"))
|
||||
|
||||
import unittest
|
||||
unittest.TextTestRunner().run(unittest.TestLoader().loadTestsFromName("femtest.testresult.TestResult.test_stress_principal"))
|
||||
unittest.TextTestRunner().run(unittest.TestLoader().loadTestsFromName("femtest.testresult.TestResult.test_stress_principal_std"))
|
||||
|
||||
import unittest
|
||||
unittest.TextTestRunner().run(unittest.TestLoader().loadTestsFromName("femtest.testresult.TestResult.test_stress_principal_reinforced"))
|
||||
|
||||
import unittest
|
||||
unittest.TextTestRunner().run(unittest.TestLoader().loadTestsFromName("femtest.testresult.TestResult.test_rho"))
|
||||
|
||||
import unittest
|
||||
unittest.TextTestRunner().run(unittest.TestLoader().loadTestsFromName("femtest.testresult.TestResult.test_disp_abs"))
|
||||
|
||||
@@ -665,6 +665,37 @@ class _CommandFemMaterialMechanicalNonlinear(CommandManager):
|
||||
FreeCAD.ActiveDocument.recompute()
|
||||
|
||||
|
||||
class _CommandFemMaterialReinforced(CommandManager):
|
||||
"The FEM_MaterialReinforced command definition"
|
||||
def __init__(self):
|
||||
super(_CommandFemMaterialReinforced, self).__init__()
|
||||
self.resources = {
|
||||
'Pixmap': 'fem-material-reinforced',
|
||||
'MenuText': QtCore.QT_TRANSLATE_NOOP(
|
||||
"FEM_MaterialReinforced",
|
||||
"Reinforced material (concrete)"
|
||||
),
|
||||
'Accel': "M, M",
|
||||
'ToolTip': QtCore.QT_TRANSLATE_NOOP(
|
||||
"FEM_MaterialReinforced",
|
||||
"Creates a material for reinforced matrix material such as concrete"
|
||||
)
|
||||
}
|
||||
self.is_active = 'with_analysis'
|
||||
|
||||
def Activated(self):
|
||||
FreeCAD.ActiveDocument.openTransaction("Create Reinforced Material")
|
||||
FreeCADGui.addModule("ObjectsFem")
|
||||
FreeCADGui.doCommand(
|
||||
"FemGui.getActiveAnalysis().addObject(ObjectsFem."
|
||||
"makeMaterialReinforced(FreeCAD.ActiveDocument, 'ReinforcedMaterial'))"
|
||||
)
|
||||
FreeCADGui.doCommand(
|
||||
"FreeCADGui.ActiveDocument.setEdit(FreeCAD.ActiveDocument.ActiveObject.Name)"
|
||||
)
|
||||
FreeCAD.ActiveDocument.recompute()
|
||||
|
||||
|
||||
class _CommandFemMaterialSolid(CommandManager):
|
||||
"The FEM_MaterialSolid command definition"
|
||||
def __init__(self):
|
||||
@@ -1296,6 +1327,10 @@ FreeCADGui.addCommand(
|
||||
'FEM_MaterialMechanicalNonlinear',
|
||||
_CommandFemMaterialMechanicalNonlinear()
|
||||
)
|
||||
FreeCADGui.addCommand(
|
||||
'FEM_MaterialReinforced',
|
||||
_CommandFemMaterialReinforced()
|
||||
)
|
||||
FreeCADGui.addCommand(
|
||||
'FEM_MaterialSolid',
|
||||
_CommandFemMaterialSolid()
|
||||
|
||||
@@ -75,6 +75,7 @@ def run_all():
|
||||
run_ccx_cantileverfaceload()
|
||||
run_ccx_cantilevernodeload()
|
||||
run_ccx_cantileverprescribeddisplacement()
|
||||
run_rcwall2d()
|
||||
|
||||
|
||||
def run_ccx_cantileverfaceload(solver=None, base_name=None):
|
||||
@@ -119,6 +120,20 @@ def run_ccx_cantileverprescribeddisplacement(solver=None, base_name=None):
|
||||
return doc
|
||||
|
||||
|
||||
def run_rcwall2d(solver=None, base_name=None):
|
||||
|
||||
from femexamples.rc_wall_2d import setup_rcwall2d as setup
|
||||
doc = setup()
|
||||
|
||||
if base_name is None:
|
||||
base_name = 'RC_FIB_Wall_2D'
|
||||
if solver is not None:
|
||||
base_name += ('_' + solver)
|
||||
run_analysis(doc, base_name)
|
||||
|
||||
return doc
|
||||
|
||||
|
||||
'''
|
||||
from femexamples.manager import *
|
||||
|
||||
@@ -132,4 +147,6 @@ doc = run_ccx_cantilevernodeload('calculix')
|
||||
doc = run_ccx_cantilevernodeload('ccxtools')
|
||||
doc = run_ccx_cantilevernodeload('z88')
|
||||
|
||||
doc = run_rcwall2d()
|
||||
|
||||
'''
|
||||
|
||||
1343
src/Mod/Fem/femexamples/meshes/mesh_rc_wall_2d_tria6.py
Normal file
1343
src/Mod/Fem/femexamples/meshes/mesh_rc_wall_2d_tria6.py
Normal file
File diff suppressed because it is too large
Load Diff
165
src/Mod/Fem/femexamples/rc_wall_2d.py
Normal file
165
src/Mod/Fem/femexamples/rc_wall_2d.py
Normal file
@@ -0,0 +1,165 @@
|
||||
# ***************************************************************************
|
||||
# * Copyright (c) 2019 Bernd Hahnebach <bernd@bimstatik.org> *
|
||||
# * *
|
||||
# * This file is part of the FreeCAD CAx development system. *
|
||||
# * *
|
||||
# * 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. *
|
||||
# * *
|
||||
# * FreeCAD 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 FreeCAD; if not, write to the Free Software *
|
||||
# * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 *
|
||||
# * USA *
|
||||
# * *
|
||||
# ***************************************************************************
|
||||
|
||||
|
||||
import FreeCAD
|
||||
import ObjectsFem
|
||||
import Fem
|
||||
|
||||
mesh_name = 'Mesh' # needs to be Mesh to work with unit tests
|
||||
|
||||
|
||||
def init_doc(doc=None):
|
||||
if doc is None:
|
||||
doc = FreeCAD.newDocument()
|
||||
return doc
|
||||
|
||||
|
||||
def setup_rcwall2d(doc=None, solver='ccxtools'):
|
||||
# setup reinfoced wall in 2D
|
||||
|
||||
if doc is None:
|
||||
doc = init_doc()
|
||||
|
||||
# part
|
||||
from FreeCAD import Vector as vec
|
||||
import Part
|
||||
from Part import makeLine as ln
|
||||
|
||||
v1 = vec(0, -2000, 0)
|
||||
v2 = vec(500, -2000, 0)
|
||||
v3 = vec(500, 0, 0)
|
||||
v4 = vec(3500, 0, 0)
|
||||
v5 = vec(3500, -2000, 0)
|
||||
v6 = vec(4000, -2000, 0)
|
||||
v7 = vec(4000, 2000, 0)
|
||||
v8 = vec(0, 2000, 0)
|
||||
l1 = ln(v1, v2)
|
||||
l2 = ln(v2, v3)
|
||||
l3 = ln(v3, v4)
|
||||
l4 = ln(v4, v5)
|
||||
l5 = ln(v5, v6)
|
||||
l6 = ln(v6, v7)
|
||||
l7 = ln(v7, v8)
|
||||
l8 = ln(v8, v1)
|
||||
rcwall = doc.addObject("Part::Feature", "FIB_Wall")
|
||||
rcwall.Shape = Part.Face(Part.Wire([l1, l2, l3, l4, l5, l6, l7, l8]))
|
||||
|
||||
# analysis
|
||||
analysis = ObjectsFem.makeAnalysis(doc, 'Analysis')
|
||||
|
||||
solver
|
||||
# TODO How to pass multiple solver for one analysis in one doc
|
||||
if solver is None:
|
||||
pass # no solver is added
|
||||
elif solver is 'calculix':
|
||||
solver = analysis.addObject(
|
||||
ObjectsFem.makeSolverCalculix(doc, 'SolverCalculiX')
|
||||
)[0]
|
||||
solver.AnalysisType = 'static'
|
||||
solver.GeometricalNonlinearity = 'linear'
|
||||
solver.ThermoMechSteadyState = False
|
||||
solver.MatrixSolverType = 'default'
|
||||
solver.IterationsControlParameterTimeUse = False
|
||||
elif solver is 'ccxtools':
|
||||
solver = analysis.addObject(
|
||||
ObjectsFem.makeSolverCalculixCcxTools(doc, 'CalculiXccxTools')
|
||||
)[0]
|
||||
solver.AnalysisType = 'static'
|
||||
solver.GeometricalNonlinearity = 'linear'
|
||||
solver.ThermoMechSteadyState = False
|
||||
solver.MatrixSolverType = 'default'
|
||||
solver.IterationsControlParameterTimeUse = False
|
||||
solver.WorkingDir = u''
|
||||
|
||||
# shell thickness
|
||||
thickness = analysis.addObject(
|
||||
ObjectsFem.makeElementGeometry2D(doc, 0, 'ShellThickness')
|
||||
)[0]
|
||||
thickness.Thickness = 150.0
|
||||
|
||||
# material
|
||||
matrixprop = {}
|
||||
matrixprop['Name'] = "Concrete-EN-C35/45"
|
||||
matrixprop['YoungsModulus'] = "32000 MPa"
|
||||
matrixprop['PoissonRatio'] = "0.17"
|
||||
matrixprop['CompressiveStrength'] = "15.75 MPa"
|
||||
# make some hint on the possible angle units in material system
|
||||
matrixprop['AngleOfFriction'] = "30 deg"
|
||||
matrixprop['Density'] = '2500 kg/m^3'
|
||||
reinfoprop = {}
|
||||
reinfoprop['Name'] = "Reinforcement-FIB-B500"
|
||||
reinfoprop['YieldStrength'] = "315 MPa"
|
||||
# not an official FreeCAD material property
|
||||
reinfoprop['ReinforcementRatio'] = "0.0"
|
||||
material_reinforced = analysis.addObject(
|
||||
ObjectsFem.makeMaterialReinforced(doc, 'MaterialReinforced')
|
||||
)[0]
|
||||
material_reinforced.Material = matrixprop
|
||||
material_reinforced.Reinforcement = reinfoprop
|
||||
|
||||
# fixed_constraint
|
||||
fixed_constraint = analysis.addObject(
|
||||
ObjectsFem.makeConstraintFixed(doc, name="ConstraintFixed")
|
||||
)[0]
|
||||
fixed_constraint.References = [(rcwall, "Edge1"), (rcwall, "Edge5")]
|
||||
|
||||
# force constraint
|
||||
force_constraint = doc.Analysis.addObject(
|
||||
ObjectsFem.makeConstraintForce(doc, name="ConstraintForce")
|
||||
)[0]
|
||||
force_constraint.References = [(rcwall, "Edge7")]
|
||||
force_constraint.Force = 1000000.0
|
||||
force_constraint.Direction = (rcwall, ["Edge8"])
|
||||
force_constraint.Reversed = False
|
||||
|
||||
# displacement_constraint
|
||||
displacement_constraint = doc.Analysis.addObject(
|
||||
ObjectsFem.makeConstraintDisplacement(doc, name="ConstraintDisplacmentPrescribed")
|
||||
)[0]
|
||||
displacement_constraint.References = [(rcwall, "Face1")]
|
||||
displacement_constraint.zFix = True
|
||||
|
||||
# mesh
|
||||
from femexamples.meshes.mesh_rc_wall_2d_tria6 import create_nodes, create_elements
|
||||
fem_mesh = Fem.FemMesh()
|
||||
control = create_nodes(fem_mesh)
|
||||
if not control:
|
||||
print('ERROR on creating nodes')
|
||||
control = create_elements(fem_mesh)
|
||||
if not control:
|
||||
print('ERROR on creating elements')
|
||||
femmesh_obj = analysis.addObject(
|
||||
doc.addObject('Fem::FemMeshObject', mesh_name)
|
||||
)[0]
|
||||
femmesh_obj.FemMesh = fem_mesh
|
||||
|
||||
doc.recompute()
|
||||
return doc
|
||||
|
||||
|
||||
'''
|
||||
from femexamples import rc_wall_2d as rc
|
||||
rc.setup_rcwall2d()
|
||||
|
||||
'''
|
||||
500
src/Mod/Fem/femguiobjects/_ViewProviderFemMaterialReinforced.py
Normal file
500
src/Mod/Fem/femguiobjects/_ViewProviderFemMaterialReinforced.py
Normal file
@@ -0,0 +1,500 @@
|
||||
# ***************************************************************************
|
||||
# * Copyright (c) 2019 Bernd Hahnebach <bernd@bimstatik.org> *
|
||||
# * *
|
||||
# * 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__ = "FreeCAD FEM material reinforced ViewProvider for the document object"
|
||||
__author__ = "Bernd Hahnebach"
|
||||
__url__ = "http://www.freecadweb.org"
|
||||
|
||||
## @package ViewProviderFemMaterialReinforced
|
||||
# \ingroup FEM
|
||||
# \brief FreeCAD FEM _ViewProviderFemMaterialReinforced
|
||||
|
||||
import FreeCAD
|
||||
import FreeCADGui
|
||||
import FemGui # needed to display the icons in TreeView
|
||||
False if False else FemGui.__name__ # flake8, dummy FemGui usage, returns 'FemGui'
|
||||
|
||||
|
||||
# task panel
|
||||
# from . import FemSelectionWidgets
|
||||
from PySide import QtCore
|
||||
from PySide import QtGui
|
||||
import sys
|
||||
if sys.version_info.major >= 3:
|
||||
unicode = str
|
||||
|
||||
|
||||
class _ViewProviderFemMaterialReinforced:
|
||||
"A View Provider for the FemMaterialReinfocement object"
|
||||
def __init__(self, vobj):
|
||||
vobj.Proxy = self
|
||||
|
||||
def getIcon(self):
|
||||
return ":/icons/fem-material-reinforced.svg"
|
||||
|
||||
def attach(self, vobj):
|
||||
from pivy import coin
|
||||
self.ViewObject = vobj
|
||||
self.Object = vobj.Object
|
||||
self.standard = coin.SoGroup()
|
||||
vobj.addDisplayMode(self.standard, "Default")
|
||||
|
||||
def getDisplayModes(self, obj):
|
||||
return ["Default"]
|
||||
|
||||
def updateData(self, obj, prop):
|
||||
return
|
||||
|
||||
def onChanged(self, vobj, prop):
|
||||
return
|
||||
|
||||
def setEdit(self, vobj, mode=0):
|
||||
# hide all meshes
|
||||
for o in FreeCAD.ActiveDocument.Objects:
|
||||
if o.isDerivedFrom("Fem::FemMeshObject"):
|
||||
o.ViewObject.hide()
|
||||
# hide all meshes
|
||||
for o in FreeCAD.ActiveDocument.Objects:
|
||||
if o.isDerivedFrom("Fem::FemMeshObject"):
|
||||
o.ViewObject.hide()
|
||||
# show task panel
|
||||
taskd = _TaskPanelFemMaterialReinforced(self.Object)
|
||||
taskd.obj = vobj.Object
|
||||
FreeCADGui.Control.showDialog(taskd)
|
||||
return True
|
||||
|
||||
def unsetEdit(self, vobj, mode=0):
|
||||
FreeCADGui.Control.closeDialog()
|
||||
return True
|
||||
|
||||
def doubleClicked(self, vobj):
|
||||
guidoc = FreeCADGui.getDocument(vobj.Object.Document)
|
||||
# check if another VP is in edit mode
|
||||
# https://forum.freecadweb.org/viewtopic.php?t=13077#p104702
|
||||
if not guidoc.getInEdit():
|
||||
guidoc.setEdit(vobj.Object.Name)
|
||||
else:
|
||||
from PySide.QtGui import QMessageBox
|
||||
message = (
|
||||
'Active Task Dialog found! '
|
||||
'Please close this one before opening a new one!'
|
||||
)
|
||||
QMessageBox.critical(None, "Error in tree view", message)
|
||||
FreeCAD.Console.PrintError(message + '\n')
|
||||
return True
|
||||
|
||||
def __getstate__(self):
|
||||
return None
|
||||
|
||||
def __setstate__(self, state):
|
||||
return None
|
||||
|
||||
|
||||
class _TaskPanelFemMaterialReinforced:
|
||||
'''The editmode TaskPanel for FemMaterialReinforced objects'''
|
||||
|
||||
if sys.version_info.major >= 3:
|
||||
unicode = str
|
||||
|
||||
def __init__(self, obj):
|
||||
|
||||
FreeCAD.Console.PrintMessage('\n') # empty line on start task panel
|
||||
self.obj = obj
|
||||
|
||||
# init matrix and reinforcement material
|
||||
self.material_m = self.obj.Material
|
||||
self.card_path_m = ''
|
||||
self.has_transient_mat_m = False
|
||||
self.material_r = self.obj.Reinforcement
|
||||
self.card_path_r = ''
|
||||
self.has_transient_mat_r = False
|
||||
# mat_card is the FCMat file
|
||||
# card_name is the file name of the mat_card
|
||||
# card_path is the whole file path of the mat_card
|
||||
# material_name is the value of the key name in FreeCAD material dictionary
|
||||
# they might not match because of special letters in the material_name which are
|
||||
# changed in the card_name to english standard characters
|
||||
|
||||
# init for collecting all mat data and icons
|
||||
self.materials = {} # { card_path : FreeCAD material dict }
|
||||
self.cards = {} # { card_path : card_names, ... }
|
||||
self.icons = {} # { card_path : icon_path }
|
||||
|
||||
# parameter widget
|
||||
self.parameterWidget = FreeCADGui.PySideUic.loadUi(
|
||||
FreeCAD.getHomePath() + "Mod/Fem/Resources/ui/MaterialReinforcement.ui"
|
||||
)
|
||||
|
||||
# globals
|
||||
QtCore.QObject.connect(
|
||||
self.parameterWidget.cb_materials_m,
|
||||
QtCore.SIGNAL("activated(int)"),
|
||||
self.choose_material_m
|
||||
)
|
||||
QtCore.QObject.connect(
|
||||
self.parameterWidget.pb_edit_m,
|
||||
QtCore.SIGNAL("clicked()"),
|
||||
self.edit_material_m
|
||||
)
|
||||
QtCore.QObject.connect(
|
||||
self.parameterWidget.cb_materials_r,
|
||||
QtCore.SIGNAL("activated(int)"),
|
||||
self.choose_material_r
|
||||
)
|
||||
QtCore.QObject.connect(
|
||||
self.parameterWidget.pb_edit_r,
|
||||
QtCore.SIGNAL("clicked()"),
|
||||
self.edit_material_r
|
||||
)
|
||||
|
||||
# get all available materials (fill self.materials, self.cards and self.icons)
|
||||
from materialtools.cardutils import import_materials as getmats
|
||||
self.materials, self.cards, self.icons = getmats()
|
||||
# fill the material comboboxes with material cards
|
||||
self.add_cards_to_combo_boxes()
|
||||
|
||||
# search for exact the mat_card_m and mat_card_r in all known cards
|
||||
# choose the current matrix material
|
||||
self.card_path_m = self.get_material_card(self.material_m)
|
||||
FreeCAD.Console.PrintLog('card_path: {}'.format(self.card_path_m))
|
||||
if not self.card_path_m:
|
||||
# we have not found our material in self.materials dict :-(
|
||||
# we're going to add a user-defined temporary material: a document material
|
||||
FreeCAD.Console.PrintMessage(
|
||||
"Previously used material card cannot be found in material directories. "
|
||||
"Add document material.\n"
|
||||
)
|
||||
self.card_path_m = '_Document_Matrix_Material'
|
||||
self.materials[self.card_path_m] = self.material_m
|
||||
self.parameterWidget.cb_materials_m.addItem(
|
||||
QtGui.QIcon(":/icons/help-browser.svg"),
|
||||
self.card_path_m,
|
||||
self.card_path_m
|
||||
)
|
||||
index = self.parameterWidget.cb_materials_m.findData(self.card_path_m)
|
||||
# print(index)
|
||||
# fill input fields and set the current material in the cb widget
|
||||
self.choose_material_m(index)
|
||||
else:
|
||||
# we found our exact material in self.materials dict :-)
|
||||
FreeCAD.Console.PrintLog(
|
||||
"Previously used material card was found in material directories. "
|
||||
"We will use this material.\n"
|
||||
)
|
||||
index = self.parameterWidget.cb_materials_m.findData(self.card_path_m)
|
||||
# set the current material in the cb widget
|
||||
self.choose_material_m(index)
|
||||
|
||||
# choose the current reinforcement material
|
||||
self.card_path_r = self.get_material_card(self.material_r)
|
||||
FreeCAD.Console.PrintLog('card_path: {}'.format(self.card_path_r))
|
||||
if not self.card_path_r:
|
||||
# we have not found our material in self.materials dict :-(
|
||||
# we're going to add a user-defined temporary material: a document material
|
||||
FreeCAD.Console.PrintMessage(
|
||||
"Previously used material card cannot be found in material directories. "
|
||||
"Add document material.\n"
|
||||
)
|
||||
self.card_path_r = '_Document_Reinforcement_Material'
|
||||
self.materials[self.card_path_r] = self.material_r
|
||||
self.parameterWidget.cb_materials_r.addItem(
|
||||
QtGui.QIcon(":/icons/help-browser.svg"),
|
||||
self.card_path_r,
|
||||
self.card_path_r
|
||||
)
|
||||
index = self.parameterWidget.cb_materials_r.findData(self.card_path_r)
|
||||
# set the current material in the cb widget
|
||||
self.choose_material_r(index)
|
||||
else:
|
||||
# we found our exact material in self.materials dict :-)
|
||||
FreeCAD.Console.PrintLog(
|
||||
"Previously used material card was found in material directories. "
|
||||
"We will use this material.\n"
|
||||
)
|
||||
index = self.parameterWidget.cb_materials_r.findData(self.card_path_r)
|
||||
# print(index)
|
||||
# fill input fields and set the current material in the cb widget
|
||||
self.choose_material_r(index)
|
||||
|
||||
# set up the form
|
||||
self.form = self.parameterWidget
|
||||
|
||||
# leave task panel ***************************************************************************
|
||||
def accept(self):
|
||||
from materialtools.cardutils import check_mat_units as checkunits
|
||||
if checkunits(self.material_m) is True and checkunits(self.material_r) is True:
|
||||
self.obj.Material = self.material_m
|
||||
self.obj.Reinforcement = self.material_r
|
||||
else:
|
||||
error_message = (
|
||||
'Due to some wrong material quantity units in the changed '
|
||||
'material data, the task panel changes where not accepted.\n'
|
||||
)
|
||||
FreeCAD.Console.PrintError(error_message)
|
||||
QtGui.QMessageBox.critical(None, "Material data not changed", error_message)
|
||||
self.recompute_and_set_back_all()
|
||||
return True
|
||||
|
||||
def reject(self):
|
||||
self.recompute_and_set_back_all()
|
||||
return True
|
||||
|
||||
def recompute_and_set_back_all(self):
|
||||
guidoc = FreeCADGui.getDocument(self.obj.Document)
|
||||
guidoc.Document.recompute()
|
||||
guidoc.resetEdit()
|
||||
self.output_obj_mat_param()
|
||||
|
||||
def output_obj_mat_param(self):
|
||||
self.print_mat_dict(self.obj.Material)
|
||||
self.print_mat_dict(self.obj.Reinforcement)
|
||||
print('\n')
|
||||
|
||||
def print_mat_dict(self, mat_dict):
|
||||
if 'Name' in mat_dict:
|
||||
print('Material: {}'.format(mat_dict['Name']))
|
||||
else:
|
||||
print('Matrix material: no Name')
|
||||
for key in mat_dict:
|
||||
print(' {}: {}'.format(key, mat_dict[key]))
|
||||
|
||||
# choose material card ***********************************************************************
|
||||
def get_material_card(self, material):
|
||||
for a_mat in self.materials:
|
||||
unmatched_items = set(self.materials[a_mat].items()) ^ set(material.items())
|
||||
# print(a_mat + ' --> unmatched_items = ' + str(len(unmatched_items)))
|
||||
if len(unmatched_items) < 4:
|
||||
FreeCAD.Console.PrintLog('{}\n'.format(unmatched_items))
|
||||
if len(unmatched_items) == 0:
|
||||
return a_mat
|
||||
return ""
|
||||
|
||||
def choose_material_m(self, index):
|
||||
if index < 0:
|
||||
return
|
||||
# get the whole card path
|
||||
self.card_path_m = self.parameterWidget.cb_materials_m.itemData(index)
|
||||
FreeCAD.Console.PrintMessage(
|
||||
'choose_material in FEM material task panel:\n'
|
||||
' {}\n'.format(self.card_path_m)
|
||||
)
|
||||
self.material_m = self.materials[self.card_path_m]
|
||||
self.parameterWidget.cb_materials_m.setCurrentIndex(index)
|
||||
gen_mat_desc = ""
|
||||
gen_mat_name = ""
|
||||
if 'Description' in self.material_m:
|
||||
gen_mat_desc = self.material_m['Description']
|
||||
if 'Name' in self.material_m:
|
||||
gen_mat_name = self.material_m['Name']
|
||||
self.parameterWidget.l_description_m.setText(gen_mat_desc)
|
||||
self.parameterWidget.l_name_m.setText(gen_mat_name)
|
||||
|
||||
def choose_material_r(self, index):
|
||||
if index < 0:
|
||||
return
|
||||
# get the whole card path
|
||||
self.card_path_r = self.parameterWidget.cb_materials_r.itemData(index)
|
||||
FreeCAD.Console.PrintMessage(
|
||||
'choose_material in FEM material task panel:\n'
|
||||
' {}\n'.format(self.card_path_r)
|
||||
)
|
||||
self.material_r = self.materials[self.card_path_r]
|
||||
self.parameterWidget.cb_materials_r.setCurrentIndex(index)
|
||||
gen_mat_desc = ""
|
||||
gen_mat_name = ""
|
||||
if 'Description' in self.material_r:
|
||||
gen_mat_desc = self.material_r['Description']
|
||||
if 'Name' in self.material_r:
|
||||
gen_mat_name = self.material_r['Name']
|
||||
self.parameterWidget.l_description_r.setText(gen_mat_desc)
|
||||
self.parameterWidget.l_name_r.setText(gen_mat_name)
|
||||
|
||||
# transient material is needed if the user changed mat parameter by the mat editor
|
||||
def set_transient_material_m(self):
|
||||
self.card_path_m = '_Transient_Matrix_Material'
|
||||
self.materials[self.card_path_m] = self.material_m # = the current matrix mat dict
|
||||
index = self.parameterWidget.cb_materials_m.findData(self.card_path_m)
|
||||
self.choose_material_m(index)
|
||||
|
||||
def add_transient_material_m(self):
|
||||
self.has_transient_mat_m = True
|
||||
self.card_path_m = '_Transient_Matrix_Material'
|
||||
self.parameterWidget.cb_materials_m.addItem(
|
||||
QtGui.QIcon(":/icons/help-browser.svg"),
|
||||
self.card_path_m,
|
||||
self.card_path_m
|
||||
)
|
||||
self.set_transient_material_m()
|
||||
|
||||
def set_transient_material_r(self):
|
||||
self.card_path_r = '_Transient_Reinforcement_Material'
|
||||
self.materials[self.card_path_r] = self.material_r # = the current reinforced mat dict
|
||||
index = self.parameterWidget.cb_materials_r.findData(self.card_path_r)
|
||||
self.choose_material_r(index)
|
||||
|
||||
def add_transient_material_r(self):
|
||||
self.has_transient_mat_r = True
|
||||
self.card_path_r = '_Transient_Reinforcement_Material'
|
||||
self.parameterWidget.cb_materials_r.addItem(
|
||||
QtGui.QIcon(":/icons/help-browser.svg"),
|
||||
self.card_path_r,
|
||||
self.card_path_r
|
||||
)
|
||||
self.set_transient_material_r()
|
||||
|
||||
# edit material parameter ********************************************************************
|
||||
# TODO, also all mat parameter checks should be moved to material editor
|
||||
# and mat parameter checks should be done on analysis precheck in according to the analysis
|
||||
# should be checked if all needed parameter are defined and have all right values and units
|
||||
def edit_material_m(self):
|
||||
# opens the material editor to choose a material or edit material params
|
||||
import MaterialEditor
|
||||
if self.card_path_m not in self.cards:
|
||||
FreeCAD.Console.PrintLog(
|
||||
'Card path not in cards, material dict will be used to open Material Editor.\n'
|
||||
)
|
||||
new_material_params = MaterialEditor.editMaterial(material=self.material_m)
|
||||
else:
|
||||
new_material_params = MaterialEditor.editMaterial(card_path=self.card_path_m)
|
||||
# material editor returns the mat_dict only, not a card_path
|
||||
# if the material editor was canceled a empty dict will be returned
|
||||
# do not change the self.material
|
||||
# check if dict is not empty (do not use 'is True')
|
||||
if new_material_params:
|
||||
# check material quantity units
|
||||
from materialtools.cardutils import check_mat_units as checkunits
|
||||
if checkunits(new_material_params) is True:
|
||||
self.material_m = new_material_params
|
||||
self.card_path_m = self.get_material_card(self.material_m)
|
||||
FreeCAD.Console.PrintMessage('card_path: {}\n'.format(self.card_path_m))
|
||||
if not self.card_path_m:
|
||||
FreeCAD.Console.PrintMessage(
|
||||
"Material card chosen by the material editor "
|
||||
"was not found in material directories.\n"
|
||||
"Either the card does not exist or some material "
|
||||
"parameter where changed in material editor.\n"
|
||||
)
|
||||
if self.has_transient_mat_m is False:
|
||||
self.add_transient_material_m()
|
||||
else:
|
||||
self.set_transient_material_m()
|
||||
else:
|
||||
# we found our exact material in self.materials dict :-)
|
||||
FreeCAD.Console.PrintLog(
|
||||
"Material card chosen by the material editor "
|
||||
"was found in material directories. "
|
||||
"The found material card will be used.\n"
|
||||
)
|
||||
index = self.parameterWidget.cb_materials_m.findData(self.card_path_m)
|
||||
# print(index)
|
||||
# set the current material in the cb widget
|
||||
self.choose_material_m(index)
|
||||
else:
|
||||
error_message = (
|
||||
'Due to some wrong material quantity units in data passed '
|
||||
'by the material editor, the material data was not changed.\n'
|
||||
)
|
||||
FreeCAD.Console.PrintError(error_message)
|
||||
QtGui.QMessageBox.critical(None, "Material data not changed", error_message)
|
||||
else:
|
||||
FreeCAD.Console.PrintMessage('No changes where made by the material editor.\n')
|
||||
|
||||
def edit_material_r(self):
|
||||
# opens the material editor to choose a material or edit material params
|
||||
import MaterialEditor
|
||||
if self.card_path_r not in self.cards:
|
||||
FreeCAD.Console.PrintLog(
|
||||
'Card path not in cards, material dict will be used to open Material Editor.\n'
|
||||
)
|
||||
new_material_params = MaterialEditor.editMaterial(material=self.material_r)
|
||||
else:
|
||||
new_material_params = MaterialEditor.editMaterial(card_path=self.card_path_r)
|
||||
# material editor returns the mat_dict only, not a card_path
|
||||
# if the material editor was canceled a empty dict will be returned
|
||||
# do not change the self.material
|
||||
# check if dict is not empty (do not use 'is True')
|
||||
if new_material_params:
|
||||
# check material quantity units
|
||||
from materialtools.cardutils import check_mat_units as checkunits
|
||||
if checkunits(new_material_params) is True:
|
||||
self.material_r = new_material_params
|
||||
self.card_path_r = self.get_material_card(self.material_r)
|
||||
FreeCAD.Console.PrintMessage('card_path: {}\n'.format(self.card_path_r))
|
||||
if not self.card_path_r:
|
||||
FreeCAD.Console.PrintMessage(
|
||||
"Material card chosen by the material editor "
|
||||
"was not found in material directories.\n"
|
||||
"Either the card does not exist or some material "
|
||||
"parameter where changed in material editor.\n"
|
||||
)
|
||||
if self.has_transient_mat_r is False:
|
||||
self.add_transient_material_r()
|
||||
else:
|
||||
self.set_transient_material_r()
|
||||
else:
|
||||
# we found our exact material in self.materials dict :-)
|
||||
FreeCAD.Console.PrintLog(
|
||||
"Material card chosen by the material editor "
|
||||
"was found in material directories. "
|
||||
"The found material card will be used.\n"
|
||||
)
|
||||
index = self.parameterWidget.cb_materials_r.findData(self.card_path_r)
|
||||
# print(index)
|
||||
# set the current material in the cb widget
|
||||
self.choose_material_r(index)
|
||||
else:
|
||||
error_message = (
|
||||
'Due to some wrong material quantity units in data passed '
|
||||
'by the material editor, the material data was not changed.\n'
|
||||
)
|
||||
FreeCAD.Console.PrintError(error_message)
|
||||
QtGui.QMessageBox.critical(None, "Material data not changed", error_message)
|
||||
else:
|
||||
FreeCAD.Console.PrintMessage('No changes where made by the material editor.\n')
|
||||
|
||||
# fill the combo box with cards **************************************************************
|
||||
def add_cards_to_combo_boxes(self):
|
||||
# fill comboboxes, in combo box the card name is used not the material name
|
||||
self.parameterWidget.cb_materials_m.clear()
|
||||
self.parameterWidget.cb_materials_r.clear()
|
||||
|
||||
mat_prefs = FreeCAD.ParamGet("User parameter:BaseApp/Preferences/Mod/Material/Cards")
|
||||
sort_by_resources = mat_prefs.GetBool("SortByResources", False)
|
||||
|
||||
card_name_list = [] # [ [card_name, card_path, icon_path], ... ]
|
||||
|
||||
if sort_by_resources is True:
|
||||
for a_path in sorted(self.materials.keys()):
|
||||
card_name_list.append([self.cards[a_path], a_path, self.icons[a_path]])
|
||||
else:
|
||||
card_names_tmp = {}
|
||||
for path, name in self.cards.items():
|
||||
card_names_tmp[name] = path
|
||||
for a_name in sorted(card_names_tmp.keys()):
|
||||
a_path = card_names_tmp[a_name]
|
||||
card_name_list.append([a_name, a_path, self.icons[a_path]])
|
||||
|
||||
for mat in card_name_list:
|
||||
self.parameterWidget.cb_materials_m.addItem(QtGui.QIcon(mat[2]), mat[0], mat[1])
|
||||
self.parameterWidget.cb_materials_r.addItem(QtGui.QIcon(mat[2]), mat[0], mat[1])
|
||||
# the whole card path is added to the combo box to make it unique
|
||||
# see def choose_material:
|
||||
# for assignment of self.card_path the path form the parameterWidget ist used
|
||||
@@ -467,6 +467,28 @@ class _TaskPanelFemResultShow:
|
||||
exy = np.array(self.result_obj.NodeStrainXY)
|
||||
exz = np.array(self.result_obj.NodeStrainXZ)
|
||||
eyz = np.array(self.result_obj.NodeStrainYZ)
|
||||
|
||||
# Display of Reinforcement Ratios and Mohr Coulomb Criterion
|
||||
rx = np.array(self.result_obj.ReinforcementRatio_x)
|
||||
ry = np.array(self.result_obj.ReinforcementRatio_y)
|
||||
rz = np.array(self.result_obj.ReinforcementRatio_z)
|
||||
mc = np.array(self.result_obj.MohrCoulomb)
|
||||
|
||||
ps1vector = np.array(self.result_obj.PS1Vector)
|
||||
s1x = np.array(ps1vector[:, 0])
|
||||
s1y = np.array(ps1vector[:, 1])
|
||||
s1z = np.array(ps1vector[:, 2])
|
||||
|
||||
ps2vector = np.array(self.result_obj.PS2Vector)
|
||||
s2x = np.array(ps2vector[:, 0])
|
||||
s2y = np.array(ps2vector[:, 1])
|
||||
s2z = np.array(ps2vector[:, 2])
|
||||
|
||||
ps3vector = np.array(self.result_obj.PS1Vector)
|
||||
s3x = np.array(ps3vector[:, 0])
|
||||
s3y = np.array(ps3vector[:, 1])
|
||||
s3z = np.array(ps3vector[:, 2])
|
||||
|
||||
userdefined_eq = self.form.user_def_eq.toPlainText() # Get equation to be used
|
||||
UserDefinedFormula = eval(userdefined_eq).tolist()
|
||||
self.result_obj.UserDefined = UserDefinedFormula
|
||||
@@ -486,7 +508,8 @@ class _TaskPanelFemResultShow:
|
||||
del x, y, z, T, Von, Peeq, P1, P2, P3
|
||||
del sxx, syy, szz, sxy, sxz, syz
|
||||
del exx, eyy, ezz, exy, exz, eyz
|
||||
del MF, NP
|
||||
del MF, NP, rx, ry, rz, mc
|
||||
del s1x, s1y, s1z, s2x, s2y, s2z, s3x, s3y, s3z
|
||||
|
||||
def select_displacement_type(self, disp_type):
|
||||
QApplication.setOverrideCursor(Qt.WaitCursor)
|
||||
|
||||
@@ -120,19 +120,31 @@ def importFrd(
|
||||
analysis_object.addObject(res_obj)
|
||||
# complementary result object calculations
|
||||
import femresult.resulttools as restools
|
||||
import femtools.femutils as femutils
|
||||
if not res_obj.MassFlowRate:
|
||||
# only compact result if not Flow 1D results
|
||||
# compact result object, workaround for bug 2873
|
||||
# https://www.freecadweb.org/tracker/view.php?id=2873
|
||||
res_obj = restools.compact_result(res_obj)
|
||||
|
||||
# fill DisplacementLengths
|
||||
res_obj = restools.add_disp_apps(res_obj)
|
||||
# fill StressValues
|
||||
res_obj = restools.add_von_mises(res_obj)
|
||||
# fill PrincipalMax, PrincipalMed, PrincipalMin, MaxShear
|
||||
res_obj = restools.add_principal_stress(res_obj)
|
||||
if res_obj.getParentGroup():
|
||||
has_reinforced_mat = False
|
||||
for obj in res_obj.getParentGroup().Group:
|
||||
if obj.isDerivedFrom('App::MaterialObjectPython') \
|
||||
and femutils.is_of_type(obj, 'Fem::MaterialReinforced'):
|
||||
has_reinforced_mat = True
|
||||
restools.add_principal_stress_reinforced(res_obj)
|
||||
break
|
||||
if has_reinforced_mat is False:
|
||||
# fill PrincipalMax, PrincipalMed, PrincipalMin, MaxShear
|
||||
res_obj = restools.add_principal_stress_std(res_obj)
|
||||
# fill Stats
|
||||
res_obj = restools.fill_femresult_stats(res_obj)
|
||||
|
||||
else:
|
||||
error_message = (
|
||||
"We have nodes but no results in frd file, "
|
||||
|
||||
59
src/Mod/Fem/femobjects/_FemMaterialReinforced.py
Normal file
59
src/Mod/Fem/femobjects/_FemMaterialReinforced.py
Normal file
@@ -0,0 +1,59 @@
|
||||
# ***************************************************************************
|
||||
# * *
|
||||
# * Copyright (c) 2019 Bernd Hahnebach <bernd@bimstatik.org> *
|
||||
# * *
|
||||
# * 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__ = "FreeCAD FEM reinforced material"
|
||||
__author__ = "Bernd Hahnebach"
|
||||
__url__ = "http://www.freecadweb.org"
|
||||
|
||||
## @package FemMaterialReinforced
|
||||
# \ingroup FEM
|
||||
# \brief FreeCAD FEM _FemMaterialReinforced
|
||||
|
||||
|
||||
class _FemMaterialReinforced:
|
||||
"The FemMaterialReinforced object"
|
||||
def __init__(self, obj):
|
||||
obj.addProperty(
|
||||
"App::PropertyLinkSubList",
|
||||
"References",
|
||||
"Material",
|
||||
"List of material shapes"
|
||||
)
|
||||
obj.addProperty(
|
||||
"App::PropertyMap",
|
||||
"Reinforcement",
|
||||
"Composites",
|
||||
"Reinforcement material properties"
|
||||
)
|
||||
obj.addProperty(
|
||||
"App::PropertyEnumeration",
|
||||
"Category",
|
||||
"Material",
|
||||
"Matrix material properties"
|
||||
)
|
||||
obj.Category = ['Solid']
|
||||
obj.Category = 'Solid'
|
||||
obj.Proxy = self
|
||||
self.Type = "Fem::MaterialReinforced"
|
||||
|
||||
def execute(self, obj):
|
||||
return
|
||||
@@ -80,6 +80,56 @@ class _FemResultMechanical():
|
||||
"List of equivalent plastic strain values",
|
||||
True
|
||||
)
|
||||
obj.addProperty(
|
||||
"App::PropertyFloatList",
|
||||
"MohrCoulomb",
|
||||
"NodeData",
|
||||
"List of Mohr Coulomb stress values",
|
||||
True
|
||||
)
|
||||
obj.addProperty(
|
||||
"App::PropertyFloatList",
|
||||
"ReinforcementRatio_x",
|
||||
"NodeData",
|
||||
"Reinforcement ratio x-direction",
|
||||
True
|
||||
)
|
||||
obj.addProperty(
|
||||
"App::PropertyFloatList",
|
||||
"ReinforcementRatio_y",
|
||||
"NodeData",
|
||||
"Reinforcement ratio y-direction",
|
||||
True
|
||||
)
|
||||
obj.addProperty(
|
||||
"App::PropertyFloatList",
|
||||
"ReinforcementRatio_z",
|
||||
"NodeData",
|
||||
"Reinforcement ratio z-direction",
|
||||
True
|
||||
)
|
||||
obj.addProperty(
|
||||
"App::PropertyVectorList",
|
||||
"PS1Vector",
|
||||
"NodeData",
|
||||
"List of 1st Principal Stress Vectors",
|
||||
True
|
||||
)
|
||||
obj.addProperty(
|
||||
"App::PropertyVectorList",
|
||||
"PS2Vector",
|
||||
"NodeData",
|
||||
"List of 2nd Principal Stress Vectors",
|
||||
True
|
||||
)
|
||||
obj.addProperty(
|
||||
"App::PropertyVectorList",
|
||||
"PS3Vector",
|
||||
"NodeData",
|
||||
"List of 3rd Principal Stress Vectors",
|
||||
True
|
||||
)
|
||||
|
||||
# readonly in propertyEditor of comboView
|
||||
obj.addProperty(
|
||||
"App::PropertyFloatList",
|
||||
|
||||
@@ -310,7 +310,7 @@ def add_von_mises(res_obj):
|
||||
return res_obj
|
||||
|
||||
|
||||
def add_principal_stress(res_obj):
|
||||
def add_principal_stress_std(res_obj):
|
||||
prinstress1 = []
|
||||
prinstress2 = []
|
||||
prinstress3 = []
|
||||
@@ -324,7 +324,7 @@ def add_principal_stress(res_obj):
|
||||
res_obj.NodeStressYZ
|
||||
)
|
||||
for Sxx, Syy, Szz, Sxy, Sxz, Syz in iterator:
|
||||
prin1, prin2, prin3, shear = calculate_principal_stress((Sxx, Syy, Szz, Sxy, Sxz, Syz))
|
||||
prin1, prin2, prin3, shear = calculate_principal_stress_std((Sxx, Syy, Szz, Sxy, Sxz, Syz))
|
||||
prinstress1.append(prin1)
|
||||
prinstress2.append(prin2)
|
||||
prinstress3.append(prin3)
|
||||
@@ -337,6 +337,165 @@ def add_principal_stress(res_obj):
|
||||
return res_obj
|
||||
|
||||
|
||||
def get_concrete_nodes(res_obj):
|
||||
|
||||
#
|
||||
# HarryvL: determine concrete / non-concrete nodes
|
||||
#
|
||||
|
||||
from femmesh.meshtools import get_femnodes_by_refshape
|
||||
femmesh = res_obj.Mesh.FemMesh
|
||||
nsr = femmesh.NodeCount # nsr number of stress results
|
||||
|
||||
# ic[iic]:
|
||||
# ic = flag for material type; iic = node number
|
||||
# ic = 0: NOT ASSIGNED
|
||||
# ic = 1: ReinforcedMaterial
|
||||
# ic = 2: NOT ReinforcedMaterial
|
||||
ic = np.zeros(nsr)
|
||||
|
||||
for obj in res_obj.getParentGroup().Group:
|
||||
if obj.isDerivedFrom('App::MaterialObjectPython') \
|
||||
and femutils.is_of_type(obj, 'Fem::MaterialReinforced'):
|
||||
print("ReinforcedMaterial")
|
||||
if obj.References == []:
|
||||
for iic in range(nsr):
|
||||
if ic[iic] == 0:
|
||||
ic[iic] = 1
|
||||
else:
|
||||
for ref in obj.References:
|
||||
concrete_nodes = get_femnodes_by_refshape(femmesh, ref)
|
||||
for cn in concrete_nodes:
|
||||
ic[cn - 1] = 1
|
||||
elif obj.isDerivedFrom('App::MaterialObjectPython') \
|
||||
and femutils.is_of_type(obj, 'Fem::Material'):
|
||||
print("NOT ReinforcedMaterial")
|
||||
if obj.References == []:
|
||||
for iic in range(nsr):
|
||||
if ic[iic] == 0:
|
||||
ic[iic] = 2
|
||||
else:
|
||||
for ref in obj.References:
|
||||
non_concrete_nodes = get_femnodes_by_refshape(femmesh, ref)
|
||||
for ncn in non_concrete_nodes:
|
||||
ic[ncn - 1] = 2
|
||||
return ic
|
||||
|
||||
|
||||
def add_principal_stress_reinforced(res_obj):
|
||||
|
||||
#
|
||||
# HarryvL: determine concrete / non-concrete nodes
|
||||
#
|
||||
ic = get_concrete_nodes(res_obj)
|
||||
|
||||
#
|
||||
# calculate principal and max Shear and fill them in res_obj
|
||||
#
|
||||
prinstress1 = []
|
||||
prinstress2 = []
|
||||
prinstress3 = []
|
||||
shearstress = []
|
||||
ps1v = []
|
||||
ps2v = []
|
||||
ps3v = []
|
||||
#
|
||||
# HarryvL: additional arrays to hold reinforcement ratios
|
||||
# and mohr coulomb stress
|
||||
#
|
||||
rhx = []
|
||||
rhy = []
|
||||
rhz = []
|
||||
moc = []
|
||||
|
||||
# material parameter
|
||||
for obj in res_obj.getParentGroup().Group:
|
||||
if femutils.is_of_type(obj, 'Fem::MaterialReinforced'):
|
||||
matrix_af = float(
|
||||
FreeCAD.Units.Quantity(obj.Material['AngleOfFriction']).getValueAs('rad')
|
||||
)
|
||||
matrix_cs = float(
|
||||
FreeCAD.Units.Quantity(obj.Material['CompressiveStrength']).getValueAs('MPa')
|
||||
)
|
||||
reinforce_yield = float(
|
||||
FreeCAD.Units.Quantity(obj.Reinforcement['YieldStrength']).getValueAs('MPa')
|
||||
)
|
||||
# print(matrix_af)
|
||||
# print(matrix_cs)
|
||||
# print(reinforce_yield)
|
||||
|
||||
iterator = zip(
|
||||
res_obj.NodeStressXX,
|
||||
res_obj.NodeStressYY,
|
||||
res_obj.NodeStressZZ,
|
||||
res_obj.NodeStressXY,
|
||||
res_obj.NodeStressXZ,
|
||||
res_obj.NodeStressYZ
|
||||
)
|
||||
for isv, stress_tensor in enumerate(iterator):
|
||||
|
||||
rhox = 0.
|
||||
rhoy = 0.
|
||||
rhoz = 0.
|
||||
mc = 0.
|
||||
|
||||
if ic[isv] == 1:
|
||||
#
|
||||
# HarryvL: for concrete scxx etc. are affected by
|
||||
# reinforcement (see calculate_rho(stress_tensor)). for all other
|
||||
# materials scxx etc. are the original stresses
|
||||
#
|
||||
rhox, rhoy, rhoz = calculate_rho(
|
||||
stress_tensor,
|
||||
reinforce_yield
|
||||
)
|
||||
|
||||
prin1, prin2, prin3, shear, psv = calculate_principal_stress_reinforced(
|
||||
stress_tensor
|
||||
)
|
||||
|
||||
prinstress1.append(prin1)
|
||||
prinstress2.append(prin2)
|
||||
prinstress3.append(prin3)
|
||||
shearstress.append(shear)
|
||||
ps1v.append(psv[0])
|
||||
ps2v.append(psv[1])
|
||||
ps3v.append(psv[2])
|
||||
|
||||
#
|
||||
# reinforcement ratios and mohr coulomb criterion
|
||||
#
|
||||
rhx.append(rhox)
|
||||
rhy.append(rhoy)
|
||||
rhz.append(rhoz)
|
||||
if ic[isv] == 1:
|
||||
mc = calculate_mohr_coulomb(prin1, prin3, matrix_af, matrix_cs)
|
||||
moc.append(mc)
|
||||
|
||||
res_obj.PrincipalMax = prinstress1
|
||||
res_obj.PrincipalMed = prinstress2
|
||||
res_obj.PrincipalMin = prinstress3
|
||||
res_obj.MaxShear = shearstress
|
||||
#
|
||||
# HarryvL: additional concrete and principal stress plot
|
||||
# results for use in _ViewProviderFemResultMechanical
|
||||
#
|
||||
res_obj.ReinforcementRatio_x = rhx
|
||||
res_obj.ReinforcementRatio_y = rhy
|
||||
res_obj.ReinforcementRatio_z = rhz
|
||||
res_obj.MohrCoulomb = moc
|
||||
|
||||
res_obj.PS1Vector = ps1v
|
||||
res_obj.PS2Vector = ps2v
|
||||
res_obj.PS3Vector = ps3v
|
||||
|
||||
FreeCAD.Console.PrintMessage(
|
||||
'Added principal stress and max shear values as well as'
|
||||
'reinforcment rations, Mohr Coloumb values.\n'
|
||||
)
|
||||
return res_obj
|
||||
|
||||
|
||||
def compact_result(res_obj):
|
||||
'''
|
||||
compacts result.Mesh and appropriate result.NodeNumbers
|
||||
@@ -373,7 +532,7 @@ def calculate_von_mises(stress_tensor):
|
||||
return np.sqrt(1.5 * np.linalg.norm(normal - pressure)**2 + 3.0 * np.linalg.norm(shear)**2)
|
||||
|
||||
|
||||
def calculate_principal_stress(stress_tensor):
|
||||
def calculate_principal_stress_std(stress_tensor):
|
||||
s11 = stress_tensor[0] # Sxx
|
||||
s22 = stress_tensor[1] # Syy
|
||||
s33 = stress_tensor[2] # Szz
|
||||
@@ -399,6 +558,223 @@ def calculate_principal_stress(stress_tensor):
|
||||
# https://forum.freecadweb.org/viewtopic.php?f=22&t=33911&start=10#p284229
|
||||
|
||||
|
||||
def calculate_principal_stress_reinforced(stress_tensor):
|
||||
#
|
||||
# HarryvL - calculate principal stress vectors and values
|
||||
# - for total stresses use stress_tensor[0], stress_tensor[1], stress_tensor[2]
|
||||
# on the diagonal of the stress tensor
|
||||
#
|
||||
# difference to the original method:
|
||||
# https://forum.freecadweb.org/viewtopic.php?f=18&t=33106&start=90#p296539
|
||||
#
|
||||
|
||||
s11 = stress_tensor[0] # Sxx
|
||||
s22 = stress_tensor[1] # Syy
|
||||
s33 = stress_tensor[2] # Szz
|
||||
s12 = stress_tensor[3] # Sxy
|
||||
s31 = stress_tensor[4] # Sxz
|
||||
s23 = stress_tensor[5] # Syz
|
||||
sigma = np.array([
|
||||
[s11, s12, s31],
|
||||
[s12, s22, s23],
|
||||
[s31, s23, s33]
|
||||
]) # https://forum.freecadweb.org/viewtopic.php?f=18&t=24637&start=10#p240408
|
||||
|
||||
eigenvalues, eigenvectors = np.linalg.eig(sigma)
|
||||
|
||||
#
|
||||
# HarryvL: suppress complex eigenvalue and vectors that may occur for
|
||||
# near-zero (numerical noise) stress fields
|
||||
#
|
||||
|
||||
eigenvalues = eigenvalues.real
|
||||
eigenvectors = eigenvectors.real
|
||||
|
||||
eigenvectors[:, 0] = eigenvalues[0] * eigenvectors[:, 0]
|
||||
eigenvectors[:, 1] = eigenvalues[1] * eigenvectors[:, 1]
|
||||
eigenvectors[:, 2] = eigenvalues[2] * eigenvectors[:, 2]
|
||||
|
||||
idx = eigenvalues.argsort()[::-1]
|
||||
eigenvalues = eigenvalues[idx]
|
||||
eigenvectors = eigenvectors[:, idx]
|
||||
|
||||
maxshear = (eigenvalues[0] - eigenvalues[2]) / 2.0
|
||||
|
||||
return (eigenvalues[0], eigenvalues[1], eigenvalues[2], maxshear,
|
||||
tuple([tuple(row) for row in eigenvectors.T]))
|
||||
|
||||
|
||||
def calculate_rho(stress_tensor, fy):
|
||||
|
||||
#
|
||||
# HarryvL - Calculation of Reinforcement Ratios and
|
||||
# Concrete Stresses according to http://heronjournal.nl/53-4/3.pdf
|
||||
# - See post:
|
||||
# https://forum.freecadweb.org/viewtopic.php?f=18&t=28821
|
||||
# fy: factored yield strength of reinforcement bars
|
||||
#
|
||||
|
||||
rmin = 1.0e9
|
||||
eqmin = 14
|
||||
|
||||
sxx = stress_tensor[0]
|
||||
syy = stress_tensor[1]
|
||||
szz = stress_tensor[2]
|
||||
sxy = stress_tensor[3]
|
||||
syz = stress_tensor[5]
|
||||
sxz = stress_tensor[4]
|
||||
|
||||
rhox = np.zeros(15)
|
||||
rhoy = np.zeros(15)
|
||||
rhoz = np.zeros(15)
|
||||
|
||||
# i1=sxx+syy+szz NOT USED
|
||||
# i2=sxx*syy+syy*szz+szz*sxx-sxy**2-sxz**2-syz**2 NOT USED
|
||||
i3 = (sxx * syy * szz + 2 * sxy * sxz * syz - sxx * syz**2
|
||||
- syy * sxz**2 - szz * sxy**2)
|
||||
|
||||
# Solution (5)
|
||||
d = (sxx * syy - sxy**2)
|
||||
if d != 0.:
|
||||
rhoz[0] = i3 / d / fy
|
||||
|
||||
# Solution (6)
|
||||
d = (sxx * szz - sxz**2)
|
||||
if d != 0.:
|
||||
rhoy[1] = i3 / d / fy
|
||||
|
||||
# Solution (7)
|
||||
d = (syy * szz - syz**2)
|
||||
if d != 0.:
|
||||
rhox[2] = i3 / d / fy
|
||||
|
||||
# Solution (9)
|
||||
if sxx != 0.:
|
||||
fc = sxz * sxy / sxx - syz
|
||||
fxy = sxy**2 / sxx
|
||||
fxz = sxz**2 / sxx
|
||||
|
||||
# Solution (9+)
|
||||
rhoy[3] = syy - fxy + fc
|
||||
rhoy[3] /= fy
|
||||
rhoz[3] = szz - fxz + fc
|
||||
rhoz[3] /= fy
|
||||
|
||||
# Solution (9-)
|
||||
rhoy[4] = syy - fxy - fc
|
||||
rhoy[4] /= fy
|
||||
rhoz[4] = szz - fxz - fc
|
||||
rhoz[4] /= fy
|
||||
|
||||
# Solution (10)
|
||||
if syy != 0.:
|
||||
fc = syz * sxy / syy - sxz
|
||||
fxy = sxy**2 / syy
|
||||
fyz = syz**2 / syy
|
||||
|
||||
# Solution (10+)
|
||||
rhox[5] = sxx - fxy + fc
|
||||
rhox[5] /= fy
|
||||
rhoz[5] = szz - fyz + fc
|
||||
rhoz[5] /= fy
|
||||
|
||||
# Solution (10-)vm
|
||||
rhox[6] = sxx - fxy - fc
|
||||
|
||||
rhox[6] /= fy
|
||||
rhoz[6] = szz - fyz - fc
|
||||
rhoz[6] /= fy
|
||||
|
||||
# Solution (11)
|
||||
if szz != 0.:
|
||||
fc = sxz * syz / szz - sxy
|
||||
fxz = sxz**2 / szz
|
||||
fyz = syz**2 / szz
|
||||
|
||||
# Solution (11+)
|
||||
rhox[7] = sxx - fxz + fc
|
||||
rhox[7] /= fy
|
||||
rhoy[7] = syy - fyz + fc
|
||||
rhoy[7] /= fy
|
||||
|
||||
# Solution (11-)
|
||||
rhox[8] = sxx - fxz - fc
|
||||
rhox[8] /= fy
|
||||
rhoy[8] = syy - fyz - fc
|
||||
rhoy[8] /= fy
|
||||
|
||||
# Solution (13)
|
||||
rhox[9] = (sxx + sxy + sxz) / fy
|
||||
rhoy[9] = (syy + sxy + syz) / fy
|
||||
rhoz[9] = (szz + sxz + syz) / fy
|
||||
|
||||
# Solution (14)
|
||||
rhox[10] = (sxx + sxy - sxz) / fy
|
||||
rhoy[10] = (syy + sxy - syz) / fy
|
||||
rhoz[10] = (szz - sxz - syz) / fy
|
||||
|
||||
# Solution (15)
|
||||
rhox[11] = (sxx - sxy - sxz) / fy
|
||||
rhoy[11] = (syy - sxy + syz) / fy
|
||||
rhoz[11] = (szz - sxz + syz) / fy
|
||||
|
||||
# Solution (16)
|
||||
rhox[12] = (sxx - sxy + sxz) / fy
|
||||
rhoy[12] = (syy - sxy - syz) / fy
|
||||
rhoz[12] = (szz + sxz - syz) / fy
|
||||
|
||||
# Solution (17)
|
||||
if syz != 0.:
|
||||
rhox[13] = (sxx - sxy * sxz / syz) / fy
|
||||
if sxz != 0.:
|
||||
rhoy[13] = (syy - sxy * syz / sxz) / fy
|
||||
if sxy != 0.:
|
||||
rhoz[13] = (szz - sxz * syz / sxy) / fy
|
||||
|
||||
for ir in range(0, rhox.size):
|
||||
|
||||
if rhox[ir] >= -1.e-10 and rhoy[ir] >= -1.e-10 and rhoz[ir] > -1.e-10:
|
||||
|
||||
# Concrete Stresses
|
||||
scxx = sxx - rhox[ir] * fy
|
||||
scyy = syy - rhoy[ir] * fy
|
||||
sczz = szz - rhoz[ir] * fy
|
||||
ic1 = (scxx + scyy + sczz)
|
||||
ic2 = (scxx * scyy + scyy * sczz + sczz * scxx - sxy**2
|
||||
- sxz**2 - syz**2)
|
||||
ic3 = (scxx * scyy * sczz + 2 * sxy * sxz * syz - scxx * syz**2
|
||||
- scyy * sxz**2 - sczz * sxy**2)
|
||||
|
||||
if ic1 <= 1.e-6 and ic2 >= -1.e-6 and ic3 <= 1.0e-6:
|
||||
|
||||
rsum = rhox[ir] + rhoy[ir] + rhoz[ir]
|
||||
|
||||
if rsum < rmin and rsum > 0.:
|
||||
rmin = rsum
|
||||
eqmin = ir
|
||||
|
||||
return rhox[eqmin], rhoy[eqmin], rhoz[eqmin]
|
||||
|
||||
|
||||
def calculate_mohr_coulomb(prin1, prin3, phi, fck):
|
||||
#
|
||||
# HarryvL - Calculation of Mohr Coulomb yield criterion to judge
|
||||
# concrete curshing and shear failure
|
||||
# phi: angle of internal friction
|
||||
# fck: factored compressive strength of the matrix material (usually concrete)
|
||||
#
|
||||
|
||||
coh = fck * (1 - np.sin(phi)) / 2 / np.cos(phi)
|
||||
|
||||
mc_stress = ((prin1 - prin3) + (prin1 + prin3) * np.sin(phi)
|
||||
- 2. * coh * np.cos(phi))
|
||||
|
||||
if mc_stress < 0.:
|
||||
mc_stress = 0.
|
||||
|
||||
return mc_stress
|
||||
|
||||
|
||||
def calculate_disp_abs(displacements):
|
||||
# see https://forum.freecadweb.org/viewtopic.php?f=18&t=33106&start=100#p296657
|
||||
return [np.linalg.norm(nd) for nd in displacements]
|
||||
|
||||
@@ -184,9 +184,14 @@ class _Container(object):
|
||||
|
||||
# get member
|
||||
# materials
|
||||
self.materials_linear = self.get_several_member(
|
||||
std_mats = self.get_several_member(
|
||||
'Fem::Material'
|
||||
)
|
||||
rei_mats = self.get_several_member(
|
||||
'Fem::MaterialReinforced'
|
||||
)
|
||||
self.materials_linear = std_mats + rei_mats
|
||||
|
||||
self.materials_nonlinear = self.get_several_member(
|
||||
'Fem::MaterialMechanicalNonlinear'
|
||||
)
|
||||
|
||||
@@ -82,6 +82,7 @@ class TestObjectCreate(unittest.TestCase):
|
||||
analysis.addObject(ObjectsFem.makeMaterialFluid(doc))
|
||||
mat = analysis.addObject(ObjectsFem.makeMaterialSolid(doc))[0]
|
||||
analysis.addObject(ObjectsFem.makeMaterialMechanicalNonlinear(doc, mat))
|
||||
analysis.addObject(ObjectsFem.makeMaterialReinforced(doc))
|
||||
|
||||
msh = analysis.addObject(ObjectsFem.makeMeshGmsh(doc))[0]
|
||||
analysis.addObject(ObjectsFem.makeMeshBoundaryLayer(doc, msh))
|
||||
@@ -266,6 +267,10 @@ class TestObjectType(unittest.TestCase):
|
||||
'Fem::MaterialMechanicalNonlinear',
|
||||
type_of_obj(ObjectsFem.makeMaterialMechanicalNonlinear(doc, materialsolid))
|
||||
)
|
||||
self.assertEqual(
|
||||
'Fem::MaterialReinforced',
|
||||
type_of_obj(ObjectsFem.makeMaterialReinforced(doc))
|
||||
)
|
||||
mesh = ObjectsFem.makeMeshGmsh(doc)
|
||||
self.assertEqual(
|
||||
'Fem::FemMeshGmsh',
|
||||
@@ -330,7 +335,7 @@ class TestObjectType(unittest.TestCase):
|
||||
'Fem::FemEquationElmerHeat',
|
||||
type_of_obj(ObjectsFem.makeEquationHeat(doc, solverelmer))
|
||||
)
|
||||
# is = 43 (just copy in empty file to test)
|
||||
# is = 44 tests (just copy in empty file to test)
|
||||
# TODO: vtk post objs
|
||||
# TODO: use different type for fluid and solid material
|
||||
|
||||
@@ -450,6 +455,10 @@ class TestObjectType(unittest.TestCase):
|
||||
ObjectsFem.makeMaterialMechanicalNonlinear(doc, materialsolid),
|
||||
'Fem::MaterialMechanicalNonlinear'
|
||||
))
|
||||
self.assertTrue(is_of_type(
|
||||
ObjectsFem.makeMaterialReinforced(doc),
|
||||
'Fem::MaterialReinforced'
|
||||
))
|
||||
mesh = ObjectsFem.makeMeshGmsh(doc)
|
||||
self.assertTrue(is_of_type(
|
||||
mesh,
|
||||
@@ -516,7 +525,7 @@ class TestObjectType(unittest.TestCase):
|
||||
ObjectsFem.makeEquationHeat(doc, solverelmer),
|
||||
'Fem::FemEquationElmerHeat'
|
||||
))
|
||||
# is = 43 (just copy in empty file to test)
|
||||
# is = 44 tests (just copy in empty file to test)
|
||||
|
||||
# ********************************************************************************************
|
||||
def test_femobjects_derivedfromfem(
|
||||
@@ -899,6 +908,20 @@ class TestObjectType(unittest.TestCase):
|
||||
'Fem::MaterialMechanicalNonlinear'
|
||||
))
|
||||
|
||||
# MaterialReinforced
|
||||
self.assertTrue(is_derived_from(
|
||||
ObjectsFem.makeMaterialReinforced(doc),
|
||||
'App::DocumentObject'
|
||||
))
|
||||
self.assertTrue(is_derived_from(
|
||||
ObjectsFem.makeMaterialReinforced(doc),
|
||||
'App::MaterialObjectPython'
|
||||
))
|
||||
self.assertTrue(is_derived_from(
|
||||
ObjectsFem.makeMaterialReinforced(doc),
|
||||
'Fem::MaterialReinforced'
|
||||
))
|
||||
|
||||
# FemMeshGmsh
|
||||
self.assertTrue(is_derived_from(
|
||||
mesh, 'App::DocumentObject'
|
||||
@@ -1270,6 +1293,11 @@ class TestObjectType(unittest.TestCase):
|
||||
materialsolid
|
||||
).isDerivedFrom('Fem::FeaturePython')
|
||||
)
|
||||
self.assertTrue(
|
||||
ObjectsFem.makeMaterialReinforced(
|
||||
doc
|
||||
).isDerivedFrom('App::MaterialObjectPython')
|
||||
)
|
||||
mesh = ObjectsFem.makeMeshGmsh(doc)
|
||||
self.assertTrue(
|
||||
mesh.isDerivedFrom('Fem::FemMeshObjectPython')
|
||||
@@ -1356,7 +1384,7 @@ class TestObjectType(unittest.TestCase):
|
||||
solverelmer
|
||||
).isDerivedFrom('App::FeaturePython')
|
||||
)
|
||||
# is = 43 (just copy in empty file to test)
|
||||
# is = 44 tests (just copy in empty file to test)
|
||||
|
||||
# ********************************************************************************************
|
||||
def tearDown(
|
||||
|
||||
@@ -313,11 +313,11 @@ class TestResult(unittest.TestCase):
|
||||
)
|
||||
|
||||
# ********************************************************************************************
|
||||
def test_stress_principal(
|
||||
def test_stress_principal_std(
|
||||
self
|
||||
):
|
||||
expected_principal = (-178.0076, -194.0749, -468.9075, 145.4499)
|
||||
from femresult.resulttools import calculate_principal_stress as pr
|
||||
from femresult.resulttools import calculate_principal_stress_std as pr
|
||||
prin = pr(self.get_stress_values())
|
||||
rounded_prin = (
|
||||
round(prin[0], 4),
|
||||
@@ -332,6 +332,102 @@ class TestResult(unittest.TestCase):
|
||||
"Calculated principal stresses are not the expected values."
|
||||
)
|
||||
|
||||
# ********************************************************************************************
|
||||
def test_stress_principal_reinforced(
|
||||
self
|
||||
):
|
||||
expected_principal = (-178.0076, -194.0749, -468.9075, 145.4499)
|
||||
from femresult.resulttools import calculate_principal_stress_reinforced as prrc
|
||||
prin = prrc(self.get_stress_values())
|
||||
rounded_prin = (
|
||||
round(prin[0], 4),
|
||||
round(prin[1], 4),
|
||||
round(prin[2], 4),
|
||||
round(prin[3], 4))
|
||||
# fcc_print(rounded_prin)
|
||||
self.assertEqual(
|
||||
rounded_prin,
|
||||
expected_principal,
|
||||
"Calculated principal reinforced stresses are not the expected values."
|
||||
)
|
||||
|
||||
# ********************************************************************************************
|
||||
def test_rho(
|
||||
self
|
||||
):
|
||||
data = (
|
||||
(
|
||||
# Case1: Governing Eq.14
|
||||
(2.000, -2.000, 5.000, 6.000, -4.000, 2.000),
|
||||
(0.02400, 0.00400, 0.01400)
|
||||
),
|
||||
(
|
||||
# Case2: Governing Eq.10+
|
||||
(-3.000, -7.000, 0.000, 6.000, -4.000, 2.000),
|
||||
(0.00886, 0.00000, 0.00571),
|
||||
),
|
||||
(
|
||||
# Case3: Governing Eq.5
|
||||
(-1.000, -7.000, 10.000, 0.000, 0.000, 5.000),
|
||||
(0.00000, 0.00000, 0.02714)
|
||||
),
|
||||
(
|
||||
# Case4: Governing Eq.13
|
||||
(3.000, 0.000, 10.000, 0.000, 5.000, 0.000),
|
||||
(0.01600, 0.00000, 0.03000)
|
||||
),
|
||||
(
|
||||
# Case5: Governing Eq.11-
|
||||
(10.000, 7.000, -3.000, 3.000, 1.000, -2.000),
|
||||
(0.02533, 0.02133, 0.00000)
|
||||
),
|
||||
(
|
||||
# Case6: Governing Eq.14
|
||||
(4.000, -7.000, 3.000, 7.000, 0.000, -5.000),
|
||||
(0.02200, 0.01000, 0.01600)
|
||||
),
|
||||
(
|
||||
# Case7: Governing Eq.14
|
||||
(8.000, -14.000, 6.000, 14.000, 0.000, -10.000),
|
||||
(0.04400, 0.02000, 0.03200)
|
||||
),
|
||||
(
|
||||
# Case8: Governing Eq.17
|
||||
(1.000, 0.000, 3.000, 10.000, -8.000, 7.000),
|
||||
(0.02486, 0.01750, 0.01720)
|
||||
),
|
||||
(
|
||||
# Case9: Governing Eq.13
|
||||
(0.000, 0.000, 0.000, 10.000, 8.000, 7.000),
|
||||
(0.03600, 0.03400, 0.03000)
|
||||
),
|
||||
(
|
||||
# Case10: Governing Eq.13
|
||||
(15.000, 0.000, 0.000, 0.000, 0.000, 0.000),
|
||||
(0.03000, 0.00000, 0.00000)
|
||||
),
|
||||
(
|
||||
# Case11: Governing Eq.13
|
||||
(0.000, 0.000, 0.000, 5.000, 0.000, 0.000),
|
||||
(0.01000, 0.01000, 0.00000)
|
||||
)
|
||||
)
|
||||
|
||||
from femresult.resulttools import calculate_rho as calrho
|
||||
for i, case in enumerate(data):
|
||||
res = calrho(case[0], 500)
|
||||
rhores = (
|
||||
round(res[0], 5),
|
||||
round(res[1], 5),
|
||||
round(res[2], 5)
|
||||
)
|
||||
# fcc_print('Case{}: {}'.format(i + 1 , rhores))
|
||||
self.assertEqual(
|
||||
rhores, case[1],
|
||||
"Calculated rho are not the expected Case{}."
|
||||
.format(i + 1)
|
||||
)
|
||||
|
||||
# ********************************************************************************************
|
||||
def test_disp_abs(
|
||||
self
|
||||
|
||||
@@ -223,7 +223,10 @@ class FemToolsCcx(QtCore.QRunnable, QtCore.QObject):
|
||||
|
||||
## @var materials_linear
|
||||
# list of linear materials from the analysis. Updated with update_objects
|
||||
self.materials_linear = self._get_several_member('Fem::Material')
|
||||
self.materials_linear = (
|
||||
self._get_several_member('Fem::Material')
|
||||
+ self._get_several_member('Fem::MaterialReinforced')
|
||||
)
|
||||
## @var materials_nonlinear
|
||||
# list of nonlinear materials from the analysis. Updated with update_objects
|
||||
self.materials_nonlinear = self._get_several_member('Fem::MaterialMechanicalNonlinear')
|
||||
@@ -408,6 +411,47 @@ class FemToolsCcx(QtCore.QRunnable, QtCore.QObject):
|
||||
"Thermomechanical analysis: No SpecificHeat "
|
||||
"defined for at least one material.\n" # allowed to be 0.0 (in ccx)
|
||||
)
|
||||
if femutils.is_of_type(mat_obj, 'Fem::MaterialReinforced'):
|
||||
# additional tests for reinforced materials,
|
||||
# they are needed for result calculation not for ccx analysis
|
||||
mat_map_m = mat_obj.Material
|
||||
if 'AngleOfFriction' in mat_map_m:
|
||||
# print(Units.Quantity(mat_map_m['AngleOfFriction']).Value)
|
||||
if not Units.Quantity(mat_map_m['AngleOfFriction']).Value:
|
||||
message += (
|
||||
"Value of AngleOfFriction is set to 0.0 "
|
||||
"for the matrix of a reinforced material.\n"
|
||||
)
|
||||
else:
|
||||
message += (
|
||||
"No AngleOfFriction defined for the matrix "
|
||||
"of at least one reinforced material.\n"
|
||||
)
|
||||
if 'CompressiveStrength' in mat_map_m:
|
||||
# print(Units.Quantity(mat_map_m['CompressiveStrength']).Value)
|
||||
if not Units.Quantity(mat_map_m['CompressiveStrength']).Value:
|
||||
message += (
|
||||
"Value of CompressiveStrength is set to 0.0 "
|
||||
"for the matrix of a reinforced material.\n"
|
||||
)
|
||||
else:
|
||||
message += (
|
||||
"No CompressiveStrength defined for the matrinx "
|
||||
"of at least one reinforced material.\n"
|
||||
)
|
||||
mat_map_r = mat_obj.Reinforcement
|
||||
if 'YieldStrength' in mat_map_r:
|
||||
# print(Units.Quantity(mat_map_r['YieldStrength']).Value)
|
||||
if not Units.Quantity(mat_map_r['YieldStrength']).Value:
|
||||
message += (
|
||||
"Value of YieldStrength is set to 0.0 "
|
||||
"for the reinforcement of a reinforced material.\n"
|
||||
)
|
||||
else:
|
||||
message += (
|
||||
"No YieldStrength defined for the reinforcement "
|
||||
"of at least one reinforced material.\n"
|
||||
)
|
||||
if len(self.materials_linear) == 1:
|
||||
mobj = self.materials_linear[0]['Object']
|
||||
if hasattr(mobj, 'References') and mobj.References:
|
||||
|
||||
20
src/Mod/Material/StandardMaterial/Concrete-EN-C35_45.FCMat
Normal file
20
src/Mod/Material/StandardMaterial/Concrete-EN-C35_45.FCMat
Normal file
@@ -0,0 +1,20 @@
|
||||
; Concrete-EN-C35_45
|
||||
; (c) 2019 Bernd Hahnebach (CC-BY 3.0)
|
||||
; information about the content of such cards can be found on the wiki:
|
||||
; https://www.freecadweb.org/wiki/Material
|
||||
; file created by FreeCAD 0.19.16886 (Git)
|
||||
|
||||
[General]
|
||||
Name = Concrete-EN-C35/45
|
||||
Description = Concrete matrix for reinforcement material examples, 0.6 x 0.75 x 35 MPa = 15.75 MPa (https://forum.freecadweb.org/viewtopic.php?f=18&t=33106&start=200#p311075)
|
||||
Father = Aggregate
|
||||
|
||||
[Mechanical]
|
||||
AngleOfFriction = 30 deg
|
||||
CompressiveStrength = 15.75 MPa
|
||||
Density = 2500 kg/m^3
|
||||
PoissonRatio = 0.17
|
||||
YoungsModulus = 32000 MPa
|
||||
|
||||
[Cost]
|
||||
ProductURL = https://en.wikipedia.org/wiki/Concrete
|
||||
@@ -0,0 +1,15 @@
|
||||
; Reinforcement-FIB-B500
|
||||
; (c) 2019 Bernd Hahnebach (CC-BY 3.0)
|
||||
; information about the content of such cards can be found on the wiki:
|
||||
; https://www.freecadweb.org/wiki/Material
|
||||
; file created by FreeCAD 0.19.16886 (Git)
|
||||
|
||||
[General]
|
||||
Name = Reinforcement-Harry
|
||||
Description = Reinforcement inside concrete for reinforcement material examples, from fib examples, 0.84 x 0.75 x 500 MPa = 315 MPa (https://forum.freecadweb.org/viewtopic.php?f=18&t=33106&start=200#p311705)
|
||||
|
||||
[Mechanical]
|
||||
Density = 7850 kg/m^3
|
||||
PoissonRatio = 0.3
|
||||
YieldStrength = 315 MPa
|
||||
YoungsModulus = 210000 MPa
|
||||
@@ -6,6 +6,7 @@ AlMgSi1F31|AlMgSi1F31|AlMgSi1F31|||||Metal|Aluminium|Aluminium|3.2315.72|DIN 172
|
||||
Aluminum-6061-T6|Aluminum 6061-T6|||Precipitation-hardened, Nonferrous Aluminum alloy|||Metal|Aluminium|Aluminium||||||||2700 kg/m^3||0.33|||310 MPa||69000 MPa||167 W/m/K|||||||||||||||||||||||||https://en.wikipedia.org/wiki/6061_aluminium_alloy||
|
||||
AlZn4-5Mg1F35|AlZn4,5Mg1F35|AlZn4,5Mg1F35|||||Metal|Aluminium|Aluminium|3.4335.71|DIN 1725||||||2700 kg/m^3||0.3|27000 MPa|10|350 MPa|290 MPa|70000 MPa|||0.000023 m/m/K||||||||||||||||||||||||||
|
||||
CalculiX-Steel|CalculiX-Steel|||Standard steel material for CalculiX sample calculations|||Metal||||||||||7900 kg/m^3||0.3|||||210000 MPa|590 J/kg/K|43 W/m/K|0.000012 m/m/K||||||||||||||||||||||||||
|
||||
Concrete-EN-C35_45|Concrete-EN-C35/45|||Concrete matrix for reinforcement material examples, 0.6 x 0.75 x 35 MPa = 15.75 MPa (https://forum.freecadweb.org/viewtopic.php?f=18&t=33106&start=200#p311075)|||Aggregate||||||||30 deg|15.75 MPa|2500 kg/m^3||0.17|||||32000 MPa|||||||||||||||||||||||||||https://en.wikipedia.org/wiki/Concrete||
|
||||
Concrete-Generic|Concrete|||A standard C-25 construction concrete|||Aggregate|||||||Masterformat 03 33 13||25 MPa|2400 kg/m^3||0.17|||||32000 MPa|||||||||||||||||||||||||||https://en.wikipedia.org/wiki/Concrete||
|
||||
Glass-E-GlassFibre|Glass-E|||Glass Fibre|||Glass|||||||||1080 MPa|2580 kg/m^3|||||3445 MPa|||||||||||||||||||||||||||||https://en.wikipedia.org/wiki/Glass_fiber||
|
||||
Glass-Generic|Glass|||Generic soda-lime glass|Normalglas|Szkło sodowe|Glass||||||||||2520 kg/m^3||0.22|||||72000 MPa|||0.000009 m/m/K||||||||||||||||||||||||https://en.wikipedia.org/wiki/Soda-lime_glass||
|
||||
@@ -17,6 +18,7 @@ PLA-Generic|PLA|||Polylactic acid or polylactide (PLA, Poly) is a biodegradable
|
||||
PP-Generic|Polypropylene||||||||||||http://www.matweb.com/search/DataSheet.aspx?MatGUID=a882a1c603374e278d062f106dfda95b|||10 MPa|916 kg/m^3||0.44|||79.7 MPa|32.8 MPa|1470 MPa|1920 J/kg/K|0.249 W/m/K|0.000123 m/m/K||||||||||||||||||||||||https://en.wikipedia.org/wiki/Polypropylene||
|
||||
PTFE-Generic|PTFE||||||||||||http://www.matweb.com/search/datasheet.aspx?MatGUID=4d14eac958e5401a8fd152e1261b6843|||10.2 MPa|2070 kg/m^3||0.46|||34.6 MPa|20.5 MPa|564 MPa|1010 J/kg/K|0.263 W/m/K|0.000108 m/m/K||||||||||||||||||||||||https://en.wikipedia.org/wiki/Polytetrafluoroethylene||
|
||||
PVC-Generic|PVC||||||||||||http://www.matweb.com/search/DataSheet.aspx?MatGUID=1f650966ec834bb8833dd4c6e3116079||||1380 kg/m^3||0.38|||50 MPa||2800 MPa|1000 J/kg/K|0.150 W/m/K|0.000075 m/m/K||||||||||||||||||||||||https://en.wikipedia.org/wiki/Polyvinyl_chloride||
|
||||
Reinforcement-FIB-B500|Reinforcement-Harry|||Reinforcement inside concrete for reinforcement material examples, from fib examples, 0.84 x 0.75 x 500 MPa = 315 MPa (https://forum.freecadweb.org/viewtopic.php?f=18&t=33106&start=200#p311705)|||||||||||||7850 kg/m^3||0.3||||315 MPa|210000 MPa|||||||||||||||||||||||||||||
|
||||
Steel-15CrNi6|15CrNi6|||High-strength carbon steel|höchste Beanspruchung, Achsen, Wellen, Ritzel, Nocken, Kegelräder|Wysokowytrzymała stal węglowa|Metal|Case-hardened steel|Einsatzstahl|1.5919|EN 10084||||||7800 kg/m^3||0.3|81000 MPa|9|1000 MPa|680 MPa|210000 MPa|||0.000011 m/m/K||||||||||||||||||||||||||
|
||||
Steel-17CrNiMo6|17CrNiMo6|17CrNiMo6|||höchste Beanspruchung, Wellen, Zahnräder||Metal|Case-hardened steel|Einsatzstahl|1.6587|EN 10084||||||7800 kg/m^3||0.3|81000 MPa|8|1150 MPa|830 MPa|210000 MPa|||0.000011 m/m/K||||||||||||||||||||||||||
|
||||
Steel-1C22|1C22|C22||Case hardened alloy steel|kleiner Vergütungsdurchmesser, gut schweißbar|Stal stopowa do nawęglania|Metal|Heat-treatable steel|Vergütungsstahl|1.0402|EN 10083-1||||||7800 kg/m^3||0.3|81000 MPa|27|400 MPa|230 MPa|210000 MPa|||0.000011 m/m/K||||||||||||||||||||||||||
|
||||
|
||||
|
Binary file not shown.
Reference in New Issue
Block a user