dune-vtk  0.2
vtkrectilineargridwriter.impl.hh
Go to the documentation of this file.
1 #pragma once
2 
3 #include <iomanip>
4 #include <iostream>
5 #include <iterator>
6 #include <fstream>
7 #include <sstream>
8 #include <string>
9 
10 #include <dune/geometry/referenceelements.hh>
11 #include <dune/geometry/type.hh>
12 
13 #include <dune/vtk/utility/enum.hh>
16 
17 namespace Dune {
18 
19 template <class GV, class DC>
20 void VtkRectilinearGridWriter<GV,DC>
21  ::writeSerialFile (std::ofstream& out) const
22 {
23  std::vector<pos_type> offsets; // pos => offset
24  this->writeHeader(out, "RectilinearGrid");
25 
26  auto const& wholeExtent = dataCollector_->wholeExtent();
27  out << "<RectilinearGrid"
28  << " WholeExtent=\"" << Vtk::join(wholeExtent.begin(), wholeExtent.end()) << "\""
29  << ">\n";
30 
31  dataCollector_->writeLocalPiece([&out](auto const& extent) {
32  out << "<Piece Extent=\"" << Vtk::join(extent.begin(), extent.end()) << "\">\n";
33  });
34 
35  // Write point coordinates for x, y, and z ordinate
36  out << "<Coordinates>\n";
37  writeCoordinates(out, offsets);
38  out << "</Coordinates>\n";
39 
40  // Write data associated with grid points
41  out << "<PointData" << this->getNames(pointData_) << ">\n";
42  for (auto const& v : pointData_)
43  this->writeData(out, offsets, v, Super::POINT_DATA);
44  out << "</PointData>\n";
45 
46  // Write data associated with grid cells
47  out << "<CellData" << this->getNames(cellData_) << ">\n";
48  for (auto const& v : cellData_)
49  this->writeData(out, offsets, v, Super::CELL_DATA);
50  out << "</CellData>\n";
51 
52  out << "</Piece>\n";
53  out << "</RectilinearGrid>\n";
54 
55  this->writeAppended(out, offsets);
56  out << "</VTKFile>";
57 }
58 
59 
60 template <class GV, class DC>
61 void VtkRectilinearGridWriter<GV,DC>
62  ::writeParallelFile (std::ofstream& out, std::string const& pfilename, int /*size*/) const
63 {
64  this->writeHeader(out, "PRectilinearGrid");
65 
66  auto const& wholeExtent = dataCollector_->wholeExtent();
67  out << "<PRectilinearGrid"
68  << " GhostLevel=\"" << dataCollector_->ghostLevel() << "\""
69  << " WholeExtent=\"" << Vtk::join(wholeExtent.begin(), wholeExtent.end()) << "\""
70  << ">\n";
71 
72  // Write point coordinates for x, y, and z ordinate
73  out << "<PCoordinates>\n";
74  out << "<PDataArray Name=\"x\" type=\"" << to_string(datatype_) << "\" />\n";
75  out << "<PDataArray Name=\"y\" type=\"" << to_string(datatype_) << "\" />\n";
76  out << "<PDataArray Name=\"z\" type=\"" << to_string(datatype_) << "\" />\n";
77  out << "</PCoordinates>\n";
78 
79  // Write data associated with grid points
80  out << "<PPointData" << this->getNames(pointData_) << ">\n";
81  for (auto const& v : pointData_) {
82  out << "<PDataArray"
83  << " Name=\"" << v.name() << "\""
84  << " type=\"" << to_string(v.dataType()) << "\""
85  << " NumberOfComponents=\"" << v.numComponents() << "\""
86  << " />\n";
87  }
88  out << "</PPointData>\n";
89 
90  // Write data associated with grid cells
91  out << "<PCellData" << this->getNames(cellData_) << ">\n";
92  for (auto const& v : cellData_) {
93  out << "<PDataArray"
94  << " Name=\"" << v.name() << "\""
95  << " type=\"" << to_string(v.dataType()) << "\""
96  << " NumberOfComponents=\"" << v.numComponents() << "\""
97  << " />\n";
98  }
99  out << "</PCellData>\n";
100 
101  // Write piece file references
102  dataCollector_->writePieces([&out,pfilename,ext=this->fileExtension()](int p, auto const& extent, bool write_extent)
103  {
104  std::string piece_source = pfilename + "_p" + std::to_string(p) + "." + ext;
105  out << "<Piece Source=\"" << piece_source << "\"";
106  if (write_extent)
107  out << " Extent=\"" << Vtk::join(extent.begin(), extent.end()) << "\"";
108  out << " />\n";
109  });
110 
111  out << "</PRectilinearGrid>\n";
112  out << "</VTKFile>";
113 }
114 
115 
116 template <class GV, class DC>
117 void VtkRectilinearGridWriter<GV,DC>
118  ::writeCoordinates (std::ofstream& out, std::vector<pos_type>& offsets,
119  std::optional<std::size_t> timestep) const
120 {
121  std::string names = "xyz";
122  if (format_ == Vtk::FormatTypes::ASCII) {
123  auto coordinates = dataCollector_->template coordinates<double>();
124  for (std::size_t d = 0; d < 3; ++d) {
125  out << "<DataArray type=\"" << to_string(datatype_) << "\" Name=\"" << names[d] << "\" format=\"ascii\"";
126  if (timestep)
127  out << " TimeStep=\"" << *timestep << "\"";
128  out << ">\n";
129  this->writeValuesAscii(out, coordinates[d]);
130  out << "</DataArray>\n";
131  }
132  }
133  else { // Vtk::FormatTypes::APPENDED format
134  for (std::size_t j = 0; j < 3; ++j) {
135  out << "<DataArray type=\"" << to_string(datatype_) << "\" Name=\"" << names[j] << "\" format=\"appended\"";
136  if (timestep)
137  out << " TimeStep=\"" << *timestep << "\"";
138  out << " offset=";
139  offsets.push_back(out.tellp());
140  out << std::string(std::numeric_limits<std::uint64_t>::digits10 + 2, ' ');
141  out << "/>\n";
142  }
143  }
144 }
145 
146 
147 template <class GV, class DC>
148 void VtkRectilinearGridWriter<GV,DC>
149  ::writeGridAppended (std::ofstream& out, std::vector<std::uint64_t>& blocks) const
150 {
151  assert(is_a(format_, Vtk::FormatTypes::APPENDED) && "Function should by called only in appended mode!\n");
152 
153  // write coordinates along axis
154  Vtk::mapDataTypes<std::is_floating_point, std::is_integral>(datatype_, headertype_,
155  [&](auto f, auto h) {
156  using F = typename decltype(f)::type;
157  using H = typename decltype(h)::type;
158  auto coordinates = dataCollector_->template coordinates<F>();
159  blocks.push_back(this->template writeValuesAppended<H>(out, coordinates[0]));
160  blocks.push_back(this->template writeValuesAppended<H>(out, coordinates[1]));
161  blocks.push_back(this->template writeValuesAppended<H>(out, coordinates[2]));
162  });
163 }
164 
165 } // end namespace Dune
Definition: writer.hh:13
std::string to_string(Vtk::FormatTypes type)
Definition: types.cc:12
constexpr bool is_a(E a, Integer b)
Definition: enum.hh:12
std::string join(InputIter first, InputIter end, std::string sep=" ")
Definition: string.hh:110