1 /*---------------------------------------------------------------------------*\
3 \\ / F ield | OpenFOAM: The Open Source CFD Toolbox
5 \\ / A nd | Copyright (C) 1991-2009 OpenCFD Ltd.
7 -------------------------------------------------------------------------------
9 This file is part of OpenFOAM.
11 OpenFOAM is free software; you can redistribute it and/or modify it
12 under the terms of the GNU General Public License as published by the
13 Free Software Foundation; either version 2 of the License, or (at your
14 option) any later version.
16 OpenFOAM is distributed in the hope that it will be useful, but WITHOUT
17 ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
18 FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
21 You should have received a copy of the GNU General Public License
22 along with OpenFOAM; if not, write to the Free Software Foundation,
23 Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
27 \*---------------------------------------------------------------------------*/
31 #include "cellModeller.H"
33 #include "vtkUnstructuredGrid.h"
34 #include "vtkCellArray.h"
36 #include "vtkFoamInsertNextPoint.H"
38 // * * * * * * * * * * * * * * * Member Functions * * * * * * * * * * * * * //
40 void Foam::vtkFoam::addInternalMesh
43 vtkUnstructuredGrid* vtkMesh
46 SetName(vtkMesh, "Internal Mesh");
48 // Number of additional points needed by the decomposition of polyhedra
51 // Number of additional cells generated by the decomposition of polyhedra
54 const cellModel& tet = *(cellModeller::lookup("tet"));
55 const cellModel& pyr = *(cellModeller::lookup("pyr"));
56 const cellModel& prism = *(cellModeller::lookup("prism"));
57 const cellModel& wedge = *(cellModeller::lookup("wedge"));
58 const cellModel& tetWedge = *(cellModeller::lookup("tetWedge"));
59 const cellModel& hex = *(cellModeller::lookup("hex"));
61 // Scan for cells which need to be decomposed and count additional points
65 Info<< "building cell-shapes" << endl;
67 const cellShapeList& cellShapes = mesh.cellShapes();
71 Info<< "scanning" << endl;
74 forAll(cellShapes, cellI)
76 const cellModel& model = cellShapes[cellI].model();
88 const cell& cFaces = mesh.cells()[cellI];
90 forAll(cFaces, cFaceI)
92 const face& f = mesh.faces()[cFaces[cFaceI]];
94 label nFacePoints = f.size();
96 label nQuads = (nFacePoints - 2)/2;
97 label nTris = (nFacePoints - 2)%2;
98 nAddCells += nQuads + nTris;
106 // Set size of additional point addressing array
107 // (from added point to original cell)
108 addPointCellLabels_.setSize(nAddPoints);
110 // Set size of additional cells mapping array
111 // (from added cell to original cell)
112 superCells_.setSize(mesh.nCells() + nAddCells);
116 Info<< "converting points" << endl;
119 // Convert Foam mesh vertices to VTK
120 vtkPoints *vtkpoints = vtkPoints::New();
121 vtkpoints->Allocate(mesh.nPoints() + nAddPoints);
123 const Foam::pointField& points = mesh.points();
127 vtkFoamInsertNextPoint(vtkpoints, points[i]);
132 Info<< "converting cells" << endl;
135 vtkMesh->Allocate(mesh.nCells() + nAddCells);
137 // Set counters for additional points and additional cells
138 label api = 0, aci = 0;
140 forAll(cellShapes, celli)
142 const cellShape& cellShape = cellShapes[celli];
143 const cellModel& cellModel = cellShape.model();
145 superCells_[aci++] = celli;
147 if (cellModel == tet)
149 vtkMesh->InsertNextCell
153 const_cast<int*>(cellShape.begin())
156 else if (cellModel == pyr)
158 vtkMesh->InsertNextCell
162 const_cast<int*>(cellShape.begin())
165 else if (cellModel == prism)
167 vtkMesh->InsertNextCell
171 const_cast<int*>(cellShape.begin())
174 else if (cellModel == tetWedge)
176 // Treat as squeezed prism
179 vtkVerts[0] = cellShape[0];
180 vtkVerts[1] = cellShape[2];
181 vtkVerts[2] = cellShape[1];
182 vtkVerts[3] = cellShape[3];
183 vtkVerts[4] = cellShape[4];
184 vtkVerts[5] = cellShape[4];
186 vtkMesh->InsertNextCell(VTK_WEDGE, 6, vtkVerts);
188 else if (cellModel == wedge)
190 // Treat as squeezed hex
193 vtkVerts[0] = cellShape[0];
194 vtkVerts[1] = cellShape[1];
195 vtkVerts[2] = cellShape[2];
196 vtkVerts[3] = cellShape[2];
197 vtkVerts[4] = cellShape[3];
198 vtkVerts[5] = cellShape[4];
199 vtkVerts[6] = cellShape[5];
200 vtkVerts[7] = cellShape[6];
202 vtkMesh->InsertNextCell(VTK_HEXAHEDRON, 8, vtkVerts);
204 else if (cellModel == hex)
206 vtkMesh->InsertNextCell
210 const_cast<int*>(cellShape.begin())
215 // Polyhedral cell. Decompose into tets + prisms.
217 // Mapping from additional point to cell
218 addPointCellLabels_[api] = celli;
220 // Insert the new vertex from the cell-centre
221 label newVertexLabel = mesh.nPoints() + api;
222 vtkFoamInsertNextPoint(vtkpoints, mesh.C()[celli]);
224 // Whether to insert cell in place of original or not.
225 bool substituteCell = true;
227 const labelList& cFaces = mesh.cells()[celli];
229 forAll(cFaces, cFaceI)
231 const face& f = mesh.faces()[cFaces[cFaceI]];
233 label nFacePoints = f.size();
235 label nQuads = (nFacePoints - 2)/2;
236 label nTris = (nFacePoints - 2)%2;
240 for (label quadi=0; quadi<nQuads; quadi++)
242 label thisCellI = -1;
247 substituteCell = false;
251 thisCellI = mesh.nCells() + aci;
252 superCells_[aci++] = celli;
256 addVtkVerts[0] = f[0];
257 addVtkVerts[1] = f[qpi + 1];
258 addVtkVerts[2] = f[qpi + 2];
259 addVtkVerts[3] = f[qpi + 3];
260 addVtkVerts[4] = newVertexLabel;
261 vtkMesh->InsertNextCell(VTK_PYRAMID, 5, addVtkVerts);
268 label thisCellI = -1;
273 substituteCell = false;
277 thisCellI = mesh.nCells() + aci;
278 superCells_[aci++] = celli;
282 addVtkVerts[0] = f[0];
283 addVtkVerts[1] = f[qpi + 1];
284 addVtkVerts[2] = f[qpi + 2];
285 addVtkVerts[3] = newVertexLabel;
286 vtkMesh->InsertNextCell(VTK_TETRA, 4, addVtkVerts);
294 vtkMesh->SetPoints(vtkpoints);
299 // ************************************************************************* //