Skip to content
GitLab
Projects
Groups
Snippets
Help
Loading...
Help
Help
Support
Community forum
Keyboard shortcuts
?
Submit feedback
Contribute to GitLab
Sign in / Register
Toggle navigation
M
mfront-wrapper
Project overview
Project overview
Details
Activity
Releases
Repository
Repository
Files
Commits
Branches
Tags
Contributors
Graph
Compare
Issues
9
Issues
9
List
Boards
Labels
Service Desk
Milestones
Merge Requests
0
Merge Requests
0
CI / CD
CI / CD
Pipelines
Jobs
Schedules
Operations
Operations
Incidents
Environments
Analytics
Analytics
CI / CD
Repository
Value Stream
Wiki
Wiki
Members
Members
Collapse sidebar
Close sidebar
Activity
Graph
Create a new issue
Jobs
Commits
Issue Boards
Open sidebar
navier-fenics
mfront-wrapper
Commits
12c69475
Commit
12c69475
authored
Mar 08, 2020
by
Jeremy BLEYER
Browse files
Options
Browse Files
Download
Email Patches
Plain Diff
Automatic registration and modifs on size
parent
83a2967f
Changes
10
Hide whitespace changes
Inline
Side-by-side
Showing
10 changed files
with
220 additions
and
85 deletions
+220
-85
demos/StationaryHeatTransfer.py
demos/StationaryHeatTransfer.py
+1
-1
demos/logarithmic_strain_plasticity.py
demos/logarithmic_strain_plasticity.py
+3
-3
demos/multiphase_model.py
demos/multiphase_model.py
+3
-3
demos/phase_field.py
demos/phase_field.py
+2
-0
demos/small_strain_vonMises_plasticity.py
demos/small_strain_vonMises_plasticity.py
+7
-9
materials/src/Makefile.mfront
materials/src/Makefile.mfront
+2
-2
materials/src/targets.lst
materials/src/targets.lst
+47
-3
mfront_wrapper/gradient_flux.py
mfront_wrapper/gradient_flux.py
+9
-3
mfront_wrapper/nonlinear_material.py
mfront_wrapper/nonlinear_material.py
+11
-2
mfront_wrapper/nonlinear_problem.py
mfront_wrapper/nonlinear_problem.py
+135
-59
No files found.
demos/StationaryHeatTransfer.py
View file @
12c69475
...
...
@@ -38,7 +38,7 @@ material = mf.MFrontNonlinearMaterial("materials/src/libBehaviour.so",
problem
=
mf
.
MFrontNonlinearProblem
(
T
,
material
,
quadrature_degree
=
0
)
problem
.
bc
=
bc
problem
.
register_gradient
(
"TemperatureGradient"
,
grad
(
T
))
#
problem.register_gradient("TemperatureGradient", grad(T))
T
.
interpolate
(
Constant
(
Tl
))
...
...
demos/logarithmic_strain_plasticity.py
View file @
12c69475
...
...
@@ -33,15 +33,15 @@ file_results.parameters["functions_share_mesh"] = True
selfweight
=
Expression
((
"0"
,
"0"
,
"-t*qmax"
),
t
=
0.
,
qmax
=
50e6
,
degree
=
0
)
material
=
mf
.
MFrontNonlinearMaterial
(
"
../
materials/src/libBehaviour.so"
,
material
=
mf
.
MFrontNonlinearMaterial
(
"materials/src/libBehaviour.so"
,
"LogarithmicStrainPlasticity"
)
problem
=
mf
.
MFrontNonlinearProblem
(
u
,
material
)
problem
.
set_loading
(
dot
(
selfweight
,
u
)
*
dx
)
problem
.
bc
=
bc
p
=
problem
.
get_state_variable
(
name
=
"EquivalentPlasticStrain"
)
p
=
problem
.
get_state_variable
(
"EquivalentPlasticStrain"
)
assert
(
ufl
.
shape
(
p
)
==
())
epsel
=
problem
.
get_state_variable
(
name
=
"ElasticStrain"
)
epsel
=
problem
.
get_state_variable
(
"ElasticStrain"
)
print
(
ufl
.
shape
(
epsel
))
prm
=
problem
.
solver
.
parameters
...
...
demos/multiphase_model.py
View file @
12c69475
...
...
@@ -52,9 +52,9 @@ material = mf.MFrontNonlinearMaterial("materials/src/libBehaviour.so",
problem
=
mf
.
MFrontNonlinearProblem
(
u
,
material
,
quadrature_degree
=
0
)
problem
.
bc
=
bc
problem
.
register_gradient
(
"MatrixStrain"
,
sym
(
grad
(
u1
))
,
symmetric
=
True
)
problem
.
register_gradient
(
"InclusionStrain"
,
sym
(
grad
(
u2
))
,
symmetric
=
True
)
problem
.
register_gradient
(
"RelativeDisplacement"
,
diag
(
u2
-
u1
)
,
symmetric
=
True
)
problem
.
register_gradient
(
"MatrixStrain"
,
sym
(
grad
(
u1
)))
problem
.
register_gradient
(
"InclusionStrain"
,
sym
(
grad
(
u2
)))
problem
.
register_gradient
(
"RelativeDisplacement"
,
diag
(
u2
-
u1
))
problem
.
solve
(
u
.
vector
())
...
...
demos/phase_field.py
View file @
12c69475
#!/usr/bin/env python3
# -*- coding: utf-8 -*-
"""
...
...
@@ -32,6 +33,7 @@ problem.bc = bc
problem
.
register_gradient
(
"Damage"
,
d
)
problem
.
register_gradient
(
"DamageGradient"
,
grad
(
d
))
problem
.
solve
(
d
.
vector
())
#TODO: manage state variables communication with external computation
import
matplotlib.pyplot
as
plt
p
=
plot
(
d
)
...
...
demos/small_strain_vonMises_plasticity.py
View file @
12c69475
...
...
@@ -46,14 +46,12 @@ for hypothesis in ["plane_strain", "axisymmetric"]:
material_properties
=
mat_prop
)
problem
=
mf
.
MFrontNonlinearProblem
(
u
,
material
,
quadrature_degree
=
4
)
problem
.
bc
=
bc
# problem.define_form(mf.Stress(u, name="sigma"))
problem
.
register_gradient
(
"Strain"
,
sym
(
grad
(
u
)),
symmetric
=
True
)
problem
.
set_loading
(
loading
*
dot
(
n
,
u
)
*
measure
*
ds
(
4
))
# p = problem.get_state_variable(name=
"EquivalentPlasticStrain")
#
assert (ufl.shape(p) == ())
# epsel = problem.get_state_variable(name=
"ElasticStrain")
#
assert (ufl.shape(epsel)==(4, ))
p
=
problem
.
get_state_variable
(
"EquivalentPlasticStrain"
)
assert
(
ufl
.
shape
(
p
)
==
())
epsel
=
problem
.
get_state_variable
(
"ElasticStrain"
)
assert
(
ufl
.
shape
(
epsel
)
==
(
4
,
))
file_results
=
XDMFFile
(
"results/plasticity_{}_results.xdmf"
.
format
(
hypothesis
))
file_results
.
parameters
[
"flush_output"
]
=
True
...
...
@@ -70,9 +68,9 @@ for hypothesis in ["plane_strain", "axisymmetric"]:
file_results
.
write
(
u
,
t
)
# p_avg.assign(project(epsel[0]
, P0))
#
file_results.write(p_avg, t)
#
results[i+1, :] = (u(Ri, 0)[0], t)
p_avg
.
assign
(
project
(
p
,
P0
))
file_results
.
write
(
p_avg
,
t
)
results
[
i
+
1
,
:]
=
(
u
(
Ri
,
0
)[
0
],
t
)
import
matplotlib.pyplot
as
plt
...
...
materials/src/Makefile.mfront
View file @
12c69475
...
...
@@ -12,7 +12,7 @@ INCLUDES := -I../include \
CXXFLAGS
:=
-Wall
-Wfatal-errors
-ansi
$(
shell
tfel-config
--oflags
)
-fPIC
$(INCLUDES)
SRCCXX
=
MultiphaseModel-generic.cxx MultiphaseModel.cxx PhaseField-generic.cxx PhaseField
.cxx
SRCCXX
=
IsotropicLinearHardeningPlasticity-generic.cxx IsotropicLinearHardeningPlasticity.cxx LogarithmicStrainPlasticity-generic.cxx LogarithmicStrainPlasticity.cxx MultiphaseModel-generic.cxx MultiphaseModel.cxx PhaseField-generic.cxx PhaseField.cxx PhaseFieldCoupled-generic.cxx PhaseFieldCoupled.cxx StationaryHeatTransfer-generic.cxx StationaryHeatTransfer
.cxx
makefiles1
=
$(SRCCXX:.cxx=.d)
makefiles2
=
$(makefiles1:.cpp=.d)
...
...
@@ -22,7 +22,7 @@ makefiles = $(makefiles2)
all
:
libBehaviour.so
libBehaviour.so
:
MultiphaseModel-generic.o MultiphaseModel.o PhaseField-generic.o PhaseField.o
libBehaviour.so
:
MultiphaseModel-generic.o MultiphaseModel.o PhaseField-generic.o PhaseField.o
PhaseFieldCoupled-generic.o PhaseFieldCoupled.o IsotropicLinearHardeningPlasticity-generic.o IsotropicLinearHardeningPlasticity.o LogarithmicStrainPlasticity-generic.o LogarithmicStrainPlasticity.o StationaryHeatTransfer-generic.o StationaryHeatTransfer.o
@
$(CXX)
-shared
$^
-o
$@
-L
"
$(
strip
$(
shell
tfel-config --library-path
))
"
$(
patsubst
%,-l%,
$(
shell
tfel-config
--library-dependency
--material
--mfront-profiling
--physical-constants
))
install
:
...
...
materials/src/targets.lst
View file @
12c69475
...
...
@@ -9,7 +9,15 @@ sources : {
"MultiphaseModel-generic.cxx",
"MultiphaseModel.cxx",
"PhaseField-generic.cxx",
"PhaseField.cxx"
"PhaseField.cxx",
"PhaseFieldCoupled-generic.cxx",
"PhaseFieldCoupled.cxx",
"IsotropicLinearHardeningPlasticity-generic.cxx",
"IsotropicLinearHardeningPlasticity.cxx",
"LogarithmicStrainPlasticity-generic.cxx",
"LogarithmicStrainPlasticity.cxx",
"StationaryHeatTransfer-generic.cxx",
"StationaryHeatTransfer.cxx"
};
cppflags : {
"$(shell tfel-config --cppflags --compiler-flags)"
...
...
@@ -30,7 +38,27 @@ epts : {
"PhaseField_Axisymmetrical",
"PhaseField_PlaneStrain",
"PhaseField_GeneralisedPlaneStrain",
"PhaseField_Tridimensional"
"PhaseField_Tridimensional",
"PhaseFieldCoupled_AxisymmetricalGeneralisedPlaneStrain",
"PhaseFieldCoupled_Axisymmetrical",
"PhaseFieldCoupled_PlaneStrain",
"PhaseFieldCoupled_GeneralisedPlaneStrain",
"PhaseFieldCoupled_Tridimensional",
"IsotropicLinearHardeningPlasticity_AxisymmetricalGeneralisedPlaneStrain",
"IsotropicLinearHardeningPlasticity_Axisymmetrical",
"IsotropicLinearHardeningPlasticity_PlaneStrain",
"IsotropicLinearHardeningPlasticity_GeneralisedPlaneStrain",
"IsotropicLinearHardeningPlasticity_Tridimensional",
"LogarithmicStrainPlasticity_AxisymmetricalGeneralisedPlaneStrain",
"LogarithmicStrainPlasticity_Axisymmetrical",
"LogarithmicStrainPlasticity_PlaneStrain",
"LogarithmicStrainPlasticity_GeneralisedPlaneStrain",
"LogarithmicStrainPlasticity_Tridimensional",
"StationaryHeatTransfer_AxisymmetricalGeneralisedPlaneStrain",
"StationaryHeatTransfer_Axisymmetrical",
"StationaryHeatTransfer_PlaneStrain",
"StationaryHeatTransfer_GeneralisedPlaneStrain",
"StationaryHeatTransfer_Tridimensional"
};
};
headers : {
...
...
@@ -41,6 +69,22 @@ headers : {
"MFront/GenericBehaviour/PhaseField-generic.hxx",
"TFEL/Material/PhaseField.hxx",
"TFEL/Material/PhaseFieldBehaviourData.hxx",
"TFEL/Material/PhaseFieldIntegrationData.hxx"
"TFEL/Material/PhaseFieldIntegrationData.hxx",
"MFront/GenericBehaviour/PhaseFieldCoupled-generic.hxx",
"TFEL/Material/PhaseFieldCoupled.hxx",
"TFEL/Material/PhaseFieldCoupledBehaviourData.hxx",
"TFEL/Material/PhaseFieldCoupledIntegrationData.hxx",
"MFront/GenericBehaviour/IsotropicLinearHardeningPlasticity-generic.hxx",
"TFEL/Material/IsotropicLinearHardeningPlasticity.hxx",
"TFEL/Material/IsotropicLinearHardeningPlasticityBehaviourData.hxx",
"TFEL/Material/IsotropicLinearHardeningPlasticityIntegrationData.hxx",
"MFront/GenericBehaviour/LogarithmicStrainPlasticity-generic.hxx",
"TFEL/Material/LogarithmicStrainPlasticity.hxx",
"TFEL/Material/LogarithmicStrainPlasticityBehaviourData.hxx",
"TFEL/Material/LogarithmicStrainPlasticityIntegrationData.hxx",
"MFront/GenericBehaviour/StationaryHeatTransfer-generic.hxx",
"TFEL/Material/StationaryHeatTransfer.hxx",
"TFEL/Material/StationaryHeatTransferBehaviourData.hxx",
"TFEL/Material/StationaryHeatTransferIntegrationData.hxx"
};
};
mfront_wrapper/gradient_flux.py
View file @
12c69475
...
...
@@ -16,14 +16,20 @@ class Gradient:
if
symmetric
is
None
:
self
.
expression
=
expression
elif
symmetric
:
self
.
expression
=
symmetric_tensor_to_vector
(
expression
)
if
self
.
variable
.
geometric_dimension
()
==
2
:
self
.
expression
=
as_vector
([
symmetric_tensor_to_vector
(
expression
)[
i
]
for
i
in
range
(
4
)])
else
:
self
.
expression
=
symmetric_tensor_to_vector
(
expression
)
else
:
self
.
expression
=
nonsymmetric_tensor_to_vector
(
expression
)
if
self
.
variable
.
geometric_dimension
()
==
2
:
self
.
expression
=
as_vector
([
nonsymmetric_tensor_to_vector
(
expression
)[
i
]
for
i
in
range
(
5
)])
else
:
self
.
expression
=
nonsymmetric_tensor_to_vector
(
expression
)
shape
=
ufl
.
shape
(
self
.
expression
)
if
len
(
shape
)
==
1
:
self
.
shape
=
shape
[
0
]
elif
shape
==
():
self
.
shape
=
1
self
.
shape
=
0
#self.expression = as_vector([self.expression])
else
:
self
.
shape
=
shape
...
...
mfront_wrapper/nonlinear_material.py
View file @
12c69475
...
...
@@ -13,10 +13,15 @@ class MFrontNonlinearMaterial:
self
.
name
=
name
# Defining the modelling hypothesis
self
.
hypothesis
=
mgis_hypothesis
[
hypothesis
]
if
self
.
hypothesis
==
mgis_bv
.
Hypothesis
.
Tridimensional
:
self
.
_tensorsize
=
9
else
:
self
.
_tensorsize
=
5
self
.
material_properties
=
material_properties
self
.
external_state_variables
=
external_state_variables
# Loading the behaviour
self
.
behaviour
=
mgis_bv
.
load
(
self
.
path
,
self
.
name
,
self
.
hypothesis
)
self
.
finite_strain
=
self
.
behaviour
.
getBehaviourType
()
==
"StandardFiniteStrainBehaviour"
def
set_data_manager
(
self
,
ngauss
):
# Setting the material data manager
...
...
@@ -49,8 +54,12 @@ class MFrontNonlinearMaterial:
def
get_gradient_sizes
(
self
):
return
[
mgis_bv
.
getVariableSize
(
svar
,
self
.
hypothesis
)
for
svar
in
self
.
behaviour
.
gradients
]
def
get_flux_sizes
(
self
):
return
[
mgis_bv
.
getVariableSize
(
svar
,
self
.
hypothesis
)
for
svar
in
self
.
behaviour
.
thermodynamic_forces
]
return
[
self
.
_tensorsize
if
(
svar
.
name
==
"Stress"
and
self
.
finite_strain
)
else
\
mgis_bv
.
getVariableSize
(
svar
,
self
.
hypothesis
)
\
for
svar
in
self
.
behaviour
.
thermodynamic_forces
]
def
get_tangent_block_names
(
self
):
return
[(
t
[
0
].
name
,
t
[
1
].
name
)
for
t
in
self
.
behaviour
.
tangent_operator_blocks
]
def
get_tangent_block_sizes
(
self
):
return
[
tuple
([
mgis_bv
.
getVariableSize
(
tt
,
self
.
hypothesis
)
for
tt
in
t
])
for
t
in
self
.
behaviour
.
tangent_operator_blocks
]
\ No newline at end of file
return
[
tuple
([
self
.
_tensorsize
if
(
tt
.
name
==
"Stress"
and
self
.
finite_strain
)
\
else
mgis_bv
.
getVariableSize
(
tt
,
self
.
hypothesis
)
for
tt
in
t
])
\
for
t
in
self
.
behaviour
.
tangent_operator_blocks
]
\ No newline at end of file
mfront_wrapper/nonlinear_problem.py
View file @
12c69475
...
...
@@ -4,6 +4,21 @@ from mfront_wrapper.gradient_flux import *
import
mgis.behaviour
as
mgis_bv
from
ufl
import
shape
SymGrad
=
{
mgis_bv
.
Hypothesis
.
Tridimensional
:
lambda
u
:
sym
(
grad
(
u
)),
mgis_bv
.
Hypothesis
.
PlaneStrain
:
lambda
u
:
sym
(
grad
(
u
)),
mgis_bv
.
Hypothesis
.
Axisymmetrical
:
lambda
r
,
u
:
sym
(
axi_grad
(
r
,
u
))}
Grad
=
{
mgis_bv
.
Hypothesis
.
Tridimensional
:
lambda
u
:
grad
(
u
),
mgis_bv
.
Hypothesis
.
PlaneStrain
:
lambda
u
:
grad
(
u
),
mgis_bv
.
Hypothesis
.
Axisymmetrical
:
lambda
r
,
u
:
axi_grad
(
r
,
u
)}
Id_Grad
=
{
mgis_bv
.
Hypothesis
.
Tridimensional
:
lambda
u
:
Identity
(
3
)
+
grad
(
u
),
mgis_bv
.
Hypothesis
.
PlaneStrain
:
lambda
u
:
Identity
(
2
)
+
grad
(
u
),
mgis_bv
.
Hypothesis
.
Axisymmetrical
:
lambda
r
,
u
:
Identity
(
3
)
+
axi_grad
(
r
,
u
)}
predefined_gradients
=
{
"Strain"
:
SymGrad
,
"TemperatureGradient"
:
Grad
,
"DeformationGradient"
:
Id_Grad
}
class
MFrontNonlinearProblem
(
NonlinearProblem
):
def
__init__
(
self
,
u
,
material
,
quadrature_degree
=
2
):
NonlinearProblem
.
__init__
(
self
)
...
...
@@ -28,7 +43,7 @@ class MFrontNonlinearProblem(NonlinearProblem):
self
.
ngauss
=
self
.
W0
.
dim
()
# Set data manager
self
.
material
.
set_data_manager
(
self
.
ngauss
)
self
.
finite_strain
=
self
.
material
.
behaviour
.
getBehaviourType
()
==
"StandardFiniteStrainBehaviour"
if
self
.
material
.
hypothesis
==
mgis_bv
.
Hypothesis
.
Tridimensional
:
assert
self
.
u
.
geometric_dimension
()
==
3
,
"Conflicting geometric dimension and material hypothesis"
else
:
...
...
@@ -39,6 +54,7 @@ class MFrontNonlinearProblem(NonlinearProblem):
"quadrature_scheme"
:
"default"
})
if
self
.
axisymmetric
:
x
=
SpatialCoordinate
(
self
.
mesh
)
self
.
_r
=
x
[
0
]
self
.
axi_coeff
=
2
*
pi
*
abs
(
x
[
0
])
else
:
self
.
axi_coeff
=
1
...
...
@@ -48,10 +64,25 @@ class MFrontNonlinearProblem(NonlinearProblem):
self
.
_Fext
=
None
self
.
_init
=
True
self
.
state_variables
=
[]
self
.
state_variables
=
dict
.
fromkeys
(
self
.
material
.
get_state_variable_names
(),
None
)
self
.
gradients
=
dict
.
fromkeys
(
self
.
material
.
get_gradient_names
(),
None
)
self
.
fluxes
=
{}
self
.
predefined_registration
()
def
predefined_registration
(
self
):
for
g
in
self
.
gradients
.
keys
():
if
self
.
axisymmetric
:
var
=
(
self
.
_r
,
self
.
u
)
else
:
var
=
(
self
.
u
,)
case
=
predefined_gradients
.
get
(
g
,
None
)
if
case
is
not
None
:
expr
=
case
[
self
.
material
.
hypothesis
](
*
var
)
self
.
register_gradient
(
g
,
expr
)
print
(
"Automatic registration of '{}' as {}.
\n
"
.
format
(
g
,
str
(
expr
)))
def
define_form
(
self
):
# residual form (internal forces)
...
...
@@ -60,13 +91,24 @@ class MFrontNonlinearProblem(NonlinearProblem):
if
self
.
_Fext
is
not
None
:
self
.
L
-=
self
.
_Fext
# tangent bilinear form
self
.
a
=
sum
([
inner
(
g
.
variation
(
self
.
u_
),
t
*
dg
.
variation
(
self
.
du
))
try
:
self
.
a
=
sum
([
inner
(
g
.
variation
(
self
.
u_
),
t
*
dg
.
variation
(
self
.
du
))
for
(
f
,
g
)
in
zip
(
self
.
fluxes
.
values
(),
self
.
gradients
.
values
())
for
(
t
,
dg
)
in
zip
(
f
.
tangent_blocks
.
values
(),
f
.
gradients
)])
*
self
.
axi_coeff
*
self
.
dx
def
register_gradient
(
self
,
name
,
expression
,
symmetric
=
None
):
except
:
print
([(
ufl
.
shape
(
g
.
variation
(
self
.
u_
)),
ufl
.
shape
(
t
*
dg
.
variation
(
self
.
du
)))
for
(
f
,
g
)
in
zip
(
self
.
fluxes
.
values
(),
self
.
gradients
.
values
())
for
(
t
,
dg
)
in
zip
(
f
.
tangent_blocks
.
values
(),
f
.
gradients
)])
def
register_gradient
(
self
,
name
,
expression
):
pos
=
self
.
material
.
get_gradient_names
().
index
(
name
)
size
=
self
.
material
.
get_gradient_sizes
()[
pos
]
vtype
=
self
.
material
.
behaviour
.
gradients
[
pos
].
type
if
vtype
==
mgis_bv
.
VariableType
.
Tensor
:
symmetric
=
False
elif
vtype
==
mgis_bv
.
VariableType
.
Stensor
:
symmetric
=
True
else
:
symmetric
=
None
self
.
gradients
.
update
({
name
:
Gradient
(
self
.
u
,
expression
,
name
,
symmetric
=
symmetric
)})
def
set_loading
(
self
,
Fext
):
...
...
@@ -144,15 +186,19 @@ class MFrontNonlinearProblem(NonlinearProblem):
mgis_bv
.
integrate
(
self
.
material
.
data_manager
,
self
.
integration_type
,
0
,
0
,
self
.
material
.
data_manager
.
n
)
if
self
.
finite_strain
:
local_project
(
self
.
strain_measure
(
self
.
u
),
self
.
Wsig
,
self
.
dx
,
self
.
strain
)
# copy the strain values to `MGIS`
self
.
material
.
data_manager
.
s0
.
gradients
[:,
:]
=
self
.
strain
.
vector
().
get_local
().
reshape
((
self
.
material
.
data_manager
.
n
,
self
.
strain_dim
))
else
:
self
.
block_names
=
self
.
material
.
get_tangent_block_names
()
self
.
block_shapes
=
self
.
material
.
get_tangent_block_sizes
()
self
.
flattened_block_shapes
=
[
s
[
0
]
*
s
[
1
]
if
len
(
s
)
==
2
else
s
[
0
]
for
s
in
self
.
block_shapes
]
self
.
update_tangent_blocks
()
# if self.material.finite_strain:
self
.
affect_gradients
()
# else:
self
.
block_names
=
self
.
material
.
get_tangent_block_names
()
self
.
block_shapes
=
self
.
material
.
get_tangent_block_sizes
()
self
.
flattened_block_shapes
=
[
s
[
0
]
*
s
[
1
]
if
len
(
s
)
==
2
else
s
[
0
]
for
s
in
self
.
block_shapes
]
self
.
update_tangent_blocks
()
buff
=
0
for
(
i
,
s
)
in
enumerate
(
self
.
material
.
get_state_variable_names
()):
state_var
=
self
.
state_variables
[
s
]
block_shape
=
self
.
material
.
get_state_variable_sizes
()[
i
]
self
.
material
.
data_manager
.
s0
.
internal_state_variables
[:,
buff
:
buff
+
block_shape
]
=
state_var
.
vector
().
get_local
().
reshape
(
self
.
material
.
data_manager
.
n
,
block_shape
)
buff
+=
block_shape
def
update_tangent_blocks
(
self
):
buff
=
0
...
...
@@ -160,7 +206,13 @@ class MFrontNonlinearProblem(NonlinearProblem):
f
,
g
=
block
t
=
self
.
fluxes
[
f
].
tangent_blocks
[
g
]
block_shape
=
self
.
flattened_block_shapes
[
i
]
t
.
vector
().
set_local
(
self
.
material
.
data_manager
.
K
[:,
buff
:
buff
+
block_shape
].
flatten
())
if
self
.
material
.
finite_strain
and
f
==
"Stress"
:
Ctv
=
t
.
vector
().
get_local
()
mgis_bv
.
convertFiniteStrainTangentOperator
(
Ctv
,
self
.
material
.
data_manager
,
mgis_bv
.
FiniteStrainTangentOperator
.
DPK1_DF
)
t
.
vector
().
set_local
(
Ctv
)
else
:
t
.
vector
().
set_local
(
self
.
material
.
data_manager
.
K
[:,
buff
:
buff
+
block_shape
].
flatten
())
buff
+=
block_shape
def
update_fluxes
(
self
):
...
...
@@ -168,7 +220,13 @@ class MFrontNonlinearProblem(NonlinearProblem):
for
(
i
,
f
)
in
enumerate
(
self
.
material
.
get_flux_names
()):
flux
=
self
.
fluxes
[
f
]
block_shape
=
self
.
material
.
get_flux_sizes
()[
i
]
flux
.
function
.
vector
().
set_local
(
self
.
material
.
data_manager
.
s1
.
thermodynamic_forces
[:,
buff
:
buff
+
block_shape
].
flatten
())
if
self
.
material
.
finite_strain
and
f
==
"Stress"
:
pk1v
=
flux
.
function
.
vector
().
get_local
()
mgis_bv
.
convertFiniteStrainStress
(
pk1v
,
self
.
material
.
data_manager
,
mgis_bv
.
FiniteStrainStress
.
PK1
)
flux
.
function
.
vector
().
set_local
(
pk1v
)
else
:
flux
.
function
.
vector
().
set_local
(
self
.
material
.
data_manager
.
s1
.
thermodynamic_forces
[:,
buff
:
buff
+
block_shape
].
flatten
())
buff
+=
block_shape
def
update_gradients
(
self
):
...
...
@@ -177,8 +235,34 @@ class MFrontNonlinearProblem(NonlinearProblem):
gradient
=
self
.
gradients
[
g
]
local_project
(
gradient
(
self
.
u
),
gradient
.
function_space
,
self
.
dx
,
gradient
.
function
)
block_shape
=
self
.
material
.
get_gradient_sizes
()[
i
]
self
.
material
.
data_manager
.
s1
.
gradients
[:,
buff
:
buff
+
block_shape
]
=
\
gradient
.
function
.
vector
().
get_local
().
reshape
((
self
.
material
.
data_manager
.
n
,
gradient
.
shape
))
grad_vals
=
gradient
.
function
.
vector
().
get_local
()
if
gradient
.
shape
>
0
:
grad_vals
=
grad_vals
.
reshape
((
self
.
material
.
data_manager
.
n
,
gradient
.
shape
))
else
:
grad_vals
=
grad_vals
[:,
np
.
newaxis
]
self
.
material
.
data_manager
.
s1
.
gradients
[:,
buff
:
buff
+
block_shape
]
=
grad_vals
buff
+=
block_shape
def
affect_gradients
(
self
):
buff
=
0
for
(
i
,
g
)
in
enumerate
(
self
.
material
.
get_gradient_names
()):
gradient
=
self
.
gradients
[
g
]
local_project
(
gradient
(
self
.
u
),
gradient
.
function_space
,
self
.
dx
,
gradient
.
function
)
block_shape
=
self
.
material
.
get_gradient_sizes
()[
i
]
grad_vals
=
gradient
.
function
.
vector
().
get_local
()
if
gradient
.
shape
>
0
:
grad_vals
=
grad_vals
.
reshape
((
self
.
material
.
data_manager
.
n
,
gradient
.
shape
))
else
:
grad_vals
=
grad_vals
[:,
np
.
newaxis
]
self
.
material
.
data_manager
.
s0
.
gradients
[:,
buff
:
buff
+
block_shape
]
=
grad_vals
buff
+=
block_shape
def
update_state_variables
(
self
):
buff
=
0
for
(
i
,
s
)
in
enumerate
(
self
.
material
.
get_state_variable_names
()):
state_var
=
self
.
state_variables
[
s
]
block_shape
=
self
.
material
.
get_state_variable_sizes
()[
i
]
state_var
.
vector
().
set_local
(
self
.
material
.
data_manager
.
s1
.
internal_state_variables
[:,
buff
:
buff
+
block_shape
].
flatten
())
buff
+=
block_shape
...
...
@@ -189,48 +273,40 @@ class MFrontNonlinearProblem(NonlinearProblem):
0
,
0
,
self
.
material
.
data_manager
.
n
);
# getting the stress and consistent tangent operator back to
# the FEniCS world.
if
self
.
finite_strain
:
pk1v
=
self
.
stress
.
vector
().
get_local
()
mgis_bv
.
convertFiniteStrainStress
(
pk1v
,
self
.
material
.
data_manager
,
mgis_bv
.
FiniteStrainStress
.
PK1
)
self
.
stress
.
vector
().
set_local
(
pk1v
)
Ctv
=
self
.
Ct
.
vector
().
get_local
()
mgis_bv
.
convertFiniteStrainTangentOperator
(
Ctv
,
self
.
material
.
data_manager
,
mgis_bv
.
FiniteStrainTangentOperator
.
DPK1_DF
)
self
.
Ct
.
vector
().
set_local
(
Ctv
)
else
:
self
.
update_fluxes
()
self
.
update_tangent_blocks
()
sizes
=
self
.
material
.
get_state_variable_sizes
()
for
i
in
range
(
len
(
self
.
state_variables
)):
size
=
sizes
[
i
]
s_values
=
self
.
material
.
data_manager
.
s1
.
internal_state_variables
[:,
i
:(
i
+
size
)].
flatten
()
state
=
self
.
state_variables
[
i
]
if
isinstance
(
state
,
Flux
):
state
.
function
.
vector
().
set_local
(
s_values
)
shapes
=
[
ufl
.
shape
(
t
)
for
t
in
state
.
tangents
]
flattened_shapes
=
[
s
[
0
]
*
s
[
1
]
if
len
(
s
)
==
2
else
s
[
0
]
if
len
(
s
)
==
1
else
1
for
s
in
shapes
]
# FIXME: Assumes gradients of state variables are defined after fluxes and in right order
for
(
j
,
t
)
in
enumerate
(
state
.
tangents
):
s
=
flattened_shapes
[
j
]
t
.
vector
().
set_local
(
K
[:,
buff
:
buff
+
s
].
flatten
())
buff
+=
s
else
:
state
.
vector
().
set_local
(
s_values
)
def
get_state_variable
(
self
,
name
=
None
,
position
=
None
):
if
name
is
not
None
:
# if self.material.finite_strain:
# pk1v = self.stress.vector().get_local()
# mgis_bv.convertFiniteStrainStress(pk1v, self.material.data_manager,
# mgis_bv.FiniteStrainStress.PK1)
# self.stress.vector().set_local(pk1v)
# else:
self
.
update_fluxes
()
self
.
update_tangent_blocks
()
self
.
update_state_variables
()
# sizes = self.material.get_state_variable_sizes()
# for i in range(len(self.state_variables)):
# size = sizes[i]
# s_values = self.material.data_manager.s1.internal_state_variables[:, i:(i+size)].flatten()
# state = self.state_variables[i]
# if isinstance(state, Flux):
# state.function.vector().set_local(s_values)
# shapes = [ufl.shape(t) for t in state.tangents]
# flattened_shapes = [s[0]*s[1] if len(s)==2 else s[0] if len(s)==1 else 1 for s in shapes]
# # FIXME: Assumes gradients of state variables are defined after fluxes and in right order
# for (j,t) in enumerate(state.tangents):
# s = flattened_shapes[j]
# t.vector().set_local(K[:,buff:buff+s].flatten())
# buff += s
# else:
# state.vector().set_local(s_values)
def
get_state_variable
(
self
,
name
):
if
self
.
state_variables
[
name
]
is
None
:
position
=
self
.
material
.
get_state_variable_names
().
index
(
name
)
elif
position
is
not
None
:
name
=
self
.
material
.
get_state_variable_names
()[
position
]
else
:
raise
ValueError
(
"Name or position of state variable must be specified."
)
shape
=
self
.
material
.
get_state_variable_sizes
()[
position
]
We
=
get_quadrature_element
(
self
.
mesh
.
ufl_cell
(),
self
.
quadrature_degree
,
shape
)
W
=
FunctionSpace
(
self
.
mesh
,
We
)
self
.
state_variables
.
append
([
Function
(
W
,
name
=
name
),
position
])
return
self
.
state_variables
[
-
1
][
0
]
shape
=
self
.
material
.
get_state_variable_sizes
()[
position
]
We
=
get_quadrature_element
(
self
.
mesh
.
ufl_cell
(),
self
.
quadrature_degree
,
shape
)
W
=
FunctionSpace
(
self
.
mesh
,
We
)
self
.
state_variables
[
name
]
=
Function
(
W
,
name
=
name
)
return
self
.
state_variables
[
name
]
def
form
(
self
,
A
,
P
,
b
,
x
):
...
...
Write
Preview
Markdown
is supported
0%
Try again
or
attach a new file
.
Attach a file
Cancel
You are about to add
0
people
to the discussion. Proceed with caution.
Finish editing this message first!
Cancel
Please
register
or
sign in
to comment