FiberVISH 0.2
Fish - The Fiber Bundle API for the Vish Visualization Shell
FEM.hpp
1
2//
3// $Id: hpp,v 1.0 2000/01/01 00:00:01 werner Exp $
4//
5// $Log: hpp,v $
6// Created 2012/05/16 16:22:16 marcel
7// Initial version
8//
9//
11#ifndef __FIBER_GRID_TYPES_FEM_HPP
12#define __FIBER_GRID_TYPES_FEM_HPP
13
14#include "gridtypesDllApi.h"
15#include <grid/Grid.hpp>
16#include <eagle/PhysicalSpace.hpp>
17
18#include <aerie/KDTree.hpp>
19#include <aerie/GeometricFunctions.hpp>
20#include <aerie/BoundingBox.hpp>
21
22#include <field/OnDemandCreator.hpp>
23//#include "FEMFields.hpp"
24
25
26//#define VERBOSE
27
28namespace Fiber
29{
30
31typedef uint32_t FEMIndex_t;
32typedef std::vector<FEMIndex_t> FEMIndices_t;
33
34typedef std::vector<Eagle::PhysicalSpace::tvector> FEMDirections_t;
35
36typedef std::vector<std::vector<FEMIndex_t> > FEMFaceList_t;
37
38
39template<>
40inline std::string element_to_string(const FEMFaceList_t&EdgeList)
41{
42string retval = "{(" + std::to_string(EdgeList.size()) + ") ";
43
44 if (EdgeList.size()>0)
45 retval += "<>"; // std::to_string(EdgeList[0]);
46
47 for(size_t i = 1; i<EdgeList.size(); i++)
48 {
49 retval += ", <>"; // + std::to_string(EdgeList[i]);
50 }
51
52 return retval + " }";
53}
54
55template<>
56inline std::string element_to_string(const FEMDirections_t&FEM)
57{
58string retval = "{(" + std::to_string(FEM.size()) + ") ";
59
60 if (FEM.size()>0)
61 retval += "<>"; // std::to_string(EdgeList[0]);
62
63 for(size_t i = 1; i<FEM.size(); i++)
64 {
65 retval += ", <>"; // + std::to_string(EdgeList[i]);
66 }
67
68 return retval + " }";
69}
70
71
72
73enum {FEM_VERTS=0, FEM_CELLS};
74
75namespace FEMFunc
76{
77typedef Eagle::PhysicalSpace::point point_t;
78typedef Eagle::PhysicalSpace::tvector tvector_t;
79
80extern gridtypes_API
81point_t getLocalC3D8GaussCoords( size_t IPNr );
82extern gridtypes_API
83point_t getLocalC3D20GaussCoords( size_t IPNr );
84#ifdef NOT_IMPLEMENTED
85point_t getLocalC3D20RGaussCoords( unsigned IPNr );
86#endif
87
88extern gridtypes_API
89double getC3D8Weight( const point_t& local, size_t node);
90extern gridtypes_API
91double getC3D20Weight( const point_t& local, size_t node);
92
93extern gridtypes_API
94double getC3D8GaussWeight( size_t gauss_nr, size_t node_nr );
95extern gridtypes_API
96double getC3D20GaussWeight( size_t gauss_nr, size_t node_nr );
97extern gridtypes_API
98double getC3D20RGaussWeight( size_t gauss_nr, size_t node_nr );
99
100
101
102
103// maybe better use a const array instead modulos for the -1 1 0 shuffling
104// for vlen
105template<class T>
106T getInterpolatedC3D8( const point_t& local, const FEMIndices_t& coords_cell, const MultiArray<1, T>& data )
107{
108T ret;
109 for( unsigned i = 0; i < T::Dims; i++ )
110 ret[i] = 0;
111
112
113 for( unsigned j = 0; j < 8; j++ )
114 {
115 double weight = getC3D8Weight( local, j );
116
117 for( unsigned i = 0; i < T::Dims; i++ )
118 ret[i] += weight * T(data[ coords_cell[j] ])[i];
119 }
120 return ret;
121}
122
123
124
125//for fixed size
126template<class T>
127T getInterpolatedC3D8( const point_t& local, const MultiArray<2, FEMIndex_t>& coords_cell, index_t l, const MultiArray<1, T>& data )
128{
129T ret;
130 for( unsigned i = 0; i < T::Dims; i++ )
131 ret[i] = 0;
132
133MultiIndex<2> mi;
134
135 for( unsigned j = 0; j < 8; j++ )
136 {
137 mi = j, l;
138 double weight = getC3D8Weight( local, j );
139
140 for( unsigned i = 0; i < T::Dims; i++ )
141 ret[i] += weight * T(data[ coords_cell[mi] ])[i];
142 }
143 return ret;
144}
145
146// specialization for non compound types
147template<> gridtypes_API
148float getInterpolatedC3D8<float>( const point_t& local, const MultiArray<2, FEMIndex_t>& coords_cell, index_t l, const MultiArray<1, float>& data );
149
150template<> gridtypes_API
151double getInterpolatedC3D8<double>( const point_t& local, const MultiArray<2, FEMIndex_t>& coords_cell, index_t l, const MultiArray<1, double>& data );
152
153
154template<class T, int N>
155T getInterpolatedC3D8Dn( const point_t& local, const MultiArray<2, FEMIndex_t>& coords_cell, index_t cell, const MultiArray<1, T>& data )
156{
157T ret;
158 Verbose(0) << "getInterpolatedC3D8Dn() derivation in N=" << N << " not implemented!";
159 return ret;
160}
161
162template<> gridtypes_API
163point_t getInterpolatedC3D8Dn<point_t, 0>( const point_t& local, const MultiArray<2, FEMIndex_t>& coords_cell, index_t cell, const MultiArray<1, point_t>& data );
164
165template<> gridtypes_API
166point_t getInterpolatedC3D8Dn<point_t, 1>( const point_t& local, const MultiArray<2, FEMIndex_t>& coords_cell, index_t cell, const MultiArray<1, point_t>& data );
167
168template<> gridtypes_API
169point_t getInterpolatedC3D8Dn<point_t, 2>( const point_t& local, const MultiArray<2, FEMIndex_t>& coords_cell, index_t cell, const MultiArray<1, point_t>& data );
170
171
172// maybe better use a const array instead modulos for the -1 1 0 shuffling
173// for vlen
174template<class T>
175T getInterpolatedC3D20( const point_t& local, const FEMIndices_t& coords_cell, const MultiArray<1, T>& data )
176{
177T ret;
178 for( unsigned i = 0; i < T::Dims; i++ )
179 ret[i] = 0;
180
181double weight;
182 // corner nodes
183 for(size_t j = 0; j < 20; j++)
184 {
185 weight = getC3D20Weight( local, j );
186
187 for( unsigned i = 0; i < T::Dims; i++ )
188 ret[i] += weight * T(data[ coords_cell[j] ])[i];
189 }
190
191 return ret;
192}
193
194
195
196//for fixed size
197template<class T>
198T getInterpolatedC3D20( const point_t& local, const MultiArray<2, FEMIndex_t>& coords_cell, index_t l, const MultiArray<1, T>& data )
199{
200T ret;
201 for( unsigned i = 0; i < T::Dims; i++ )
202 ret[i] = 0;
203
204MultiIndex<2> mi;
205
206double weight;
207 // corner nodes
208 for(size_t j = 0; j < 20; j++)
209 {
210 mi = j, l;
211 weight = getC3D20Weight( local, j );
212
213 for( unsigned i = 0; i < T::Dims; i++ )
214 ret[i] += weight * T(data[ coords_cell[mi] ])[i];
215 }
216
217 return ret;
218}
219
220// specialization for non compound types
221template<>
222float getInterpolatedC3D20<float>( const point_t& local, const MultiArray<2, FEMIndex_t>& coords_cell, index_t l, const MultiArray<1, float>& data );
223
224template<>
225double getInterpolatedC3D20<double>( const point_t& local, const MultiArray<2, FEMIndex_t>& coords_cell, index_t l, const MultiArray<1, double>& data );
226
227}
228
229
230
231
232
233//namespace fem
234//{
235
236
237
239{
240 enum { UNKNOWN, MIXED, C3D8, C3D8R, C3D20, C3D20R, C3D4, C3D10, C3D6, C3D15, T3D2,
241 S2D4 } fe_type;
242
243FEMFaceList_t face_list;
244
245bool valid;
246
247// use 32bit for opengl
248RefPtr<Grid> v_grid;
249RefPtr<Grid> i_grid;
250
251RefPtr<Skeleton> v_vertices, v_cells;
252RefPtr<Skeleton> i_vertices, i_cells;
253
254RefPtr<Representation> v_cells_as_vertices, i_cells_as_vertices,
255 v_points, i_points, v_vertices_as_cells;
256
257//must have
258int cells_dim;
259
260RefPtr<Field> v_coords;
262
263RefPtr<MemArray<1, Eagle::PhysicalSpace::point> > v_coords_arr; // <-- really load data here?
264RefPtr<Field> v_cell_positions;
265RefPtr< MemArray<2, FEMIndex_t> > v_cell_arr; // <-- really load data here?
266
267//RefPtr<Field> v_displacement;
268RefPtr<Field> v_as_cell_positions;
269
270
271RefPtr<Field> i_cell_positions;
272//RefPtr<Field> i_distorsion;
273MultiIndex<1> i_size;
274//RefPtr<Field> i_tension;
275//RefPtr<MemArray<1, Eagle::metric33> > i_tension_arr;
276
277//optional (flags call of setup standard field (if null));
278RefPtr<Field> i_coords;
279
280public:
281
282RefPtr<Field> getVertexField( string field_name )
283{
284 if(!v_grid)
285 return NullPtr();
286
287 return (*v_grid)(field_name);
288}
289
290RefPtr<Field> getDisplacementField( )
291{
292RefPtr<Field> displacement = getVertexField( "U" );
293
294 if(!displacement)
295 {
297 v_points->iterate( displacement_finder );
298
299 displacement = displacement_finder.getBestField();
300 }
301
302 return displacement;
303}
304
305
306RefPtr<Field> getVertexCellField( string field_name )
307{
308 if(!v_cells_as_vertices)
309 return NullPtr();
310
311 return (*v_cells_as_vertices)(field_name);
312}
313
314
315RefPtr<Field> getIntegrationPointField( string field_name )
316{
317 if(!i_grid)
318 return NullPtr();
319
320 return (*i_grid)(field_name);
321}
322
323
324static SkeletonID cellID3D()
325{
326return SkeletonID(3,2);
327}
328
329static SkeletonID cellID2D()
330{
331return SkeletonID(2,2);
332}
333
334
335
336static double maxCellSize( RefPtr<MemArray<1, FEMIndices_t> >& cells );
337
338template<class PointType>
340
341RefPtr<MemArray<1, FEMIndices_t> > getIntPointCellPositions( const RefPtr<FragmentID>& f = NullPtr() )
342{
343 if(!i_cell_positions)
344 return NullPtr();
345 return i_cell_positions->getData( f );
346}
347
348RefPtr<MemArray<1, FEMIndices_t> > getVertexCellPositions( const RefPtr<FragmentID>& f = NullPtr() )
349{
350 if(!v_cell_positions)
351 return NullPtr();
352
353 return v_cell_positions->getData( f );
354}
355
356MultiIndex<1> getIntPointSize()
357{
358 return i_size;
359}
360
361MultiIndex<1> getVertexSize()
362{
363 if( !v_coords )
364 return 0;
365
366//Having no size interface does NOT mean there are no vertices!
367 if (RefPtr<SizeInterface> SI = getSize( v_coords->getCreator() ))
368 {
369 return SI->nElements();
370 }
371
372 return 0;
373}
374
375//@todo interface? not load cell array in constructor?
376MultiIndex<2> getVertexCellSize()
377{
378 if( !v_cell_arr )
379 return MultiIndex<2>(0,0);
380
381 return v_cell_arr->Size();
382}
383
384
385MultiIndex<2> getCellsSize()
386{
387 if( !v_cell_arr )
388 return MultiIndex<2>(0,0);
389
390 return v_cell_arr->Size();
391}
392// no fragment support here ... yet
394{
395 assert( v_coords_arr );
396 return v_coords_arr;
397}
398
400
401bool isValid()
402{
403 return valid;
404}
405
407 {
408 static const char
409 DISPLACEMENT[],
410 MEAN_STRESS[],
416 DEVIATORIC_RADIUS[],
420 STRESS_INVARIANT1[],
421
425 STRESS_INVARIANT2[],
426
430 STRESS_INVARIANT3[],
431 STRESS_MISES[],
432 DEVIATORIC_STRESS[],
433 STRESS[],
434 AVERAGED[],
435 VERT_AS_CELLS[],
436 POSTFIX_IP[],
437 POSTFIX_TRIANGULAR[];
438};
439
440 PredefinedFieldNames FieldNames;
441
442
443 FEM( const WeakPtr<Grid>&VG, const WeakPtr<Grid>&IG );
444
445 ~FEM();
446
448 {
449 MultiIndex<1> m_size;
450
452 bool apply (const FieldID &d, const Field &R);
453 };
454
456 {
457 RefPtr<Representation> m_i_points;
458 RefPtr<Field> m_i_tension;
459 RefPtr<Field> m_first;
460
462 bool apply (const FieldID &d, const Field &R);
463 RefPtr<Field> getBestField();
464 };
465
467 {
468 RefPtr<Representation> m_v_points;
469 RefPtr<Field> m_v_displacement;
470 RefPtr<Field> m_first;
471
473 bool apply (const FieldID &d, const Field &R);
474 RefPtr<Field> getBestField();
475 };
476
478 {
479 RefPtr<Grid> m_v_grid, m_i_grid;
480 RefPtr<Representation> m_i_points;
481 MultiIndex<1> m_size;
482
483 SetupDerivedFields( const RefPtr<Grid> v_grid, const RefPtr<Grid> i_grid, const RefPtr<Representation> i_points, MultiIndex<1> size );
484 bool apply (const FieldID &d, const Field &R);
485
486 template<class T>
487 void setFieldCreator( string source_field, string field_name );
488 };
489
491 {
492 RefPtr<Grid> m_v_grid, m_i_grid;
494 MultiIndex<2> m_size;
495
497 bool apply (const FieldID &d, const Field &R);
498
499 template<class T>
500 void setFieldCreator( string source_field, string field_name );
501 };
502
503
505 {
506 RefPtr<Grid> m_v_grid, m_i_grid;
507 RefPtr<Representation> m_v_points;
508 MultiIndex<1> m_size;
509
510 AverageToVertexFields( const RefPtr<Grid> v_grid, const RefPtr<Grid> i_grid, const RefPtr<Representation> v_points, MultiIndex<1> size );
511 bool apply (const FieldID &d, const Field &R);
512
513 template<class T>
514 void setFieldCreator( string source_field, string field_name );
515 };
516
517
518 RefPtr<Field> setUpStandardFields();
519
520 bool isC3D8() const;
521 bool isC3D8R() const;
522 bool isC3D20() const;
523 bool isC3D20R()const;
524 bool isMixed() const ;
525 bool isUnknown() const;
526 bool isC3D4() const;
527 bool isC3D10() const;
528 bool isC3D6() const;
529 bool isC3D15() const;
530 bool isT3D2() const;
531 bool isS2D4() const;
532 // ...
533
534 bool isHexa() const;
535 bool isTetra() const;
536 bool isWedge() const;
537 bool isBar() const;
538
539 RefPtr<Field> getVertexCells()
540 {
541 return v_cell_positions;
542 }
543
544
545 FEMFaceList_t& getFaceList()
546 {
547 return face_list;
548 }
549
550// static RefPtr<MemArray<1, Eagle::PhysicalSpace::point> > getLocalC3D8IPCoords();
551
552
553
554
555/*
556 RefPtr<MemArray<1, Eagle::PhysicalSpace::point> > getVertexCoords( const RefPtr<FragmentID>& f = NullPtr() )
557 {
558 if( !v_coords )
559 {
560 puts("FEm::getVertexCoords no vertex coords");
561 return NullPtr();
562 }
563 return v_coords->getData( f );
564 }
565
566 RefPtr<MemArray<1, FEMIndices_t> > getCellsAsVertices( const RefPtr<FragmentID>& f = NullPtr() )
567 {
568 if(!v_cell_positions)
569 {
570 puts("FEm::getCellsAsVertices no vertex cells");
571 return NullPtr();
572 }
573 return v_cell_positions->getData( f );
574 }
575
576
577 RefPtr<MemArray<1, FEMIndices_t> > getCellsAsIntPoints( const RefPtr<FragmentID>& f = NullPtr() )
578 {
579 if(!i_cell_positions)
580 {
581 puts("FEm::getCellsAsVertices no vertex cells");
582 return NullPtr();
583 }
584 return i_cell_positions->getData( f );
585 }
586*/
587
588void getCellCandidates( std::set<index_t>&res_candidates,
589 const Eagle::PhysicalSpace::tvector& range, const Eagle::PhysicalSpace::point& center )
590{
591 res_candidates.clear();
592
593//MultiArray< 2, FEMIndex_t >& cells = *v_cell_arr;
594//MultiArray<1, Eagle::point3>& crds = *v_coords_arr;
595
596 if( !v_coords_tree )
597 {
598 Verbose(0) << "FEM::getCellCandidates() no tree!";
599 exit(0);
600 }
601
602 if( ! v_as_cell_positions )
603 {
604 Verbose(0) << "FEM::getCellCandidates() vertices as cell array!";
605 exit(0);
606 }
607
608RefPtr<MemArray<1, FEMIndices_t> > v_as_cell_arr;
609 v_as_cell_arr = v_as_cell_positions->getData();
610
611 assert( v_as_cell_arr );
612
613MultiArray<1, FEMIndices_t>& v_cells = *v_as_cell_arr;
614
615std::multimap<double, index_t> result_vertices;
616
617 v_coords_tree->getManhattenRange( center, range, result_vertices );
618
619// assert( result_vertices.size() > 0 );
620
621#ifdef VERBOSE
622 std::cout << "found " << result_vertices.size() << " vertices via tree" << std::endl;
623#endif
624
625
626
628 for( res_it = result_vertices.begin(); res_it != result_vertices.end(); res_it++ )
629 {
630 FEMIndices_t::const_iterator cell_it;
631 for( cell_it = v_cells[res_it->second].begin() ; cell_it != v_cells[res_it->second].end(); cell_it++ )
632 res_candidates.insert( *cell_it );
633// break;
634 }
635
636#ifdef VERBOSE
638 std::cout << "cell canditates are: " ;
639 for( cand_it = res_candidates.begin(); cand_it != res_candidates.end(); cand_it++ )
640 std::cout << *cand_it << " ";
642#endif
643}
644
645void getCellCandidates( std::set<index_t>&res_candidates, const Eagle::BoundingBox&bb )
646{
647Eagle::PhysicalSpace::tvector range;
648
649 range = ( bb.maxcoord() - bb.mincoord() ) / 2;
650
651 getCellCandidates( res_candidates, range, bb.getCenter() );
652}
653
654
655
656// think about templatification
657// prototype does it projectively
658int getLocalCoordinate( Eagle::point3& local, FEMIndex_t& cell, const Eagle::point3& world )
659{
660//RefPtr< MemArray<2, FEMIndex_t> > cell_arr = v_cell_positions->getData();
661// assert(cell_arr);
662
663std::set<index_t> cell_candidates;
664
665Eagle::PhysicalSpace::tvector range;
666 range.x() = 2;
667 range.y() = 2;
668 range.z() = 2;
669
670
671 // todo: replacve by adjusted number
672
673 getCellCandidates(cell_candidates, range, world );
674
675MultiArray<1, Eagle::point3>& crds = *v_coords_arr;
676MultiArray< 2, FEMIndex_t >& cells = *v_cell_arr;
677
679 for( cand_it = cell_candidates.begin(); cand_it != cell_candidates.end(); cand_it++ )
680 {
681
682
683 // project in candidates
684 MultiIndex<2> max = v_cell_arr->Size();
685
686 if( max[0] == 8 || max[0] == 20)
687 cuboidToUnitCube( local, world,
688 crds[ cells[*cand_it][0] ],
689 crds[ cells[*cand_it][4] ],
690 crds[ cells[*cand_it][3] ],
691 crds[ cells[*cand_it][1] ],
692 crds[ cells[*cand_it][6] ] );
693
694#ifdef VERBOSE
695 std::cout << "getLocalCoordinate() checking cand: " << *cand_it << " : " << local << std::endl;
696#endif
697
698 if( local[0] >= 0.0 && local[1] >= 0.0 && local[2] >= 0.0 &&
699 local[0] <= 1.0 && local[1] <= 1.0 && local[2] <= 1.0 )
700 {
701#ifdef VERBOSE
702 std::cout << "point found in cell: " << *cand_it << std::endl;
703#endif
704 // compute local crds from 0..1 to -1..+1
705 local += Eagle::PhysicalSpace::tvector(local) - Eagle::PhysicalSpace::tvector(1.,1.,1.);
706 //local[0] *= -1;
707 //local[1] *= -1;
708 //local[2] *= -1;
709 cell = FEMIndex_t(*cand_it);
710
711#ifdef VERBOSE
712 std::cout << "getLocalCoordinate() EXIT 0" << std::endl;
713 std::cout.flush();
714#endif
715
716 return 0;
717 }
718 }
719
720
721#ifdef VERBOSE
722 std::cout << "getLocalCoordinate() EXIT 1 " << std::endl;
723 std::cout.flush();
724#endif
725 return 1;
726}
727
728//( Eagle::point3& local, FEMIndex_t& cell, const Eagle::point3& world )
729bool getLocalCoordinateNewton( Eagle::PhysicalSpace::point & local, const FEMIndex_t& cell,
730 const Eagle::PhysicalSpace::point&world, const double prec = 0.01, const unsigned max_iterations = 20 )
731{
732// Verbose(0) << "getLocalCoordinateNewton() cell: " << cell;
733// Verbose(0) << "getLocalCoordinateNewton() nodes size: " << v_coords_arr->Size();
734
735 if( cell > v_coords_arr->Size()[0] )
736 {
737 Verbose(0) << "getLocalCoordinateNewton() cell out of bounds!";
738 return 1;
739// exit(0);
740 }
741
743typedef Eagle::PhysicalSpace::tvector tvector;
744
745unsigned iterations = 0;
746point local_iterative, world_iterative;
747tvector dPdU, dPdV, dPdW;
748tvector delta_world;
749
750Eagle::Quadratic<3, double> sys, sys_inv;
751Eagle::Column<3, double> d_local, b;
752
753// guess in mid of cell
754 local_iterative = { 0.0, 0.0, 0.0 };
755
756 world_iterative = FEMFunc::getInterpolatedC3D8<point>( local_iterative, *v_cell_arr, cell, *v_coords_arr );
757
758 // do newton iteration until a certain precision
759 while( norm2(world - world_iterative) > prec*prec )
760 {
761 Verbose(0) << "iteration: " << iterations;
762
763 dPdU = tvector( FEMFunc::getInterpolatedC3D8Dn<point, 0> ( local_iterative, *v_cell_arr, cell, *v_coords_arr ) );
764 dPdV = tvector( FEMFunc::getInterpolatedC3D8Dn<point, 1> ( local_iterative, *v_cell_arr, cell, *v_coords_arr ) );
765 dPdW = tvector( FEMFunc::getInterpolatedC3D8Dn<point, 2> ( local_iterative, *v_cell_arr, cell, *v_coords_arr ) );
766
767 Verbose(60) << "dPdU: " << dPdU;
768 Verbose(60) << "dPdV: " << dPdV;
769 Verbose(60) << "dPdW: " << dPdW;
770
771// solve system for (dU, dV, dW):
772 // the 3x3 system:
773 // dPdU[0]*dU + dPdV[0]*dV + dPdW[0]*dW = delta_world[0]
774 // dPdU[1]*dU + dPdV[1]*dV + dPdW[1]*dW = delta_world[1]
775 // dPdU[2]*dU + dPdV[2]*dV + dPdW[2]*dW = delta_world[2]
776
777 sys = dPdU[0], dPdU[1], dPdU[2],
778 dPdV[0], dPdV[1], dPdV[2],
779 dPdW[0], dPdW[1], dPdW[2];
780
781 delta_world = world - world_iterative;
782
783 Verbose(0) << "delta world: " << delta_world;
784
785 try
786 {
787 ComputeInverse(sys_inv, sys);
788 }
789 catch(const Eagle::DegeneratedMatrix&)
790 {
791 Verbose(0) << "getLocalCoordinateNewton() Degenerated matrix error in inversion!";
792 assert(0);
793 }
794
795 Eagle::Matrix<3,3, double> &sysm_inv = sys_inv ;
796 Eagle::Matrix<3,3, double> &sysm = sys;
797
798 b = delta_world;
799 d_local = sysm_inv * b;
800
801 tvector d_world = tvector::DomainVector_t(sysm * d_local);
802
803 local_iterative[0] += d_local[0];
804 local_iterative[1] += d_local[1];
805 local_iterative[2] += d_local[2];
806
807 world_iterative += d_world;
808
809 Verbose(51) << "getLocalCoordinateNewton() in loop[" << iterations << "]: local=" << local_iterative;
810
811 Verbose(0) <<"world: " << world;
812 Verbose(0) <<"world_iterative: " << world_iterative;
813 Verbose(0) <<"residuum: " << norm2(world - world_iterative);
814// local = local_iterative;
815
816
817 if( iterations++ > max_iterations )
818 {
819 Verbose(0) << "getLocalCoordinateNewton prevented endless loop";
820 return 1;
821 }
822 }
823
824 local = local_iterative;
825
826
827 for( unsigned i = 0; i < 3; i++ )
828 {
829 if( local_iterative[i] < -1 )
830 {
831 Verbose(0) << "getLocalCoordinateNewton local out of -bounds: " << local_iterative;
832// local_iterative[i] = -0.99;
833 return 1;
834 }
835 if( local_iterative[i] > 1. )
836 {
837 Verbose(0) << "getLocalCoordinateNewton local out of +bounds: " << local_iterative;
838// local_iterative[i] = 0.99;
839 return 1;
840
841 }
842 }
843
844 Verbose(0) << "getLocalCoordinateNewton found local: " << local;
845
846 return 0;
847}
848
849
850template<class T>
851std::pair<bool, T> getInterpolatedVertexField( const Eagle::PhysicalSpace::point& world_pos, const Field& vertex_data_field )
852{
853#ifdef VERBOSE
854 std::cout << "getInterpolatedVertexField() ENTER" << std::endl;
855#endif
857FEMIndex_t cell_nr = 0;
858
859//int check = getLocalCoordinate( local_pos, cell_nr, world_pos );
860// Verbose(0) << "getInterpolatedVertexField() local projective: " << local_pos;
861
862int check = 1;
863
864// get candidates:
865std::set<index_t> cell_candidates;
866Eagle::PhysicalSpace::tvector range;
867 range.x() = 3;
868 range.y() = 3;
869 range.z() = 3;
870
871 getCellCandidates(cell_candidates, range, world_pos );
872
873unsigned count = 0;
876
878 for( cand_it = cell_candidates.begin(); cand_it != cell_candidates.end(); cand_it++ )
879 {
880 check = getLocalCoordinateNewton( local_pos, *cand_it, world_pos );
881 Verbose(0) << "getInterpolatedVertexField() local newtonr: " << local_pos;
882
883 double greatest_value = std::max( std::max( local_pos[0], local_pos[1] ), local_pos[2]);
884 closest[ greatest_value ] = *cand_it;
885 local[*cand_it] = local_pos;
886
887 if( check == 0)
888 break;
889 }
890
891 if( check != 0 )
892 {
893 Verbose(0) << "getInterpolatedVertexField()::getLocalCoordinate() returned 1!";
894
895 if( closest.size() == 0 )
896 return std::pair<bool, T>(false, T());
897
898 cell_nr = closest.begin()->second;
899 local_pos = local[cell_nr];
900
901 for( unsigned i = 0; i < 3; i++ )
902 {
903 if( local_pos[i] < -1 )
904 local_pos[i] = -0.99;
905 if( local_pos[i] > 1. )
906 local_pos[i] = 0.99;
907 }
908
909 RefPtr< MemArray<1, T> > data_arr;
910
911#ifdef USE_OPENMP
912#pragma omp critical
913{
914#endif
915// std::cout << "creating averaged field" << std::endl;
916// exit(0);
917 data_arr = vertex_data_field.getData();
918 assert(data_arr);
919#ifdef USE_OPENMP
920}
921#endif
922
923Verbose(0) << "-------------------------------------------------------------------------------- cell_nr: " << cell_nr;
924Verbose(0) << "-------------------------------------------------------------------------------- local_pos: " << local_pos;
925
926 return std::pair<bool, T>(true, FEMFunc::getInterpolatedC3D8<T>(local_pos, *v_cell_arr, cell_nr, *data_arr ));
927 }
928// assert(check == 0);
929
930#ifdef VERBOSE
931 std::cout << "getInterpolatedVertexField()[" << check << "] world: " << world_pos << "-->" << local_pos << std::endl;
932#endif
933
934//RefPtr< MemArray<2, FEMIndex_t> > cell_arr = v_cell_positions->getData();
935// assert(v_cell_arr);
936//#ifdef USE_OPENMP
937
938//#endif
939 RefPtr< MemArray<1, T> > data_arr;
940#ifdef USE_OPENMP
941#pragma omp critical
942{
943#endif
944// std::cout << "creating averaged field" << std::endl;
945// exit(0);
946 data_arr = vertex_data_field.getData();
947 assert(data_arr);
948#ifdef USE_OPENMP
949}
950#endif
951
952return std::pair<bool, T>(true, FEMFunc::getInterpolatedC3D8<T>( local_pos, *v_cell_arr, cell_nr, *data_arr ));
953
954
955}
956
957};
958
959
960
961//}
962
963}
964
965
966#endif
_Tp max() const
valarray< size_t > size() const
_Expr< _ValFunClos< _ValArray, _Tp >, _Tp > apply(_Tp __func(_Tp)) const
constexpr const _Tp & max(const _Tp &__a, const _Tp &__b)
basic_string< char > string
basic_ostream< _CharT, _Traits > & endl(basic_ostream< _CharT, _Traits > &__os)
ostream cout
const_iterator end() const noexcept
size_type size() const noexcept
const_iterator begin() const noexcept
size_type size() const noexcept
const_iterator begin() const noexcept
iterator end() const noexcept
void insert(_InputIterator __first, _InputIterator __last)
void clear() noexcept
iterator begin() const noexcept
const point_t & getCenter() const
const point_t & mincoord() const
const point_t & maxcoord() const
An iterator with an optional DataCreator, which is just a class to intercept creation of data along a...
Definition CreativeIterator.hpp:34
Definition FEM.hpp:239
Identifier for Fields within a Grid.
Definition FieldID.hpp:53
Class for iterating over fields, in particular those contained in a Representation object.
Definition FieldID.hpp:134
A Field is a collection of CreativeArrayBase reference pointers which are accessed via FragmentID obj...
Definition Field.hpp:245
index_t count() const
Return the number of steps which can be traversed through this ElementIterator.
Definition HyperslabParameters.hpp:147
Identifier for Skeletons within a Grid.
Definition SkeletonID.hpp:24
double norm2(const PhysicalSpace::bivector &v)
Given a fragmented field of curvilinear coordinates, (3D array of coordinates), build a uniform Grid ...
Definition FAQ.dox:2
std::nullptr_t NullPtr
string to_string(const Eagle::FixedArray< ElementType, N > &A, const char *OpenBrace="{", const char *CloseBrace="}", const char *Separator=",")
Definition FEM.hpp:505
Definition FEM.hpp:448
Definition FEM.hpp:407
Definition FEM.hpp:478