dune-grid  2.4.1
vtkwriter.hh
Go to the documentation of this file.
1 // -*- tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 2 -*-
2 // vi: set et ts=4 sw=2 sts=2:
3 
4 #ifndef DUNE_VTKWRITER_HH
5 #define DUNE_VTKWRITER_HH
6 
7 #include <cstring>
8 #include <iostream>
9 #include <string>
10 #include <fstream>
11 #include <sstream>
12 #include <iomanip>
13 
14 #include <vector>
15 #include <list>
16 
17 #include <dune/common/deprecated.hh>
18 #include <dune/common/typetraits.hh>
19 #include <dune/common/exceptions.hh>
20 #include <dune/common/std/memory.hh>
21 #include <dune/common/indent.hh>
22 #include <dune/common/iteratorfacades.hh>
23 #include <dune/common/path.hh>
24 #include <dune/common/shared_ptr.hh>
25 #include <dune/geometry/referenceelements.hh>
34 
48 namespace Dune
49 {
50 
51  namespace detail {
52 
53  template<typename F, typename = int>
55  : public std::false_type
56  {};
57 
58  template<typename T>
59  struct _has_local_context<T,typename std::enable_if<(sizeof(static_cast<T*>(nullptr)->localContext()) > 0),int>::type>
60  : public std::true_type
61  {};
62 
63  }
64 
65  namespace VTKWriteTypeTraits {
66  template<typename T>
68  {
69  };
70  }
71 
72  // Forward-declaration here, so the class can be friend of VTKWriter
73  template <class GridView>
75  template <class GridView>
76  class VTKSequenceWriter;
77 
86  template< class GridView >
87  class VTKWriter {
88 
89  // VTKSequenceWriterBase needs getSerialPieceName
90  // and getParallelHeaderName
92  // VTKSequenceWriter needs the grid view, to get the MPI size and rank
93  friend class VTKSequenceWriter<GridView>;
94 
95  // extract types
96  typedef typename GridView::Grid Grid;
97  typedef typename GridView::ctype DT;
98  enum { n = GridView::dimension };
99  enum { w = GridView::dimensionworld };
100 
101  typedef typename GridView::template Codim< 0 >::Entity Cell;
102  typedef typename GridView::template Codim< n >::Entity Vertex;
103  typedef Cell Entity;
104 
105  typedef typename GridView::IndexSet IndexSet;
106 
107  static const PartitionIteratorType VTK_Partition = InteriorBorder_Partition;
108  //static const PartitionIteratorType VTK_Partition = All_Partition;
109 
110  typedef typename GridView::template Codim< 0 >
111  ::template Partition< VTK_Partition >::Iterator
112  GridCellIterator;
113  typedef typename GridView::template Codim< n >
114  ::template Partition< VTK_Partition >::Iterator
115  GridVertexIterator;
116 
117  typedef typename GridCellIterator::Reference EntityReference;
118 
119  typedef typename GridView::template Codim< 0 >
120  ::Entity::Geometry::LocalCoordinate Coordinate;
121 
122  typedef MultipleCodimMultipleGeomTypeMapper< GridView, MCMGVertexLayout > VertexMapper;
123 
124  // return true if entity should be skipped in Vertex and Corner iterator
125  static bool skipEntity( const PartitionType entityType )
126  {
127  switch( VTK_Partition )
128  {
129  // for All_Partition no entity has to be skipped
130  case All_Partition: return false;
131  case InteriorBorder_Partition: return ( entityType != InteriorEntity );
132  default: DUNE_THROW(NotImplemented,"Add check for this partition type");
133  }
134  return false ;
135  }
136 
137  public:
138 
140  typedef shared_ptr< const VTKFunction > VTKFunctionPtr;
141 
142  protected:
143 
145 
149  {
150 
151  public:
152 
154 
157  {
158 
160  virtual void bind(const Entity& e) = 0;
161 
163  virtual void unbind() = 0;
164 
166 
169  virtual void write(const Coordinate& pos, Writer& w, std::size_t count) const = 0;
170 
172  {}
173 
174  };
175 
177  template<typename F>
179  : public FunctionWrapperBase
180  {
181  typedef typename std::decay<F>::type Function;
182 
183  template<typename F_>
185  : _f(std::forward<F_>(f))
186  {}
187 
188  virtual void bind(const Entity& e)
189  {
190  _f.bind(e);
191  }
192 
193  virtual void unbind()
194  {
195  _f.unbind();
196  }
197 
198  virtual void write(const Coordinate& pos, Writer& w, std::size_t count) const
199  {
200  auto r = _f(pos);
201  // we need to do different things here depending on whether r supports indexing into it or not.
202  do_write(w,r,count,is_indexable<decltype(r)>());
203  }
204 
205  private:
206 
207  template<typename R>
208  void do_write(Writer& w, const R& r, std::size_t count, std::true_type) const
209  {
210  for (std::size_t i = 0; i < count; ++i)
211  w.write(r[i]);
212  }
213 
214  template<typename R>
215  void do_write(Writer& w, const R& r, std::size_t count, std::false_type) const
216  {
217  assert(count == 1);
218  w.write(r);
219  }
220 
221  Function _f;
222  };
223 
226  : public FunctionWrapperBase
227  {
229  : _f(f)
230  , _entity(nullptr)
231  {}
232 
233  virtual void bind(const Entity& e)
234  {
235  _entity = &e;
236  }
237 
238  virtual void unbind()
239  {
240  _entity = nullptr;
241  }
242 
243  virtual void write(const Coordinate& pos, Writer& w, std::size_t count) const
244  {
245  for (std::size_t i = 0; i < count; ++i)
246  w.write(_f->evaluate(i,*_entity,pos));
247  }
248 
249  private:
250 
251  VTKFunctionPtr _f;
252  const Entity* _entity;
253 
254  };
255 
257  template<typename F>
259  typename std::enable_if<detail::_has_local_context<F>::value,int>::type dummy = 0)
260  : _f(Dune::Std::make_unique<FunctionWrapper<F> >(std::forward<F>(f)))
261  , _fieldInfo(fieldInfo)
262  {}
263 
265  template<typename F>
267  typename std::enable_if<not detail::_has_local_context<F>::value,int>::type dummy = 0)
268  : _f(Dune::Std::make_unique< FunctionWrapper<
269  typename std::decay<decltype(localFunction(std::forward<F>(f)))>::type
270  > >(localFunction(std::forward<F>(f))))
271  , _fieldInfo(fieldInfo)
272  {}
273 
275  explicit VTKLocalFunction (const VTKFunctionPtr& vtkFunctionPtr)
276  : _f(Dune::Std::make_unique<VTKFunctionWrapper>(vtkFunctionPtr))
277  , _fieldInfo(
278  vtkFunctionPtr->name(),
279  vtkFunctionPtr->ncomps() > 1 ? VTK::FieldInfo::Type::vector : VTK::FieldInfo::Type::scalar,
280  vtkFunctionPtr->ncomps()
281  )
282  {}
283 
285  std::string name() const
286  {
287  return fieldInfo().name();
288  }
289 
291  const VTK::FieldInfo& fieldInfo() const
292  {
293  return _fieldInfo;
294  }
295 
297  void bind(const Entity& e) const
298  {
299  _f->bind(e);
300  }
301 
303  void unbind() const
304  {
305  _f->unbind();
306  }
307 
309  void write(const Coordinate& pos, Writer& w) const
310  {
311  _f->write(pos,w,fieldInfo().size());
312  }
313 
314  std::shared_ptr<FunctionWrapperBase> _f;
316 
317  };
318 
319  typedef typename std::list<VTKLocalFunction>::const_iterator FunctionIterator;
320 
322 
327  class CellIterator : public GridCellIterator
328  {
329  public:
331  CellIterator(const GridCellIterator & x) : GridCellIterator(x) {}
334  const FieldVector<DT,n> position() const
335  {
336  return ReferenceElements<DT,n>::general((*this)->type()).position(0,0);
337  }
338  };
339 
341  {
342  return gridView_.template begin< 0, VTK_Partition >();
343  }
344 
346  {
347  return gridView_.template end< 0, VTK_Partition >();
348  }
349 
351 
366  public ForwardIteratorFacade<VertexIterator, const Entity, EntityReference, int>
367  {
368  GridCellIterator git;
369  GridCellIterator gend;
370  VTK::DataMode datamode;
371  // Index of the currently visited corner within the current element.
372  // NOTE: this is in Dune-numbering, in contrast to CornerIterator.
373  int cornerIndexDune;
374  const VertexMapper & vertexmapper;
375  std::vector<bool> visited;
376  // in conforming mode, for each vertex id (as obtained by vertexmapper)
377  // hold its number in the iteration order (VertexIterator)
378  int offset;
379 
380  // hide operator ->
381  void operator->();
382  protected:
384  {
385  if( git == gend )
386  return;
387  ++cornerIndexDune;
388  const int numCorners = git->subEntities(n);
389  if( cornerIndexDune == numCorners )
390  {
391  offset += numCorners;
392  cornerIndexDune = 0;
393 
394  ++git;
395  while( (git != gend) && skipEntity( git->partitionType() ) )
396  ++git;
397  }
398  }
399  public:
400  VertexIterator(const GridCellIterator & x,
401  const GridCellIterator & end,
402  const VTK::DataMode & dm,
403  const VertexMapper & vm) :
404  git(x), gend(end), datamode(dm), cornerIndexDune(0),
405  vertexmapper(vm), visited(vm.size(), false),
406  offset(0)
407  {
408  if (datamode == VTK::conforming && git != gend)
409  visited[vertexmapper.subIndex(*git,cornerIndexDune,n)] = true;
410  }
411  void increment ()
412  {
413  switch (datamode)
414  {
415  case VTK::conforming :
416  while(visited[vertexmapper.subIndex(*git,cornerIndexDune,n)])
417  {
418  basicIncrement();
419  if (git == gend) return;
420  }
421  visited[vertexmapper.subIndex(*git,cornerIndexDune,n)] = true;
422  break;
423  case VTK::nonconforming :
424  basicIncrement();
425  break;
426  }
427  }
428  bool equals (const VertexIterator & cit) const
429  {
430  return git == cit.git
431  && cornerIndexDune == cit.cornerIndexDune
432  && datamode == cit.datamode;
433  }
434  EntityReference dereference() const
435  {
436  return *git;
437  }
439  int localindex () const
440  {
441  return cornerIndexDune;
442  }
444  const FieldVector<DT,n> & position () const
445  {
446  return ReferenceElements<DT,n>::general(git->type())
447  .position(cornerIndexDune,n);
448  }
449  };
450 
452  {
453  return VertexIterator( gridView_.template begin< 0, VTK_Partition >(),
454  gridView_.template end< 0, VTK_Partition >(),
455  datamode, *vertexmapper );
456  }
457 
459  {
460  return VertexIterator( gridView_.template end< 0, VTK_Partition >(),
461  gridView_.template end< 0, VTK_Partition >(),
462  datamode, *vertexmapper );
463  }
464 
466 
481  public ForwardIteratorFacade<CornerIterator, const Entity, EntityReference, int>
482  {
483  GridCellIterator git;
484  GridCellIterator gend;
485  VTK::DataMode datamode;
486  // Index of the currently visited corner within the current element.
487  // NOTE: this is in VTK-numbering, in contrast to VertexIterator.
488  int cornerIndexVTK;
489  const VertexMapper & vertexmapper;
490  // in conforming mode, for each vertex id (as obtained by vertexmapper)
491  // hold its number in the iteration order of VertexIterator (*not*
492  // CornerIterator)
493  const std::vector<int> & number;
494  // holds the number of corners of all the elements we have seen so far,
495  // excluding the current element
496  int offset;
497 
498  // hide operator ->
499  void operator->();
500  public:
501  CornerIterator(const GridCellIterator & x,
502  const GridCellIterator & end,
503  const VTK::DataMode & dm,
504  const VertexMapper & vm,
505  const std::vector<int> & num) :
506  git(x), gend(end), datamode(dm), cornerIndexVTK(0),
507  vertexmapper(vm),
508  number(num), offset(0) {}
509  void increment ()
510  {
511  if( git == gend )
512  return;
513  ++cornerIndexVTK;
514  const int numCorners = git->subEntities(n);
515  if( cornerIndexVTK == numCorners )
516  {
517  offset += numCorners;
518  cornerIndexVTK = 0;
519 
520  ++git;
521  while( (git != gend) && skipEntity( git->partitionType() ) )
522  ++git;
523  }
524  }
525  bool equals (const CornerIterator & cit) const
526  {
527  return git == cit.git
528  && cornerIndexVTK == cit.cornerIndexVTK
529  && datamode == cit.datamode;
530  }
531  EntityReference dereference() const
532  {
533  return *git;
534  }
536 
540  int id () const
541  {
542  switch (datamode)
543  {
544  case VTK::conforming :
545  return
546  number[vertexmapper.subIndex(*git,VTK::renumber(*git,cornerIndexVTK),
547  n)];
548  case VTK::nonconforming :
549  return offset + VTK::renumber(*git,cornerIndexVTK);
550  default :
551  DUNE_THROW(IOError,"VTKWriter: unsupported DataMode" << datamode);
552  }
553  }
554  };
555 
557  {
558  return CornerIterator( gridView_.template begin< 0, VTK_Partition >(),
559  gridView_.template end< 0, VTK_Partition >(),
560  datamode, *vertexmapper, number );
561  }
562 
564  {
565  return CornerIterator( gridView_.template end< 0, VTK_Partition >(),
566  gridView_.template end< 0, VTK_Partition >(),
567  datamode, *vertexmapper, number );
568  }
569 
570  public:
578  explicit VTKWriter ( const GridView &gridView,
580  : gridView_( gridView ),
581  datamode( dm )
582  { }
583 
588  void addCellData (const VTKFunctionPtr & p)
589  {
590  celldata.push_back(VTKLocalFunction(p));
591  }
592 
593  template<typename F>
594  void addCellData(F&& f, VTK::FieldInfo vtkFieldInfo)
595  {
596  celldata.push_back(VTKLocalFunction(std::forward<F>(f),vtkFieldInfo));
597  }
598 
604  void addCellData (VTKFunction* p) DUNE_DEPRECATED_MSG("Don't pass raw pointers, use the version with shared_ptr")
605  {
607  }
608 
624  template<class V>
625  void addCellData (const V& v, const std::string &name, int ncomps = 1)
626  {
627  typedef P0VTKFunction<GridView, V> Function;
628  for (int c=0; c<ncomps; ++c) {
629  std::stringstream compName;
630  compName << name;
631  if (ncomps>1)
632  compName << "[" << c << "]";
633  VTKFunction* p = new Function(gridView_, v, compName.str(), ncomps, c);
635  }
636  }
637 
643  void addVertexData (VTKFunction* p) DUNE_DEPRECATED_MSG("Don't pass raw pointers, use the version with shared_ptr")
644  {
646  }
647 
652  void addVertexData (const VTKFunctionPtr & p)
653  {
654  vertexdata.push_back(VTKLocalFunction(p));
655  }
656 
657  template<typename F>
658  void addVertexData(F&& f, VTK::FieldInfo vtkFieldInfo)
659  {
660  vertexdata.push_back(VTKLocalFunction(std::forward<F>(f),vtkFieldInfo));
661  }
662 
663 
679  template<class V>
680  void addVertexData (const V& v, const std::string &name, int ncomps=1)
681  {
682  typedef P1VTKFunction<GridView, V> Function;
683  for (int c=0; c<ncomps; ++c) {
684  std::stringstream compName;
685  compName << name;
686  if (ncomps>1)
687  compName << "[" << c << "]";
688  VTKFunction* p = new Function(gridView_, v, compName.str(), ncomps, c);
690  }
691  }
692 
694  void clear ()
695  {
696  celldata.clear();
697  vertexdata.clear();
698  }
699 
701  virtual ~VTKWriter ()
702  {
703  this->clear();
704  }
705 
717  std::string write ( const std::string &name,
718  VTK::OutputType type = VTK::ascii )
719  {
720  return write( name, type, gridView_.comm().rank(), gridView_.comm().size() );
721  }
722 
749  std::string pwrite ( const std::string & name, const std::string & path, const std::string & extendpath,
750  VTK::OutputType type = VTK::ascii )
751  {
752  return pwrite( name, path, extendpath, type, gridView_.comm().rank(), gridView_.comm().size() );
753  }
754 
755  protected:
757 
768  std::string getParallelPieceName(const std::string& name,
769  const std::string& path,
770  int commRank, int commSize) const
771  {
772  std::ostringstream s;
773  if(path.size() > 0) {
774  s << path;
775  if(path[path.size()-1] != '/')
776  s << '/';
777  }
778  s << 's' << std::setw(4) << std::setfill('0') << commSize << '-';
779  s << 'p' << std::setw(4) << std::setfill('0') << commRank << '-';
780  s << name;
781  if(GridView::dimension > 1)
782  s << ".vtu";
783  else
784  s << ".vtp";
785  return s.str();
786  }
787 
789 
799  std::string getParallelHeaderName(const std::string& name,
800  const std::string& path,
801  int commSize) const
802  {
803  std::ostringstream s;
804  if(path.size() > 0) {
805  s << path;
806  if(path[path.size()-1] != '/')
807  s << '/';
808  }
809  s << 's' << std::setw(4) << std::setfill('0') << commSize << '-';
810  s << name;
811  if(GridView::dimension > 1)
812  s << ".pvtu";
813  else
814  s << ".pvtp";
815  return s.str();
816  }
817 
819 
831  std::string getSerialPieceName(const std::string& name,
832  const std::string& path) const
833  {
834  static const std::string extension =
835  GridView::dimension == 1 ? ".vtp" : ".vtu";
836 
837  return concatPaths(path, name+extension);
838  }
839 
855  std::string write ( const std::string &name,
856  VTK::OutputType type,
857  const int commRank,
858  const int commSize )
859  {
860  // in the parallel case, just use pwrite, it has all the necessary
861  // stuff, so we don't need to reimplement it here.
862  if(commSize > 1)
863  return pwrite(name, "", "", type, commRank, commSize);
864 
865  // make data mode visible to private functions
866  outputtype = type;
867 
868  // generate filename for process data
869  std::string pieceName = getSerialPieceName(name, "");
870 
871  // write process data
872  std::ofstream file;
873  file.exceptions(std::ios_base::badbit | std::ios_base::failbit |
874  std::ios_base::eofbit);
875  // check if file can be opened
876  try {
877  file.open( pieceName.c_str(), std::ios::binary );
878  }
879  catch(...) {
880  std::cerr << "Filename: " << pieceName << " could not be opened" << std::endl;
881  throw;
882  }
883  if (! file.is_open())
884  DUNE_THROW(IOError, "Could not write to piece file " << pieceName);
885  writeDataFile( file );
886  file.close();
887 
888  return pieceName;
889  }
890 
892 
915  std::string pwrite(const std::string& name, const std::string& path,
916  const std::string& extendpath,
917  VTK::OutputType ot, const int commRank,
918  const int commSize )
919  {
920  // make data mode visible to private functions
921  outputtype=ot;
922 
923  // do some magic because paraview can only cope with relative pathes to piece files
924  std::ofstream file;
925  file.exceptions(std::ios_base::badbit | std::ios_base::failbit |
926  std::ios_base::eofbit);
927  std::string piecepath = concatPaths(path, extendpath);
928  std::string relpiecepath = relativePath(path, piecepath);
929 
930  // write this processes .vtu/.vtp piece file
931  std::string fullname = getParallelPieceName(name, piecepath, commRank,
932  commSize);
933  // check if file can be opened
934  try {
935  file.open(fullname.c_str(),std::ios::binary);
936  }
937  catch(...) {
938  std::cerr << "Filename: " << fullname << " could not be opened" << std::endl;
939  throw;
940  }
941  if (! file.is_open())
942  DUNE_THROW(IOError, "Could not write to piecefile file " << fullname);
943  writeDataFile(file);
944  file.close();
945  gridView_.comm().barrier();
946 
947  // if we are rank 0, write .pvtu/.pvtp parallel header
948  fullname = getParallelHeaderName(name, path, commSize);
949  if( commRank ==0 )
950  {
951  file.open(fullname.c_str());
952  if (! file.is_open())
953  DUNE_THROW(IOError, "Could not write to parallel file " << fullname);
954  writeParallelHeader(file,name,relpiecepath, commSize );
955  file.close();
956  }
957  gridView_.comm().barrier();
958  return fullname;
959  }
960 
961  private:
963 
980  void writeParallelHeader(std::ostream& s, const std::string& piecename,
981  const std::string& piecepath, const int commSize)
982  {
983  VTK::FileType fileType =
985 
986  VTK::PVTUWriter writer(s, fileType);
987 
988  writer.beginMain();
989 
990  // PPointData
991  {
992  std::string scalars, vectors;
993  std::tie(scalars,vectors) = getDataNames(vertexdata);
994  writer.beginPointData(scalars, vectors);
995  }
996  for (auto it = vertexdata.begin(),
997  end = vertexdata.end();
998  it != end;
999  ++it)
1000  {
1001  unsigned writecomps = it->fieldInfo().size();
1002  if(writecomps == 2) writecomps = 3;
1003  writer.addArray<float>(it->name(), writecomps);
1004  }
1005  writer.endPointData();
1006 
1007  // PCellData
1008  {
1009  std::string scalars, vectors;
1010  std::tie(scalars,vectors) = getDataNames(celldata);
1011  writer.beginCellData(scalars, vectors);
1012  }
1013  for (auto it = celldata.begin(),
1014  end = celldata.end();
1015  it != end;
1016  ++it)
1017  {
1018  unsigned writecomps = it->fieldInfo().size();
1019  if(writecomps == 2) writecomps = 3;
1020  writer.addArray<float>(it->name(), writecomps);
1021  }
1022  writer.endCellData();
1023 
1024  // PPoints
1025  writer.beginPoints();
1026  writer.addArray<float>("Coordinates", 3);
1027  writer.endPoints();
1028 
1029  // Pieces
1030  for( int i = 0; i < commSize; ++i )
1031  {
1032  const std::string& fullname = getParallelPieceName(piecename,
1033  piecepath, i,
1034  commSize);
1035  writer.addPiece(fullname);
1036  }
1037 
1038  writer.endMain();
1039  }
1040 
1042  void writeDataFile (std::ostream& s)
1043  {
1044  VTK::FileType fileType =
1045  (n == 1) ? VTK::polyData : VTK::unstructuredGrid;
1046 
1047  VTK::VTUWriter writer(s, outputtype, fileType);
1048 
1049  // Grid characteristics
1050  vertexmapper = new VertexMapper( gridView_ );
1051  if (datamode == VTK::conforming)
1052  {
1053  number.resize(vertexmapper->size());
1054  for (std::vector<int>::size_type i=0; i<number.size(); i++) number[i] = -1;
1055  }
1057 
1058  writer.beginMain(ncells, nvertices);
1059  writeAllData(writer);
1060  writer.endMain();
1061 
1062  // write appended binary data section
1063  if(writer.beginAppended())
1064  writeAllData(writer);
1065  writer.endAppended();
1066 
1067  delete vertexmapper; number.clear();
1068  }
1069 
1070  void writeAllData(VTK::VTUWriter& writer) {
1071  // PointData
1072  writeVertexData(writer);
1073 
1074  // CellData
1075  writeCellData(writer);
1076 
1077  // Points
1078  writeGridPoints(writer);
1079 
1080  // Cells
1081  writeGridCells(writer);
1082  }
1083 
1084  protected:
1085  std::string getFormatString() const
1086  {
1087  if (outputtype==VTK::ascii)
1088  return "ascii";
1089  if (outputtype==VTK::base64)
1090  return "binary";
1092  return "appended";
1094  return "appended";
1095  DUNE_THROW(IOError, "VTKWriter: unsupported OutputType" << outputtype);
1096  }
1097 
1098  std::string getTypeString() const
1099  {
1100  if (n==1)
1101  return "PolyData";
1102  else
1103  return "UnstructuredGrid";
1104  }
1105 
1107  virtual void countEntities(int &nvertices, int &ncells, int &ncorners)
1108  {
1109  nvertices = 0;
1110  ncells = 0;
1111  ncorners = 0;
1112  for (CellIterator it=cellBegin(); it!=cellEnd(); ++it)
1113  {
1114  ncells++;
1115  // because of the use of vertexmapper->map(), this iteration must be
1116  // in the order of Dune's numbering.
1117  const int subEntities = it->subEntities(n);
1118  for (int i=0; i<subEntities; ++i)
1119  {
1120  ncorners++;
1121  if (datamode == VTK::conforming)
1122  {
1123  int alpha = vertexmapper->subIndex(*it,i,n);
1124  if (number[alpha]<0)
1125  number[alpha] = nvertices++;
1126  }
1127  else
1128  {
1129  nvertices++;
1130  }
1131  }
1132  }
1133  }
1134 
1135  template<typename T>
1136  std::tuple<std::string,std::string> getDataNames(const T& data) const
1137  {
1138  std::string scalars = "";
1139  for (auto it = data.begin(),
1140  end = data.end();
1141  it != end;
1142  ++it)
1143  if (it->fieldInfo().type() == VTK::FieldInfo::Type::scalar)
1144  {
1145  scalars = it->name();
1146  break;
1147  }
1148 
1149  std::string vectors = "";
1150  for (auto it = data.begin(),
1151  end = data.end();
1152  it != end;
1153  ++it)
1154  if (it->fieldInfo().type() == VTK::FieldInfo::Type::vector)
1155  {
1156  vectors = it->name();
1157  break;
1158  }
1159  return std::make_tuple(scalars,vectors);
1160  }
1161 
1162  template<typename Data, typename Iterator>
1163  void writeData(VTK::VTUWriter& writer, const Data& data, const Iterator begin, const Iterator end, int nentries)
1164  {
1165  for (auto it = data.begin(),
1166  iend = data.end();
1167  it != iend;
1168  ++it)
1169  {
1170  const auto& f = *it;
1171  VTK::FieldInfo fieldInfo = f.fieldInfo();
1172  std::size_t writecomps = fieldInfo.size();
1173  switch (fieldInfo.type())
1174  {
1176  break;
1178  // vtk file format: a vector data always should have 3 comps (with
1179  // 3rd comp = 0 in 2D case)
1180  if (writecomps > 3)
1181  DUNE_THROW(IOError,"Cannot write VTK vectors with more than 3 components (components was " << writecomps << ")");
1182  writecomps = 3;
1183  break;
1185  DUNE_THROW(NotImplemented,"VTK output for tensors not implemented yet");
1186  }
1187  shared_ptr<VTK::DataArrayWriter<float> > p
1188  (writer.makeArrayWriter<float>(f.name(), writecomps, nentries));
1189  if(!p->writeIsNoop())
1190  for (Iterator eit = begin; eit!=end; ++eit)
1191  {
1192  const Entity & e = *eit;
1193  f.bind(e);
1194  f.write(eit.position(),*p);
1195  f.unbind();
1196  // vtk file format: a vector data always should have 3 comps
1197  // (with 3rd comp = 0 in 2D case)
1198  for (std::size_t j=fieldInfo.size(); j < writecomps; ++j)
1199  p->write(0.0);
1200  }
1201  }
1202  }
1203 
1205  virtual void writeCellData(VTK::VTUWriter& writer)
1206  {
1207  if(celldata.size() == 0)
1208  return;
1209 
1210  std::string scalars, vectors;
1211  std::tie(scalars,vectors) = getDataNames(celldata);
1212 
1213  writer.beginCellData(scalars, vectors);
1215  writer.endCellData();
1216  }
1217 
1219  virtual void writeVertexData(VTK::VTUWriter& writer)
1220  {
1221  if(vertexdata.size() == 0)
1222  return;
1223 
1224  std::string scalars, vectors;
1225  std::tie(scalars,vectors) = getDataNames(vertexdata);
1226 
1227  writer.beginPointData(scalars, vectors);
1229  writer.endPointData();
1230  }
1231 
1233  virtual void writeGridPoints(VTK::VTUWriter& writer)
1234  {
1235  writer.beginPoints();
1236 
1237  shared_ptr<VTK::DataArrayWriter<float> > p
1238  (writer.makeArrayWriter<float>("Coordinates", 3, nvertices));
1239  if(!p->writeIsNoop()) {
1240  VertexIterator vEnd = vertexEnd();
1241  for (VertexIterator vit=vertexBegin(); vit!=vEnd; ++vit)
1242  {
1243  int dimw=w;
1244  for (int j=0; j<std::min(dimw,3); j++)
1245  p->write((*vit).geometry().corner(vit.localindex())[j]);
1246  for (int j=std::min(dimw,3); j<3; j++)
1247  p->write(0.0);
1248  }
1249  }
1250  // free the VTK::DataArrayWriter before touching the stream
1251  p.reset();
1252 
1253  writer.endPoints();
1254  }
1255 
1257  virtual void writeGridCells(VTK::VTUWriter& writer)
1258  {
1259  writer.beginCells();
1260 
1261  // connectivity
1262  {
1263  shared_ptr<VTK::DataArrayWriter<int> > p1
1264  (writer.makeArrayWriter<int>("connectivity", 1, ncorners));
1265  if(!p1->writeIsNoop())
1266  for (CornerIterator it=cornerBegin(); it!=cornerEnd(); ++it)
1267  p1->write(it.id());
1268  }
1269 
1270  // offsets
1271  {
1272  shared_ptr<VTK::DataArrayWriter<int> > p2
1273  (writer.makeArrayWriter<int>("offsets", 1, ncells));
1274  if(!p2->writeIsNoop()) {
1275  int offset = 0;
1276  for (CellIterator it=cellBegin(); it!=cellEnd(); ++it)
1277  {
1278  offset += it->subEntities(n);
1279  p2->write(offset);
1280  }
1281  }
1282  }
1283 
1284  // types
1285  if (n>1)
1286  {
1287  shared_ptr<VTK::DataArrayWriter<unsigned char> > p3
1288  (writer.makeArrayWriter<unsigned char>("types", 1, ncells));
1289  if(!p3->writeIsNoop())
1290  for (CellIterator it=cellBegin(); it!=cellEnd(); ++it)
1291  {
1292  int vtktype = VTK::geometryType(it->type());
1293  p3->write(vtktype);
1294  }
1295  }
1296 
1297  writer.endCells();
1298  }
1299 
1300  protected:
1301  // the list of registered functions
1302  std::list<VTKLocalFunction> celldata;
1303  std::list<VTKLocalFunction> vertexdata;
1304 
1305  // the grid
1307 
1308  // temporary grid information
1309  int ncells;
1312  private:
1313  VertexMapper* vertexmapper;
1314  // in conforming mode, for each vertex id (as obtained by vertexmapper)
1315  // hold its number in the iteration order (VertexIterator)
1316  std::vector<int> number;
1317  VTK::DataMode datamode;
1318  protected:
1320  };
1321 
1322 }
1323 
1324 #endif
void write(const Coordinate &pos, Writer &w) const
Write the value of the data set at local coordinate pos to the writer w.
Definition: vtkwriter.hh:309
const VTK::FieldInfo & fieldInfo() const
Returns the VTK::FieldInfo for the data set.
Definition: vtkwriter.hh:291
void increment()
Definition: vtkwriter.hh:411
virtual void write(const Coordinate &pos, Writer &w, std::size_t count) const =0
Evaluate data set at local position pos inside the current entity and write result to w...
virtual void unbind()
Unbind data set from current grid entity - mostly here for performance and symmetry reasons...
Definition: vtkwriter.hh:238
std::string pwrite(const std::string &name, const std::string &path, const std::string &extendpath, VTK::OutputType type=VTK::ascii)
write output (interface might change later)
Definition: vtkwriter.hh:749
void endCellData()
finish CellData section
Definition: vtuwriter.hh:218
std::string getParallelPieceName(const std::string &name, const std::string &path, int commRank, int commSize) const
return name of a parallel piece file
Definition: vtkwriter.hh:768
void bind(const Entity &e) const
Bind the data set to grid entity e.
Definition: vtkwriter.hh:297
Ouput is to the file is appended raw binary.
Definition: common.hh:46
void basicIncrement()
Definition: vtkwriter.hh:383
void beginCellData(const std::string &scalars="", const std::string &vectors="")
start CellData section
Definition: vtuwriter.hh:203
std::decay< F >::type Function
Definition: vtkwriter.hh:181
Implementation class for a multiple codim and multiple geometry type mapper.
Definition: mcmgmapper.hh:102
virtual void writeVertexData(VTK::VTUWriter &writer)
write vertex data
Definition: vtkwriter.hh:1219
Common stuff for the VTKWriter.
virtual void unbind()
Unbind data set from current grid entity - mostly here for performance and symmetry reasons...
Definition: vtkwriter.hh:193
Functions for VTK output.
DataMode
Whether to produce conforming or non-conforming output.
Definition: common.hh:64
Type type() const
The type of the data field.
Definition: common.hh:336
Writer for the ouput of grid functions in the vtk format.Writes arbitrary grid functions (living on c...
Definition: vtksequencewriter.hh:23
Definition: vtkwriter.hh:54
CornerIterator cornerBegin() const
Definition: vtkwriter.hh:556
The dimension of the grid.
Definition: common/gridview.hh:130
virtual void write(const Coordinate &pos, Writer &w, std::size_t count) const
Evaluate data set at local position pos inside the current entity and write result to w...
Definition: vtkwriter.hh:198
virtual void writeGridCells(VTK::VTUWriter &writer)
write the connectivity array
Definition: vtkwriter.hh:1257
void beginCells()
start section for the grid cells/PolyData lines
Definition: vtuwriter.hh:272
std::string write(const std::string &name, VTK::OutputType type=VTK::ascii)
write output (interface might change later)
Definition: vtkwriter.hh:717
virtual void bind(const Entity &e)
Bind data set to grid entity - must be called before evaluating (i.e. calling write()) ...
Definition: vtkwriter.hh:188
Data array writers for the VTKWriter.
EntityReference dereference() const
Definition: vtkwriter.hh:434
for .vtu files (UnstructuredGrid)
Definition: common.hh:294
VTKLocalFunction(const VTKFunctionPtr &vtkFunctionPtr)
Construct a VTKLocalFunction for a legacy VTKFunction.
Definition: vtkwriter.hh:275
GeometryType geometryType(const Dune::GeometryType &t)
mapping from GeometryType to VTKGeometryType
Definition: common.hh:195
Descriptor struct for VTK fields.
Definition: common.hh:306
void unbind() const
Unbind the data set from the currently bound entity.
Definition: vtkwriter.hh:303
std::string write(const std::string &name, VTK::OutputType type, const int commRank, const int commSize)
write output (interface might change later)
Definition: vtkwriter.hh:855
std::string getFormatString() const
Definition: vtkwriter.hh:1085
int renumber(const Dune::GeometryType &t, int i)
renumber VTK <-> Dune
Definition: common.hh:224
CornerIterator(const GridCellIterator &x, const GridCellIterator &end, const VTK::DataMode &dm, const VertexMapper &vm, const std::vector< int > &num)
Definition: vtkwriter.hh:501
FunctionWrapper(F_ &&f)
Definition: vtkwriter.hh:184
std::list< VTKLocalFunction > celldata
Definition: vtkwriter.hh:1302
CellIterator cellEnd() const
Definition: vtkwriter.hh:345
int ncorners
Definition: vtkwriter.hh:1311
shared_ptr< const VTKFunction > VTKFunctionPtr
Definition: vtkwriter.hh:140
const FieldVector< DT, n > & position() const
position of vertex inside the entity
Definition: vtkwriter.hh:444
Output to the file is in ascii.
Definition: common.hh:42
DataArrayWriter< T > * makeArrayWriter(const std::string &name, unsigned ncomps, unsigned nitems)
aquire a DataArrayWriter
Definition: vtuwriter.hh:379
VertexIterator vertexBegin() const
Definition: vtkwriter.hh:451
Index subIndex(const typename GV::template Codim< 0 >::Entity &e, int i, unsigned int codim) const
Map subentity of codim 0 entity to array index.
Definition: mcmgmapper.hh:190
virtual void writeGridPoints(VTK::VTUWriter &writer)
write the positions of vertices
Definition: vtkwriter.hh:1233
GridView gridView_
Definition: vtkwriter.hh:1306
VTKFunctionWrapper(const VTKFunctionPtr &f)
Definition: vtkwriter.hh:228
all interior entities
Definition: gridenums.hh:29
virtual void bind(const Entity &e)
Bind data set to grid entity - must be called before evaluating (i.e. calling write()) ...
Definition: vtkwriter.hh:233
FileType
which type of VTK file to write
Definition: common.hh:290
Base class for polymorphic container of underlying data set.
Definition: vtkwriter.hh:156
std::string name() const
The name of the data field.
Definition: common.hh:330
PartitionType
Attributes used in the generic overlap model.
Definition: gridenums.hh:28
all entities
Definition: gridenums.hh:139
Type erasure wrapper for VTK data sets.
Definition: vtkwriter.hh:148
std::string getSerialPieceName(const std::string &name, const std::string &path) const
return name of a serial piece file
Definition: vtkwriter.hh:831
void endPointData()
finish PointData section
Definition: vtuwriter.hh:180
Traits::Grid Grid
type of the grid
Definition: common/gridview.hh:77
std::string name() const
Returns the name of the data set.
Definition: vtkwriter.hh:285
Type erasure implementation for legacy VTKFunctions.
Definition: vtkwriter.hh:225
Grid::ctype ctype
type used for coordinates in grid
Definition: common/gridview.hh:127
base class for data array writers
Definition: dataarraywriter.hh:53
EntityReference dereference() const
Definition: vtkwriter.hh:531
std::size_t size() const
The number of components in the data field.
Definition: common.hh:342
Mapper for multiple codim and multiple geometry types.
Dump a .vtu/.vtp files contents to a stream.
Definition: vtuwriter.hh:96
interior and border entities
Definition: gridenums.hh:136
int size() const
Return total number of entities in the entity set managed by the mapper.
Definition: mcmgmapper.hh:205
void addCellData(const V &v, const std::string &name, int ncomps=1)
Add a grid function (represented by container) that lives on the cells of the grid to the visualizati...
Definition: vtkwriter.hh:625
CornerIterator cornerEnd() const
Definition: vtkwriter.hh:563
virtual void write(T data)=0
write one data element
const FieldVector< DT, n > position() const
Definition: vtkwriter.hh:334
VertexIterator vertexEnd() const
Definition: vtkwriter.hh:458
Iterator over the grids elements.
Definition: vtkwriter.hh:327
Traits::IndexSet IndexSet
type of the index set
Definition: common/gridview.hh:80
Iterate over the grid's vertices.
Definition: vtkwriter.hh:365
VTKLocalFunction(F &&f, VTK::FieldInfo fieldInfo, typename std::enable_if< detail::_has_local_context< F >::value, int >::type dummy=0)
Construct a VTKLocalFunction for a dune-functions style LocalFunction.
Definition: vtkwriter.hh:258
VTKLocalFunction(F &&f, VTK::FieldInfo fieldInfo, typename std::enable_if< not detail::_has_local_context< F >::value, int >::type dummy=0)
Construct a VTKLocalFunction for a dune-functions style Function.
Definition: vtkwriter.hh:266
vector-valued field (always 3D, will be padded if necessary)
Output to the file is inline base64 binary.
Definition: common.hh:44
void addVertexData(const V &v, const std::string &name, int ncomps=1)
Add a grid function (represented by container) that lives on the vertices of the grid to the visualiz...
Definition: vtkwriter.hh:680
Iterate over the elements' corners.
Definition: vtkwriter.hh:480
std::string getTypeString() const
Definition: vtkwriter.hh:1098
tensor field (always 3x3)
std::list< VTKLocalFunction >::const_iterator FunctionIterator
Definition: vtkwriter.hh:319
std::tuple< std::string, std::string > getDataNames(const T &data) const
Definition: vtkwriter.hh:1136
void addVertexData(F &&f, VTK::FieldInfo vtkFieldInfo)
Definition: vtkwriter.hh:658
int ncells
Definition: vtkwriter.hh:1309
VTK::FieldInfo _fieldInfo
Definition: vtkwriter.hh:315
const CollectiveCommunication & comm() const
obtain collective communication object
Definition: common/gridview.hh:249
virtual void unbind()=0
Unbind data set from current grid entity - mostly here for performance and symmetry reasons...
std::string getParallelHeaderName(const std::string &name, const std::string &path, int commSize) const
return name of a parallel header file
Definition: vtkwriter.hh:799
A base class for grid functions with any return type and dimension.
Definition: function.hh:38
CellIterator(const GridCellIterator &x)
construct a CellIterator from the gridview's Iterator.
Definition: vtkwriter.hh:331
void beginPoints()
start section for the point coordinates
Definition: vtuwriter.hh:236
The dimension of the world the grid lives in.
Definition: common/gridview.hh:134
void addVertexData(VTKFunction *p)
Add a grid function that lives on the vertices of the grid to the visualization.
Definition: vtkwriter.hh:643
void writeData(VTK::VTUWriter &writer, const Data &data, const Iterator begin, const Iterator end, int nentries)
Definition: vtkwriter.hh:1163
void addCellData(F &&f, VTK::FieldInfo vtkFieldInfo)
Definition: vtkwriter.hh:594
int nvertices
Definition: vtkwriter.hh:1310
Writer for the ouput of grid functions in the vtk format.Writes arbitrary grid functions (living on c...
Definition: vtkwriter.hh:87
std::string pwrite(const std::string &name, const std::string &path, const std::string &extendpath, VTK::OutputType ot, const int commRank, const int commSize)
write output; interface might change later
Definition: vtkwriter.hh:915
std::shared_ptr< FunctionWrapperBase > _f
Definition: vtkwriter.hh:314
void addVertexData(const VTKFunctionPtr &p)
Add a grid function that lives on the vertices of the grid to the visualization.
Definition: vtkwriter.hh:652
Output conforming data.
Definition: common.hh:70
std::list< VTKLocalFunction > vertexdata
Definition: vtkwriter.hh:1303
Take a vector and interpret it as point data for the VTKWriter.
Definition: function.hh:186
void addCellData(VTKFunction *p)
Add a grid function that lives on the cells of the grid to the visualization.
Definition: vtkwriter.hh:604
virtual ~VTKWriter()
destructor
Definition: vtkwriter.hh:701
virtual void write(const Coordinate &pos, Writer &w, std::size_t count) const
Evaluate data set at local position pos inside the current entity and write result to w...
Definition: vtkwriter.hh:243
Output non-conforming data.
Definition: common.hh:78
Type erasure implementation for functions conforming to the dune-functions LocalFunction interface...
Definition: vtkwriter.hh:178
CellIterator cellBegin() const
Definition: vtkwriter.hh:340
VTK::DataArrayWriter< float > Writer
Definition: vtkwriter.hh:153
void beginPointData(const std::string &scalars="", const std::string &vectors="")
start PointData section
Definition: vtuwriter.hh:165
Dump a .vtu/.vtp files contents to a stream.
Definition: pvtuwriter.hh:60
for .vtp files (PolyData)
Definition: common.hh:292
Grid view abstract base class.
Definition: common/gridview.hh:58
bool equals(const CornerIterator &cit) const
Definition: vtkwriter.hh:525
VTKWriter(const GridView &gridView, VTK::DataMode dm=VTK::conforming)
Construct a VTKWriter working on a specific GridView.
Definition: vtkwriter.hh:578
Base class to write pvd-files which contains a list of all collected vtk-files.
Definition: vtksequencewriterbase.hh:32
Ouput is to the file is appended base64 binary.
Definition: common.hh:48
virtual void countEntities(int &nvertices, int &ncells, int &ncorners)
count the vertices, cells and corners
Definition: vtkwriter.hh:1107
int min(const DofVectorPointer< int > &dofVector)
Definition: dofvector.hh:346
virtual ~FunctionWrapperBase()
Definition: vtkwriter.hh:171
void addCellData(const VTKFunctionPtr &p)
Add a grid function that lives on the cells of the grid to the visualization.
Definition: vtkwriter.hh:588
virtual void bind(const Entity &e)=0
Bind data set to grid entity - must be called before evaluating (i.e. calling write()) ...
OutputType
How the bulk data should be stored in the file.
Definition: common.hh:40
Dune::VTKFunction< GridView > VTKFunction
Definition: vtkwriter.hh:139
int localindex() const
index of vertex within the entity, in Dune-numbering
Definition: vtkwriter.hh:439
virtual void writeCellData(VTK::VTUWriter &writer)
write cell data
Definition: vtkwriter.hh:1205
PartitionIteratorType
Parameter to be used for the parallel level- and leaf iterators.
Definition: gridenums.hh:134
void endPoints()
finish section for the point coordinates
Definition: vtuwriter.hh:247
VertexIterator(const GridCellIterator &x, const GridCellIterator &end, const VTK::DataMode &dm, const VertexMapper &vm)
Definition: vtkwriter.hh:400
int id() const
Process-local consecutive zero-starting vertex id.
Definition: vtkwriter.hh:540
VTK::OutputType outputtype
Definition: vtkwriter.hh:1319
void clear()
clear list of registered functions
Definition: vtkwriter.hh:694
void endCells()
start section for the grid cells/PolyData lines
Definition: vtuwriter.hh:283
bool equals(const VertexIterator &cit) const
Definition: vtkwriter.hh:428
void increment()
Definition: vtkwriter.hh:509
Take a vector and interpret it as cell data for the VTKWriter.
Definition: function.hh:88