1 /*---------------------------------------------------------------------------*\
3 \\ / F ield | OpenFOAM: The Open Source CFD Toolbox
5 \\ / A nd | Copyright (C) 1991-2008 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
26 Reader module for Fieldview9 to read Foam mesh&data.
27 Creates new 'fvbin' type executable which needs to be installed in place
30 Implements a reader for combined mesh&results on an unstructured mesh.
32 See Fieldview Release 9 Reference Manual and coding in user/ directory
33 of the Fieldview release.
35 \*---------------------------------------------------------------------------*/
38 #include "IOobjectList.H"
39 #include "GeometricField.H"
40 #include "pointFields.H"
41 #include "volPointInterpolation.H"
42 #include "readerDatabase.H"
43 #include "wallPolyPatch.H"
45 #include "cellModeller.H"
47 // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
51 // Define various Fieldview constants and prototypes
53 #include "fv_reader_tags.h"
55 static const int FVHEX = 2;
56 static const int FVPRISM = 3;
57 static const int FVPYRAMID = 4;
58 static const int FVTET = 1;
59 static const int ITYPE = 1;
61 unsigned int fv_encode_elem_header(int elem_type, int wall_info[]);
62 void time_step_get_value(float*, int, int*, float*, int*);
63 void fv_error_msg(const char*, const char*);
65 void reg_single_unstruct_reader
70 char*, int*, int*, int*, int*, int*, int*,
71 int[], int*, char[][80], int[], int*, char[][80], int*
75 int*, int*, int*, float[], int*, float[], int*
79 int create_tet(const int, const int[8], const int[]);
80 int create_pyramid(const int, const int[8], const int[]);
81 int create_prism(const int, const int[8], const int[]);
82 int create_hex(const int, const int[8], const int[]);
84 typedef unsigned char uChar;
85 extern uChar create_bndry_face_buffered
95 * just define empty readers here for ease of linking.
96 * Comment out if you have doubly defined linking error on this symbol
98 void ftn_register_data_readers()
102 * just define empty readers here for ease of linking.
103 * Comment out if you have doubly defined linking error on this symbol
105 void ftn_register_functions()
109 * just define empty readers here for ease of linking.
110 * Comment out if you have doubly defined linking error on this symbol
112 void register_functions()
116 // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
120 // Storage for all Foam state (mainly database & mesh)
122 static readerDatabase db_;
125 // Write fv error message.
126 static void errorMsg(const string& msg)
128 fv_error_msg("Foam Reader", msg.c_str());
132 // Simple check if directory is valid case directory.
133 static bool validCase(const fileName& rootAndCase)
135 //if (dir(rootAndCase/"system") && dir(rootAndCase/"constant"))
136 if (dir(rootAndCase/"constant"))
147 // Check whether case has topo changes by looking back from last time
148 // to first directory with polyMesh/cells.
149 static bool hasTopoChange(const instantList& times)
151 label lastIndex = times.size()-1;
153 const Time& runTime = db_.runTime();
155 // Only set time; do not update mesh.
156 runTime.setTime(times[lastIndex], lastIndex);
158 fileName facesInst(runTime.findInstance(polyMesh::meshSubDir, "faces"));
160 // See if cellInst is constant directory. Note extra .name() is for
161 // parallel cases when runTime.constant is '../constant'
162 if (facesInst != runTime.constant().name())
164 Info<< "Found cells file in " << facesInst << " so case has "
165 << "topological changes" << endl;
171 Info<< "Found cells file in " << facesInst << " so case has "
172 << "no topological changes" << endl;
179 static bool selectTime(const instantList& times, int* iret)
181 List<float> fvTimes(2*times.size());
185 fvTimes[2*timeI] = float(timeI);
186 fvTimes[2*timeI+1] = float(times[timeI].value());
195 time_step_get_value(fvTimes.begin(), times.size(), &istep, &time, iret);
199 errorMsg("Out of memory.");
210 errorMsg("Unspecified error.");
214 Info<< "Selected timeStep:" << istep << " time:" << scalar(time) << endl;
216 // Set time and load mesh.
217 db_.setTime(times[istep], istep);
223 // Gets (names of) all fields in all timesteps.
224 static void createFieldNames
227 const instantList& Times,
231 // From foamToFieldView9/getFieldNames.H:
233 HashSet<word> volScalarHash;
234 HashSet<word> volVectorHash;
235 HashSet<word> surfScalarHash;
236 HashSet<word> surfVectorHash;
238 if (setName.size() == 0)
242 const word& timeName = Times[timeI].name();
244 // Add all fields to hashtable
245 IOobjectList objects(runTime, timeName);
247 wordList vsNames(objects.names(volScalarField::typeName));
249 forAll(vsNames, fieldI)
251 volScalarHash.insert(vsNames[fieldI]);
254 wordList vvNames(objects.names(volVectorField::typeName));
256 forAll(vvNames, fieldI)
258 volVectorHash.insert(vvNames[fieldI]);
262 db_.setFieldNames(volScalarHash.toc(), volVectorHash.toc());
266 // Appends interpolated values of fieldName to vars array.
267 static void storeScalarField
269 const volPointInterpolation& pInterp,
270 const word& fieldName,
275 label nPoints = db_.mesh().nPoints();
276 label nTotPoints = nPoints + db_.polys().size();
282 db_.runTime().timeName(),
288 if (ioHeader.headerOk())
290 Info<< "Storing " << nTotPoints << " of interpolated " << fieldName
293 volScalarField field(ioHeader, db_.mesh());
295 pointScalarField psf(pInterp.interpolate(field));
299 vars[pointI++] = float(psf[i]);
302 const labelList& polys = db_.polys();
306 label cellI = polys[i];
308 vars[pointI++] = float(field[cellI]);
313 Info<< "Storing " << nTotPoints << " of dummy values of " << fieldName
316 for(label i = 0; i < nPoints; i++)
318 vars[pointI++] = 0.0;
321 const labelList& polys = db_.polys();
325 vars[pointI++] = 0.0;
331 // Appends interpolated values of fieldName to vars array.
332 static void storeVectorField
334 const volPointInterpolation& pInterp,
335 const word& fieldName,
340 label nPoints = db_.mesh().nPoints();
342 label nTotPoints = nPoints + db_.polys().size();
348 db_.runTime().timeName(),
354 if (ioHeader.headerOk())
356 Info<< "Storing " << nTotPoints << " of interpolated " << fieldName
359 volVectorField field(ioHeader, db_.mesh());
361 for (direction d = 0; d < vector::nComponents; d++)
363 tmp<volScalarField> tcomp = field.component(d);
364 const volScalarField& comp = tcomp();
366 pointScalarField psf(pInterp.interpolate(comp));
370 vars[pointI++] = float(psf[i]);
373 const labelList& polys = db_.polys();
377 label cellI = polys[i];
379 vars[pointI++] = float(comp[cellI]);
385 Info<< "Storing " << nTotPoints << " of dummy values of " << fieldName
388 for (direction d = 0; d < vector::nComponents; d++)
390 for(label i = 0; i < nPoints; i++)
392 vars[pointI++] = 0.0;
395 const labelList& polys = db_.polys();
399 vars[pointI++] = 0.0;
406 // Returns Fieldview face_type of mesh face faceI.
407 static label getFvType(const polyMesh& mesh, const label faceI)
409 return mesh.boundaryMesh().whichPatch(faceI) + 1;
413 // Returns Fieldview face_type of face f.
414 static label getFaceType
416 const polyMesh& mesh,
417 const labelList& faceLabels,
421 // Search in subset faceLabels of faces for index of face f.
422 const faceList& faces = mesh.faces();
424 forAll(faceLabels, i)
426 label faceI = faceLabels[i];
428 if (f == faces[faceI])
430 // Convert patch to Fieldview face_type.
431 return getFvType(mesh, faceI);
435 FatalErrorIn("getFaceType")
436 << "Cannot find face " << f << " in mesh face subset " << faceLabels
437 << abort(FatalError);
443 // Returns Fieldview face_types for set of faces
444 static labelList getFaceTypes
446 const polyMesh& mesh,
447 const labelList& cellFaces,
448 const faceList& cellShapeFaces
451 labelList faceLabels(cellShapeFaces.size());
453 forAll(cellShapeFaces, i)
455 faceLabels[i] = getFaceType(mesh, cellFaces, cellShapeFaces[i]);
462 * Callback for querying file contents. Taken from user/user_unstruct_combined.f
464 void user_query_file_function
467 char* fname, /* filename */
468 int* lenf, /* length of fName */
469 int* iunit, /* fortran unit to use */
470 int* max_grids, /* maximum number of grids allowed */
471 int* max_face_types,/* maximum number of face types allowed */
472 int* max_vars, /* maximum number of result variables allowed per */
476 int* num_grids, /* number of grids that will be read from data file */
477 int num_nodes[], /* (array of node counts for all grids) */
478 int* num_face_types, /* number of special face types */
479 char face_type_names[][80], /* array of face-type names */
480 int wall_flags[], /* array of flags for the "wall" behavior */
481 int* num_vars, /* number of result variables per grid point */
482 char var_names[][80], /* array of variable names */
483 int* iret /* return value */
486 fprintf(stderr, "\n** user_query_file_function\n");
488 string rootAndCaseString(fname, *lenf);
490 fileName rootAndCase(rootAndCaseString);
494 if (!validCase(rootAndCase))
496 setName = rootAndCase.name();
498 rootAndCase = rootAndCase.path();
500 word setDir = rootAndCase.name();
502 rootAndCase = rootAndCase.path();
504 word meshDir = rootAndCase.name();
506 rootAndCase = rootAndCase.path();
507 rootAndCase = rootAndCase.path();
512 && meshDir == polyMesh::typeName
513 && validCase(rootAndCase)
516 // Valid set (hopefully - cannot check contents of setName yet).
522 "Could not find system/ and constant/ directory in\n"
524 + "\nPlease select a Foam case directory."
534 fileName rootDir(rootAndCase.path());
536 fileName caseName(rootAndCase.name());
538 // handle trailing '/'
539 if (caseName.size() == 0)
541 caseName = rootDir.name();
542 rootDir = rootDir.path();
546 Info<< "rootDir : " << rootDir << endl
547 << "caseName : " << caseName << endl
548 << "setName : " << setName << endl;
551 // Get/reuse database and mesh
554 bool caseChanged = db_.setRunTime(rootDir, caseName, setName);
561 instantList Times = db_.runTime().times();
563 // If topo case set database time and update mesh.
564 if (hasTopoChange(Times))
566 if (!selectTime(Times, iret))
571 else if (caseChanged)
573 // Load mesh (if case changed) to make sure we have nPoints etc.
579 // Set output variables
584 const fvMesh& mesh = db_.mesh();
586 label nTotPoints = mesh.nPoints() + db_.polys().size();
588 num_nodes[0] = nTotPoints;
590 Info<< "setting num_nodes:" << num_nodes[0] << endl;
592 Info<< "setting num_face_types:" << mesh.boundary().size() << endl;
594 *num_face_types = mesh.boundary().size();
596 if (*num_face_types > *max_face_types)
598 errorMsg("Too many patches. FieldView limit:" + name(*max_face_types));
606 forAll(mesh.boundaryMesh(), patchI)
608 const polyPatch& patch = mesh.boundaryMesh()[patchI];
610 strcpy(face_type_names[patchI], patch.name().c_str());
612 if (isType<wallPolyPatch>(patch))
614 wall_flags[patchI] = 1;
618 wall_flags[patchI] = 0;
620 Info<< "Patch " << patch.name() << " is wall:"
621 << wall_flags[patchI] << endl;
624 //- Find all volFields and add them to database
625 createFieldNames(db_.runTime(), Times, setName);
627 *num_vars = db_.volScalarNames().size() + 3*db_.volVectorNames().size();
629 if (*num_vars > *max_vars)
631 errorMsg("Too many variables. FieldView limit:" + name(*max_vars));
641 forAll(db_.volScalarNames(), i)
643 const word& fieldName = db_.volScalarNames()[i];
645 const word& fvName = db_.getFvName(fieldName);
647 strcpy(var_names[nameI++], fvName.c_str());
650 forAll(db_.volVectorNames(), i)
652 const word& fieldName = db_.volVectorNames()[i];
654 const word& fvName = db_.getFvName(fieldName);
656 strcpy(var_names[nameI++], (fvName + "x;" + fvName).c_str());
657 strcpy(var_names[nameI++], (fvName + "y").c_str());
658 strcpy(var_names[nameI++], (fvName + "z").c_str());
666 * Callback for reading timestep. Taken from user/user_unstruct_combined.f
668 void user_read_one_grid_function
670 int* iunit, /* in: fortran unit number */
671 int* igrid, /* in: grid number to read */
672 int* nodecnt, /* in: number of nodes to read */
673 float xyz[], /* out: coordinates of nodes: x1..xN y1..yN z1..zN */
674 int* num_vars, /* in: number of results per node */
675 float vars[], /* out: values per node */
676 int* iret /* out: return value */
679 fprintf(stderr, "\n** user_read_one_grid_function\n");
683 errorMsg("Illegal grid number " + Foam::name(*igrid));
691 instantList Times = db_.runTime().times();
693 // Set database time and update mesh.
694 // Note: this should not be nessecary here. We already have the correct
695 // time set and mesh loaded. This is only nessecary because Fieldview
696 // otherwise thinks the case is non-transient.
697 if (!selectTime(Times, iret))
703 const fvMesh& mesh = db_.mesh();
705 // With mesh now loaded check for change in number of points.
706 label nTotPoints = mesh.nPoints() + db_.polys().size();
708 if (*nodecnt != nTotPoints)
712 "nodecnt differs from number of points in mesh.\nnodecnt:"
713 + Foam::name(*nodecnt)
715 + Foam::name(nTotPoints)
727 != (db_.volScalarNames().size() + 3*db_.volVectorNames().size())
730 errorMsg("Illegal number of variables " + name(*num_vars));
741 const pointField& points = mesh.points();
744 int yIndex = xIndex + nTotPoints;
745 int zIndex = yIndex + nTotPoints;
747 // Add mesh points first.
748 forAll(points, pointI)
750 xyz[xIndex++] = points[pointI].x();
751 xyz[yIndex++] = points[pointI].y();
752 xyz[zIndex++] = points[pointI].z();
755 // Add cell centres of polys
756 const pointField& ctrs = mesh.cellCentres();
758 const labelList& polys = db_.polys();
762 label cellI = polys[i];
764 xyz[xIndex++] = ctrs[cellI].x();
765 xyz[yIndex++] = ctrs[cellI].y();
766 xyz[zIndex++] = ctrs[cellI].z();
771 // Define elements by calling fv routines
774 static const cellModel& tet = *(cellModeller::lookup("tet"));
775 static const cellModel& tetWedge = *(cellModeller::lookup("tetWedge"));
776 static const cellModel& pyr = *(cellModeller::lookup("pyr"));
777 static const cellModel& prism = *(cellModeller::lookup("prism"));
778 static const cellModel& wedge = *(cellModeller::lookup("wedge"));
779 static const cellModel& hex = *(cellModeller::lookup("hex"));
780 //static const cellModel& splitHex = *(cellModeller::lookup("splitHex"));
792 const cellShapeList& cellShapes = mesh.cellShapes();
793 const faceList& faces = mesh.faces();
794 const cellList& cells = mesh.cells();
795 const labelList& owner = mesh.faceOwner();
796 label nPoints = mesh.nPoints();
798 // Fieldview face_types array with all faces marked as internal.
799 labelList internalFaces(6, 0);
801 // Mark all cells next to boundary so we don't have to calculate
802 // wall_types for internal cells and can just pass internalFaces.
803 boolList wallCell(mesh.nCells(), false);
805 label nWallCells = 0;
807 for (label faceI = mesh.nInternalFaces(); faceI < mesh.nFaces(); faceI++)
809 label cellI = owner[faceI];
811 if (!wallCell[cellI])
813 wallCell[cellI] = true;
821 forAll(cellShapes, cellI)
823 const cellShape& cellShape = cellShapes[cellI];
824 const cellModel& cellModel = cellShape.model();
825 const cell& cellFaces = cells[cellI];
829 if (cellModel == tet)
831 tetVerts[0] = cellShape[3] + 1;
832 tetVerts[1] = cellShape[0] + 1;
833 tetVerts[2] = cellShape[1] + 1;
834 tetVerts[3] = cellShape[2] + 1;
838 labelList faceTypes =
839 getFaceTypes(mesh, cellFaces, cellShape.faces());
841 tetFaces[0] = faceTypes[2];
842 tetFaces[1] = faceTypes[3];
843 tetFaces[2] = faceTypes[0];
844 tetFaces[3] = faceTypes[1];
846 istat = create_tet(ITYPE, tetVerts, tetFaces);
850 // All faces internal so use precalculated zero.
851 istat = create_tet(ITYPE, tetVerts, internalFaces.begin());
854 else if (cellModel == tetWedge)
856 prismVerts[0] = cellShape[0] + 1;
857 prismVerts[1] = cellShape[3] + 1;
858 prismVerts[2] = cellShape[4] + 1;
859 prismVerts[3] = cellShape[1] + 1;
860 prismVerts[4] = cellShape[4] + 1;
861 prismVerts[5] = cellShape[2] + 1;
865 labelList faceTypes =
866 getFaceTypes(mesh, cellFaces, cellShape.faces());
868 prismFaces[0] = faceTypes[1];
869 prismFaces[1] = faceTypes[2];
870 prismFaces[2] = faceTypes[3];
871 prismFaces[3] = faceTypes[0];
872 prismFaces[4] = faceTypes[3];
874 istat = create_prism(ITYPE, prismVerts, prismFaces);
878 istat = create_prism(ITYPE, prismVerts, internalFaces.begin());
881 else if (cellModel == pyr)
883 pyrVerts[0] = cellShape[0] + 1;
884 pyrVerts[1] = cellShape[1] + 1;
885 pyrVerts[2] = cellShape[2] + 1;
886 pyrVerts[3] = cellShape[3] + 1;
887 pyrVerts[4] = cellShape[4] + 1;
891 labelList faceTypes =
892 getFaceTypes(mesh, cellFaces, cellShape.faces());
894 pyrFaces[0] = faceTypes[0];
895 pyrFaces[1] = faceTypes[3];
896 pyrFaces[2] = faceTypes[2];
897 pyrFaces[3] = faceTypes[1];
898 pyrFaces[4] = faceTypes[4];
900 istat = create_pyramid(ITYPE, pyrVerts, pyrFaces);
904 istat = create_pyramid(ITYPE, pyrVerts, internalFaces.begin());
907 else if (cellModel == prism)
909 prismVerts[0] = cellShape[0] + 1;
910 prismVerts[1] = cellShape[3] + 1;
911 prismVerts[2] = cellShape[4] + 1;
912 prismVerts[3] = cellShape[1] + 1;
913 prismVerts[4] = cellShape[5] + 1;
914 prismVerts[5] = cellShape[2] + 1;
918 labelList faceTypes =
919 getFaceTypes(mesh, cellFaces, cellShape.faces());
921 prismFaces[0] = faceTypes[4];
922 prismFaces[1] = faceTypes[2];
923 prismFaces[2] = faceTypes[3];
924 prismFaces[3] = faceTypes[0];
925 prismFaces[4] = faceTypes[1];
927 istat = create_prism(ITYPE, prismVerts, prismFaces);
931 istat = create_prism(ITYPE, prismVerts, internalFaces.begin());
934 else if (cellModel == wedge)
936 hexVerts[0] = cellShape[0] + 1;
937 hexVerts[1] = cellShape[1] + 1;
938 hexVerts[2] = cellShape[0] + 1;
939 hexVerts[3] = cellShape[2] + 1;
940 hexVerts[4] = cellShape[3] + 1;
941 hexVerts[5] = cellShape[4] + 1;
942 hexVerts[6] = cellShape[6] + 1;
943 hexVerts[7] = cellShape[5] + 1;
947 labelList faceTypes =
948 getFaceTypes(mesh, cellFaces, cellShape.faces());
950 hexFaces[0] = faceTypes[2];
951 hexFaces[1] = faceTypes[3];
952 hexFaces[2] = faceTypes[0];
953 hexFaces[3] = faceTypes[1];
954 hexFaces[4] = faceTypes[4];
955 hexFaces[5] = faceTypes[5];
957 istat = create_hex(ITYPE, hexVerts, hexFaces);
961 istat = create_hex(ITYPE, hexVerts, internalFaces.begin());
964 else if (cellModel == hex)
966 hexVerts[0] = cellShape[0] + 1;
967 hexVerts[1] = cellShape[1] + 1;
968 hexVerts[2] = cellShape[3] + 1;
969 hexVerts[3] = cellShape[2] + 1;
970 hexVerts[4] = cellShape[4] + 1;
971 hexVerts[5] = cellShape[5] + 1;
972 hexVerts[6] = cellShape[7] + 1;
973 hexVerts[7] = cellShape[6] + 1;
977 labelList faceTypes =
978 getFaceTypes(mesh, cellFaces, cellShape.faces());
980 hexFaces[0] = faceTypes[0];
981 hexFaces[1] = faceTypes[1];
982 hexFaces[2] = faceTypes[4];
983 hexFaces[3] = faceTypes[5];
984 hexFaces[4] = faceTypes[2];
985 hexFaces[5] = faceTypes[3];
987 istat = create_hex(ITYPE, hexVerts, hexFaces);
991 istat = create_hex(ITYPE, hexVerts, internalFaces.begin());
996 forAll(cellFaces, cFaceI)
998 label faceI = cellFaces[cFaceI];
1000 // Get Fieldview facetype (internal/on patch)
1001 label fvFaceType = getFvType(mesh, faceI);
1003 const face& f = faces[faceI];
1005 // Indices into storage
1009 // Storage for triangles and quads created by face
1010 // decomposition (sized for worst case)
1011 faceList quadFaces((f.size() - 2)/2);
1012 faceList triFaces(f.size() - 2);
1023 // Label of cell centre in fv point list.
1024 label polyCentrePoint = nPoints + nPolys;
1026 for (label i=0; i<nTris; i++)
1028 if (cellI == owner[faceI])
1030 tetVerts[0] = triFaces[i][0] + 1;
1031 tetVerts[1] = triFaces[i][1] + 1;
1032 tetVerts[2] = triFaces[i][2] + 1;
1033 tetVerts[3] = polyCentrePoint + 1;
1037 tetVerts[0] = triFaces[i][2] + 1;
1038 tetVerts[1] = triFaces[i][1] + 1;
1039 tetVerts[2] = triFaces[i][0] + 1;
1040 tetVerts[3] = polyCentrePoint + 1;
1043 if (wallCell[cellI])
1045 // Outside face is one without polyCentrePoint
1046 tetFaces[0] = fvFaceType;
1051 istat = create_tet(ITYPE, tetVerts, tetFaces);
1060 internalFaces.begin()
1065 for (label i=0; i<nQuads; i++)
1067 if (cellI == owner[faceI])
1069 pyrVerts[0] = quadFaces[i][3] + 1;
1070 pyrVerts[1] = quadFaces[i][2] + 1;
1071 pyrVerts[2] = quadFaces[i][1] + 1;
1072 pyrVerts[3] = quadFaces[i][0] + 1;
1073 pyrVerts[4] = polyCentrePoint + 1;
1078 pyrVerts[0] = quadFaces[i][0] + 1;
1079 pyrVerts[1] = quadFaces[i][1] + 1;
1080 pyrVerts[2] = quadFaces[i][2] + 1;
1081 pyrVerts[3] = quadFaces[i][3] + 1;
1082 pyrVerts[4] = polyCentrePoint + 1;
1085 if (wallCell[cellI])
1087 // Outside face is one without polyCentrePoint
1088 pyrFaces[0] = fvFaceType;
1094 istat = create_pyramid(ITYPE, pyrVerts, pyrFaces);
1103 internalFaces.begin()
1110 errorMsg("Error during adding cell " + name(cellI));
1123 errorMsg("Error during adding cell " + name(cellI));
1137 pointMesh pMesh(mesh);
1139 volPointInterpolation pInterp(mesh, pMesh);
1143 forAll(db_.volScalarNames(), i)
1145 const word& fieldName = db_.volScalarNames()[i];
1147 storeScalarField(pInterp, fieldName, vars, pointI);
1151 forAll(db_.volVectorNames(), i)
1153 const word& fieldName = db_.volVectorNames()[i];
1155 storeVectorField(pInterp, fieldName, vars, pointI);
1158 // Return without failure.
1163 void register_data_readers()
1167 ** You should edit this file to "register" a user-defined data
1168 ** reader with FIELDVIEW, if the user functions being registered
1169 ** here are written in C.
1170 ** You should edit "ftn_register_data_readers.f" if the user functions
1171 ** being registered are written in Fortran.
1172 ** In either case, the user functions being registered may call other
1173 ** functions written in either language (C or Fortran); only the
1174 ** language of the "query" and "read" functions referenced here matters
1177 ** The following shows a sample user-defined data reader being
1178 ** "registered" with FIELDVIEW.
1180 ** The "extern void" declarations should match the names of the
1181 ** query and grid-reading functions you are providing. It is
1182 ** strongly suggested that all such names begin with "user" so
1183 ** as not to conflict with global names in FIELDVIEW.
1185 ** You may call any combination of the data reader registration
1186 ** functions shown below ("register_two_file_reader" and/or
1187 ** "register_single_file_reader" and/or "register_single_unstruct_reader"
1188 ** and/or "register_double_unstruct_reader") as many times as you like,
1189 ** in order to create several different data readers. Each data reader
1190 ** should of course have different "query" and "read" functions, all of
1191 ** which should also appear in "extern void" declarations.
1196 ** like this for combined unstructured grids & results in a single file
1198 reg_single_unstruct_reader (
1199 "Foam Reader", /* title you want for data reader */
1200 user_query_file_function, /* whatever you called this */
1201 user_read_one_grid_function /* whatever you called this */
1211 // ************************************************************************* //