Branch data Line data Source code
1 : : /**
2 : : * MOAB, a Mesh-Oriented datABase, is a software component for creating,
3 : : * storing and accessing finite element mesh data.
4 : : *
5 : : * Copyright 2004 Sandia Corporation. Under the terms of Contract
6 : : * DE-AC04-94AL85000 with Sandia Corporation, the U.S. Government
7 : : * retains certain rights in this software.
8 : : *
9 : : * This library is free software; you can redistribute it and/or
10 : : * modify it under the terms of the GNU Lesser General Public
11 : : * License as published by the Free Software Foundation; either
12 : : * version 2.1 of the License, or (at your option) any later version.
13 : : *
14 : : */
15 : :
16 : : #ifdef WIN32
17 : : #ifdef _DEBUG
18 : : // turn off warnings that say they debugging identifier has been truncated
19 : : // this warning comes up when using some STL containers
20 : : #pragma warning( disable : 4786 )
21 : : #endif
22 : : #endif
23 : :
24 : : #include "WriteSmf.hpp"
25 : :
26 : : #include <fstream>
27 : : #include <iostream>
28 : : #include <stdio.h>
29 : : #include <assert.h>
30 : : #include <vector>
31 : : #include <set>
32 : : #include <iterator>
33 : : #include <algorithm>
34 : :
35 : : #include "moab/Interface.hpp"
36 : : #include "moab/Range.hpp"
37 : : #include "moab/CN.hpp"
38 : : #include "MBTagConventions.hpp"
39 : : #include "moab/WriteUtilIface.hpp"
40 : : #include "Internals.hpp"
41 : : #include "moab/FileOptions.hpp"
42 : :
43 : : namespace moab
44 : : {
45 : :
46 : : const int DEFAULT_PRECISION = 10;
47 : : // const bool DEFAULT_STRICT = true;
48 : :
49 : 0 : WriterIface* WriteSmf::factory( Interface* iface )
50 : : {
51 [ # # ]: 0 : return new WriteSmf( iface );
52 : : }
53 : :
54 : 0 : WriteSmf::WriteSmf( Interface* impl ) : mbImpl( impl ), writeTool( 0 )
55 : : {
56 [ # # ]: 0 : assert( impl != NULL );
57 [ # # ]: 0 : impl->query_interface( writeTool );
58 : 0 : }
59 : :
60 : 0 : WriteSmf::~WriteSmf()
61 : : {
62 : 0 : mbImpl->release_interface( writeTool );
63 [ # # ]: 0 : }
64 : :
65 : 0 : ErrorCode WriteSmf::write_file( const char* file_name, const bool overwrite, const FileOptions& opts,
66 : : const EntityHandle* output_list, const int num_sets,
67 : : const std::vector< std::string >& /* qa_list */, const Tag* /* tag_list */,
68 : : int /* num_tags */, int /* export_dimension */ )
69 : : {
70 : : ErrorCode rval;
71 : :
72 : : // Get precision for node coordinates
73 : : int precision;
74 [ # # ][ # # ]: 0 : if( MB_SUCCESS != opts.get_int_option( "PRECISION", precision ) ) precision = DEFAULT_PRECISION;
75 : :
76 : : // Honor overwrite flag
77 [ # # ]: 0 : if( !overwrite )
78 : : {
79 [ # # ]: 0 : rval = writeTool->check_doesnt_exist( file_name );
80 [ # # ]: 0 : if( MB_SUCCESS != rval ) return rval;
81 : : }
82 : :
83 : : // Create file
84 [ # # ][ # # ]: 0 : std::ofstream file( file_name );
85 [ # # ][ # # ]: 0 : if( !file ) { MB_SET_ERR( MB_FILE_WRITE_ERROR, "Could not open file: " << file_name ); }
[ # # ][ # # ]
[ # # ][ # # ]
[ # # ][ # # ]
86 [ # # ]: 0 : file.precision( precision );
87 : :
88 : : // Get entities to write
89 [ # # ]: 0 : Range triangles;
90 [ # # ][ # # ]: 0 : if( !output_list || !num_sets )
91 : : {
92 [ # # ]: 0 : rval = mbImpl->get_entities_by_type( 0, MBTRI, triangles, false );
93 [ # # ]: 0 : if( MB_SUCCESS != rval ) return rval;
94 : :
95 : : // Somehow get all the nodes from this range, order them, uniquify, then use binary search
96 : : }
97 : : else
98 : : {
99 : : // Get all triangles from output sets
100 [ # # ]: 0 : for( int i = 0; i < num_sets; i++ )
101 [ # # ]: 0 : rval = mbImpl->get_entities_by_type( output_list[i], MBTRI, triangles, false );
102 : : }
103 : : // Use an array with all the connectivities in the triangles; it will be converted later to ints
104 [ # # ]: 0 : int numTriangles = triangles.size();
105 : 0 : int array_alloc = 3 * numTriangles; // Allocated size of 'array'
106 [ # # ][ # # ]: 0 : EntityHandle* array = new EntityHandle[array_alloc]; // ptr to working array of result handles
107 : : // Fill up array with node handles; reorder and uniquify
108 [ # # ]: 0 : if( !array ) return MB_MEMORY_ALLOCATION_FAILED;
109 : 0 : int fillA = 0;
110 [ # # ][ # # ]: 0 : for( Range::const_iterator e = triangles.begin(); e != triangles.end(); ++e )
[ # # ][ # # ]
[ # # ]
111 : : {
112 : : const EntityHandle* conn;
113 : : int conn_len;
114 [ # # ][ # # ]: 0 : rval = mbImpl->get_connectivity( *e, conn, conn_len );
115 [ # # ]: 0 : if( MB_SUCCESS != rval )
116 : : {
117 [ # # ]: 0 : delete[] array;
118 : 0 : return rval;
119 : : }
120 [ # # ]: 0 : if( 3 != conn_len )
121 : : {
122 [ # # ]: 0 : delete[] array;
123 : 0 : return MB_INVALID_SIZE;
124 : : }
125 : :
126 [ # # ]: 0 : for( int i = 0; i < conn_len; ++i )
127 : 0 : array[fillA++] = conn[i];
128 : : }
129 [ # # ]: 0 : if( fillA != array_alloc )
130 : : {
131 [ # # ]: 0 : delete[] array;
132 : 0 : return MB_INVALID_SIZE;
133 : : }
134 : :
135 [ # # ]: 0 : std::sort( array, array + array_alloc );
136 [ # # ]: 0 : int numNodes = std::unique( array, array + array_alloc ) - array;
137 : :
138 [ # # ]: 0 : file << "#$SMF 1.0\n";
139 [ # # ][ # # ]: 0 : file << "#$vertices " << numNodes << std::endl;
[ # # ]
140 [ # # ][ # # ]: 0 : file << "#$faces " << numTriangles << std::endl;
[ # # ]
141 [ # # ]: 0 : file << "# \n";
142 [ # # ]: 0 : file << "# output from MOAB \n";
143 [ # # ]: 0 : file << "# \n";
144 : :
145 : : // Output first the nodes
146 : : // num nodes??
147 : : // Write the nodes
148 : : double coord[3];
149 [ # # ]: 0 : for( int i = 0; i < numNodes; i++ )
150 : : {
151 : 0 : EntityHandle node_handle = array[i];
152 : :
153 [ # # ]: 0 : rval = mbImpl->get_coords( &node_handle, 1, coord );
154 [ # # ]: 0 : if( rval != MB_SUCCESS )
155 : : {
156 [ # # ]: 0 : delete[] array;
157 : 0 : return rval;
158 : : }
159 : :
160 [ # # ][ # # ]: 0 : file << "v " << coord[0] << " " << coord[1] << " " << coord[2] << std::endl;
[ # # ][ # # ]
[ # # ][ # # ]
[ # # ]
161 : : }
162 : : // Write faces now
163 : : // Leave a blank line for cosmetics
164 [ # # ]: 0 : file << " \n";
165 [ # # ][ # # ]: 0 : for( Range::const_iterator e = triangles.begin(); e != triangles.end(); ++e )
[ # # ][ # # ]
[ # # ]
166 : : {
167 : : const EntityHandle* conn;
168 : : int conn_len;
169 [ # # ][ # # ]: 0 : rval = mbImpl->get_connectivity( *e, conn, conn_len );
170 [ # # ]: 0 : if( MB_SUCCESS != rval )
171 : : {
172 [ # # ]: 0 : delete[] array;
173 : 0 : return rval;
174 : : }
175 [ # # ]: 0 : if( 3 != conn_len )
176 : : {
177 [ # # ]: 0 : delete[] array;
178 : 0 : return MB_INVALID_SIZE;
179 : : }
180 [ # # ]: 0 : file << "f ";
181 [ # # ]: 0 : for( int i = 0; i < conn_len; ++i )
182 : : {
183 [ # # ]: 0 : int indexInArray = std::lower_bound( array, array + numNodes, conn[i] ) - array;
184 [ # # ][ # # ]: 0 : file << indexInArray + 1 << " ";
185 : : }
186 [ # # ]: 0 : file << std::endl;
187 : : }
188 : :
189 [ # # ]: 0 : file.close();
190 [ # # ]: 0 : delete[] array;
191 : 0 : return MB_SUCCESS;
192 : : }
193 : :
194 [ + - ][ + - ]: 228 : } // namespace moab
|