1 /*---------------------------------------------------------------------------*\
2 * OpenSG NURBS Library *
5 * Copyright (C) 2001-2006 by the University of Bonn, Computer Graphics Group*
7 * http://cg.cs.uni-bonn.de/ *
9 * contact: edhellon@cs.uni-bonn.de, guthe@cs.uni-bonn.de, rk@cs.uni-bonn.de *
11 \*---------------------------------------------------------------------------*/
12 /*---------------------------------------------------------------------------*\
15 * This library is free software; you can redistribute it and/or modify it *
16 * under the terms of the GNU Library General Public License as published *
17 * by the Free Software Foundation, version 2. *
19 * This library is distributed in the hope that it will be useful, but *
20 * WITHOUT ANY WARRANTY; without even the implied warranty of *
21 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU *
22 * Library General Public License for more details. *
24 * You should have received a copy of the GNU Library General Public *
25 * License along with this library; if not, write to the Free Software *
26 * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. *
28 \*---------------------------------------------------------------------------*/
29 /*---------------------------------------------------------------------------*\
37 \*---------------------------------------------------------------------------*/
39 # pragma warning (disable : 985)
41 #include "OSGBSplineTrimmedSurface.h"
49 static char THIS_FILE
[] = __FILE__
;
53 const char BSplineTrimmedSurface::ff_const_1
[] = "BEGINTRIMMEDSURFACE";
54 const char BSplineTrimmedSurface::ff_const_2
[] = "NUMBEROFCURVELOOPS";
55 const char BSplineTrimmedSurface::ff_const_3
[] = "CURVESPERLOOP";
57 // I/O facilities - FIXME: read( char *fname ), etc. missing
58 int BSplineTrimmedSurface::read(std::istream
&infile
)
60 //FIXME: maybe we need more checks!!!
63 unsigned int numcurves
;
64 unsigned int i
,j
; //,k;
66 /* infile.getline( txtbuffer, 255 ); //read line
67 //FIXME: quick hack to allow us to step through
68 while ( strcmp( txtbuffer, ff_const_1 ) && lc < 10 ) {
69 infile.getline( txtbuffer, 255 ); //read line
72 if ( strcmp( txtbuffer, ff_const_1 ) ) return -1; //bad file format
74 infile >> txtbuffer; //FIXME: error prone: too long string causes problem!!!
75 if ( strcmp( txtbuffer, ff_const_2 ) ) return -1; // yeah, bad file format again*/
77 infile
>> txtbuffer
>> std::ws
; //FIXME: error prone: too long string causes problem!!!
78 if(strcmp(txtbuffer
, ff_const_1
) == 0)
80 infile
>> txtbuffer
>> std::ws
; //FIXME: error prone: too long string causes problem!!!
83 // infile >> txtbuffer >> std::ws; //FIXME: error prone: too long string causes problem!!!
84 // std::cerr << "check " << ff_const_2 << " " << txtbuffer << std::endl;
85 if(strcmp(txtbuffer
, ff_const_2
) )
86 return -1; // yeah, bad file format again
88 infile
>> numcurves
>> std::ws
;
90 return -12; // bad number of curves
91 trimming
.resize(numcurves
);
93 for(i
= 0; i
< numcurves
; i
++)
96 infile
>> txtbuffer
; //FIXME: error prone: too long string causes problem!!!
97 if(strcmp(txtbuffer
, ff_const_3
) )
98 return -13; // bad file format
99 infile
>> actnumofcurves
>> std::ws
;
100 trimming
[i
].resize(actnumofcurves
);
104 err
= surf
.read(infile
);
107 std::cerr
<< "error loading surfacedata." << std::endl
;
111 std::vector
<int> ignored_curves
;
114 for(i
= 0; i
< numcurves
; i
++)
116 ignored_curves
.clear();
118 for(j
= 0; j
< trimming
[i
].size(); j
++)
120 err
= trimming
[i
][j
].read(infile
);
121 if(err
!= 0 && err
!= -10)
123 std::cerr
<< "error loading trimming curve data, i: " << i
<< " j: " << j
<< std::endl
;
126 else if(err
== -10) // FIXME: burntin val
129 ignored_curves
.push_back(j
);
133 for(kk
= 0; kk
< ignored_curves
.size(); ++kk
)
135 trimming
[i
].erase(trimming
[i
].begin() + ignored_curves
[kk
]);
142 void BSplineTrimmedSurface::normalize(void)
149 unsigned int numcurves
= UInt32(trimming
.size());
150 unsigned int i
, j
, k
;
152 surf
.getParameterInterval_U(d_offset_u
, d_scale_u
);
153 surf
.getParameterInterval_V(d_offset_v
, d_scale_v
);
154 d_offset_u
= -d_offset_u
;
155 d_offset_v
= -d_offset_v
;
156 #ifdef OSG_INTEGER_MESH
157 d_scale_u
= 1000000.0 / (d_scale_u
+ d_offset_u
);
158 d_scale_v
= 1000000.0 / (d_scale_v
+ d_offset_v
);
160 d_scale_u
= 10000.0 / (d_scale_u
+ d_offset_u
);
161 d_scale_v
= 10000.0 / (d_scale_v
+ d_offset_v
);
164 for(i
= 0; i
< surf
.getKnotVector_U().size(); ++i
)
166 surf
.getKnotVector_U()[i
] =
167 (surf
.getKnotVector_U()[i
] + d_offset_u
) * d_scale_u
;
170 for(i
= 0; i
< surf
.getKnotVector_V().size(); ++i
)
172 surf
.getKnotVector_V()[i
] =
173 (surf
.getKnotVector_V()[i
] + d_offset_v
) * d_scale_v
;
176 for(i
= 0; i
< numcurves
; i
++)
178 for(j
= 0; j
< trimming
[i
].size(); j
++)
180 for(k
= 0; k
< trimming
[i
][j
].getControlPointVector().size(); ++k
)
182 weight
= trimming
[i
][j
].getControlPointVector()[k
][2];
183 trimming
[i
][j
].getControlPointVector()[k
][0] =
184 (trimming
[i
][j
].getControlPointVector()[k
][0] + d_offset_u
* weight
) * d_scale_u
;
185 trimming
[i
][j
].getControlPointVector()[k
][1] =
186 (trimming
[i
][j
].getControlPointVector()[k
][1] + d_offset_v
* weight
) * d_scale_v
;
192 int BSplineTrimmedSurface::write(std::ostream
&outfile
)
194 //FIXME: maybe we need more checks!!!
197 outfile
.precision(DCTP_PRECISION
);
198 outfile
<< ff_const_1
<< std::endl
;
199 outfile
<< ff_const_2
<< " " << trimming
.size() << std::endl
;
201 for(i
= 0; i
< trimming
.size(); i
++)
202 outfile
<< ff_const_3
<< " " << trimming
[i
].size() << std::endl
;
206 for(i
= 0; i
< trimming
.size(); i
++)
208 for(bscvector::size_type j
= 0; j
< trimming
[i
].size(); j
++)
210 trimming
[i
][j
].write(outfile
);
217 // flip the whole surface
218 // TODO: fix this function for rational surfaces and re-enable it
219 // Should work now for rational surfaces but it is untested!
220 void BSplineTrimmedSurface::flip(void)
222 // mirror the u-knot vector
223 DCTPdvector
& rvd_knots
= surf
.getKnotVector_U();
224 const unsigned int cui_knot_cnt
= UInt32(rvd_knots
.size());
225 const double cd_min_param
= rvd_knots
[0];
226 const double cd_max_param
= rvd_knots
[cui_knot_cnt
- 1];
230 for(ui_swap
= 0; ui_swap
< cui_knot_cnt
; ++ui_swap
)
232 rvd_knots
[ui_swap
] = cd_min_param
+ cd_max_param
- rvd_knots
[ui_swap
];
235 for(ui_swap
= 0; ui_swap
< (cui_knot_cnt
>> 1); ++ui_swap
)
237 d_swap
= rvd_knots
[ui_swap
];
238 rvd_knots
[ui_swap
] = rvd_knots
[cui_knot_cnt
- 1 - ui_swap
];
239 rvd_knots
[cui_knot_cnt
- 1 - ui_swap
] = d_swap
;
242 // swap the control points along the u-direction
243 DCTPVec4dmatrix
& rvvcl_control_points
= surf
.getControlPointMatrix();
244 const unsigned int cui_cp_cnt
= UInt32(rvvcl_control_points
.size());
245 DCTPVec4dvector vcl_swap
;
247 for(ui_swap
= 0; ui_swap
< (cui_cp_cnt
>> 1); ++ui_swap
)
249 vcl_swap
= rvvcl_control_points
[ui_swap
];
250 rvvcl_control_points
[ui_swap
] = rvvcl_control_points
[cui_cp_cnt
- 1 - ui_swap
];
251 rvvcl_control_points
[cui_cp_cnt
- 1 - ui_swap
] = vcl_swap
;
254 // mirror the u-param of the trimming curves
255 const unsigned int cui_loop_cnt
= UInt32(trimming
.size());
256 unsigned int ui_loop
;
257 unsigned int ui_curve_cnt
;
258 unsigned int ui_curve
;
260 for(ui_loop
= 0; ui_loop
< cui_loop_cnt
; ++ui_loop
)
262 ui_curve_cnt
= UInt32(trimming
[ui_loop
].size());
264 for(ui_curve
= 0; ui_curve
< ui_curve_cnt
; ++ui_curve
)
266 // mirror the knot vector
267 DCTPdvector
& rvd_knots_
= trimming
[ui_loop
][ui_curve
].getKnotVector();
268 const unsigned int cui_knot_cnt_
= UInt32(rvd_knots_
.size());
269 const double cd_min_cparam
= rvd_knots_
[0];
270 const double cd_max_cparam
= rvd_knots_
[cui_knot_cnt_
- 1];
272 /* std::cerr.precision( 15 );
273 std::cerr<<"--------------------------------------------"<<std::endl;
274 std::cerr <<"Before: ";*/
275 for(ui_swap
= 0; ui_swap
< cui_knot_cnt_
; ++ui_swap
)
277 // std::cerr << rvd_knots_[ ui_swap ] << " ";
278 rvd_knots_
[ui_swap
] = cd_min_cparam
+ cd_max_cparam
- rvd_knots_
[ui_swap
];
282 std::cerr <<std::endl<<"After1: ";
283 for( ui_swap = 0; ui_swap < cui_knot_cnt_; ++ui_swap )
285 std::cerr << rvd_knots_[ ui_swap ] << " ";
288 for(ui_swap
= 0; ui_swap
< (cui_knot_cnt_
>> 1); ++ui_swap
)
290 d_swap
= rvd_knots_
[ui_swap
];
291 rvd_knots_
[ui_swap
] = rvd_knots_
[cui_knot_cnt_
- 1 - ui_swap
];
292 rvd_knots_
[cui_knot_cnt_
- 1 - ui_swap
] = d_swap
;
296 std::cerr <<std::endl<<"After2: ";
297 for( ui_swap = 0; ui_swap < cui_knot_cnt_; ++ui_swap )
299 std::cerr << rvd_knots_[ ui_swap ] << " ";
301 std::cerr << std::endl;
302 std::cerr.precision( 6 );
304 // swap and mirror the control points
305 DCTPVec3dvector
& rvcl_control_points
= trimming
[ui_loop
][ui_curve
].getControlPointVector();
306 const unsigned int cui_cp_cnt_
= UInt32(rvcl_control_points
.size());
309 for(ui_swap
= 0; ui_swap
< cui_cp_cnt_
; ++ui_swap
)
311 rvcl_control_points
[ui_swap
][0] =
312 (cd_min_param
+ cd_max_param
) * rvcl_control_points
[ui_swap
][2]
313 - rvcl_control_points
[ui_swap
][0];
316 for(ui_swap
= 0; ui_swap
< (cui_cp_cnt_
>> 1); ++ui_swap
)
318 cl_swap
= rvcl_control_points
[ui_swap
];
319 rvcl_control_points
[ui_swap
] = rvcl_control_points
[cui_cp_cnt_
- 1 - ui_swap
];
320 rvcl_control_points
[cui_cp_cnt_
- 1 - ui_swap
] = cl_swap
;
324 // and swap the trimming curves
325 BSplineCurve2D cl_swap
;
327 for(ui_swap
= 0; ui_swap
< (ui_curve_cnt
>> 1); ++ui_swap
)
329 cl_swap
= trimming
[ui_loop
][ui_swap
];
330 trimming
[ui_loop
][ui_swap
] = trimming
[ui_loop
][ui_curve_cnt
- 1 - ui_swap
];
331 trimming
[ui_loop
][ui_curve_cnt
- 1 - ui_swap
] = cl_swap
;