Blender V2.61 - r43446
|
00001 /* 00002 * ***** BEGIN GPL LICENSE BLOCK ***** 00003 * 00004 * This program is free software; you can redistribute it and/or 00005 * modify it under the terms of the GNU General Public License 00006 * as published by the Free Software Foundation; either version 2 00007 * of the License, or (at your option) any later version. 00008 * 00009 * This program is distributed in the hope that it will be useful, 00010 * but WITHOUT ANY WARRANTY; without even the implied warranty of 00011 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 00012 * GNU General Public License for more details. 00013 * 00014 * You should have received a copy of the GNU General Public License 00015 * along with this program; if not, write to the Free Software Foundation, 00016 * Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. 00017 * 00018 * Contributor(s): Nicholas Bishop 00019 * 00020 * ***** END GPL LICENSE BLOCK ***** 00021 */ 00022 00023 #include <cassert> 00024 #include "dualcon.h" 00025 #include "ModelReader.h" 00026 #include "octree.h" 00027 00028 #include <cstdio> 00029 00030 void veccopy(float dst[3], const float src[3]) 00031 { 00032 dst[0] = src[0]; 00033 dst[1] = src[1]; 00034 dst[2] = src[2]; 00035 } 00036 00037 #define GET_FACE(_mesh, _n) \ 00038 (*(DualConFaces)(((char*)(_mesh)->faces) + ((_n) * (_mesh)->face_stride))) 00039 00040 #define GET_CO(_mesh, _n) \ 00041 (*(DualConCo)(((char*)(_mesh)->co) + ((_n) * (_mesh)->co_stride))) 00042 00043 class DualConInputReader : public ModelReader 00044 { 00045 private: 00046 const DualConInput *input_mesh; 00047 int tottri, curface, offset; 00048 float min[3], max[3], maxsize; 00049 float scale; 00050 public: 00051 DualConInputReader(const DualConInput *mesh, float _scale) 00052 : input_mesh(mesh), scale(_scale) 00053 { 00054 reset(); 00055 } 00056 00057 void reset() 00058 { 00059 tottri = 0; 00060 curface = 0; 00061 offset = 0; 00062 maxsize = 0; 00063 00064 /* initialize tottri */ 00065 for(int i = 0; i < input_mesh->totface; i++) 00066 tottri += GET_FACE(input_mesh, i)[3] ? 2 : 1; 00067 00068 veccopy(min, input_mesh->min); 00069 veccopy(max, input_mesh->max); 00070 00071 /* initialize maxsize */ 00072 for(int i = 0; i < 3; i++) { 00073 float d = max[i] - min[i]; 00074 if(d > maxsize) 00075 maxsize = d; 00076 } 00077 00078 /* redo the bounds */ 00079 for(int i = 0; i < 3; i++) 00080 { 00081 min[i] = (max[i] + min[i]) / 2 - maxsize / 2; 00082 max[i] = (max[i] + min[i]) / 2 + maxsize / 2; 00083 } 00084 00085 for(int i = 0; i < 3; i++) 00086 min[i] -= maxsize * (1 / scale - 1) / 2; 00087 maxsize *= 1 / scale; 00088 } 00089 00090 Triangle* getNextTriangle() 00091 { 00092 if(curface == input_mesh->totface) 00093 return 0; 00094 00095 Triangle* t = new Triangle(); 00096 00097 unsigned int *f = GET_FACE(input_mesh, curface); 00098 if(offset == 0) { 00099 veccopy(t->vt[0], GET_CO(input_mesh, f[0])); 00100 veccopy(t->vt[1], GET_CO(input_mesh, f[1])); 00101 veccopy(t->vt[2], GET_CO(input_mesh, f[2])); 00102 } 00103 else { 00104 veccopy(t->vt[0], GET_CO(input_mesh, f[2])); 00105 veccopy(t->vt[1], GET_CO(input_mesh, f[3])); 00106 veccopy(t->vt[2], GET_CO(input_mesh, f[0])); 00107 } 00108 00109 if(offset == 0 && f[3]) 00110 offset++; 00111 else { 00112 offset = 0; 00113 curface++; 00114 } 00115 00116 return t; 00117 } 00118 00119 int getNextTriangle(int t[3]) 00120 { 00121 if(curface == input_mesh->totface) 00122 return 0; 00123 00124 unsigned int *f = GET_FACE(input_mesh, curface); 00125 if(offset == 0) { 00126 t[0] = f[0]; 00127 t[1] = f[1]; 00128 t[2] = f[2]; 00129 } 00130 else { 00131 t[0] = f[2]; 00132 t[1] = f[3]; 00133 t[2] = f[0]; 00134 } 00135 00136 if(offset == 0 && f[3]) 00137 offset++; 00138 else { 00139 offset = 0; 00140 curface++; 00141 } 00142 00143 return 1; 00144 } 00145 00146 int getNumTriangles() 00147 { 00148 return tottri; 00149 } 00150 00151 int getNumVertices() 00152 { 00153 return input_mesh->totco; 00154 } 00155 00156 float getBoundingBox(float origin[3]) 00157 { 00158 veccopy(origin, min); 00159 return maxsize ; 00160 } 00161 00162 /* output */ 00163 void getNextVertex(float v[3]) 00164 { 00165 /* not used */ 00166 } 00167 00168 /* stubs */ 00169 void printInfo() {} 00170 int getMemory() { return sizeof(DualConInputReader); } 00171 }; 00172 00173 void *dualcon(const DualConInput *input_mesh, 00174 /* callbacks for output */ 00175 DualConAllocOutput alloc_output, 00176 DualConAddVert add_vert, 00177 DualConAddQuad add_quad, 00178 00179 DualConFlags flags, 00180 DualConMode mode, 00181 float threshold, 00182 float hermite_num, 00183 float scale, 00184 int depth) 00185 { 00186 DualConInputReader r(input_mesh, scale); 00187 Octree o(&r, alloc_output, add_vert, add_quad, 00188 flags, mode, depth, threshold, hermite_num); 00189 o.scanConvert(); 00190 return o.getOutputMesh(); 00191 }