G+Smo  24.08.0
Geometry + Simulation Modules
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Macros Groups Pages
gsThinShellAssembler.hpp
Go to the documentation of this file.
1 
16 #pragma once
17 
23 
25 
26 #include <gsCore/gsFunctionExpr.h>
28 
29 #include <gsIO/gsWriteParaview.h>
30 
32 
33 #include <unordered_set>
34 
35 namespace gismo
36 {
37 
38 template<short_t d, class T, bool bending>
40  const gsMultiBasis<T> & basis,
41  const gsBoundaryConditions<T> & bconditions,
42  const gsFunction<T> & surface_force,
43  const gsMaterialMatrixContainer<T> & materialMatrices
44  )
45  :
46  m_patches(patches),
47  m_basis(basis),
48  m_spaceBasis(&m_basis),
49  m_bcs(bconditions),
50  m_forceFun(&surface_force),
51  m_materialMatrices(materialMatrices)
52 {
53  this->_defaultOptions();
54  this->_getOptions();
55  this->_initialize();
56 }
57 
58 template<short_t d, class T, bool bending>
60  const gsMultiBasis<T> & basis,
61  const gsBoundaryConditions<T> & bconditions,
62  const gsFunction<T> & surface_force,
63  gsMaterialMatrixBase<T> * materialMatrix
64  )
65  :
66  m_patches(patches),
67  m_basis(basis),
68  m_spaceBasis(&basis),
69  m_bcs(bconditions),
70  m_forceFun(&surface_force)
71 {
72  m_materialMatrices = gsMaterialMatrixContainer<T>(m_patches.nPatches());
73  GISMO_ASSERT(materialMatrix!=nullptr,"Material matrix is incomplete!");
74  GISMO_ASSERT(materialMatrix->initialized(),"Material matrix is incomplete!");
75  for (size_t p=0; p!=m_patches.nPatches(); p++)
76  m_materialMatrices.set(p,materialMatrix);
77 
78  this->_defaultOptions();
79  this->_getOptions();
80  this->_initialize();
81 }
82 
83 template<short_t d, class T, bool bending>
85 {
86  if (this!=&other)
87  {
88  m_mapper=other.m_mapper;
89  m_assembler=other.m_assembler;
90  m_evaluator=other.m_evaluator;
91  m_patches=other.m_patches;
92  m_itpatches=other.m_itpatches;
93  m_basis=other.m_basis;
94  m_spaceBasis=other.m_spaceBasis;
95  m_bcs=other.m_bcs;
96  m_ddofs=other.m_ddofs;
97  m_mass=other.m_mass;
98  m_forceFun=other.m_forceFun;
99  m_foundFun=other.m_foundFun;
100  m_pressFun=other.m_pressFun;
101  m_materialMatrices=other.m_materialMatrices;
102  m_pLoads=other.m_pLoads;
103  m_pMass=other.m_pMass;
104  m_solvector=other.m_solvector;
105  m_rhs=other.m_rhs;
106  m_options=other.m_options;
107  m_foundInd=other.m_foundInd;
108  m_pressInd=other.m_pressInd;
109  m_continuity=other.m_continuity;
110  m_alpha_d_bc=other.m_alpha_d_bc;
111  m_alpha_r_bc=other.m_alpha_r_bc;
112  m_alpha_d_ifc=other.m_alpha_d_ifc;
113  m_alpha_r_ifc=other.m_alpha_r_ifc;
114  m_IfcDefault=other.m_IfcDefault;
115  m_inPlane=other.m_inPlane;
116  m_outPlane=other.m_outPlane;
117  m_uncoupled=other.m_uncoupled;
118  m_strongC0=other.m_strongC0;
119  m_weakC0=other.m_weakC0;
120  m_strongC1=other.m_strongC1;
121  m_weakC1=other.m_weakC1;
122  m_unassigned=other.m_unassigned;
123 
124  // To do: make copy constructor for the gsExprAssembler
125  m_assembler.setIntegrationElements(m_basis);
126  GISMO_ENSURE(m_options.hasGroup("ExprAssembler"),"The option list does not contain options with the label 'ExprAssembler'!");
127  m_assembler.setOptions(m_options.getGroup("ExprAssembler"));
128  }
129  return *this;
130 }
131 
132 template<short_t d, class T, bool bending>
134 {
135  m_mapper=give(other.m_mapper);
136  m_assembler=give(other.m_assembler);
137  m_evaluator=give(other.m_evaluator);
138  m_patches=give(other.m_patches);
139  m_itpatches=give(other.m_itpatches);
140  m_basis=give(other.m_basis);
141  m_spaceBasis=give(other.m_spaceBasis);
142  m_bcs=give(other.m_bcs);
143  m_ddofs=give(other.m_ddofs);
144  m_mass=give(other.m_mass);
145  m_forceFun=give(other.m_forceFun);
146  m_foundFun=give(other.m_foundFun);
147  m_pressFun=give(other.m_pressFun);
148  m_materialMatrices=give(other.m_materialMatrices);
149  m_pLoads=give(other.m_pLoads);
150  m_pMass=give(other.m_pMass);
151  m_solvector=give(other.m_solvector);
152  m_rhs=give(other.m_rhs);
153  m_options=give(other.m_options);
154  m_foundInd=give(other.m_foundInd);
155  m_pressInd=give(other.m_pressInd);
156  m_continuity=give(other.m_continuity);
157  m_alpha_d_bc=give(other.m_alpha_d_bc);
158  m_alpha_r_bc=give(other.m_alpha_r_bc);
159  m_alpha_d_ifc=give(other.m_alpha_d_ifc);
160  m_alpha_r_ifc=give(other.m_alpha_r_ifc);
161  m_IfcDefault=give(other.m_IfcDefault);
162  m_inPlane=give(other.m_inPlane);
163  m_outPlane=give(other.m_outPlane);
164  m_uncoupled=give(other.m_uncoupled);
165  m_strongC0=give(other.m_strongC0);
166  m_weakC0=give(other.m_weakC0);
167  m_strongC1=give(other.m_strongC1);
168  m_weakC1=give(other.m_weakC1);
169  m_unassigned=give(other.m_unassigned);
170  // To do: make copy constructor for the gsExprAssembler
171  m_assembler.setIntegrationElements(m_basis);
172  GISMO_ENSURE(m_options.hasGroup("ExprAssembler"),"The option list does not contain options with the label 'ExprAssembler'!");
173  m_assembler.setOptions(m_options.getGroup("ExprAssembler"));
174  return *this;
175 }
176 
177 template<short_t d, class T, bool bending>
179 {
180  m_options.addReal("WeakDirichlet","Penalty parameter weak dirichlet conditions",1e3);
181  m_options.addReal("WeakClamped","Penalty parameter weak clamped conditions",1e3);
182  m_options.addInt("Continuity","Set the continuity for the space",-1);
183 
184  m_options.addReal("IfcPenalty","Penalty parameter weak coupling conditions on the interface",1e3);
185  m_options.addInt("IfcDefault","Default weak(!) interface coupling; C^k, k={-1,0,1}",1);
186  m_options.addString("Solver","Sparse linear solver", "CGDiagonal");
187 
188  // Assembler options
189  gsOptionList assemblerOptions = m_assembler.defaultOptions().wrapIntoGroup("ExprAssembler");
190  m_options.update(assemblerOptions,gsOptionList::addIfUnknown);
191 
192  m_continuity = -1;
193 }
194 
195 
196 template <short_t d, class T, bool bending>
197 void gsThinShellAssembler<d, T, bending>::_getOptions()
198 {
199  // If the continuity changed, we need to re-initialize the space.
200  index_t continuity = m_continuity;
201  m_continuity = m_options.getInt("Continuity");
202  if (continuity != m_options.getInt("Continuity"))
203  this->_initialize();
204 
205  m_alpha_d_bc = m_options.getReal("WeakDirichlet");
206  m_alpha_r_bc = m_options.getReal("WeakClamped");
207  m_alpha_d_ifc = m_alpha_r_ifc = m_options.getReal("IfcPenalty");
208  m_IfcDefault = m_options.getInt("IfcDefault");
209 }
210 
211 template<short_t d, class T, bool bending>
213 {
214  // Check if the continuity option changed
215  // Get old continuity
216  index_t continuity = m_options.getInt("Continuity");
217 
218  m_options.update(options,gsOptionList::ignoreIfUnknown);
219 
220  // If the continuity changed, we need to re-initialize the space.
221  if (continuity != m_options.getInt("Continuity"))
222  this->_initialize();
223 }
224 
225 template<short_t d, class T, bool bending>
227 {
228  //gsInfo<<"Active options:\n"<< m_assembler.options() <<"\n";
229 
230  // Elements used for numerical integration
231  m_assembler.setIntegrationElements(m_basis);
232  GISMO_ENSURE(m_options.hasGroup("ExprAssembler"),"The option list does not contain options with the label 'ExprAssembler'!");
233  m_assembler.setOptions(m_options.getGroup("ExprAssembler"));
234 
235  GISMO_ASSERT(m_bcs.hasGeoMap(),"No geometry map was assigned to the boundary conditions. Use bc.setGeoMap to assign one!");
236 
237  // Initialize the geometry maps
238  // geometryMap m_ori = m_assembler.getMap(m_patches);
239  // geometryMap m_def = m_assembler.getMap(*m_defpatches);
240 
241  // Set the discretization space
242  space m_space = m_assembler.getSpace(*m_spaceBasis, d, 0); // last argument is the space ID
243 
244  this->_assembleDirichlet();
245 
246  m_ddofs = m_space.fixedPart();
247  m_mapper = m_space.mapper();
248 
249  // foundation is off by default
250  m_foundInd = false;
251  // pressure is off by default
252  m_pressInd = false;
253 
254  GISMO_ASSERT(m_forceFun->targetDim()==d,"Force must have " << d<<" dimensions but has "<<m_forceFun->targetDim());
255 
256  // test interfaces on in-plane and out-of-plane connection and put them in respective containers
257  // _ifcTest();
258  // match interfaces where needed
259  // todo
260  // Put the interfaces in the right container depending on the
261 
262 }
263 
264 template<short_t d, class T, bool bending>
265 void gsThinShellAssembler<d, T, bending>::addStrongC0(const gsBoxTopology::ifContainer & interfaces)
266 {
267  m_strongC0 = interfaces;
268 }
269 
270 template<short_t d, class T, bool bending>
271 void gsThinShellAssembler<d, T, bending>::addStrongC1(const gsBoxTopology::ifContainer & interfaces)
272 {
273  m_strongC1 = interfaces;
274 }
275 
276 template<short_t d, class T, bool bending>
277 void gsThinShellAssembler<d, T, bending>::addWeakC0(const gsBoxTopology::ifContainer & interfaces)
278 {
279  m_weakC0 = interfaces;
280 }
281 
282 template<short_t d, class T, bool bending>
283 void gsThinShellAssembler<d, T, bending>::addWeakC1(const gsBoxTopology::ifContainer & interfaces)
284 {
285  m_weakC1 = interfaces;
286 }
287 
288 template<short_t d, class T, bool bending>
289 void gsThinShellAssembler<d, T, bending>::addUncoupled(const gsBoxTopology::ifContainer & interfaces)
290 {
291  m_uncoupled = interfaces;
292 }
293 
294 template<short_t d, class T, bool bending>
295 void gsThinShellAssembler<d, T, bending>::initInterfaces()
296 {
297  this->_getOptions();
298  // Find unassigned interfaces and add them to the right containers
299  for (gsBoxTopology::const_iiterator it = m_patches.topology().iBegin(); it!=m_patches.topology().iEnd(); it++)
300  {
301  if (
302  std::find(m_strongC0.begin(), m_strongC0.end(), *it) == m_strongC0.end() // m_strongC0 does not contain *it
303  && std::find(m_strongC1.begin(), m_strongC1.end(), *it) == m_strongC1.end() // m_strongC1 does not contain *it
304  && std::find(m_weakC0.begin(), m_weakC0.end(), *it) == m_weakC0.end() // m_weakC0 does not contain *it
305  && std::find(m_weakC1.begin(), m_weakC1.end(), *it) == m_weakC1.end() // m_weakC1 does not contain *it
306  && std::find(m_uncoupled.begin(), m_uncoupled.end(), *it) == m_uncoupled.end() // m_uncoupled does not contain *it
307  )
308  {
309  if (m_IfcDefault==-1)
310  continue;
311  else if (m_IfcDefault==0)
312  m_weakC0.push_back(*it);
313  else if (m_IfcDefault==1)
314  m_weakC1.push_back(*it);
315  else
316  GISMO_ERROR("Option unknown");
317  }
318  }
319 
320  // Set strong C0 using the setup function.
321 }
322 
323 template<short_t d, class T, bool bending>
324 void gsThinShellAssembler<d, T, bending>::_assembleNeumann()
325 {
326  _assembleNeumann_impl<d>();
327 }
328 
329 template <short_t d, class T, bool bending>
330 template <short_t _d>
331 typename std::enable_if<(_d==3), void>::type
332 gsThinShellAssembler<d, T, bending>::_assembleNeumann_impl()
333 {
334  geometryMap m_ori = m_assembler.getMap(m_patches);
335 
336  space m_space = m_assembler.trialSpace(0); // last argument is the space ID
337  auto g_N = m_assembler.getBdrFunction(m_ori);
338  m_assembler.assembleBdr(m_bcs.get("Neumann"),m_space * g_N * meas(m_ori));
339 }
340 
341 template <short_t d, class T, bool bending>
342 template <short_t _d>
343 typename std::enable_if<!(_d==3), void>::type
344 gsThinShellAssembler<d, T, bending>::_assembleNeumann_impl()
345 {
346  geometryMap m_ori = m_assembler.getMap(m_patches);
347 
348  space m_space = m_assembler.trialSpace(0); // last argument is the space ID
349  auto g_N = m_assembler.getBdrFunction(m_ori);
350  m_assembler.assembleBdr(m_bcs.get("Neumann"), m_space * g_N * meas(m_ori));
351 }
352 
353 template<short_t d, class T, bool bending>
354 template<bool _matrix>
355 void gsThinShellAssembler<d, T, bending>::_assemblePressure(const gsFunction<T> & pressFun)
356 {
357  this->_getOptions();
358  _assemblePressure_impl<d,_matrix>(pressFun);
359 }
360 
361 template <short_t d, class T, bool bending>
362 template <short_t _d, bool matrix>
363 typename std::enable_if<(_d==3) && matrix, void>::type
364 gsThinShellAssembler<d, T, bending>::_assemblePressure_impl(const gsFunction<T> &)
365 {
366  // No matrix contribution for the linear case
367 }
368 
369 template <short_t d, class T, bool bending>
370 template <short_t _d, bool _matrix>
371 typename std::enable_if<(_d==3) && !_matrix, void>::type
372 gsThinShellAssembler<d, T, bending>::_assemblePressure_impl(const gsFunction<T> & pressFun)
373 {
374  gsMultiPatch<T> & defpatches = m_patches;
375  geometryMap m_ori = m_assembler.getMap(m_patches);
376  geometryMap m_def = m_assembler.getMap(defpatches);
377 
378  space m_space = m_assembler.trialSpace(0); // last argument is the space ID
379 
380  auto m_pressure = m_assembler.getCoeff(pressFun, m_ori);
381  GISMO_ASSERT(pressFun.targetDim()==1,"Pressure function has dimension "<<pressFun.targetDim()<<", but expected 1");
382 
383  m_assembler.assemble(
384  m_pressure.val() * m_space * usn(m_def) * meas(m_ori)
385  );
386 }
387 
388 template <short_t d, class T, bool bending>
389 template <short_t _d, bool _matrix>
390 typename std::enable_if<!(_d==3), void>::type
391 gsThinShellAssembler<d, T, bending>::_assemblePressure_impl(const gsFunction<T> &)
392 {
393  // Since pressure works out-of-plane, this function has no effect
394 }
395 
396 template<short_t d, class T, bool bending>
397 template<bool _matrix>
398 void gsThinShellAssembler<d, T, bending>::_assemblePressure(const gsFunction<T> & pressFun, const gsFunctionSet<T> & deformed)
399 {
400  this->_getOptions();
401  _assemblePressure_impl<d,_matrix>(pressFun,deformed);
402 }
403 
404 template <short_t d, class T, bool bending>
405 template <short_t _d, bool matrix>
406 typename std::enable_if<(_d==3) && matrix, void>::type
407 gsThinShellAssembler<d, T, bending>::_assemblePressure_impl(const gsFunction<T> & pressFun, const gsFunctionSet<T> & deformed)
408 {
409  geometryMap m_ori = m_assembler.getMap(m_patches);
410  geometryMap m_def = m_assembler.getMap(deformed);
411 
412  space m_space = m_assembler.trialSpace(0); // last argument is the space ID
413 
414  auto m_pressure = m_assembler.getCoeff(pressFun, m_ori);
415  GISMO_ASSERT(pressFun.targetDim()==1,"Pressure function has dimension "<<pressFun.targetDim()<<", but expected 1");
416 
417  m_assembler.assemble(
418  -m_pressure.val() * m_space * var1(m_space,m_def).tr()* meas(m_ori)
419  //-m_pressure.val() * jac(m_space) * sn(m_def).normalized() * meas(m_ori)
420  );
421 }
422 
423 template <short_t d, class T, bool bending>
424 template <short_t _d, bool _matrix>
425 typename std::enable_if<(_d==3) && !_matrix, void>::type
426 gsThinShellAssembler<d, T, bending>::_assemblePressure_impl(const gsFunction<T> & pressFun, const gsFunctionSet<T> & deformed)
427 {
428  geometryMap m_ori = m_assembler.getMap(m_patches);
429  geometryMap m_def = m_assembler.getMap(deformed);
430 
431  space m_space = m_assembler.trialSpace(0); // last argument is the space ID
432 
433  auto m_pressure = m_assembler.getCoeff(pressFun, m_ori);
434  GISMO_ASSERT(pressFun.targetDim()==1,"Pressure function has dimension "<<pressFun.targetDim()<<", but expected 1");
435 
436  // Assemble vector
437  m_assembler.assemble(
438  m_pressure.val() * m_space * sn(m_def).normalized() * meas(m_ori)
439  );
440 }
441 
442 template <short_t d, class T, bool bending>
443 template <short_t _d, bool _matrix>
444 typename std::enable_if<!(_d==3), void>::type
445 gsThinShellAssembler<d, T, bending>::_assemblePressure_impl(const gsFunction<T> & , const gsFunctionSet<T> & )
446 {
447  // Since pressure works out-of-plane, this function has no effect
448 }
449 
450 template<short_t d, class T, bool bending>
451 template<bool _matrix>
452 void gsThinShellAssembler<d, T, bending>::_assembleFoundation(const gsFunction<T> & foundFun)
453 {
454  this->_getOptions();
455  _assembleFoundation_impl<d,_matrix>(foundFun);
456 }
457 
458 template <short_t d, class T, bool bending>
459 template <short_t _d, bool _matrix>
460 typename std::enable_if<(_d==3) && _matrix, void>::type
461 gsThinShellAssembler<d, T, bending>::_assembleFoundation_impl(const gsFunction<T> & foundFun)
462 {
463  // No matrix contribution for the linear case
464 }
465 
466 template <short_t d, class T, bool bending>
467 template <short_t _d, bool _matrix>
468 typename std::enable_if<(_d==3) && !_matrix, void>::type
469 gsThinShellAssembler<d, T, bending>::_assembleFoundation_impl(const gsFunction<T> & foundFun)
470 {
471  geometryMap m_ori = m_assembler.getMap(m_patches);
472 
473  space m_space = m_assembler.trialSpace(0); // last argument is the space ID
474 
475  auto m_foundation = m_assembler.getCoeff(foundFun, m_ori);
476  GISMO_ASSERT(foundFun.targetDim()==3,"Foundation function has dimension "<<foundFun.targetDim()<<", but expected 3");
477 
478  m_assembler.assemble(
479  m_space * m_foundation.asDiag() * m_space.tr() * meas(m_ori)
480  );
481 }
482 
483 template <short_t d, class T, bool bending>
484 template <short_t _d, bool _matrix>
485 typename std::enable_if<!(_d==3), void>::type
486 gsThinShellAssembler<d, T, bending>::_assembleFoundation_impl(const gsFunction<T> & )
487 {
488  // Since foundation works out-of-plane, this function has no effect
489 }
490 
491 template<short_t d, class T, bool bending>
492 template<bool _matrix>
493 void gsThinShellAssembler<d, T, bending>::_assembleFoundation(const gsFunction<T> & foundFun, const gsFunctionSet<T> & deformed)
494 {
495  this->_getOptions();
496  _assembleFoundation_impl<d,_matrix>(foundFun,deformed);
497 }
498 
499 template <short_t d, class T, bool bending>
500 template <short_t _d, bool matrix>
501 typename std::enable_if<(_d==3) && matrix, void>::type
502 gsThinShellAssembler<d, T, bending>::_assembleFoundation_impl(const gsFunction<T> & foundFun, const gsFunctionSet<T> & deformed)
503 {
504  geometryMap m_ori = m_assembler.getMap(m_patches);
505 
506  space m_space = m_assembler.trialSpace(0); // last argument is the space ID
507 
508  auto m_foundation = m_assembler.getCoeff(foundFun, m_ori);
509  GISMO_ASSERT(foundFun.targetDim()==3,"Foundation function has dimension "<<foundFun.targetDim()<<", but expected 3");
510 
511  m_assembler.assemble(
512  m_space * m_foundation.asDiag() * m_space.tr() * meas(m_ori)
513  );
514 }
515 
516 template <short_t d, class T, bool bending>
517 template <short_t _d, bool _matrix>
518 typename std::enable_if<(_d==3) && !_matrix, void>::type
519 gsThinShellAssembler<d, T, bending>::_assembleFoundation_impl(const gsFunction<T> & foundFun, const gsFunctionSet<T> & deformed)
520 {
521  geometryMap m_ori = m_assembler.getMap(m_patches);
522  geometryMap m_def = m_assembler.getMap(deformed);
523 
524  space m_space = m_assembler.trialSpace(0); // last argument is the space ID
525 
526  auto m_foundation = m_assembler.getCoeff(foundFun, m_ori);
527  GISMO_ASSERT(foundFun.targetDim()==3,"Foundation function has dimension "<<foundFun.targetDim()<<", but expected 3");
528 
529  // Assemble vector
530  m_assembler.assemble(
531  m_space * m_foundation.asDiag() * (m_def - m_ori) * meas(m_ori) // [v_x,v_y,v_z] diag([k_x,k_y,k_z]) [u_x; u_y; u_z]
532  );
533 }
534 
535 template <short_t d, class T, bool bending>
536 template <short_t _d, bool _matrix>
537 typename std::enable_if<!(_d==3), void>::type
538 gsThinShellAssembler<d, T, bending>::_assembleFoundation_impl(const gsFunction<T> & , const gsFunctionSet<T> & )
539 {
540  // Since foundation works out-of-plane, this function has no effect
541 }
542 
543 template<short_t d, class T, bool bending>
544 template<bool _matrix>
545 void gsThinShellAssembler<d, T, bending>::_assembleWeakBCs()
546 {
547  this->_getOptions();
548  _assembleWeakBCs_impl<d,_matrix>();
549 }
550 
551 template <short_t d, class T, bool bending>
552 template <short_t _d, bool _matrix>
553 typename std::enable_if<(_d==3) && _matrix, void>::type
554 gsThinShellAssembler<d, T, bending>::_assembleWeakBCs_impl()
555 {
556  gsMultiPatch<T> & defpatches = m_patches;
557  geometryMap m_ori = m_assembler.getMap(m_patches);
558 
559  space m_space = m_assembler.trialSpace(0); // last argument is the space ID
560  // auto g_N = m_assembler.getBdrFunction(m_ori);
561 
562  gsMaterialMatrixIntegrate<T,MaterialOutput::MatrixA> m_mmA(m_materialMatrices,&m_patches,&defpatches);
563  gsMaterialMatrixIntegrate<T,MaterialOutput::MatrixD> m_mmD(m_materialMatrices,&m_patches,&defpatches);
564  auto mmA = m_assembler.getCoeff(m_mmA);
565  auto mmD = m_assembler.getCoeff(m_mmD);
566 
567  auto cart2cov = cartcov(m_ori);
568  auto con2cartI = cartcon(m_ori).inv();
569 
570  auto mmAcart = (con2cartI * reshape(mmA,3,3) * cart2cov);
571  auto mmDcart = (con2cartI * reshape(mmD,3,3) * cart2cov);
572 
573  element el = m_assembler.getElement();
574  auto alpha_d = m_alpha_d_bc * reshape(mmAcart,9,1).max().val() / el.area(m_ori);
575  auto alpha_r = m_alpha_r_bc * reshape(mmDcart,9,1).max().val() / el.area(m_ori);
576 
577  // Weak BCs
578  m_assembler.assembleBdr
579  (
580  m_bcs.get("Weak Dirichlet")
581  ,
582  -(alpha_d * m_space * m_space.tr()) * meas(m_ori)
583  );
584 
585  // for weak clamped
586  m_assembler.assembleBdr
587  (
588  m_bcs.get("Weak Clamped")
589  ,
590  (
591  alpha_r * ( ( var1(m_space,m_ori) * unv(m_ori) ) * ( var1(m_space,m_ori) * unv(m_ori) ).tr() )
592  ) * meas(m_ori)
593  );
594 }
595 
596 template <short_t d, class T, bool bending>
597 template <short_t _d, bool _matrix>
598 typename std::enable_if<(_d==3) && !_matrix, void>::type
599 gsThinShellAssembler<d, T, bending>::_assembleWeakBCs_impl()
600 {
601  gsMultiPatch<T> & defpatches = m_patches;
602  geometryMap m_ori = m_assembler.getMap(m_patches);
603 
604  space m_space = m_assembler.trialSpace(0); // last argument is the space ID
605  auto g_N = m_assembler.getBdrFunction(m_ori);
606 
607  gsMaterialMatrixIntegrate<T,MaterialOutput::MatrixA> m_mmA(m_materialMatrices,&m_patches,&defpatches);
608  auto mmA = m_assembler.getCoeff(m_mmA);
609 
610  auto cart2cov = cartcov(m_ori);
611  auto con2cartI = cartcon(m_ori).inv();
612 
613  auto mmAcart = (con2cartI * reshape(mmA,3,3) * cart2cov);
614 
615  element el = m_assembler.getElement();
616  auto alpha_d = m_alpha_d_bc * reshape(mmAcart,9,1).max().val() / el.area(m_ori);
617 
618  // Weak BCs
619 
620  m_assembler.assembleBdr
621  (
622  m_bcs.get("Weak Dirichlet")
623  ,
624  -(alpha_d * m_space * g_N ) * meas(m_ori)
625  );
626 
627  // for weak clamped
628  // do nothing
629 }
630 
631 template <short_t d, class T, bool bending>
632 template <short_t _d, bool _matrix>
633 typename std::enable_if<!(_d==3) && _matrix, void>::type
634 gsThinShellAssembler<d, T, bending>::_assembleWeakBCs_impl()
635 {
636  gsMultiPatch<T> & defpatches = m_patches;
637  geometryMap m_ori = m_assembler.getMap(m_patches);
638 
639  space m_space = m_assembler.trialSpace(0); // last argument is the space ID
640  // auto g_N = m_assembler.getBdrFunction(m_ori);
641 
642  gsMaterialMatrixIntegrate<T,MaterialOutput::MatrixA> m_mmA(m_materialMatrices,&m_patches,&defpatches);
643  auto mmA = m_assembler.getCoeff(m_mmA);
644 
645  auto cart2cov = cartcov(m_ori);
646  auto con2cartI = cartcon(m_ori).inv();
647 
648  auto mmAcart = (con2cartI * reshape(mmA,3,3) * cart2cov);
649 
650  element el = m_assembler.getElement();
651  auto alpha_d = m_alpha_d_bc * reshape(mmAcart,9,1).max().val() / el.area(m_ori);
652 
653  // Weak BCs
654  m_assembler.assembleBdr
655  (
656  m_bcs.get("Weak Dirichlet")
657  ,
658  -(alpha_d * m_space * m_space.tr()) * meas(m_ori)
659  );
660 }
661 
662 template <short_t d, class T, bool bending>
663 template <short_t _d, bool _matrix>
664 typename std::enable_if<!(_d==3) && !_matrix, void>::type
665 gsThinShellAssembler<d, T, bending>::_assembleWeakBCs_impl()
666 {
667  geometryMap m_ori = m_assembler.getMap(m_patches);
668 
669  space m_space = m_assembler.trialSpace(0); // last argument is the space ID
670  auto g_N = m_assembler.getBdrFunction(m_ori);
671 
672  // Weak BCs
673  m_assembler.assembleBdr
674  (
675  m_bcs.get("Weak Dirichlet")
676  ,
677  (m_alpha_d_bc * (m_space * (m_ori - m_ori) - m_space * (g_N) )) * meas(m_ori)
678  );
679 }
680 
681 template <short_t d, class T, bool bending>
682 template <bool _matrix>
683 void gsThinShellAssembler<d, T, bending>::_assembleWeakBCs(const gsFunctionSet<T> & deformed)
684 {
685  this->_getOptions();
686  _assembleWeakBCs_impl<d,_matrix>(deformed);
687 }
688 
689 template <short_t d, class T, bool bending>
690 template <short_t _d, bool _matrix>
691 typename std::enable_if<(_d==3) && _matrix, void>::type
692 gsThinShellAssembler<d, T, bending>::_assembleWeakBCs_impl(const gsFunctionSet<T> & deformed)
693 {
694  geometryMap m_ori = m_assembler.getMap(m_patches);
695  geometryMap m_def = m_assembler.getMap(deformed);
696 
697  space m_space = m_assembler.trialSpace(0); // last argument is the space ID
698  // auto g_N = m_assembler.getBdrFunction(m_ori);
699 
700  gsMaterialMatrixIntegrate<T,MaterialOutput::MatrixA> m_mmA(m_materialMatrices,&m_patches,&deformed);
701  gsMaterialMatrixIntegrate<T,MaterialOutput::MatrixD> m_mmD(m_materialMatrices,&m_patches,&deformed);
702  auto mmA = m_assembler.getCoeff(m_mmA);
703  auto mmD = m_assembler.getCoeff(m_mmD);
704 
705  auto cart2cov = cartcov(m_ori);
706  auto con2cartI = cartcon(m_ori).inv();
707 
708  auto mmAcart = (con2cartI * reshape(mmA,3,3) * cart2cov);
709  auto mmDcart = (con2cartI * reshape(mmD,3,3) * cart2cov);
710 
711  element el = m_assembler.getElement();
712  auto alpha_d = m_alpha_d_bc * reshape(mmAcart,9,1).max().val() / el.area(m_ori);
713  auto alpha_r = m_alpha_r_bc * reshape(mmDcart,9,1).max().val() / el.area(m_ori);
714 
715 
716  auto du = m_def - m_ori;
717  auto dnN = ( usn(m_def).tr()*unv(m_ori) - usn(m_ori).tr()*unv(m_ori) ).val();
718 
719  // Weak BCs
720  m_assembler.assembleBdr
721  (
722  m_bcs.get("Weak Dirichlet")
723  ,
724  -alpha_d * m_space * m_space.tr() * meas(m_ori)
725  );
726 
727  // for weak clamped
728  m_assembler.assembleBdr
729  (
730  m_bcs.get("Weak Clamped")
731  ,
732  (
733  alpha_r * dnN * ( var2deriv2(m_space,m_space,m_def,unv(m_ori).tr()) )
734  +
735  alpha_r * ( ( var1(m_space,m_def) * unv(m_ori) ) * ( var1(m_space,m_def) * unv(m_ori) ).tr() )
736  ) * meas(m_ori)
737  );
738 }
739 
740 template <short_t d, class T, bool bending>
741 template <short_t _d, bool _matrix>
742 typename std::enable_if<(_d==3) && !_matrix, void>::type
743 gsThinShellAssembler<d, T, bending>::_assembleWeakBCs_impl(const gsFunctionSet<T> & deformed)
744 {
745  geometryMap m_ori = m_assembler.getMap(m_patches);
746  geometryMap m_def = m_assembler.getMap(deformed);
747 
748  space m_space = m_assembler.trialSpace(0); // last argument is the space ID
749  auto g_N = m_assembler.getBdrFunction(m_ori);
750 
751  gsMaterialMatrixIntegrate<T,MaterialOutput::MatrixA> m_mmA(m_materialMatrices,&m_patches,&deformed);
752  gsMaterialMatrixIntegrate<T,MaterialOutput::MatrixD> m_mmD(m_materialMatrices,&m_patches,&deformed);
753  auto mmA = m_assembler.getCoeff(m_mmA);
754  auto mmD = m_assembler.getCoeff(m_mmD);
755 
756  auto cart2cov = cartcov(m_ori);
757  auto con2cartI = cartcon(m_ori).inv();
758 
759  auto mmAcart = (con2cartI * reshape(mmA,3,3) * cart2cov);
760  auto mmDcart = (con2cartI * reshape(mmD,3,3) * cart2cov);
761 
762  element el = m_assembler.getElement();
763  auto alpha_d = m_alpha_d_bc * reshape(mmAcart,9,1).max().val() / el.area(m_ori);
764  auto alpha_r = m_alpha_r_bc * reshape(mmDcart,9,1).max().val() / el.area(m_ori);
765 
766  auto du = m_def - m_ori;
767  auto dnN = ( usn(m_def).tr()*nv(m_ori) - usn(m_ori).tr()*nv(m_ori) ).val();
768 
769  // Weak BCs
770  m_assembler.assembleBdr
771  (
772  m_bcs.get("Weak Dirichlet")
773  ,
774  alpha_d * (m_space * du - m_space * (g_N) ) * meas(m_ori)
775  );
776 
777  // for weak clamped
778  m_assembler.assembleBdr
779  (
780  m_bcs.get("Weak Clamped")
781  ,
782  (
783  - alpha_r * dnN * ( var1(m_space,m_def) * usn(m_ori) )
784  ) * meas(m_ori)
785  );
786 }
787 
788 template <short_t d, class T, bool bending>
789 template <short_t _d, bool _matrix>
790 typename std::enable_if<!(_d==3) && _matrix, void>::type
791 gsThinShellAssembler<d, T, bending>::_assembleWeakBCs_impl(const gsFunctionSet<T> & deformed)
792 {
793  geometryMap m_ori = m_assembler.getMap(m_patches);
794 
795  space m_space = m_assembler.trialSpace(0); // last argument is the space ID
796 
797  gsMaterialMatrixIntegrate<T,MaterialOutput::MatrixA> m_mmA(m_materialMatrices,&m_patches,&deformed);
798  auto mmA = m_assembler.getCoeff(m_mmA);
799 
800  auto cart2cov = cartcov(m_ori);
801  auto con2cartI = cartcon(m_ori).inv();
802 
803  auto mmAcart = (con2cartI * reshape(mmA,3,3) * cart2cov);
804 
805  element el = m_assembler.getElement();
806  auto alpha_d = m_alpha_d_bc * reshape(mmAcart,9,1).max().val() / el.area(m_ori);
807 
808  // Weak BCs
809  m_assembler.assembleBdr
810  (
811  m_bcs.get("Weak Dirichlet")
812  ,
813  -alpha_d * m_space * m_space.tr() * meas(m_ori)
814  );
815 }
816 
817 template <short_t d, class T, bool bending>
818 template <short_t _d, bool _matrix>
819 typename std::enable_if<!(_d==3) && !_matrix, void>::type
820 gsThinShellAssembler<d, T, bending>::_assembleWeakBCs_impl(const gsFunctionSet<T> & deformed)
821 {
822  geometryMap m_ori = m_assembler.getMap(m_patches);
823  geometryMap m_def = m_assembler.getMap(deformed);
824 
825  space m_space = m_assembler.trialSpace(0); // last argument is the space ID
826  auto g_N = m_assembler.getBdrFunction(m_ori);
827 
828  gsMaterialMatrixIntegrate<T,MaterialOutput::MatrixA> m_mmA(m_materialMatrices,&m_patches,&deformed);
829  auto mmA = m_assembler.getCoeff(m_mmA);
830 
831  auto cart2cov = cartcov(m_ori);
832  auto con2cartI = cartcon(m_ori).inv();
833 
834  auto mmAcart = (con2cartI * reshape(mmA,3,3) * cart2cov);
835 
836  element el = m_assembler.getElement();
837  auto alpha_d = m_alpha_d_bc * reshape(mmAcart,9,1).max().val() / el.area(m_ori);
838 
839  // Weak BCs
840  m_assembler.assembleBdr
841  (
842  m_bcs.get("Weak Dirichlet")
843  ,
844  alpha_d * (m_space * (m_def - m_ori) - m_space * (g_N) ) * meas(m_ori)
845  );
846 }
847 
848 template<short_t d, class T, bool bending>
849 template<bool _matrix>
850 void gsThinShellAssembler<d, T, bending>::_assembleWeakIfc()
851 {
852  this->_getOptions();
853  if (m_weakC0.size()==0 && m_weakC1.size()==0)
854  return;
855  _assembleWeakIfc_impl<d,_matrix>();
856 }
857 
858 template <short_t d, class T, bool bending>
859 template <short_t _d, bool _matrix>
860 typename std::enable_if<(_d==3) && _matrix, void>::type
861 gsThinShellAssembler<d, T, bending>::_assembleWeakIfc_impl()
862 {
863  gsMultiPatch<T> & defpatches = m_patches;
864  geometryMap m_ori = m_assembler.getMap(m_patches);
865 
866  space m_space = m_assembler.trialSpace(0); // last argument is the space ID
867  // auto g_N = m_assembler.getBdrFunction(m_ori);
868 
869  gsMaterialMatrixIntegrate<T,MaterialOutput::MatrixA> m_mmA(m_materialMatrices,&m_patches,&defpatches);
870  gsMaterialMatrixIntegrate<T,MaterialOutput::MatrixD> m_mmD(m_materialMatrices,&m_patches,&defpatches);
871  auto mmA = m_assembler.getCoeff(m_mmA);
872  auto mmD = m_assembler.getCoeff(m_mmD);
873 
874  auto cart2cov = cartcov(m_ori);
875  auto con2cartI = cartcon(m_ori).inv();
876 
877  auto mmAcart = (con2cartI * reshape(mmA,3,3) * cart2cov);
878  auto mmDcart = (con2cartI * reshape(mmD,3,3) * cart2cov);
879 
880  element el = m_assembler.getElement();
881  auto h = (el.area(m_ori.left()) + el.area(m_ori.right())) / 2;
882  auto alpha_d = m_alpha_d_ifc * reshape(mmAcart,9,1).max().val() / h;
883  auto alpha_r = m_alpha_r_ifc * reshape(mmDcart,9,1).max().val() / h;
884 
885  // C^0 coupling
886  m_assembler.assembleIfc(m_weakC0,
887  alpha_d * m_space.left() * m_space.left().tr() * meas(m_ori)
888  ,
889  -alpha_d * m_space.right()* m_space.left() .tr() * meas(m_ori)
890  ,
891  -alpha_d * m_space.left() * m_space.right().tr() * meas(m_ori)
892  ,
893  alpha_d * m_space.right()* m_space.right().tr() * meas(m_ori)
894  );
895 
896  // C^1 coupling
897  // Penalty of out-of-plane coupling
898  // dW^pr / du_r --> second line
899  m_assembler.assembleIfc(m_weakC1,
900  alpha_r * ( var1(m_space.left(),m_ori.left()) * usn(m_ori.right()) ) * ( var1(m_space.left(),m_ori.left()) * usn(m_ori.right()) ).tr() * meas(m_ori) // left left
901  ,
902  alpha_r * ( var1(m_space.left(),m_ori.left()) * usn(m_ori.right()) ) * ( var1(m_space.right(),m_ori.right()) * usn(m_ori.left()) ).tr() * meas(m_ori) // left right
903  ,
904  alpha_r * ( var1(m_space.right(),m_ori.right()) * usn(m_ori.left()) ) * ( var1(m_space.left(),m_ori.left()) * usn(m_ori.right()) ).tr() * meas(m_ori) // right left
905  ,
906  alpha_r * ( var1(m_space.right(),m_ori.right()) * usn(m_ori.left()) ) * ( var1(m_space.right(),m_ori.right()) * usn(m_ori.left()) ).tr() * meas(m_ori) // right right
907  ,
908  // Symmetry
909  alpha_r * ( var1(m_space.right(),m_ori.right()) * usn(m_ori.left()) ) * ( var1(m_space.right(),m_ori.right()) * usn(m_ori.left()) ).tr() * meas(m_ori) // right right
910  ,
911  alpha_r * ( var1(m_space.right(),m_ori.right()) * usn(m_ori.left()) ) * ( var1(m_space.left(),m_ori.left()) * usn(m_ori.right()) ).tr() * meas(m_ori) // right left
912  ,
913  alpha_r * ( var1(m_space.left(),m_ori.left()) * usn(m_ori.right()) ) * ( var1(m_space.right(),m_ori.right()) * usn(m_ori.left()) ).tr() * meas(m_ori) // left right
914  ,
915  alpha_r * ( var1(m_space.left(),m_ori.left()) * usn(m_ori.right()) ) * ( var1(m_space.left(),m_ori.left()) * usn(m_ori.right()) ).tr() * meas(m_ori) // left left
916  );
917 
918  // Penalty of in-plane coupling
919  // dW^pr / du_r --> fourth line
920  m_assembler.assembleIfc(m_weakC1,
921  alpha_r * ( ovar1(m_space.left() ,m_ori.left() ) * usn(m_ori.right()) ) * ( ovar1(m_space.left() ,m_ori.left() ) * usn(m_ori.right()) ).tr() * meas(m_ori) // left left
922  + // Symmetry
923  alpha_r * ( var1(m_space.left() ,m_ori.left() ) * unv(m_ori.right()) ) * ( var1(m_space.left() ,m_ori.left() ) * unv(m_ori.right()) ).tr() * meas(m_ori) // left left
924  ,
925  alpha_r * ( ovar1(m_space.left() ,m_ori.left() ) * usn(m_ori.right()) ) * ( var1(m_space.right(),m_ori.right()) * unv(m_ori.left() ) ).tr() * meas(m_ori) // left right
926  + // Symmetry
927  alpha_r * ( var1(m_space.left() ,m_ori.left() ) * unv(m_ori.right()) ) * ( ovar1(m_space.right(),m_ori.right()) * usn(m_ori.left() ) ).tr() * meas(m_ori) // left right
928  ,
929  alpha_r * ( var1(m_space.right(),m_ori.right()) * unv(m_ori.left() ) ) * ( ovar1(m_space.left() ,m_ori.left() ) * usn(m_ori.right()) ).tr() * meas(m_ori) // right left
930  + // Symmetry
931  alpha_r * ( ovar1(m_space.right(),m_ori.right()) * usn(m_ori.left() ) ) * ( var1(m_space.left() ,m_ori.left() ) * unv(m_ori.right()) ).tr() * meas(m_ori) // right left
932  ,
933  alpha_r * ( var1(m_space.right(),m_ori.right()) * unv(m_ori.left() ) ) * ( var1(m_space.right(),m_ori.right()) * unv(m_ori.left() ) ).tr() * meas(m_ori) // right right
934  + // Symmetry
935  alpha_r * ( ovar1(m_space.right(),m_ori.right()) * usn(m_ori.left() ) ) * ( ovar1(m_space.right(),m_ori.right()) * usn(m_ori.left() ) ).tr() * meas(m_ori) // right right
936  );
937 }
938 
939 template <short_t d, class T, bool bending>
940 template <short_t _d, bool _matrix>
941 typename std::enable_if<(_d==3) && !_matrix, void>::type
942 gsThinShellAssembler<d, T, bending>::_assembleWeakIfc_impl()
943 {
944 /*
945  empty
946  */
947 }
948 
949 template <short_t d, class T, bool bending>
950 template <short_t _d, bool _matrix>
951 typename std::enable_if<!(_d==3) && _matrix, void>::type
952 gsThinShellAssembler<d, T, bending>::_assembleWeakIfc_impl()
953 {
954  gsMultiPatch<T> & defpatches = m_patches;
955  geometryMap m_ori = m_assembler.getMap(m_patches);
956 
957  space m_space = m_assembler.trialSpace(0); // last argument is the space ID
958 
959  gsMaterialMatrixIntegrate<T,MaterialOutput::MatrixA> m_mmA(m_materialMatrices,&m_patches,&defpatches);
960  auto mmA = m_assembler.getCoeff(m_mmA);
961 
962  auto cart2cov = cartcov(m_ori);
963  auto con2cartI = cartcon(m_ori).inv();
964 
965  auto mmAcart = (con2cartI * reshape(mmA,3,3) * cart2cov);
966 
967  element el = m_assembler.getElement();
968  auto h = (el.area(m_ori.left()) + el.area(m_ori.right())) / 2;
969  auto alpha_d = m_alpha_d_ifc * reshape(mmAcart,9,1).max().val() / h;
970 
971  // C^0 coupling
972  m_assembler.assembleIfc(m_weakC0,
973  alpha_d * m_space.left() * m_space.left().tr() * meas(m_ori) * meas(m_ori)
974  ,
975  -alpha_d * m_space.right()* m_space.left() .tr() * meas(m_ori) * meas(m_ori)
976  ,
977  -alpha_d * m_space.left() * m_space.right().tr() * meas(m_ori) * meas(m_ori)
978  ,
979  alpha_d * m_space.right()* m_space.right().tr() * meas(m_ori) * meas(m_ori)
980  );
981 
982  // C^1 coupling DOES NOT CONTRIBUTE IN 2D PROBLEMS
983 }
984 
985 template <short_t d, class T, bool bending>
986 template <short_t _d, bool _matrix>
987 typename std::enable_if<!(_d==3) && !_matrix, void>::type
988 gsThinShellAssembler<d, T, bending>::_assembleWeakIfc_impl()
989 {
990 /*
991  empty
992  */
993 }
994 
995 template<short_t d, class T, bool bending>
996 template<bool _matrix>
997 void gsThinShellAssembler<d, T, bending>::_assembleWeakIfc(const gsFunctionSet<T> & deformed)
998 {
999  this->_getOptions();
1000  _assembleWeakIfc_impl<d,_matrix>(deformed);
1001 }
1002 
1003 template <short_t d, class T, bool bending>
1004 template <short_t _d, bool _matrix>
1005 typename std::enable_if<(_d==3) && _matrix, void>::type
1006 gsThinShellAssembler<d, T, bending>::_assembleWeakIfc_impl(const gsFunctionSet<T> & deformed)
1007 {
1008  geometryMap m_ori = m_assembler.getMap(m_patches);
1009  geometryMap m_def = m_assembler.getMap(deformed);
1010 
1011  space m_space = m_assembler.trialSpace(0); // last argument is the space ID
1012 
1013  gsMaterialMatrixIntegrate<T,MaterialOutput::MatrixA> m_mmA(m_materialMatrices,&m_patches,&deformed);
1014  gsMaterialMatrixIntegrate<T,MaterialOutput::MatrixD> m_mmD(m_materialMatrices,&m_patches,&deformed);
1015  auto mmA = m_assembler.getCoeff(m_mmA);
1016  auto mmD = m_assembler.getCoeff(m_mmD);
1017 
1018  auto cart2cov = cartcov(m_ori);
1019  auto con2cartI = cartcon(m_ori).inv();
1020 
1021  auto mmAcart = (con2cartI * reshape(mmA,3,3) * cart2cov);
1022  auto mmDcart = (con2cartI * reshape(mmD,3,3) * cart2cov);
1023 
1024  element el = m_assembler.getElement();
1025  auto h = (el.area(m_ori.left()) + el.area(m_ori.right())) / 2;
1026  auto alpha_d = m_alpha_d_ifc * reshape(mmAcart,9,1).max().val() / h;
1027  auto alpha_r = m_alpha_r_ifc * reshape(mmDcart,9,1).max().val() / h;
1028 
1029  auto du = ((m_def.left()-m_ori.left()) - (m_def.right()-m_ori.right()));
1030 
1031  auto dN_lr = (usn(m_def.left()).tr()*usn(m_def.right())
1032  - usn(m_ori.left()).tr()*usn(m_ori.right())).val();
1033 
1034  auto dN_rl = (usn(m_def.right()).tr()*usn(m_def.left())
1035  - usn(m_ori.right()).tr()*usn(m_ori.left())).val();
1036 
1037  auto dnN_lr= (unv(m_def.left()).tr()*usn(m_def.right())
1038  - unv(m_ori.left()).tr()*usn(m_ori.right())).val();
1039 
1040  auto dnN_rl= (unv(m_def.right()).tr()*usn(m_def.left())
1041  - unv(m_ori.right()).tr()*usn(m_ori.left())).val();
1042 
1043  // C^0 coupling
1044  m_assembler.assembleIfc(m_weakC0,
1045  alpha_d * m_space.left() * m_space.left().tr() * meas(m_ori)
1046  ,
1047  -alpha_d * m_space.right()* m_space.left() .tr() * meas(m_ori)
1048  ,
1049  -alpha_d * m_space.left() * m_space.right().tr() * meas(m_ori)
1050  ,
1051  alpha_d * m_space.right()* m_space.right().tr() * meas(m_ori)
1052  );
1053 
1054  // C^1 coupling
1055  // Penalty of out-of-plane coupling
1056  // dW^pr / du_r --> first line
1057  m_assembler.assembleIfc(m_weakC1,
1058  alpha_r * dN_lr * var2(m_space.left() ,m_space.left() ,m_def.left() ,usn(m_def.right()).tr() ) * meas(m_ori) // left left
1059  +//Symmetry
1060  alpha_r * dN_rl * var2( m_space.left(),m_space.left(),m_def.left(),usn(m_def.right() ).tr() ) * meas(m_ori) // left left
1061  ,
1062  alpha_r * dN_lr * ( var1(m_space.left() ,m_def.left() ) * var1(m_space.right(),m_def.right()).tr() ) * meas(m_ori)// left right
1063  +//Symmetry
1064  alpha_r * dN_rl * ( var1(m_space.left(),m_def.left()) * var1(m_space.right() ,m_def.right() ).tr() ) * meas(m_ori)// left right
1065  ,
1066  alpha_r * dN_lr * ( var1(m_space.right(),m_def.right()) * var1(m_space.left() ,m_def.left() ).tr() ) * meas(m_ori)// right left
1067  +//Symmetry
1068  alpha_r * dN_rl * ( var1(m_space.right() ,m_def.right() ) * var1(m_space.left(),m_def.left()).tr() ) * meas(m_ori)// right left
1069  ,
1070  alpha_r * dN_lr * var2( m_space.right(),m_space.right(),m_def.right(),usn(m_def.left() ).tr() ) * meas(m_ori) // right right
1071  +//Symmetry
1072  alpha_r * dN_rl * var2(m_space.right() ,m_space.right() ,m_def.right() ,usn(m_def.left()).tr() ) * meas(m_ori) // right right
1073  );
1074 
1075  // Penalty of out-of-plane coupling
1076  // dW^pr / du_r --> second line
1077  m_assembler.assembleIfc(m_weakC1,
1078  alpha_r * ( var1(m_space.left(),m_def.left()) * usn(m_def.right()) ) * ( var1(m_space.left(),m_def.left()) * usn(m_def.right()) ).tr() * meas(m_ori) // left left
1079  ,
1080  alpha_r * ( var1(m_space.left(),m_def.left()) * usn(m_def.right()) ) * ( var1(m_space.right(),m_def.right()) * usn(m_def.left()) ).tr() * meas(m_ori) // left right
1081  ,
1082  alpha_r * ( var1(m_space.right(),m_def.right()) * usn(m_def.left()) ) * ( var1(m_space.left(),m_def.left()) * usn(m_def.right()) ).tr() * meas(m_ori) // right left
1083  ,
1084  alpha_r * ( var1(m_space.right(),m_def.right()) * usn(m_def.left()) ) * ( var1(m_space.right(),m_def.right()) * usn(m_def.left()) ).tr() * meas(m_ori) // right right
1085  ,
1086  // Symmetry
1087  alpha_r * ( var1(m_space.right(),m_def.right()) * usn(m_def.left()) ) * ( var1(m_space.right(),m_def.right()) * usn(m_def.left()) ).tr() * meas(m_ori) // right right
1088  ,
1089  alpha_r * ( var1(m_space.right(),m_def.right()) * usn(m_def.left()) ) * ( var1(m_space.left(),m_def.left()) * usn(m_def.right()) ).tr() * meas(m_ori) // right left
1090  ,
1091  alpha_r * ( var1(m_space.left(),m_def.left()) * usn(m_def.right()) ) * ( var1(m_space.right(),m_def.right()) * usn(m_def.left()) ).tr() * meas(m_ori) // left right
1092  ,
1093  alpha_r * ( var1(m_space.left(),m_def.left()) * usn(m_def.right()) ) * ( var1(m_space.left(),m_def.left()) * usn(m_def.right()) ).tr() * meas(m_ori) // left left
1094  );
1095 
1096  // Penalty of in-plane coupling
1097  // dW^pr / du_r --> third line
1098  m_assembler.assembleIfc(m_weakC1,
1099  alpha_r * dnN_lr * ovar2(m_space.left(),m_space.left(),m_def.left(),usn(m_def.right()).tr()) * meas(m_ori) // left left
1100  + // Symmetry
1101  alpha_r * dnN_rl * ovar2(m_space.left(),m_space.left(),m_def.left(),usn(m_def.right()).tr()) * meas(m_ori) // left left
1102  ,
1103  alpha_r * dnN_lr * ( ovar1(m_space.left() ,m_def.left() ) * var1(m_space.right(),m_def.right()).tr() ) * meas(m_ori) // left right
1104  + // Symmetry
1105  alpha_r * dnN_rl * ( ovar1(m_space.left() ,m_def.left() ) * var1(m_space.right(),m_def.right()).tr() ) * meas(m_ori) // right left
1106  ,
1107  alpha_r * dnN_lr * ( ovar1(m_space.right(),m_def.right()) * var1(m_space.left() ,m_def.left() ).tr() ) * meas(m_ori) // right left
1108  + // Symmetry
1109  alpha_r * dnN_rl * ( ovar1(m_space.right(),m_def.right()) * var1(m_space.left() ,m_def.left() ).tr() ) * meas(m_ori) // right left
1110  ,
1111  alpha_r * dnN_lr * ovar2(m_space.right(),m_space.right(),m_def.right(),usn(m_def.left()).tr()) * meas(m_ori) // right right
1112  + // Symmetry
1113  alpha_r * dnN_rl * ovar2(m_space.right(),m_space.right(),m_def.right(),usn(m_def.left()).tr()) * meas(m_ori) // right right
1114  );
1115 
1116  // Penalty of in-plane coupling
1117  // dW^pr / du_r --> fourth line
1118  m_assembler.assembleIfc(m_weakC1,
1119  alpha_r * ( ovar1(m_space.left() ,m_def.left() ) * usn(m_def.right()) ) * ( ovar1(m_space.left() ,m_def.left() ) * usn(m_def.right()) ).tr() * meas(m_ori) // left left
1120  + // Symmetry
1121  alpha_r * ( var1(m_space.left() ,m_def.left() ) * unv(m_def.right()) ) * ( var1(m_space.left() ,m_def.left() ) * unv(m_def.right()) ).tr() * meas(m_ori) // left left
1122  ,
1123  alpha_r * ( ovar1(m_space.left() ,m_def.left() ) * usn(m_def.right()) ) * ( var1(m_space.right(),m_def.right()) * unv(m_def.left() ) ).tr() * meas(m_ori) // left right
1124  + // Symmetry
1125  alpha_r * ( var1(m_space.left() ,m_def.left() ) * unv(m_def.right()) ) * ( ovar1(m_space.right(),m_def.right()) * usn(m_def.left() ) ).tr() * meas(m_ori) // left right
1126  ,
1127  alpha_r * ( var1(m_space.right(),m_def.right()) * unv(m_def.left() ) ) * ( ovar1(m_space.left() ,m_def.left() ) * usn(m_def.right()) ).tr() * meas(m_ori) // right left
1128  + // Symmetry
1129  alpha_r * ( ovar1(m_space.right(),m_def.right()) * usn(m_def.left() ) ) * ( var1(m_space.left() ,m_def.left() ) * unv(m_def.right()) ).tr() * meas(m_ori) // right left
1130  ,
1131  alpha_r * ( var1(m_space.right(),m_def.right()) * unv(m_def.left() ) ) * ( var1(m_space.right(),m_def.right()) * unv(m_def.left() ) ).tr() * meas(m_ori) // right right
1132  + // Symmetry
1133  alpha_r * ( ovar1(m_space.right(),m_def.right()) * usn(m_def.left() ) ) * ( ovar1(m_space.right(),m_def.right()) * usn(m_def.left() ) ).tr() * meas(m_ori) // right right
1134  );
1135 }
1136 
1137 template <short_t d, class T, bool bending>
1138 template <short_t _d, bool _matrix>
1139 typename std::enable_if<(_d==3) && !_matrix, void>::type
1140 gsThinShellAssembler<d, T, bending>::_assembleWeakIfc_impl(const gsFunctionSet<T> & deformed)
1141 {
1142  geometryMap m_ori = m_assembler.getMap(m_patches);
1143  geometryMap m_def = m_assembler.getMap(deformed);
1144 
1145  space m_space = m_assembler.trialSpace(0); // last argument is the space ID
1146 
1147  gsMaterialMatrixIntegrate<T,MaterialOutput::MatrixA> m_mmA(m_materialMatrices,&m_patches,&deformed);
1148  gsMaterialMatrixIntegrate<T,MaterialOutput::MatrixD> m_mmD(m_materialMatrices,&m_patches,&deformed);
1149  auto mmA = m_assembler.getCoeff(m_mmA);
1150  auto mmD = m_assembler.getCoeff(m_mmD);
1151 
1152  auto cart2cov = cartcov(m_ori);
1153  auto con2cartI = cartcon(m_ori).inv();
1154 
1155  auto mmAcart = (con2cartI * reshape(mmA,3,3) * cart2cov);
1156  auto mmDcart = (con2cartI * reshape(mmD,3,3) * cart2cov);
1157 
1158  element el = m_assembler.getElement();
1159  auto h = (el.area(m_ori.left()) + el.area(m_ori.right())) / 2;
1160  auto alpha_d = m_alpha_d_ifc * reshape(mmAcart,9,1).max().val() / h;
1161  auto alpha_r = m_alpha_r_ifc * reshape(mmDcart,9,1).max().val() / h;
1162 
1163  auto du = ((m_def.left()-m_ori.left()) - (m_def.right()-m_ori.right()));
1164 
1165  auto dN_lr = (usn(m_def.left()).tr()*usn(m_def.right())
1166  - usn(m_ori.left()).tr()*usn(m_ori.right())).val();
1167 
1168  auto dN_rl = (usn(m_def.right()).tr()*usn(m_def.left())
1169  - usn(m_ori.right()).tr()*usn(m_ori.left())).val();
1170 
1171  auto dnN_lr= (unv(m_def.left()).tr()*usn(m_def.right())
1172  - unv(m_ori.left()).tr()*usn(m_ori.right())).val();
1173 
1174  auto dnN_rl= (unv(m_def.right()).tr()*usn(m_def.left())
1175  - unv(m_ori.right()).tr()*usn(m_ori.left())).val();
1176 
1177  // C^0 coupling
1178  m_assembler.assembleIfc(m_weakC0,
1179  -alpha_d * m_space.left() * du * meas(m_ori)
1180  ,
1181  alpha_d * m_space.right()* du * meas(m_ori)
1182  );
1183 
1184  // C^1 coupling
1185  m_assembler.assembleIfc(m_weakC1,
1186  -alpha_r * dN_lr * var1(m_space.left(),m_def.left()) * usn(m_def.right()) * meas(m_ori)
1187  ,
1188  -alpha_r * dN_lr * var1(m_space.right(),m_def.right()) * usn(m_def.left() ) * meas(m_ori)
1189  ,
1190  // Symmetry
1191  -alpha_r * dN_rl * var1(m_space.right(),m_def.right()) * usn(m_def.left()) * meas(m_ori)
1192  ,
1193  -alpha_r * dN_rl * var1(m_space.left(),m_def.left()) * usn(m_def.right() ) * meas(m_ori)
1194  );
1195 
1196  // Penalty of in-plane coupling
1197  // dW^pr / du_r --> second line
1198  m_assembler.assembleIfc(m_weakC1,
1199  -alpha_r * dnN_lr* ovar1(m_space.left(),m_def.left()) * usn(m_def.right()) * meas(m_ori)
1200  ,
1201  -alpha_r * dnN_lr* var1(m_space.right(),m_def.right()) * unv(m_def.left() ) * meas(m_ori)
1202  ,
1203  // Symmetry
1204  -alpha_r * dnN_rl* ovar1(m_space.right(),m_def.right()) * usn(m_def.left()) * meas(m_ori)
1205  ,
1206  -alpha_r * dnN_rl* var1(m_space.left(),m_def.left()) * unv(m_def.right() ) * meas(m_ori)
1207  );
1208 }
1209 
1210 template <short_t d, class T, bool bending>
1211 template <short_t _d, bool _matrix>
1212 typename std::enable_if<!(_d==3) && _matrix, void>::type
1213 gsThinShellAssembler<d, T, bending>::_assembleWeakIfc_impl(const gsFunctionSet<T> & deformed)
1214 {
1215  geometryMap m_ori = m_assembler.getMap(m_patches);
1216  geometryMap m_def = m_assembler.getMap(deformed);
1217 
1218  space m_space = m_assembler.trialSpace(0); // last argument is the space ID
1219 
1220  gsMaterialMatrixIntegrate<T,MaterialOutput::MatrixA> m_mmA(m_materialMatrices,&m_patches,&deformed);
1221  auto mmA = m_assembler.getCoeff(m_mmA);
1222 
1223  auto cart2cov = cartcov(m_ori);
1224  auto con2cartI = cartcon(m_ori).inv();
1225 
1226  auto mmAcart = (con2cartI * reshape(mmA,3,3) * cart2cov);
1227 
1228  element el = m_assembler.getElement();
1229  auto h = (el.area(m_ori.left()) + el.area(m_ori.right())) / 2;
1230  auto alpha_d = m_alpha_d_ifc * reshape(mmAcart,9,1).max().val() / h;
1231 
1232  auto du = ((m_def.left()-m_ori.left()) - (m_def.right()-m_ori.right()));
1233 
1234  // C^0 coupling
1235  m_assembler.assembleIfc(m_weakC0,
1236  alpha_d * m_space.left() * m_space.left().tr() * meas(m_ori)
1237  ,
1238  -alpha_d * m_space.right()* m_space.left() .tr() * meas(m_ori)
1239  ,
1240  -alpha_d * m_space.left() * m_space.right().tr() * meas(m_ori)
1241  ,
1242  alpha_d * m_space.right()* m_space.right().tr() * meas(m_ori)
1243  );
1244 
1245  // C^1 coupling DOES NOT CONTRIBUTE IN 2D PROBLEMS
1246 }
1247 
1248 template <short_t d, class T, bool bending>
1249 template <short_t _d, bool _matrix>
1250 typename std::enable_if<!(_d==3) && !_matrix, void>::type
1251 gsThinShellAssembler<d, T, bending>::_assembleWeakIfc_impl(const gsFunctionSet<T> & deformed)
1252 {
1253  geometryMap m_ori = m_assembler.getMap(m_patches);
1254  geometryMap m_def = m_assembler.getMap(deformed);
1255 
1256  space m_space = m_assembler.trialSpace(0); // last argument is the space ID
1257 
1258  gsMaterialMatrixIntegrate<T,MaterialOutput::MatrixA> m_mmA(m_materialMatrices,&m_patches,&deformed);
1259  auto mmA = m_assembler.getCoeff(m_mmA);
1260 
1261  auto cart2cov = cartcov(m_ori);
1262  auto con2cartI = cartcon(m_ori).inv();
1263 
1264  auto mmAcart = (con2cartI * reshape(mmA,3,3) * cart2cov);
1265 
1266  element el = m_assembler.getElement();
1267  auto h = (el.area(m_ori.left()) + el.area(m_ori.right())) / 2;
1268  auto alpha_d = m_alpha_d_ifc * reshape(mmAcart,9,1).max().val() / h;
1269 
1270  auto du = ((m_def.left()-m_ori.left()) - (m_def.right()-m_ori.right()));
1271 
1272  // C^0 coupling
1273  m_assembler.assembleIfc(m_weakC0,
1274  alpha_d * m_space.left() * du * meas(m_ori)
1275  ,
1276  -alpha_d * m_space.right()* du * meas(m_ori)
1277  );
1278 
1279  // C^1 coupling DOES NOT CONTRIBUTE IN 2D PROBLEMS
1280 }
1281 
1282 template<short_t d, class T, bool bending>
1283 void gsThinShellAssembler<d, T, bending>::_assembleDirichlet()
1284 {
1285  this->_getOptions();
1286  space m_space = m_assembler.trialSpace(0); // last argument is the space ID
1287  // if statement
1288  m_space.setup(m_bcs, dirichlet::l2Projection, m_continuity);
1289  // m_assembler.initSystem();
1290 }
1291 
1292 template<short_t d, class T, bool bending>
1294 {
1295  this->_getOptions();
1296  space m_space = m_assembler.trialSpace(0); // last argument is the space ID
1297  m_space.setup(m_bcs, dirichlet::homogeneous, m_continuity);
1298  // space m_space = m_assembler.trialSpace(0); // last argument is the space ID
1299  // const_cast<expr::gsFeSpace<T> & >(m_space).fixedPart().setZero();
1300 }
1301 
1302 template<short_t d, class T, bool bending>
1304 {
1305  gsMatrix<T> bVals;
1306  gsMatrix<index_t> acts,globalActs;
1307 
1308  space m_space = m_assembler.trialSpace(0);
1309  m_mapper = m_space.mapper();
1310 
1311  for (size_t i = 0; i< m_pLoads.numLoads(); ++i )
1312  {
1313  GISMO_ASSERT(m_pLoads[i].value.size()==d,"Point load has wrong dimension "<<m_pLoads[i].value.size()<<" instead of "<<d<<"\n");
1314  GISMO_ASSERT((size_t)m_pLoads[i].patch<m_patches.nPatches(),"Point load is defined on a patch with index "<<m_pLoads[i].patch<<" while the geometry has "<<m_patches.nPatches()<<" patches\n");
1315  // Compute actives and values of basis functions on point load location.
1316  if ( m_pLoads[i].parametric ) // in parametric space
1317  {
1318  if (const gsMappedBasis<2,T> * mbasis = dynamic_cast<const gsMappedBasis<2,T> * >(m_spaceBasis))
1319  {
1320  mbasis->active_into(m_pLoads[i].patch,m_pLoads[i].point, acts );
1321  mbasis->eval_into (m_pLoads[i].patch,m_pLoads[i].point, bVals );
1322  }
1323  else if (const gsMultiBasis<T> * mbasis = dynamic_cast<const gsMultiBasis<T> * >(m_spaceBasis))
1324  {
1325  mbasis->basis(m_pLoads[i].patch).active_into( m_pLoads[i].point, acts);
1326  mbasis->basis(m_pLoads[i].patch).eval_into ( m_pLoads[i].point, bVals);
1327  }
1328  else
1329  GISMO_ERROR("Basis type not understood");
1330  }
1331  else // in physical space
1332  {
1333  gsMatrix<T> forcePoint;
1334  m_patches.patch(m_pLoads[i].patch).invertPoints(m_pLoads[i].point,forcePoint);
1335 
1336  if (const gsMappedBasis<2,T> * mbasis = dynamic_cast<const gsMappedBasis<2,T> * >(m_spaceBasis))
1337  {
1338  mbasis->active_into(m_pLoads[i].patch,forcePoint, acts );
1339  mbasis->eval_into (m_pLoads[i].patch,forcePoint, bVals );
1340  }
1341  else if (const gsMultiBasis<T> * mbasis = dynamic_cast<const gsMultiBasis<T> * >(m_spaceBasis))
1342  {
1343  mbasis->basis(m_pLoads[i].patch).active_into( forcePoint, acts);
1344  mbasis->basis(m_pLoads[i].patch).eval_into ( forcePoint, bVals);
1345  }
1346  else
1347  GISMO_ERROR("Basis type not understood");
1348  }
1349 
1350  // Add the point load values in the right entries in the global RHS
1351  for (size_t j = 0; j< d; ++j)
1352  {
1353  if (m_pLoads[i].value[j] != 0.0)
1354  {
1355  m_mapper.localToGlobal(acts, m_pLoads[i].patch, globalActs,j);
1356  for (index_t k=0; k < globalActs.rows(); ++k)
1357  {
1358  if (m_mapper.is_free_index(globalActs(k,0)))
1359  m_rhs(globalActs(k,0), 0) += bVals(k,0) * m_pLoads[i].value[j];
1360  }
1361  }
1362  }
1363  }
1364 }
1365 
1366 template<short_t d, class T, bool bending>
1367 void gsThinShellAssembler<d, T, bending>::_applyMass()
1368 {
1369  gsMatrix<T> bVals;
1370  gsMatrix<index_t> acts,globalActs;
1371 
1372  space m_space = m_assembler.trialSpace(0);
1373  m_mapper = m_space.mapper();
1374 
1375  GISMO_ASSERT(m_mass.rows()!=0,"Mass matrix must be assembled first");
1376 
1377  for (size_t i = 0; i< m_pMass.numLoads(); ++i )
1378  {
1379  GISMO_ASSERT(m_pMass[i].value.size()==1,"Mass should be one-dimensional");
1380 
1381  // Compute actives and values of basis functions on point load location.
1382  if ( m_pMass[i].parametric ) // in parametric space
1383  {
1384  m_basis.front().basis(m_pMass[i].patch).active_into( m_pMass[i].point, acts );
1385  m_basis.front().basis(m_pMass[i].patch).eval_into ( m_pMass[i].point, bVals);
1386  }
1387  else // in physical space
1388  {
1389  gsMatrix<T> forcePoint;
1390  m_patches.patch(m_pMass[i].patch).invertPoints(m_pMass[i].point,forcePoint);
1391  m_basis.front().basis(m_pMass[i].patch).active_into( forcePoint, acts );
1392  m_basis.front().basis(m_pMass[i].patch).eval_into ( forcePoint, bVals);
1393  }
1394 
1395  // Add the point load values in the right entries in the global RHS
1396  for (size_t j = 0; j< d; ++j)
1397  {
1398  if (m_pMass[i].value[0] != 0.0)
1399  {
1400  m_mapper.localToGlobal(acts, m_pMass[i].patch, globalActs,j);
1401  for (index_t k=0; k < globalActs.rows(); ++k)
1402  {
1403  for (index_t l=0; l < globalActs.rows(); ++l)
1404  {
1405  if (m_mapper.is_free_index(globalActs(k,0)) && m_mapper.is_free_index(globalActs(l,0)))
1406  m_mass(globalActs(k,0), globalActs(l,0)) += bVals(k,0) * bVals(l,0) * m_pMass[i].value[0];
1407  }
1408  }
1409  }
1410  }
1411  }
1412 }
1413 
1414 template<short_t d, class T, bool bending>
1416 {
1417  m_assembler.cleanUp();
1418  GISMO_ENSURE(m_options.hasGroup("ExprAssembler"),"The option list does not contain options with the label 'ExprAssembler'!");
1419  m_assembler.setOptions(m_options.getGroup("ExprAssembler"));
1420 
1421  geometryMap m_ori = m_assembler.getMap(m_patches);
1422 
1423  // Initialize stystem
1424  m_assembler.initSystem();
1425 
1426  gsMaterialMatrixIntegrate<T,MaterialOutput::Density> m_mm(m_materialMatrices,&m_patches);
1427  auto mm0 = m_assembler.getCoeff(m_mm);
1428 
1429  space m_space = m_assembler.trialSpace(0);
1430  m_space.setup(m_bcs, dirichlet::homogeneous, m_continuity);
1431  // this->homogenizeDirichlet();
1432 
1433  gsExprEvaluator<T> ev(m_assembler);
1434  gsVector<> pt(2);
1435  pt.setConstant(.25);
1436 
1437  try
1438  {
1439  // assemble system
1440  if (!lumped)
1441  m_assembler.assemble(mm0.val()*m_space*m_space.tr()*meas(m_ori));
1442  else
1443  m_assembler.assemble(mm0.val()*(m_space.rowSum())*meas(m_ori));
1444 
1445 /* // assemble system
1446  if (!lumped)
1447  {
1448  m_assembler.assemble(mm0.val()*m_space*m_space.tr()*meas(m_ori));
1449  m_mass = m_assembler.matrix();
1450  this->_applyMass();
1451  }
1452  else
1453  {
1454  // To do: add point masses in lumped case
1455  m_assembler.assemble(mm0.val()*(m_space.rowSum())*meas(m_ori));
1456  m_rhs = m_assembler.rhs();
1457  }
1458  m_mass = m_assembler.matrix();
1459 
1460  this->_applyMass();
1461  m_status = ThinShellAssemblerStatus::Success;*/
1462  }
1463  catch (...)
1464  {
1465  m_assembler.cleanUp();
1467  }
1468  return m_status;
1469 }
1470 
1471 // legacy
1472 template<short_t d, class T, bool bending>
1474 {
1475  m_assembler.cleanUp();
1476  GISMO_ENSURE(m_options.hasGroup("ExprAssembler"),"The option list does not contain options with the label 'ExprAssembler'!");
1477  m_assembler.setOptions(m_options.getGroup("ExprAssembler"));
1478 
1479  geometryMap m_ori = m_assembler.getMap(m_patches);
1480 
1481  // Initialize stystem
1482  m_assembler.initSystem();
1483  auto m_foundation = m_assembler.getCoeff(*m_foundFun, m_ori);
1484  GISMO_ASSERT(m_foundFun->targetDim()==3,"Foundation function has dimension "<<m_foundFun->targetDim()<<", but expected 3");
1485 
1486  space m_space = m_assembler.trialSpace(0);
1487 
1488  try
1489  {
1490  m_assembler.assemble(m_space * m_foundation.asDiag() * m_space.tr() * meas(m_ori));
1492  }
1493  catch (...)
1494  {
1495  m_assembler.cleanUp();
1497  }
1498  return m_status;
1499 }
1500 
1501 template<short_t d, class T, bool bending>
1503 {
1504  return assemble_impl<d, bending>();
1505 }
1506 
1514 template <short_t d, typename T, bool bending>
1515 template <short_t _d, bool _bending>
1516 typename std::enable_if<(_d==3) && _bending, ThinShellAssemblerStatus>::type
1518 {
1519  this->_getOptions();
1520 
1521  m_assembler.cleanUp();
1522  GISMO_ENSURE(m_options.hasGroup("ExprAssembler"),"The option list does not contain options with the label 'ExprAssembler'!");
1523  m_assembler.setOptions(m_options.getGroup("ExprAssembler"));
1524 
1525  // Linear assembly: deformed and undeformed geometries are the same
1526  gsMultiPatch<T> & defpatches = m_patches;
1527  geometryMap m_ori = m_assembler.getMap(m_patches);
1528  geometryMap m_def = m_assembler.getMap(defpatches);
1529 
1530  // Initialize stystem
1531  m_assembler.initSystem();
1532  m_assembler.initVector(1);
1533 
1534  gsMaterialMatrixIntegrate<T,MaterialOutput::MatrixA> m_mmA(m_materialMatrices,&m_patches,&defpatches);
1535  gsMaterialMatrixIntegrate<T,MaterialOutput::MatrixB> m_mmB(m_materialMatrices,&m_patches,&defpatches);
1536  gsMaterialMatrixIntegrate<T,MaterialOutput::MatrixC> m_mmC(m_materialMatrices,&m_patches,&defpatches);
1537  gsMaterialMatrixIntegrate<T,MaterialOutput::MatrixD> m_mmD(m_materialMatrices,&m_patches,&defpatches);
1538  auto mmA = m_assembler.getCoeff(m_mmA);
1539  auto mmB = m_assembler.getCoeff(m_mmB);
1540  auto mmC = m_assembler.getCoeff(m_mmC);
1541  auto mmD = m_assembler.getCoeff(m_mmD);
1542 
1543  gsFunctionExpr<> mult2t("1","0","0","0","1","0","0","0","2",2);
1544  auto m_m2 = m_assembler.getCoeff(mult2t);
1545 
1546  space m_space = m_assembler.trialSpace(0);
1547 
1548  auto m_force = m_assembler.getCoeff(*m_forceFun, m_ori);
1549 
1550 
1551  auto m_Em_der = flat( jac(m_def).tr() * jac(m_space) );
1552  auto m_Ef_der = -( deriv2(m_space,sn(m_def).normalized().tr() ) + deriv2(m_def,var1(m_space,m_def) ) ) * reshape(m_m2,3,3);
1553 
1554  auto m_N_der = m_Em_der * reshape(mmA,3,3) + m_Ef_der * reshape(mmB,3,3);
1555  auto m_M_der = m_Em_der * reshape(mmC,3,3) + m_Ef_der * reshape(mmD,3,3);
1556 
1557  try
1558  {
1559  if (m_foundInd)
1560  {
1561  this->_assembleFoundation<true>(*m_foundFun);
1562  this->_assembleFoundation<false>(*m_foundFun);
1563  }
1564  if (m_pressInd)
1565  {
1566  this->_assemblePressure<true>(*m_pressFun);
1567  this->_assemblePressure<false>(*m_pressFun);
1568  }
1569 
1570  m_assembler.assemble(
1571  (
1572  m_N_der * m_Em_der.tr()
1573  +
1574  m_M_der * m_Ef_der.tr()
1575  ) * meas(m_ori)
1576  ,
1577  m_space * m_force * meas(m_ori)
1578  );
1579 
1580  this->_assembleWeakBCs<true>();
1581  this->_assembleWeakBCs<false>();
1582  this->_assembleWeakIfc<true>();
1583  this->_assembleWeakIfc<false>();
1584  this->_assembleNeumann();
1585 
1586  // Assemble the loads
1587  if ( m_pLoads.numLoads() != 0 )
1588  {
1589  m_rhs = m_assembler.rhs();
1590  _applyLoads();
1591  }
1593  }
1594  catch (...)
1595  {
1596  m_assembler.cleanUp();
1598  }
1599  return m_status;
1600 }
1601 
1602 template <short_t d, typename T, bool bending>
1603 template <short_t _d, bool _bending>
1604 typename std::enable_if<!(_d==3 && _bending), ThinShellAssemblerStatus>::type
1606 {
1607  this->_getOptions();
1608 
1609  m_assembler.cleanUp();
1610  GISMO_ENSURE(m_options.hasGroup("ExprAssembler"),"The option list does not contain options with the label 'ExprAssembler'!");
1611  m_assembler.setOptions(m_options.getGroup("ExprAssembler"));
1612 
1613  // Linear assembly: deformed and undeformed geometries are the same
1614  gsMultiPatch<T> & defpatches = m_patches;
1615  geometryMap m_ori = m_assembler.getMap(m_patches);
1616  geometryMap m_def = m_assembler.getMap(defpatches);
1617 
1618  // Initialize stystem
1619  m_assembler.initSystem();
1620 
1621  gsMaterialMatrixIntegrate<T,MaterialOutput::MatrixA> m_mmA(m_materialMatrices,&m_patches,&defpatches);
1622  auto mmA = m_assembler.getCoeff(m_mmA);
1623 
1624  space m_space = m_assembler.trialSpace(0);
1625  auto m_force = m_assembler.getCoeff(*m_forceFun, m_ori);
1626 
1627  auto jacG = jac(m_def);
1628  auto m_Em_der = flat( jacG.tr() * jac(m_space) ) ; //[checked]
1629  auto m_N_der = m_Em_der * reshape(mmA,3,3);
1630 
1631  try
1632  {
1633  if (m_foundInd)
1634  {
1635  this->_assembleFoundation<true>(*m_foundFun);
1636  this->_assembleFoundation<false>(*m_foundFun);
1637  }
1638  if (m_pressInd)
1639  {
1640  this->_assemblePressure<true>(*m_pressFun);
1641  this->_assemblePressure<false>(*m_pressFun);
1642  }
1643 
1644  m_assembler.assemble(
1645  (
1646  m_N_der * m_Em_der.tr()
1647  ) * meas(m_ori)
1648  ,
1649  m_space * m_force * meas(m_ori)
1650  );
1651 
1652  this->_assembleWeakBCs<true>();
1653  this->_assembleWeakBCs<false>();
1654  this->_assembleWeakIfc<true>();
1655  this->_assembleWeakIfc<false>();
1656  this->_assembleNeumann();
1657 
1658  // Assemble the loads
1659  if ( m_pLoads.numLoads() != 0 )
1660  {
1661  m_rhs = m_assembler.rhs();
1662  _applyLoads();
1663  }
1664 
1666  }
1667  catch (...)
1668  {
1669  m_assembler.cleanUp();
1671  }
1672  return m_status;
1673 }
1674 
1675 template<short_t d, class T, bool bending>
1677 {
1678  return assembleMatrix_impl<d, bending>(deformed);
1679 }
1680 
1681 template <short_t d, typename T, bool bending>
1682 template <short_t _d, bool _bending>
1683 typename std::enable_if<(_d==3) && _bending, ThinShellAssemblerStatus>::type
1685 {
1686  m_assembler.cleanUp();
1687  GISMO_ENSURE(m_options.hasGroup("ExprAssembler"),"The option list does not contain options with the label 'ExprAssembler'!");
1688  m_assembler.setOptions(m_options.getGroup("ExprAssembler"));
1689 
1690  geometryMap m_ori = m_assembler.getMap(m_patches);
1691  geometryMap m_def = m_assembler.getMap(deformed);
1692 
1693  // Initialize matrix
1694  m_assembler.initSystem();
1695  m_assembler.initMatrix();
1696 
1697  gsMaterialMatrixIntegrate<T,MaterialOutput::MatrixA> m_mmA(m_materialMatrices,&m_patches,&deformed);
1698  gsMaterialMatrixIntegrate<T,MaterialOutput::MatrixB> m_mmB(m_materialMatrices,&m_patches,&deformed);
1699  gsMaterialMatrixIntegrate<T,MaterialOutput::MatrixC> m_mmC(m_materialMatrices,&m_patches,&deformed);
1700  gsMaterialMatrixIntegrate<T,MaterialOutput::MatrixD> m_mmD(m_materialMatrices,&m_patches,&deformed);
1701  gsMaterialMatrixIntegrate<T,MaterialOutput::VectorN> m_S0(m_materialMatrices,&m_patches,&deformed);
1702  gsMaterialMatrixIntegrate<T,MaterialOutput::VectorM> m_S1(m_materialMatrices,&m_patches,&deformed);
1703  auto mmA = m_assembler.getCoeff(m_mmA);
1704  auto mmB = m_assembler.getCoeff(m_mmB);
1705  auto mmC = m_assembler.getCoeff(m_mmC);
1706  auto mmD = m_assembler.getCoeff(m_mmD);
1707  auto S0 = m_assembler.getCoeff(m_S0);
1708  auto S1 = m_assembler.getCoeff(m_S1);
1709 
1710  gsFunctionExpr<T> mult2t("1","0","0","0","1","0","0","0","2",2);
1711  auto m_m2 = m_assembler.getCoeff(mult2t);
1712 
1713  space m_space = m_assembler.trialSpace(0);
1714 
1715  this->homogenizeDirichlet();
1716 
1717  gsVector<T> pt(2);
1718  pt.setConstant(0.25);
1719  gsExprEvaluator<T> ev(m_assembler);
1720 
1721  auto m_N = S0.tr();
1722  auto m_Em_der = flat( jac(m_def).tr() * jac(m_space) ) ; //[checked]
1723  auto m_Em_der2 = flatdot( jac(m_space),jac(m_space).tr(), m_N ); //[checked]
1724 
1725 
1726  auto m_M = S1.tr(); // output is a column
1727  auto m_Ef_der = -( deriv2(m_space,sn(m_def).normalized().tr() ) + deriv2(m_def,var1(m_space,m_def) ) ) * reshape(m_m2,3,3); //[checked]
1728  auto m_Ef_der2 = -(flatdot2( deriv2(m_space), var1(m_space,m_def).tr(), m_M ).symmetrize()
1729  + var2deriv2(m_space,m_space,m_def, m_M ));
1730 
1731  auto m_N_der = m_Em_der * reshape(mmA,3,3) + m_Ef_der * reshape(mmB,3,3);
1732  auto m_M_der = m_Em_der * reshape(mmC,3,3) + m_Ef_der * reshape(mmD,3,3);
1733 
1734  try
1735  {
1736  if (m_foundInd) this->_assembleFoundation<true>(*m_foundFun,deformed);
1737  if (m_pressInd) this->_assemblePressure<true>(*m_pressFun,deformed);
1738 
1739  // Assemble matrix
1740  m_assembler.assemble(
1741  (
1742  m_N_der * m_Em_der.tr()
1743  +
1744  m_Em_der2
1745  +
1746  m_M_der * m_Ef_der.tr()
1747  +
1748  m_Ef_der2
1749  ) * meas(m_ori)
1750  );
1751 
1752  this->_assembleWeakBCs<true>(deformed);
1753  this->_assembleWeakIfc<true>(deformed);
1754 
1756  }
1757  catch (...)
1758  {
1759  m_assembler.cleanUp();
1761  }
1762  return m_status;
1763 }
1764 
1765 template <short_t d, typename T, bool bending>
1766 template <short_t _d, bool _bending>
1767 typename std::enable_if<!(_d==3 && _bending), ThinShellAssemblerStatus>::type
1769 {
1770  m_assembler.cleanUp();
1771  GISMO_ENSURE(m_options.hasGroup("ExprAssembler"),"The option list does not contain options with the label 'ExprAssembler'!");
1772  m_assembler.setOptions(m_options.getGroup("ExprAssembler"));
1773 
1774  geometryMap m_ori = m_assembler.getMap(m_patches);
1775  geometryMap m_def = m_assembler.getMap(deformed);
1776 
1777  // Initialize matrix
1778  m_assembler.initSystem();
1779  m_assembler.initMatrix();
1780 
1781  gsMaterialMatrixIntegrate<T,MaterialOutput::MatrixA> m_mmA(m_materialMatrices,&m_patches,&deformed);
1782  gsMaterialMatrixIntegrate<T,MaterialOutput::VectorN> m_S0(m_materialMatrices,&m_patches,&deformed);
1783  auto mmA = m_assembler.getCoeff(m_mmA);
1784  auto S0 = m_assembler.getCoeff(m_S0);
1785 
1786  space m_space = m_assembler.trialSpace(0);
1787 
1788 
1789  this->homogenizeDirichlet();
1790 
1791  auto m_N = S0.tr();
1792  auto m_Em_der = flat( jac(m_def).tr() * jac(m_space) ) ; //[checked]
1793  auto m_Em_der2 = flatdot( jac(m_space),jac(m_space).tr(), m_N ); //[checked]
1794 
1795  auto m_N_der = m_Em_der * reshape(mmA,3,3);
1796 
1797  // Assemble matrix
1798  try
1799  {
1800  if (m_foundInd) this->_assembleFoundation<true>(*m_foundFun,deformed);
1801  if (m_pressInd) this->_assemblePressure<true>(*m_pressFun,deformed);
1802 
1803  m_assembler.assemble(
1804  (
1805  m_N_der * m_Em_der.tr()
1806  +
1807  m_Em_der2
1808  ) * meas(m_ori)
1809  );
1810  this->_assembleWeakBCs<true>(deformed);
1811  this->_assembleWeakIfc<true>(deformed);
1812 
1814  }
1815  catch (...) // add specific cases?
1816  {
1817  m_assembler.cleanUp();
1819  }
1820  return m_status;
1821 }
1822 
1823 template<short_t d, class T, bool bending>
1825 {
1826  gsMultiPatch<T> def;
1827  constructSolution(solVector, def);
1828  return assembleMatrix(def);
1829 }
1830 
1831 template<short_t d, class T, bool bending>
1833 {
1834  return assembleMatrix_impl<d, bending>(deformed, previous, update);
1835 }
1836 
1837 template <short_t d, typename T, bool bending>
1838 template <short_t _d, bool _bending>
1839 typename std::enable_if<(_d==3) && _bending, ThinShellAssemblerStatus>::type
1841 {
1842  m_assembler.cleanUp();
1843  GISMO_ENSURE(m_options.hasGroup("ExprAssembler"),"The option list does not contain options with the label 'ExprAssembler'!");
1844  m_assembler.setOptions(m_options.getGroup("ExprAssembler"));
1845 
1846  geometryMap m_ori = m_assembler.getMap(m_patches);
1847  geometryMap m_def = m_assembler.getMap(deformed);
1848  geometryMap m_prev = m_assembler.getMap(previous);
1849  // Initialize matrix
1850  m_assembler.initSystem();
1851  m_assembler.initMatrix();
1852 
1853  gsMaterialMatrixIntegrate<T,MaterialOutput::MatrixA> m_mmA(m_materialMatrices,&m_patches,&deformed);
1854  gsMaterialMatrixIntegrate<T,MaterialOutput::MatrixB> m_mmB(m_materialMatrices,&m_patches,&deformed);
1855  gsMaterialMatrixIntegrate<T,MaterialOutput::MatrixC> m_mmC(m_materialMatrices,&m_patches,&deformed);
1856  gsMaterialMatrixIntegrate<T,MaterialOutput::MatrixD> m_mmD(m_materialMatrices,&m_patches,&deformed);
1857  gsMaterialMatrixIntegrate<T,MaterialOutput::VectorN> m_S0(m_materialMatrices,&m_patches,&deformed);
1858  gsMaterialMatrixIntegrate<T,MaterialOutput::VectorM> m_S1(m_materialMatrices,&m_patches,&deformed);
1859  auto mmA = m_assembler.getCoeff(m_mmA);
1860  auto mmB = m_assembler.getCoeff(m_mmB);
1861  auto mmC = m_assembler.getCoeff(m_mmC);
1862  auto mmD = m_assembler.getCoeff(m_mmD);
1863  // auto S0 = m_assembler.getCoeff(m_S0);
1864  // auto S1 = m_assembler.getCoeff(m_S1);
1865 
1866  gsMaterialMatrixIntegrate<T,MaterialOutput::MatrixA> m_mmAd(m_materialMatrices,&m_patches,&previous);
1867  gsMaterialMatrixIntegrate<T,MaterialOutput::MatrixB> m_mmBd(m_materialMatrices,&m_patches,&previous);
1868  gsMaterialMatrixIntegrate<T,MaterialOutput::MatrixC> m_mmCd(m_materialMatrices,&m_patches,&previous);
1869  gsMaterialMatrixIntegrate<T,MaterialOutput::MatrixD> m_mmDd(m_materialMatrices,&m_patches,&previous);
1870  gsMaterialMatrixIntegrate<T,MaterialOutput::VectorN> m_S0d(m_materialMatrices,&m_patches,&previous);
1871  gsMaterialMatrixIntegrate<T,MaterialOutput::VectorM> m_S1d(m_materialMatrices,&m_patches,&previous);
1872  auto mmAp = m_assembler.getCoeff(m_mmAd);
1873  auto mmBp = m_assembler.getCoeff(m_mmBd);
1874  auto mmCp = m_assembler.getCoeff(m_mmCd);
1875  auto mmDp = m_assembler.getCoeff(m_mmDd);
1876  auto S0 = m_assembler.getCoeff(m_S0d);
1877  auto S1 = m_assembler.getCoeff(m_S1d);
1878 
1879  gsFunctionExpr<> mult2t("1","0","0","0","1","0","0","0","2",2);
1880  auto m_m2 = m_assembler.getCoeff(mult2t);
1881 
1882  space m_space = m_assembler.trialSpace(0);
1883  solution m_du = m_assembler.getSolution(m_space,update);
1884 
1885  this->homogenizeDirichlet();
1886 
1887  auto m_E_mc = flat( jac(m_prev).tr() * grad(m_du) ) ; //[checked]
1888  auto m_E_fc = -( deriv2(m_du,sn(m_prev).normalized().tr() ) + deriv2(m_prev,var1(m_du,m_prev) ) ) * reshape(m_m2,3,3); //[checked]
1889  auto m_N_c = m_E_mc * reshape(mmAp,3,3) + m_E_fc * reshape(mmBp,3,3);
1890  auto m_M_c = m_E_mc * reshape(mmCp,3,3) + m_E_fc * reshape(mmDp,3,3);
1891 
1892  auto m_N = S0.tr() + m_N_c;
1893  auto m_Em_der = flat( jac(m_def).tr() * jac(m_space) ) ; //[checked]
1894  auto m_Em_der2 = flatdot( jac(m_space),jac(m_space).tr(), m_N ); //[checked]
1895 
1896  auto m_M = S1.tr() + m_M_c; // output is a column
1897  auto m_Ef_der = -( deriv2(m_space,sn(m_def).normalized().tr() ) + deriv2(m_def,var1(m_space,m_def) ) ) * reshape(m_m2,3,3); //[checked]
1898  auto m_Ef_der2 = -(flatdot2( deriv2(m_space), var1(m_space,m_def).tr(), m_M ).symmetrize()
1899  + var2deriv2(m_space,m_space,m_def, m_M ));
1900 
1901  auto m_N_der = m_Em_der * reshape(mmA,3,3) + m_Ef_der * reshape(mmB,3,3);
1902  auto m_M_der = m_Em_der * reshape(mmC,3,3) + m_Ef_der * reshape(mmD,3,3);
1903 
1904  try
1905  {
1906  if (m_foundInd) this->_assembleFoundation<true>(*m_foundFun,deformed);
1907  if (m_pressInd) this->_assemblePressure<true>(*m_pressFun,deformed);
1908 
1909  // Assemble matrix
1910  m_assembler.assemble(
1911  (
1912  m_N_der * m_Em_der.tr()
1913  +
1914  m_Em_der2
1915  +
1916  m_M_der * m_Ef_der.tr()
1917  +
1918  m_Ef_der2
1919  ) * meas(m_ori)
1920  );
1921  this->_assembleWeakBCs<true>(deformed);
1922  this->_assembleWeakIfc<true>(deformed);
1923 
1925  }
1926  catch (...)
1927  {
1928  m_assembler.cleanUp();
1930  }
1931  return m_status;
1932 }
1933 
1934 // template <short_t d, typename T, bool bending>
1935 // template <short_t _d, bool _bending>
1936 // typename std::enable_if<!(_d==3 && _bending), ThinShellAssemblerStatus>::type
1937 // gsThinShellAssembler<d, T, bending>::assembleMatrix_impl(const gsMultiPatch<T> & deformed, const gsMultiPatch<T> & previous, gsMatrix<T> & update)
1938 // {
1939 // GISMO_NO_IMPLEMENTATION;
1940 // }
1941 
1942 template<short_t d, class T, bool bending>
1944 {
1945  // gsMultiPatch<T> deformed;
1946  // constructSolution(solVector, deformed);
1947  // assembleMatrix(deformed);
1948 
1949  gsMultiPatch<T> def, it;
1950  constructSolution(solVector, def);
1951  constructSolution(prevVector, it);
1952  gsMatrix<T> update = solVector - prevVector;
1953  return assembleMatrix(def,it,update);
1954 }
1955 
1956 template<short_t d, class T, bool bending>
1958 {
1959  return assembleVector_impl<d, bending>(deformed,homogenize);
1960 }
1961 
1962 template <short_t d, typename T, bool bending>
1963 template <short_t _d, bool _bending>
1964 typename std::enable_if<(_d==3) && _bending, ThinShellAssemblerStatus>::type
1966 {
1967  m_assembler.cleanUp();
1968  GISMO_ENSURE(m_options.hasGroup("ExprAssembler"),"The option list does not contain options with the label 'ExprAssembler'!");
1969  m_assembler.setOptions(m_options.getGroup("ExprAssembler"));
1970 
1971  geometryMap m_ori = m_assembler.getMap(m_patches);
1972  geometryMap m_def = m_assembler.getMap(deformed);
1973 
1974  // Initialize vector
1975  m_assembler.initVector(1);
1976 
1977  gsMaterialMatrixIntegrate<T,MaterialOutput::VectorN> m_S0(m_materialMatrices,&m_patches,&deformed);
1978  gsMaterialMatrixIntegrate<T,MaterialOutput::VectorM> m_S1(m_materialMatrices,&m_patches,&deformed);
1979  auto S0 = m_assembler.getCoeff(m_S0);
1980  auto S1 = m_assembler.getCoeff(m_S1);
1981 
1982  gsFunctionExpr<> mult2t("1","0","0","0","1","0","0","0","2",2);
1983  auto m_m2 = m_assembler.getCoeff(mult2t);
1984 
1985  space m_space = m_assembler.trialSpace(0);
1986  auto m_force = m_assembler.getCoeff(*m_forceFun, m_ori);
1987 
1988 
1989  if (homogenize) this->homogenizeDirichlet();
1990  else this->_assembleDirichlet();
1991 
1992  auto m_N = S0.tr();
1993  auto m_Em_der = flat( jac(m_def).tr() * jac(m_space) ) ;
1994 
1995  auto m_M = S1.tr(); // output is a column
1996  auto m_Ef_der = -( deriv2(m_space,sn(m_def).normalized().tr() ) + deriv2(m_def,var1(m_space,m_def) ) ) * reshape(m_m2,3,3); //[checked]
1997 
1998  try
1999  {
2000  if (m_foundInd) this->_assembleFoundation<false>(*m_foundFun,deformed);
2001  if (m_pressInd) this->_assemblePressure<false>(*m_pressFun,deformed);
2002 
2003  // Assemble vector
2004  m_assembler.assemble(m_space * m_force * meas(m_ori) -
2005  ( ( m_N * m_Em_der.tr() + m_M * m_Ef_der.tr() ) * meas(m_ori) ).tr()
2006  );
2007 
2008  this->_assembleWeakBCs<false>(deformed);
2009  this->_assembleWeakIfc<false>(deformed);
2010  this->_assembleNeumann();
2011 
2012  // Assemble the loads
2013  if ( m_pLoads.numLoads() != 0 )
2014  {
2015  m_rhs = m_assembler.rhs();
2016  _applyLoads();
2017  }
2018 
2020  }
2021  catch (...)
2022  {
2023  m_assembler.cleanUp();
2025  }
2026  return m_status;
2027 }
2028 
2029 template <short_t d, typename T, bool bending>
2030 template <short_t _d, bool _bending>
2031 typename std::enable_if<!(_d==3 && _bending), ThinShellAssemblerStatus>::type
2033 {
2034  m_assembler.cleanUp();
2035  GISMO_ENSURE(m_options.hasGroup("ExprAssembler"),"The option list does not contain options with the label 'ExprAssembler'!");
2036  m_assembler.setOptions(m_options.getGroup("ExprAssembler"));
2037 
2038  geometryMap m_ori = m_assembler.getMap(m_patches);
2039  geometryMap m_def = m_assembler.getMap(deformed);
2040 
2041  // Initialize vector
2042  m_assembler.initVector(1);
2043 
2044  gsMaterialMatrixIntegrate<T,MaterialOutput::VectorN> m_S0(m_materialMatrices,&m_patches,&deformed);
2045  auto S0 = m_assembler.getCoeff(m_S0);
2046 
2047  space m_space = m_assembler.trialSpace(0);
2048  auto m_force = m_assembler.getCoeff(*m_forceFun, m_ori);
2049 
2050  if (homogenize) this->homogenizeDirichlet();
2051  else this->_assembleDirichlet();
2052 
2053  auto m_N = S0.tr();
2054  auto m_Em_der = flat( jac(m_def).tr() * jac(m_space) ) ;
2055 
2056  try
2057  {
2058  if (m_foundInd) this->_assembleFoundation<false>(*m_foundFun,deformed);
2059  if (m_pressInd) this->_assemblePressure<false>(*m_pressFun,deformed);
2060 
2061  // Assemble vector
2062  m_assembler.assemble(m_space * m_force * meas(m_ori) -
2063  ( ( m_N * m_Em_der.tr() ) * meas(m_ori) ).tr()
2064  );
2065 
2066  this->_assembleWeakBCs<false>(deformed);
2067  this->_assembleWeakIfc<false>(deformed);
2068  this->_assembleNeumann();
2069 
2070  // Assemble the loads
2071  if ( m_pLoads.numLoads() != 0 )
2072  {
2073  m_rhs = m_assembler.rhs();
2074  _applyLoads();
2075  }
2076 
2078  }
2079  catch (...)
2080  {
2081  m_assembler.cleanUp();
2083  }
2084  return m_status;
2085 }
2086 
2087 template<short_t d, class T, bool bending>
2089 {
2090  try
2091  {
2092  this->_assemblePressure<true>(pressFun);
2094  }
2095  catch (...)
2096  {
2098  }
2099  return m_status;
2100 }
2101 
2102 template<short_t d, class T, bool bending>
2104 {
2105  gsConstantFunction<T> pressFun(pressure,d);
2106  try
2107  {
2108  this->_assemblePressure<true>(pressFun);
2110  }
2111  catch (...)
2112  {
2114  }
2115  return m_status;
2116 }
2117 
2118 template<short_t d, class T, bool bending>
2120 {
2121  try
2122  {
2123  this->_assemblePressure<true>(pressFun,deformed);
2125  }
2126  catch (...)
2127  {
2129  }
2130  return m_status;
2131 }
2132 
2133 template<short_t d, class T, bool bending>
2135 {
2136  gsConstantFunction<T> pressFun(pressure,d);
2137  try
2138  {
2139  this->_assemblePressure<true>(pressFun, deformed);
2141  }
2142  catch (...)
2143  {
2145  }
2146  return m_status;
2147 }
2148 
2149 template<short_t d, class T, bool bending>
2151 {
2152  try
2153  {
2154  this->_assemblePressure<false>(pressFun);
2156  }
2157  catch (...)
2158  {
2160  }
2161  return m_status;
2162 }
2163 
2164 template<short_t d, class T, bool bending>
2166 {
2167  gsConstantFunction<T> pressFun(pressure,d);
2168  try
2169  {
2170  this->_assemblePressure<false>(pressFun);
2172  }
2173  catch (...)
2174  {
2176  }
2177  return m_status;
2178 }
2179 
2180 template<short_t d, class T, bool bending>
2182 {
2183  try
2184  {
2185  this->_assemblePressure<false>(pressFun,deformed);
2187  }
2188  catch (...)
2189  {
2191  }
2192  return m_status;
2193 }
2194 
2195 template<short_t d, class T, bool bending>
2197 {
2198  gsConstantFunction<T> pressFun(pressure,d);
2199  try
2200  {
2201  this->_assemblePressure<false>(pressFun, deformed);
2203  }
2204  catch (...)
2205  {
2207  }
2208  return m_status;
2209 }
2210 
2211 template<short_t d, class T, bool bending>
2213 {
2214  try
2215  {
2216  this->assemblePressureVector(*m_pressFun,deformed);
2218  }
2219  catch (...)
2220  {
2222  }
2223  return m_status;
2224 }
2225 
2226 template<short_t d, class T, bool bending>
2228 {
2229  try
2230  {
2231  this->assembleFoundationVector(*m_foundFun,deformed);
2233  }
2234  catch (...)
2235  {
2237  }
2238  return m_status;
2239 }
2240 
2241 template<short_t d, class T, bool bending>
2243 {
2244  try
2245  {
2246  this->_assembleFoundation<false>(foundFun,deformed);
2248  }
2249  catch (...)
2250  {
2252  }
2253  return m_status;
2254 }
2255 
2256 template<short_t d, class T, bool bending>
2257 gsMatrix<T> gsThinShellAssembler<d, T, bending>::boundaryForce(const gsFunctionSet<T> & deformed, const std::vector<patchSide> & patchSides) const
2258 {
2259  return boundaryForce_impl<d, bending>(deformed,patchSides);
2260 }
2261 
2262 template <short_t d, typename T, bool bending>
2263 template <short_t _d, bool _bending>
2264 typename std::enable_if<(_d==3) && _bending, gsMatrix<T> >::type
2265 gsThinShellAssembler<d, T, bending>::boundaryForce_impl(const gsFunctionSet<T> & deformed, const std::vector<patchSide> & patchSides) const
2266 {
2267  gsExprAssembler<T> assembler;
2268  assembler.setIntegrationElements(m_basis);
2269  space u = assembler.getSpace(*m_spaceBasis, d, 0); // last argument is the space ID
2270 
2272  u.setup(bc, dirichlet::l2Projection, m_continuity);
2273 
2274  gsVector<T> F(d);
2275  F.setZero();
2276  if (const gsMultiBasis<T> * mbasis = dynamic_cast<const gsMultiBasis<T>*>(&u.source()))
2277  {
2278  // Collect indices of the functions on the selected boundaries
2279  std::vector<std::unordered_set<index_t>> indices(d);
2281  for (std::vector<patchSide>::const_iterator bdr = patchSides.begin(); bdr != patchSides.end(); bdr++)
2282  {
2283  boundary = mbasis->basis(bdr->patch).boundary(bdr->side());
2284  for (index_t k=0; k!=boundary.rows(); k++)
2285  for (index_t c=0; c!=d; c++)
2286  indices[c].insert(u.mapper().index(boundary.at(k),bdr->patch,c));
2287  }
2288 
2289  assembler.initSystem();
2290 
2291  geometryMap m_ori = assembler.getMap(m_patches);
2292  geometryMap m_def = assembler.getMap(deformed);
2293 
2294  // Initialize vector
2295  // m_assembler.initVector(1);
2296 
2297  gsMaterialMatrixIntegrate<T,MaterialOutput::VectorN> m_S0(m_materialMatrices,&m_patches,&deformed);
2298  gsMaterialMatrixIntegrate<T,MaterialOutput::VectorM> m_S1(m_materialMatrices,&m_patches,&deformed);
2299  auto S0 = assembler.getCoeff(m_S0);
2300  auto S1 = assembler.getCoeff(m_S1);
2301 
2302  gsFunctionExpr<> mult2t("1","0","0","0","1","0","0","0","2",2);
2303  auto m_m2 = assembler.getCoeff(mult2t);
2304 
2305  // this->homogenizeDirichlet();
2306 
2307  auto m_N = S0.tr();
2308  auto m_Em_der = flat( jac(m_def).tr() * jac(u) ) ;
2309 
2310  auto m_M = S1.tr(); // output is a column
2311  auto m_Ef_der = -( deriv2(u,sn(m_def).normalized().tr() ) + deriv2(m_def,var1(u,m_def) ) ) * reshape(m_m2,3,3); //[checked]
2312 
2313  // Assemble vector (slow?)
2314  try
2315  {
2316  assembler.assemble(
2317  - ( ( m_N * m_Em_der.tr() + m_M * m_Ef_der.tr() ) * meas(m_ori) ).tr()
2318  );
2319  }
2320  catch (...)
2321  {
2322  GISMO_ERROR("Assembly of the force vector failed.");
2323  }
2324 
2325  // Grab and sum control point forces on boundary indices
2326  for (index_t c = 0; c != d; c++)
2327  for (std::unordered_set<index_t>::const_iterator it = indices[c].begin(); it!=indices[c].end(); it++)
2328  F[c] += assembler.rhs().at(*it);
2329  }
2330  else
2331  GISMO_ERROR("The basis is not a gsMultiBasis!");
2332 
2333  return F;
2334 }
2335 
2336 template <short_t d, typename T, bool bending>
2337 template <short_t _d, bool _bending>
2338 typename std::enable_if<!(_d==3 && _bending), gsMatrix<T> >::type
2339 gsThinShellAssembler<d, T, bending>::boundaryForce_impl(const gsFunctionSet<T> & deformed, const std::vector<patchSide> & patchSides) const
2340 {
2341  gsExprAssembler<T> assembler;
2342  assembler.setIntegrationElements(m_basis);
2343  space u = assembler.getSpace(*m_spaceBasis, d, 0); // last argument is the space ID
2344 
2346  u.setup(bc, dirichlet::l2Projection, m_continuity);
2347 
2348  gsVector<T> F(d);
2349  F.setZero();
2350  if (const gsMultiBasis<T> * mbasis = dynamic_cast<const gsMultiBasis<T>*>(&u.source()))
2351  {
2352  // Collect indices of the functions on the selected boundaries
2353  std::vector<std::unordered_set<index_t>> indices(d);
2355  for (std::vector<patchSide>::const_iterator bdr = patchSides.begin(); bdr != patchSides.end(); bdr++)
2356  {
2357  boundary = mbasis->basis(bdr->patch).boundary(bdr->side());
2358  for (index_t k=0; k!=boundary.rows(); k++)
2359  for (index_t c=0; c!=d; c++)
2360  indices[c].insert(u.mapper().index(boundary.at(k),bdr->patch,c));
2361  }
2362 
2363  assembler.initSystem();
2364 
2365  geometryMap m_ori = assembler.getMap(m_patches);
2366  geometryMap m_def = assembler.getMap(deformed);
2367 
2368  // Initialize vector
2369  // m_assembler.initVector(1);
2370 
2371  gsMaterialMatrixIntegrate<T,MaterialOutput::VectorN> m_S0(m_materialMatrices,&m_patches,&deformed);
2372  auto S0 = assembler.getCoeff(m_S0);
2373 
2374  // this->homogenizeDirichlet();
2375 
2376  auto m_N = S0.tr();
2377  auto m_Em_der = flat( jac(m_def).tr() * jac(u) ) ;
2378 
2379  // Assemble vector (slow?)
2380  try
2381  {
2382  assembler.assemble(
2383  - ( ( m_N * m_Em_der.tr() ) * meas(m_ori) ).tr()
2384  );
2385  }
2386  catch (...)
2387  {
2388  GISMO_ERROR("Assembly of the force vector failed.");
2389  }
2390 
2391  // Grab and sum control point forces on boundary indices
2392  for (index_t c = 0; c != d; c++)
2393  for (std::unordered_set<index_t>::const_iterator it = indices[c].begin(); it!=indices[c].end(); it++)
2394  F[c] += assembler.rhs().at(*it);
2395  }
2396  else
2397  GISMO_ERROR("The basis is not a gsMultiBasis!");
2398 
2399  return F;
2400 }
2401 
2402 template<short_t d, class T, bool bending>
2404 {
2405  gsMultiPatch<T> def;
2406  constructSolution(solVector, def);
2407  return assembleVector(def,homogenize);
2408 }
2409 
2410 template<short_t d, class T, bool bending>
2412  const bool Matrix, const bool homogenize)
2413 {
2414  ThinShellAssemblerStatus status;
2415  if (Matrix)
2416  {
2417  status = assembleMatrix(deformed);
2419  return status;
2420  }
2421 
2422  return assembleVector(deformed,homogenize);
2423 }
2424 template<short_t d, class T, bool bending>
2426  const bool Matrix, const bool homogenize)
2427 {
2428  gsMultiPatch<T> def;
2429  constructSolution(solVector, def);
2430  return assemble(def,Matrix,homogenize);
2431 }
2432 
2433 template <short_t d, class T, bool bending>
2435 {
2436  gsMultiPatch<T> mp = m_patches;
2437  gsMultiPatch<T> displacement = constructDisplacement(solVector);
2438  for ( size_t k =0; k!=displacement.nPatches(); ++k) // Deform the geometry
2439  mp.patch(k).coefs() += displacement.patch(k).coefs();; // defG points to mp_def, therefore updated
2440 
2441  return mp;
2442 }
2443 
2444 template <short_t d, class T, bool bending>
2446 {
2447  return _constructSolution(solVector,m_patches);
2448 }
2449 
2450 template <short_t d, class T, bool bending>
2452 {
2453  deformed = _constructSolution(solVector,m_patches);
2454 }
2455 
2456 template <short_t d, class T, bool bending>
2458 {
2459  mp = _constructSolution(solVector,mp);
2460 }
2461 
2462 template<short_t d, class T, bool bending>
2464 {
2465  m_assembler.cleanUp();
2466  GISMO_ENSURE(m_options.hasGroup("ExprAssembler"),"The option list does not contain options with the label 'ExprAssembler'!");
2467  m_assembler.setOptions(m_options.getGroup("ExprAssembler"));
2468 
2469  geometryMap G = m_assembler.getMap(geometry);
2470 
2471  gsExprEvaluator<T> evaluator(m_assembler);
2472  T result = evaluator.integral(meas(G));
2473  return result;
2474 }
2475 
2476 template<short_t d, class T, bool bending>
2478 {
2479  m_assembler.cleanUp();
2480  GISMO_ENSURE(m_options.hasGroup("ExprAssembler"),"The option list does not contain options with the label 'ExprAssembler'!");
2481  m_assembler.setOptions(m_options.getGroup("ExprAssembler"));
2482 
2483  geometryMap m_ori = m_assembler.getMap(m_patches);
2484  geometryMap m_def = m_assembler.getMap(deformed);
2485 
2486  auto u = m_def - m_ori;
2487 
2488  gsExprEvaluator<T> evaluator(m_assembler);
2489  T result = evaluator.integral( u.tr() * u * meas(m_def));
2490  T area = evaluator.integral(meas(m_ori));
2491 
2492  return std::pow(result/area,0.5);
2493 }
2494 
2495 template<short_t d, class T, bool bending>
2497 {
2498  m_assembler.cleanUp();
2499  GISMO_ENSURE(m_options.hasGroup("ExprAssembler"),"The option list does not contain options with the label 'ExprAssembler'!");
2500  m_assembler.setOptions(m_options.getGroup("ExprAssembler"));
2501 
2502  geometryMap m_ori = m_assembler.getMap(m_patches);
2503  geometryMap m_def = m_assembler.getMap(deformed);
2504 
2505  gsMaterialMatrixIntegrate<T,MaterialOutput::VectorN> m_S0(m_materialMatrices,&deformed);
2506  gsMaterialMatrixIntegrate<T,MaterialOutput::VectorM> m_S1(m_materialMatrices,&deformed);
2507  auto S0 = m_assembler.getCoeff(m_S0);
2508  auto S1 = m_assembler.getCoeff(m_S1);
2509  auto u = m_def - m_ori;
2510 
2511  auto m_N = S0.tr();
2512  auto m_M = S1.tr(); // output is a column
2513 
2514  gsExprEvaluator<T> evaluator(m_assembler);
2515  T result = evaluator.integral(0.5 * ( u.tr() * ( m_N + m_M ).tr() ) * meas(m_def));
2516  return result;
2517 }
2518 
2519 template<short_t d, class T, bool bending>
2520 void gsThinShellAssembler<d, T, bending>::plotSolution(std::string string, const gsMatrix<T> & solVector)
2521 {
2522  m_solvector = solVector;
2523  space m_space = m_assembler.trialSpace(0);
2524  solution m_solution = m_assembler.getSolution(m_space, m_solvector);
2525  geometryMap G = m_assembler.getMap(m_patches);
2526  gsExprEvaluator<T> ev(m_assembler);
2527  ev.options().setSwitch("plot.elements", false);
2528  ev.options().setInt ("plot.npts" , 500);
2529  ev.writeParaview( m_solution, G, string);
2530 }
2531 
2532 template<short_t d, class T, bool bending>
2533 T gsThinShellAssembler<d, T, bending>::interfaceErrorC0(const gsFunctionSet<T> & deformed, const ifContainer & iFaces)
2534 {
2535  geometryMap G = m_assembler.getMap(deformed);
2536  gsExprEvaluator<T> ev(m_assembler);
2537  ev.integralInterface( ( G.left() - G.right() ).sqNorm() , iFaces);
2538  ev.calcSqrt();
2539  return ev.value();
2540 }
2541 
2542 template<short_t d, class T, bool bending>
2543 T gsThinShellAssembler<d, T, bending>::interfaceErrorG1(const gsFunctionSet<T> & deformed, const ifContainer & iFaces)
2544 {
2545  geometryMap G = m_assembler.getMap(deformed);
2546  gsExprEvaluator<T> ev(m_assembler);
2547  ev.integralInterface( (sn(G.left()).normalized()-sn(G.right()).normalized()).sqNorm() , iFaces);
2548  ev.calcSqrt();
2549  return ev.value();
2550 }
2551 
2552 template<short_t d, class T, bool bending>
2553 T gsThinShellAssembler<d, T, bending>::interfaceErrorNormal(const gsFunctionSet<T> & deformed, const ifContainer & iFaces)
2554 {
2555  geometryMap G = m_assembler.getMap(deformed);
2556  gsExprEvaluator<T> ev(m_assembler);
2557  ev.maxInterface( (sn(G.left())-sn(G.right())).norm() , iFaces);
2558  return ev.value();
2559 }
2560 
2561 template<short_t d, class T, bool bending>
2562 T gsThinShellAssembler<d, T, bending>::interfaceErrorGaussCurvature(const gsFunctionSet<T> & deformed, const ifContainer & iFaces)
2563 {
2564  geometryMap G = m_assembler.getMap(deformed);
2565  gsExprEvaluator<T> ev(m_assembler);
2566  ev.maxInterface( abs( (fform(G.left() ).inv()*fform2nd(G.left() )).det() -
2567  (fform(G.right()).inv()*fform2nd(G.right())).det() ) , iFaces);
2568  return ev.value();
2569 }
2570 template<short_t d, class T, bool bending>
2571 T gsThinShellAssembler<d, T, bending>::interfaceErrorMeanCurvature(const gsFunctionSet<T> & deformed, const ifContainer & iFaces)
2572 {
2573  geometryMap G = m_assembler.getMap(deformed);
2574  gsExprEvaluator<T> ev(m_assembler);
2575  ev.maxInterface( abs( (fform(G.left() ).inv()*fform2nd(G.left() )).trace().val() -
2576  (fform(G.right()).inv()*fform2nd(G.right())).trace().val() ) , iFaces);
2577  return ev.value();
2578 }
2579 template<short_t d, class T, bool bending>
2581 {
2582  m_solvector = solVector;
2583  space m_space = m_assembler.trialSpace(0);
2584  m_space.setup(m_bcs, dirichlet::l2Projection, m_continuity);
2585  const_cast<expr::gsFeSpace<T> & >(m_space).fixedPart() = m_ddofs; //CHECK FIXEDPART
2586 
2587  if (const gsMappedBasis<2,T> * mbasis = dynamic_cast<const gsMappedBasis<2,T> * >(m_spaceBasis))
2588  {
2589  gsMatrix<T> tmp;
2590  const index_t dim = m_space.dim();
2591  GISMO_ASSERT(static_cast<size_t>(dim*mbasis->size())==m_mapper.mapSize(),"Something is wrong in the sizes, basis size = "<<mbasis->size()<<" mapper size = "<<m_mapper.mapSize());
2592 
2593  gsMatrix<T> cc(mbasis->size(),d);
2594  cc.setZero();
2595 
2596 
2597  for ( index_t p =0; p!=m_patches.nPieces(); ++p) // Deform the geometry
2598  {
2599  for (index_t c = 0; c!=dim; c++) // for all components
2600  {
2601  // loop over all basis functions (even the eliminated ones)
2602  for (size_t i = 0; i < m_mapper.patchSize(p,c); ++i)
2603  {
2604  const index_t ii = m_mapper.index(i, p, c);
2605  if ( m_mapper.is_free_index(ii) ) // DoF value is in the solVector
2606  cc(i,c) = m_solvector.at(ii);
2607  else // eliminated DoF: fill with Dirichlet data
2608  {
2609  cc(i,c) = m_ddofs.at( m_mapper.global_to_bindex(ii) );
2610  }
2611  }
2612 
2613  }
2614 
2615  }
2616  mbasis->global_coef_to_local_coef(cc,tmp);
2617  return mbasis->exportToPatches(tmp);
2618  }
2619  else
2620  {
2621  gsMultiPatch<T> result;
2622  // Solution vector and solution variable
2623  solution m_solution = m_assembler.getSolution(m_space, m_solvector);
2624 
2625  gsMatrix<T> cc;
2626  for ( index_t p =0; p!=m_patches.nPieces(); ++p) // Deform the geometry
2627  {
2628  m_solution.extract(cc, p);
2629  result.addPatch(m_basis.basis(p).makeGeometry( give(cc) )); // defG points to mp_def, therefore updated
2630  }
2631  return result;
2632  }
2633 }
2634 
2635 template<short_t d, class T, bool bending>
2637 {
2638  return constructMultiPatch(solVector);
2639 }
2640 
2641 template<short_t d, class T, bool bending>
2643 {
2644  gsMatrix<T> solVector = vector;
2645  space m_space = m_assembler.trialSpace(0);
2646  m_space.setup(m_bcs, dirichlet::l2Projection, m_continuity);
2647  solution m_solution = m_assembler.getSolution(m_space, solVector);
2648  gsMatrix<T> result;
2649  m_solution.extractFull(result);
2650  return result.col(0);
2651 }
2652 
2653 template<short_t d, class T, bool bending>
2655 {
2656  gsVector<T> result(m_mapper.freeSize());
2657 
2658  for (size_t p=0; p!=displacements.nPatches(); p++)
2659  {
2660  for (size_t dim = 0; dim!=d; dim++)
2661  {
2662  for (size_t k=0; k!=m_mapper.patchSize(p,dim); k++)
2663  {
2664  if (m_mapper.is_free(k,p,dim))
2665  {
2666  result.at(m_mapper.index(k,p,dim)) = displacements.patch(p).coefs()(k,dim);
2667  }
2668  }
2669  }
2670 
2671  }
2672  return result;
2673 }
2674 
2675 template<short_t d, class T, bool bending>
2677 {
2678  deformed = constructDisplacement(solVector);
2679 }
2680 
2681 // template<short_t d, class T, bool bending>
2682 // void gsThinShellAssembler<d, T, bending>::constructStresses(const gsMultiPatch<T> & deformed,
2683 // gsPiecewiseFunction<T> & result,
2684 // stress_type::type type) const
2685 // {
2686 // deformed = constructDisplacement(solVector);
2687 // }
2688 
2689 template<short_t d, class T, bool bending>
2691 {
2692  // gsDebug<<"Warning: Principle Stretch computation of gsThinShellAssembler is depreciated...\n";
2693  gsMatrix<T> Z(1,1);
2694  Z.setZero();
2695  gsMatrix<T> result(3,u.cols());
2696  result.setZero();
2697  gsMatrix<T> zmat(1,1);
2698  zmat<<z;
2699  this->_getOptions();
2700 
2701  m_assembler.cleanUp();
2702  GISMO_ENSURE(m_options.hasGroup("ExprAssembler"),"The option list does not contain options with the label 'ExprAssembler'!");
2703  m_assembler.setOptions(m_options.getGroup("ExprAssembler"));
2704 
2705  // geometryMap m_ori = m_assembler.getMap(m_patches);
2706  // geometryMap m_def = m_assembler.getMap(*m_defpatches);
2707  // m_assembler.initSystem();
2708 
2709  gsMaterialMatrixEval<T,MaterialOutput::Stretch> m_mm(m_materialMatrices,&deformed,zmat);
2710  auto mm0 = m_assembler.getCoeff(m_mm);
2711 
2712  gsExprEvaluator<T> evaluator(m_assembler);
2713 
2714  for (index_t k = 0; k != u.cols(); ++k)
2715  result.col(k) = evaluator.eval(mm0,u.col(k));
2716  return result;
2717 }
2718 
2719 template <short_t d, class T, bool bending>
2721 {
2722  // gsDebug<<"Warning: Principle Stretch computation of gsThinShellAssembler is depreciated...\n";
2723  gsMatrix<T> Z(1,1);
2724  Z.setZero();
2725  gsMatrix<T> result(2,u.cols());
2726  result.setZero();
2727  gsMatrix<T> zmat(1,1);
2728  zmat<<z;
2729  this->_getOptions();
2730 
2731  m_assembler.cleanUp();
2732  GISMO_ENSURE(m_options.hasGroup("ExprAssembler"),"The option list does not contain options with the label 'ExprAssembler'!");
2733  m_assembler.setOptions(m_options.getGroup("ExprAssembler"));
2734 
2735  // geometryMap m_ori = m_assembler.getMap(m_patches);
2736  // geometryMap m_def = m_assembler.getMap(*m_defpatches);
2737  // m_assembler.initSystem();
2738 
2739  gsMaterialMatrixEval<T,MaterialOutput::PStress> m_mm(m_materialMatrices,&deformed,zmat);
2740  auto mm0 = m_assembler.getCoeff(m_mm);
2741 
2742  gsExprEvaluator<T> evaluator(m_assembler);
2743 
2744  for (index_t k = 0; k != u.cols(); ++k)
2745  {
2746  result.col(k) = evaluator.eval(mm0,u.col(k));
2747  }
2748  return result;
2749 }
2750 
2751 template<short_t d, class T, bool bending>
2753  gsPiecewiseFunction<T> & result,
2754  stress_type::type type)
2755 {
2756  constructStress(m_patches,deformed,result,type);
2757 }
2758 
2759 template<short_t d, class T, bool bending>
2761  const gsFunctionSet<T> & original,
2762  const gsFunctionSet<T> & deformed,
2763  gsPiecewiseFunction<T> & result,
2764  stress_type::type type)
2765 {
2766  result.clear();
2767 
2768  for (size_t p = 0; p < m_patches.nPatches(); ++p )
2769  result.addPiecePointer(new gsShellStressFunction<T>(original,deformed,m_materialMatrices,p,type));
2770 
2771 }
2772 
2773 // template<short_t d, class T, bool bending>
2774 // gsField<T> gsThinShellAssembler<d, T, bending>::constructStress(const gsMultiPatch<T> & deformed,
2775 // stress_type::type type)
2776 // {
2777 // gsPiecewiseFunction<T> result;
2778 // result.clear();
2779 
2780 // for (size_t p = 0; p < m_patches.nPatches(); ++p )
2781 // result.addPiecePointer(new gsShellStressFunction<d, T, bending>(m_patches,deformed,m_materialMatrices,p,type,m_assembler));
2782 
2783 // gsField<T> stressField(m_patches,result, true);
2784 // return stressField;
2785 
2786 // }
2787 
2788 template<short_t d, class T, bool bending>
2790 {
2791  // /// todo: make a projection with BCs?
2792  // /// todo: test
2793  // // this->_getOptions();
2794 
2795  // m_assembler.cleanUp();
2796  // GISMO_ENSURE(m_options.hasGroup("ExprAssembler"),"The option list does not contain options with the label 'ExprAssembler'!");
2797  // m_assembler.setOptions(m_options.getGroup("ExprAssembler"));
2798 
2799  // geometryMap m_ori = m_assembler.getMap(m_patches);
2800 
2801  // // Initialize stystem
2802  // m_assembler.initSystem();
2803 
2804  // space m_space = m_assembler.trialSpace(0);
2805  // auto function = m_assembler.getCoeff(fun, m_ori);
2806  // // auto function = m_assembler.getCoeff(fun);
2807 
2808  // // assemble system
2809  // m_assembler.assemble(m_space*m_space.tr()*meas(m_ori),m_space * function*meas(m_ori));
2810 
2811  // gsSparseSolver<>::uPtr solver = gsSparseSolver<T>::get( m_options.askString("Solver","CGDiagonal") );
2812  // solver->compute(m_assembler.matrix());
2813  // result = solver->solve(m_assembler.rhs());
2814 }
2815 
2816 template<short_t d, class T, bool bending>
2818 {
2821  gsMatrix<T> tmp = projectL2(fun);
2822  mp = m_patches;
2823 
2824  // Solution vector and solution variable
2825  space m_space = m_assembler.trialSpace(0);
2826  m_space.setup(m_bcs, dirichlet::l2Projection, m_continuity);
2827  const_cast<expr::gsFeSpace<T> & >(m_space).fixedPart() = m_ddofs;
2828 
2829  solution m_solution = m_assembler.getSolution(m_space, tmp);
2830 
2831  gsMatrix<T> cc;
2832  for ( size_t k =0; k!=mp.nPatches(); ++k) // Deform the geometry
2833  {
2834  // // extract deformed geometry
2835  m_solution.extract(cc, k);
2836  mp.patch(k).coefs() += cc; // defG points to mp_def, therefore updated
2837  }
2838 }
2839 
2840 
2841 template<short_t d, class T, bool bending>
2843 {
2846  gsMatrix<T> result;
2847  this->projectL2_into(fun,result);
2848  return result;
2849 }
2850 
2851 template <short_t d, class T, bool bending>
2853 {
2854  m_assembler.cleanUp();
2855  m_assembler.setOptions(m_options);
2856 
2857  geometryMap ori = m_assembler.getMap(original);
2858  geometryMap def = m_assembler.getMap(deformed);
2859 
2860  gsExprEvaluator<T> evaluator(m_assembler);
2861  T result = evaluator.integral(def.sqNorm() * meas(ori));
2862  return result;
2863 }
2864 
2865 template<short_t d, class T, bool bending>
2867 {
2868  geometryMap m_ori = m_assembler.getMap(m_patches);
2869  gsExprEvaluator<T> ev(m_assembler);
2870 
2871  m_inPlane.clear();
2872  m_outPlane.clear();
2873 
2874  for (gsBoxTopology::const_iiterator it = m_patches.topology().iBegin(); it!=m_patches.topology().iEnd(); it++)
2875  {
2876  // G1 condition
2877  ev.integralInterface( (sn(m_ori.left()).normalized()-sn(m_ori.right()).normalized()).sqNorm() );
2878  ev.calcSqrt();
2879 
2880  // // Continuous normal condition
2881  // ev.maxInterface( (sn(m_ori.left())-sn(m_ori.right())).norm() );
2882  // ev.calcSqrt();
2883 
2884  if (ev.value() < tol)
2885  m_inPlane.push_back(*it);
2886  else
2887  m_outPlane.push_back(*it);
2888  }
2889 }
2890 
2891 template<short_t d, class T, bool bending>
2892 bool gsThinShellAssembler<d, T, bending>::_isInPlane(const boundaryInterface & ifc, const T tol)
2893 {
2894  geometryMap m_ori = m_assembler.getMap(m_patches);
2895  gsExprEvaluator<T> ev(m_assembler);
2896 
2897  // G1 condition
2898  ev.integralInterface( (sn(m_ori.left()).normalized()-sn(m_ori.right()).normalized()).sqNorm() );
2899  ev.calcSqrt();
2900 
2901  // // Continuous normal condition
2902  // ev.maxInterface( (sn(m_ori.left())-sn(m_ori.right())).norm() );
2903  // ev.calcSqrt();
2904 
2905  return (ev.value() < tol);
2906 }
2907 
2908 
2909 }// namespace gismo
Provides an evaluator for material matrices for thin shells.
index_t addPatch(typename gsGeometry< T >::uPtr g)
Add a patch from a gsGeometry&lt;T&gt;::uPtr.
Definition: gsMultiPatch.hpp:210
void constructStress(const gsFunctionSet< T > &deformed, gsPiecewiseFunction< T > &result, stress_type::type type)
See gsThinShellAssemblerBase for details.
Definition: gsThinShellAssembler.hpp:2752
Compute Cauchy stresses for a previously computed/defined displacement field. Can be pushed into gsPi...
Definition: gsThinShellFunctions.h:80
T integral(const expr::_expr< E > &expr)
Calculates the integral of the expression expr on the whole integration domain.
Definition: gsExprEvaluator.h:154
Definition: gsExprAssembler.h:30
std::enable_if<(_d==3)&&_bending, ThinShellAssemblerStatus >::type assembleVector_impl(const gsFunctionSet< T > &deformed, const bool homogenize)
Implementation of assembleVector for surfaces (3D)
Definition: gsThinShellAssembler.hpp:1965
ThinShellAssemblerStatus
Definition: gsThinShellAssembler.h:53
Provides declaration of FunctionExpr class.
T getArea(const gsFunctionSet< T > &geometry)
See gsThinShellAssemblerBase for details.
Definition: gsThinShellAssembler.hpp:2463
ThinShellAssemblerStatus assembleMatrix(const gsFunctionSet< T > &deformed)
See gsThinShellAssemblerBase for details.
Definition: gsThinShellAssembler.hpp:1676
void _initialize()
Initializes the method.
Definition: gsThinShellAssembler.hpp:226
gsMultiPatch< T > _constructSolution(const gsMatrix< T > &solVector, const gsMultiPatch< T > &undeformed) const
See gsThinShellAssemblerBase for details.
Definition: gsThinShellAssembler.hpp:2434
Struct that defines the boundary sides and corners and types of a geometric object.
Definition: gsBoundary.h:55
T interfaceErrorC0(const gsFunctionSet< T > &deformed)
See gsThinShellAssemblerBase for details.
Definition: gsThinShellAssembler.h:470
This class serves as the evaluator of material matrices, based on gsMaterialMatrixBase.
Definition: gsMaterialMatrixContainer.h:33
void setSwitch(const std::string &label, const bool &value)
Sets an existing option label to be equal to value.
Definition: gsOptionList.cpp:174
std::enable_if<(_d==3)&&_bending, ThinShellAssemblerStatus >::type assemble_impl()
Specialisation of assemble() for surfaces (3D)
Definition: gsThinShellAssembler.hpp:1517
T interfaceErrorNormal(const gsFunctionSet< T > &deformed)
See gsThinShellAssemblerBase for details.
Definition: gsThinShellAssembler.h:480
S give(S &x)
Definition: gsMemory.h:266
void assemble(const expr &...args)
Adds the expressions args to the system matrix/rhs The arguments are considered as integrals over the...
Definition: gsExprAssembler.h:756
Assembly failed due to an error in the expression (e.g. overflow)
#define index_t
Definition: gsConfig.h:32
#define GISMO_ENSURE(cond, message)
Definition: gsDebug.h:102
A function from a n-dimensional domain to an m-dimensional image.
Definition: gsFunction.h:59
std::enable_if<(_d==3)&&_bending, gsMatrix< T > >::type boundaryForce_impl(const gsFunctionSet< T > &deformed, const std::vector< patchSide > &patchSides) const
Implementation of the boundary force vector for surfaces (3D)
Definition: gsThinShellAssembler.hpp:2265
EIGEN_STRONG_INLINE fform2nd_expr< T > fform2nd(const gsGeometryMap< T > &G)
The second fundamental form of G.
Definition: gsExpressions.h:4523
Provides declaration of functions writing Paraview files.
gsMatrix< T > computePrincipalStresses(const gsMatrix< T > &points, const gsFunctionSet< T > &deformed, const T z=0)
See gsThinShellAssemblerBase for details.
Definition: gsThinShellAssembler.hpp:2720
ThinShellAssemblerStatus assembleMass(const bool lumped=false)
See gsThinShellAssemblerBase for details.
Definition: gsThinShellAssembler.hpp:1415
#define GISMO_ASSERT(cond, message)
Definition: gsDebug.h:89
This class defines the base class for material matrices.
Definition: gsMaterialMatrixBase.h:32
T interfaceErrorGaussCurvature(const gsFunctionSet< T > &deformed)
See gsThinShellAssemblerBase for details.
Definition: gsThinShellAssembler.h:485
gsVector< T > constructSolutionVector(const gsMultiPatch< T > &deformed) const
See gsThinShellAssemblerBase for details.
Definition: gsThinShellAssembler.hpp:2654
T getElasticEnergy(const gsFunctionSet< T > &deformed)
See gsThinShellAssemblerBase for details.
Definition: gsThinShellAssembler.hpp:2496
gsMultiPatch< T > constructMultiPatch(const gsMatrix< T > &solVector) const
Construct solution field from computed solution vector solVector and returns a multipatch.
Definition: gsThinShellAssembler.hpp:2580
ThinShellAssemblerStatus assemblePressureVector(const gsFunction< T > &pressFun)
See gsThinShellAssemblerBase for details.
Definition: gsThinShellAssembler.hpp:2150
void projectL2_into(const gsFunction< T > &fun, gsMatrix< T > &result)
See gsThinShellAssemblerBase for details.
Definition: gsThinShellAssembler.hpp:2789
const gsMatrix< T > & rhs() const
Returns the right-hand side vector(s)
Definition: gsExprAssembler.h:129
Provides an evaluator for material matrices for thin shells.
gsMatrix< T > boundaryForce(const gsFunctionSet< T > &deformed, const std::vector< patchSide > &patchSides) const
See gsThinShellAssemblerBase for details.
Definition: gsThinShellAssembler.hpp:2257
Provides declaration of gsWeightMapper class.
index_t index(index_t i, index_t k=0, index_t c=0) const
Returns the global dof index associated to local dof i of patch k.
Definition: gsDofMapper.h:325
T at(index_t i) const
Returns the i-th element of the vectorization of the matrix.
Definition: gsMatrix.h:211
A vector with arbitrary coefficient type and fixed or dynamic size.
Definition: gsVector.h:35
void setInt(const std::string &label, const index_t &value)
Sets an existing option label to be equal to value.
Definition: gsOptionList.cpp:158
ThinShellAssemblerStatus assembleFoundation()
See gsThinShellAssemblerBase for details.
Definition: gsThinShellAssembler.hpp:1473
Holds a set of patch-wise bases and their topology information.
Definition: gsMultiBasis.h:36
EIGEN_STRONG_INLINE onormal_expr< T > nv(const gsGeometryMap< T > &u)
The (outer pointing) boundary normal of a geometry map.
Definition: gsExpressions.h:4506
gsGeometry< T > & patch(size_t i) const
Return the i-th patch.
Definition: gsMultiPatch.h:226
T interfaceErrorG1(const gsFunctionSet< T > &deformed)
See gsThinShellAssemblerBase for details.
Definition: gsThinShellAssembler.h:475
size_t nPatches() const
Number of patches.
Definition: gsMultiPatch.h:208
ThinShellAssemblerStatus assembleVector(const gsFunctionSet< T > &deformed, const bool homogenize=true)
See gsThinShellAssemblerBase for details.
Definition: gsThinShellAssembler.hpp:1957
gsMultiPatch< T > constructDisplacement(const gsMatrix< T > &solVector) const
See gsThinShellAssemblerBase for details.
Definition: gsThinShellAssembler.hpp:2636
Assembles the system matrix and vectors for 2D and 3D shell problems, including geometric nonlinearit...
Definition: gsThinShellAssembler.h:76
T deformationNorm(const gsMultiPatch< T > &deformed, const gsMultiPatch< T > &original)
See gsThinShellAssemblerBase for details.
Definition: gsThinShellAssembler.hpp:2852
Definition: gsDirichletValues.h:23
Interface for the set of functions defined on a domain (the total number of functions in the set equa...
Definition: gsFuncData.h:23
T at(index_t i) const
Returns the i-th element of the vector.
Definition: gsVector.h:177
void eval(const expr::_expr< E > &expr, gsGridIterator< T, mode, d > &git, const index_t patchInd=0)
geometryMap getMap(const gsFunctionSet< T > &g)
Registers g as an isogeometric geometry map and return a handle to it.
Definition: gsExprAssembler.h:161
Provides declaration of a gsPiecewiseFunction class.
gsOptionList wrapIntoGroup(const std::string &gn) const
Creates a new gsOptionList where all labels are wrapped into a groupname gn.
Definition: gsOptionList.cpp:284
Container class for a set of geometry patches and their topology, that is, the interface connections ...
Definition: gsMultiPatch.h:33
Generic evaluator of isogeometric expressions.
Definition: gsExprEvaluator.h:38
space getSpace(const gsFunctionSet< T > &mp, index_t dim=1, index_t id=0)
Definition: gsExprAssembler.h:166
ThinShellAssemblerStatus assembleFoundationVector(const gsFunctionSet< T > &deformed)
See gsThinShellAssemblerBase for details.
Definition: gsThinShellAssembler.hpp:2227
Provides hyperelastic material matrices.
void update(const gsOptionList &other, updateType type=ignoreIfUnknown)
Updates the object using the data from other.
Definition: gsOptionList.cpp:253
type
Definition: gsThinShellFunctions.h:40
void clear()
Clear (delete) all functions.
Definition: gsPiecewiseFunction.h:148
void setOptions(gsOptionList &options)
See gsThinShellAssemblerBase for details.
Definition: gsThinShellAssembler.hpp:212
EIGEN_STRONG_INLINE reshape_expr< E > const reshape(E const &u, index_t n, index_t m)
Reshape an expression.
Definition: gsExpressions.h:1925
gsThinShellAssembler & operator=(const gsThinShellAssembler &other)
Assignment operator.
Definition: gsThinShellAssembler.hpp:84
ThinShellAssemblerStatus assemblePressureMatrix(const gsFunction< T > &pressFun)
See gsThinShellAssemblerBase for details.
Definition: gsThinShellAssembler.hpp:2088
EIGEN_STRONG_INLINE flat_expr< E > const flat(E const &u)
Make a matrix 2x2 expression &quot;flat&quot;.
Definition: gsExpressions.h:2031
Class containing a set of boundary conditions.
Definition: gsBoundaryConditions.h:341
Class defining a multivariate (real or vector) function given by a string mathematical expression...
Definition: gsFunctionExpr.h:51
EIGEN_STRONG_INLINE grad_expr< E > grad(const E &u)
The gradient of a variable.
Definition: gsExpressions.h:4490
Provides gsBoundaryConditions class.
gsMatrix< T > computePrincipalStretches(const gsMatrix< T > &points, const gsFunctionSet< T > &deformed, const T z=0)
See gsThinShellAssemblerBase for details.
Definition: gsThinShellAssembler.hpp:2690
T getDisplacementNorm(const gsFunctionSet< T > &deformed)
See gsThinShellAssemblerBase for details.
Definition: gsThinShellAssembler.hpp:2477
ThinShellAssemblerStatus assemble()
See gsThinShellAssemblerBase for details.
Definition: gsThinShellAssembler.hpp:1502
Provides a base class for material matrices.
#define GISMO_ERROR(message)
Definition: gsDebug.h:118
gsMatrix< T > projectL2(const gsFunction< T > &fun)
See gsThinShellAssemblerBase for details.
Definition: gsThinShellAssembler.hpp:2842
EIGEN_STRONG_INLINE meas_expr< T > meas(const gsGeometryMap< T > &G)
The measure of a geometry map.
Definition: gsExpressions.h:4555
EIGEN_STRONG_INLINE abs_expr< E > abs(const E &u)
Absolute value.
Definition: gsExpressions.h:4486
Class which holds a list of parameters/options, and provides easy access to them. ...
Definition: gsOptionList.h:32
T interfaceErrorMeanCurvature(const gsFunctionSet< T > &deformed)
See gsThinShellAssemblerBase for details.
Definition: gsThinShellAssembler.h:490
A function depending on an index i, typically referring to a patch/sub-domain. On each patch a differ...
Definition: gsPiecewiseFunction.h:28
void writeParaview(const expr::_expr< E > &expr, geometryMap G, std::string const &fn)
Creates a paraview file named fn containing valies of the.
Definition: gsExprEvaluator.h:323
gsThinShellAssembler()
Constructor for te shell assembler.
Definition: gsThinShellAssembler.h:129
gsMatrix< T > fullSolutionVector(const gsMatrix< T > &vector) const
See gsThinShellAssemblerBase for details.
Definition: gsThinShellAssembler.hpp:2642
void setIntegrationElements(const gsMultiBasis< T > &mesh)
Sets the domain of integration.
Definition: gsExprAssembler.h:136
gsMultiPatch< T > constructSolution(const gsMatrix< T > &solVector) const
Construct deformed shell geometry from computed solution vector solVector and returns a multipatch...
Definition: gsThinShellAssembler.hpp:2445
Provides linear and nonlinear assemblers for thin shells.
void initSystem(const index_t numRhs=1)
Initializes the sparse system (sparse matrix and rhs)
Definition: gsExprAssembler.h:290
variable getCoeff(const gsFunctionSet< T > &func)
Definition: gsExprAssembler.h:260
std::enable_if<(_d==3)&&_bending, ThinShellAssemblerStatus >::type assembleMatrix_impl(const gsFunctionSet< T > &deformed)
Implementation of assembleMatrix for surfaces (3D)
Definition: gsThinShellAssembler.hpp:1684
Class defining a globally constant function.
Definition: gsConstantFunction.h:33
EIGEN_STRONG_INLINE jac_expr< E > jac(const symbol_expr< E > &u)
The Jacobian matrix of a FE variable.
Definition: gsExpressions.h:4528
void plotSolution(std::string string, const gsMatrix< T > &solVector)
See gsThinShellAssemblerBase for details.
Definition: gsThinShellAssembler.hpp:2520
void homogenizeDirichlet()
See gsThinShellAssemblerBase for details.
Definition: gsThinShellAssembler.hpp:1293