30. Sydney#
Example provided by Michael Neunteufel
M. Neunteufel + JS: The Hellan-Herrmann-Johnson and TDNNS method for nonlinear Koiter and Naghdi shells, CAS 24
from ngsolve import *
from netgen.occ import *
from ngsolve.webgui import Draw
(model created by Sebastian Hirnschall)
mesh = Mesh(OCCGeometry(shell).GenerateMesh(maxh=2))
mesh.RefineHP(1)
mesh.Curve(3)
Draw(mesh, **ea);
t = 0.1
order = 4
E = 2.85e4
nu = 0.3
mu = E / (2 * (1 + nu))
lam = E * nu / (1 - nu**2)
def MaterialNorm(mat, E, nu):
return E / (1 - nu**2) * ((1 - nu) * InnerProduct(mat, mat) + nu * Trace(mat) ** 2)
def MaterialNormInv(mat, E, nu):
return (1 + nu) / E * (InnerProduct(mat, mat) - nu / (nu + 1) * Trace(mat) ** 2)
fesU = VectorH1(mesh, order=order, dirichlet_bbnd="fix")
fesS = HDivDivSurface(mesh, order=order - 1, discontinuous=True)
fesH = NormalFacetSurface(mesh, order=order - 1) # , dirichlet_bbnd="fix")
fes = fesU * fesS * fesH
(u, sigma, uh) = fes.TrialFunction()
# Need to take traces as we are on the surface
sigma, uh = sigma.Trace(), uh.Trace()
fesRegge = HCurlCurl(mesh, order=order - 1)
# normal, tangential, and co-normal vectors
nv = specialcf.normal(3)
tv = specialcf.tangential(3)
cnv = Cross(nv, tv)
# Projection to tangent space and surface derivatives
Ptau = Id(3) - OuterProduct(nv, nv)
grad_u = Grad(u).Trace()
Ftau = grad_u + Ptau
Etautau = 0.5 * (Ftau.trans * Ftau - Ptau) # Green strain
# sum_{i=1}^3 hesse(u_i) nv_i
Hn = (u.Operator("hesseboundary").trans * nv).Reshape((3, 3))
bfa = BilinearForm(fes, symmetric=True, condense=True)
# membrane energy
bfa += Variation(t/2 * MaterialNorm(Interpolate(Etautau, fesRegge), E, nu) * ds)
# bending energy
bfa += Variation(-12 / t**3 / 2 * MaterialNormInv(sigma, E, nu) * ds)
bfa += Variation(InnerProduct(sigma, Hn) * ds)
bfa += Variation(sigma[cnv, cnv] * (uh - grad_u[nv, :]) * cnv * ds(element_boundary=True))
force = CF((0, 0, -0.01))
bfa += Variation(-force * u * ds)
gfu = GridFunction(fes)
with TaskManager():
solvers.Newton(a=bfa, u=gfu, maxerr=1e-8, printing=True, inverse="sparsecholesky")
Newton iteration 0
err = 0.8215980701688117
Newton iteration 1
err = 0.5072311135070565
Newton iteration 2
err = 0.09621368505256139
Newton iteration 3
err = 0.02632761722210077
Newton iteration 4
err = 0.0005672477038419197
Newton iteration 5
err = 6.975755660579072e-06
Newton iteration 6
err = 2.0896790836450907e-07
Newton iteration 7
err = 2.1575734610281898e-09
Draw(gfu.components[0], scale=20, deformation=True, **ea);
Draw(Norm(gfu.components[1]), mesh, order=3, max=0.1, **ea);