OSDN Git Service

three.jsをThirdPartyに追加
[webglgame/webgl_framework.git] / webglFramework / Thirdparty / three.js-master / examples / js / geometries / TeapotBufferGeometry.js
1 /**
2  * @author Eric Haines / http://erichaines.com/
3  *
4  * Tessellates the famous Utah teapot database by Martin Newell into triangles.
5  *
6  * THREE.TeapotBufferGeometry = function ( size, segments, bottom, lid, body, fitLid, blinn )
7  *
8  * defaults: size = 50, segments = 10, bottom = true, lid = true, body = true,
9  *   fitLid = false, blinn = true
10  *
11  * size is a relative scale: I've scaled the teapot to fit vertically between -1 and 1.
12  * Think of it as a "radius".
13  * segments - number of line segments to subdivide each patch edge;
14  *   1 is possible but gives degenerates, so two is the real minimum.
15  * bottom - boolean, if true (default) then the bottom patches are added. Some consider
16  *   adding the bottom heresy, so set this to "false" to adhere to the One True Way.
17  * lid - to remove the lid and look inside, set to true.
18  * body - to remove the body and leave the lid, set this and "bottom" to false.
19  * fitLid - the lid is a tad small in the original. This stretches it a bit so you can't
20  *   see the teapot's insides through the gap.
21  * blinn - Jim Blinn scaled the original data vertically by dividing by about 1.3 to look
22  *   nicer. If you want to see the original teapot, similar to the real-world model, set
23  *   this to false. True by default.
24  *   See http://en.wikipedia.org/wiki/File:Original_Utah_Teapot.jpg for the original
25  *   real-world teapot (from http://en.wikipedia.org/wiki/Utah_teapot).
26  *
27  * Note that the bottom (the last four patches) is not flat - blame Frank Crow, not me.
28  *
29  * The teapot should normally be rendered as a double sided object, since for some
30  * patches both sides can be seen, e.g., the gap around the lid and inside the spout.
31  *
32  * Segments 'n' determines the number of triangles output.
33  *   Total triangles = 32*2*n*n - 8*n    [degenerates at the top and bottom cusps are deleted]
34  *
35  *   size_factor   # triangles
36  *       1          56
37  *       2         240
38  *       3         552
39  *       4         992
40  *
41  *      10        6320
42  *      20       25440
43  *      30       57360
44  *
45  * Code converted from my ancient SPD software, http://tog.acm.org/resources/SPD/
46  * Created for the Udacity course "Interactive Rendering", http://bit.ly/ericity
47  * Lesson: https://www.udacity.com/course/viewer#!/c-cs291/l-68866048/m-106482448
48  * YouTube video on teapot history: https://www.youtube.com/watch?v=DxMfblPzFNc
49  *
50  * See https://en.wikipedia.org/wiki/Utah_teapot for the history of the teapot
51  *
52  */
53 /*global THREE */
54
55 THREE.TeapotBufferGeometry = function ( size, segments, bottom, lid, body, fitLid, blinn ) {
56
57         "use strict";
58
59         // 32 * 4 * 4 Bezier spline patches
60         var teapotPatches = [
61 /*rim*/
62 0,1,2,3,4,5,6,7,8,9,10,11,12,13,14,15,
63 3,16,17,18,7,19,20,21,11,22,23,24,15,25,26,27,
64 18,28,29,30,21,31,32,33,24,34,35,36,27,37,38,39,
65 30,40,41,0,33,42,43,4,36,44,45,8,39,46,47,12,
66 /*body*/
67 12,13,14,15,48,49,50,51,52,53,54,55,56,57,58,59,
68 15,25,26,27,51,60,61,62,55,63,64,65,59,66,67,68,
69 27,37,38,39,62,69,70,71,65,72,73,74,68,75,76,77,
70 39,46,47,12,71,78,79,48,74,80,81,52,77,82,83,56,
71 56,57,58,59,84,85,86,87,88,89,90,91,92,93,94,95,
72 59,66,67,68,87,96,97,98,91,99,100,101,95,102,103,104,
73 68,75,76,77,98,105,106,107,101,108,109,110,104,111,112,113,
74 77,82,83,56,107,114,115,84,110,116,117,88,113,118,119,92,
75 /*handle*/
76 120,121,122,123,124,125,126,127,128,129,130,131,132,133,134,135,
77 123,136,137,120,127,138,139,124,131,140,141,128,135,142,143,132,
78 132,133,134,135,144,145,146,147,148,149,150,151,68,152,153,154,
79 135,142,143,132,147,155,156,144,151,157,158,148,154,159,160,68,
80 /*spout*/
81 161,162,163,164,165,166,167,168,169,170,171,172,173,174,175,176,
82 164,177,178,161,168,179,180,165,172,181,182,169,176,183,184,173,
83 173,174,175,176,185,186,187,188,189,190,191,192,193,194,195,196,
84 176,183,184,173,188,197,198,185,192,199,200,189,196,201,202,193,
85 /*lid*/
86 203,203,203,203,204,205,206,207,208,208,208,208,209,210,211,212,
87 203,203,203,203,207,213,214,215,208,208,208,208,212,216,217,218,
88 203,203,203,203,215,219,220,221,208,208,208,208,218,222,223,224,
89 203,203,203,203,221,225,226,204,208,208,208,208,224,227,228,209,
90 209,210,211,212,229,230,231,232,233,234,235,236,237,238,239,240,
91 212,216,217,218,232,241,242,243,236,244,245,246,240,247,248,249,
92 218,222,223,224,243,250,251,252,246,253,254,255,249,256,257,258,
93 224,227,228,209,252,259,260,229,255,261,262,233,258,263,264,237,
94 /*bottom*/
95 265,265,265,265,266,267,268,269,270,271,272,273,92,119,118,113,
96 265,265,265,265,269,274,275,276,273,277,278,279,113,112,111,104,
97 265,265,265,265,276,280,281,282,279,283,284,285,104,103,102,95,
98 265,265,265,265,282,286,287,266,285,288,289,270,95,94,93,92
99         ] ;
100
101         var teapotVertices = [
102 1.4,0,2.4,
103 1.4,-0.784,2.4,
104 0.784,-1.4,2.4,
105 0,-1.4,2.4,
106 1.3375,0,2.53125,
107 1.3375,-0.749,2.53125,
108 0.749,-1.3375,2.53125,
109 0,-1.3375,2.53125,
110 1.4375,0,2.53125,
111 1.4375,-0.805,2.53125,
112 0.805,-1.4375,2.53125,
113 0,-1.4375,2.53125,
114 1.5,0,2.4,
115 1.5,-0.84,2.4,
116 0.84,-1.5,2.4,
117 0,-1.5,2.4,
118 -0.784,-1.4,2.4,
119 -1.4,-0.784,2.4,
120 -1.4,0,2.4,
121 -0.749,-1.3375,2.53125,
122 -1.3375,-0.749,2.53125,
123 -1.3375,0,2.53125,
124 -0.805,-1.4375,2.53125,
125 -1.4375,-0.805,2.53125,
126 -1.4375,0,2.53125,
127 -0.84,-1.5,2.4,
128 -1.5,-0.84,2.4,
129 -1.5,0,2.4,
130 -1.4,0.784,2.4,
131 -0.784,1.4,2.4,
132 0,1.4,2.4,
133 -1.3375,0.749,2.53125,
134 -0.749,1.3375,2.53125,
135 0,1.3375,2.53125,
136 -1.4375,0.805,2.53125,
137 -0.805,1.4375,2.53125,
138 0,1.4375,2.53125,
139 -1.5,0.84,2.4,
140 -0.84,1.5,2.4,
141 0,1.5,2.4,
142 0.784,1.4,2.4,
143 1.4,0.784,2.4,
144 0.749,1.3375,2.53125,
145 1.3375,0.749,2.53125,
146 0.805,1.4375,2.53125,
147 1.4375,0.805,2.53125,
148 0.84,1.5,2.4,
149 1.5,0.84,2.4,
150 1.75,0,1.875,
151 1.75,-0.98,1.875,
152 0.98,-1.75,1.875,
153 0,-1.75,1.875,
154 2,0,1.35,
155 2,-1.12,1.35,
156 1.12,-2,1.35,
157 0,-2,1.35,
158 2,0,0.9,
159 2,-1.12,0.9,
160 1.12,-2,0.9,
161 0,-2,0.9,
162 -0.98,-1.75,1.875,
163 -1.75,-0.98,1.875,
164 -1.75,0,1.875,
165 -1.12,-2,1.35,
166 -2,-1.12,1.35,
167 -2,0,1.35,
168 -1.12,-2,0.9,
169 -2,-1.12,0.9,
170 -2,0,0.9,
171 -1.75,0.98,1.875,
172 -0.98,1.75,1.875,
173 0,1.75,1.875,
174 -2,1.12,1.35,
175 -1.12,2,1.35,
176 0,2,1.35,
177 -2,1.12,0.9,
178 -1.12,2,0.9,
179 0,2,0.9,
180 0.98,1.75,1.875,
181 1.75,0.98,1.875,
182 1.12,2,1.35,
183 2,1.12,1.35,
184 1.12,2,0.9,
185 2,1.12,0.9,
186 2,0,0.45,
187 2,-1.12,0.45,
188 1.12,-2,0.45,
189 0,-2,0.45,
190 1.5,0,0.225,
191 1.5,-0.84,0.225,
192 0.84,-1.5,0.225,
193 0,-1.5,0.225,
194 1.5,0,0.15,
195 1.5,-0.84,0.15,
196 0.84,-1.5,0.15,
197 0,-1.5,0.15,
198 -1.12,-2,0.45,
199 -2,-1.12,0.45,
200 -2,0,0.45,
201 -0.84,-1.5,0.225,
202 -1.5,-0.84,0.225,
203 -1.5,0,0.225,
204 -0.84,-1.5,0.15,
205 -1.5,-0.84,0.15,
206 -1.5,0,0.15,
207 -2,1.12,0.45,
208 -1.12,2,0.45,
209 0,2,0.45,
210 -1.5,0.84,0.225,
211 -0.84,1.5,0.225,
212 0,1.5,0.225,
213 -1.5,0.84,0.15,
214 -0.84,1.5,0.15,
215 0,1.5,0.15,
216 1.12,2,0.45,
217 2,1.12,0.45,
218 0.84,1.5,0.225,
219 1.5,0.84,0.225,
220 0.84,1.5,0.15,
221 1.5,0.84,0.15,
222 -1.6,0,2.025,
223 -1.6,-0.3,2.025,
224 -1.5,-0.3,2.25,
225 -1.5,0,2.25,
226 -2.3,0,2.025,
227 -2.3,-0.3,2.025,
228 -2.5,-0.3,2.25,
229 -2.5,0,2.25,
230 -2.7,0,2.025,
231 -2.7,-0.3,2.025,
232 -3,-0.3,2.25,
233 -3,0,2.25,
234 -2.7,0,1.8,
235 -2.7,-0.3,1.8,
236 -3,-0.3,1.8,
237 -3,0,1.8,
238 -1.5,0.3,2.25,
239 -1.6,0.3,2.025,
240 -2.5,0.3,2.25,
241 -2.3,0.3,2.025,
242 -3,0.3,2.25,
243 -2.7,0.3,2.025,
244 -3,0.3,1.8,
245 -2.7,0.3,1.8,
246 -2.7,0,1.575,
247 -2.7,-0.3,1.575,
248 -3,-0.3,1.35,
249 -3,0,1.35,
250 -2.5,0,1.125,
251 -2.5,-0.3,1.125,
252 -2.65,-0.3,0.9375,
253 -2.65,0,0.9375,
254 -2,-0.3,0.9,
255 -1.9,-0.3,0.6,
256 -1.9,0,0.6,
257 -3,0.3,1.35,
258 -2.7,0.3,1.575,
259 -2.65,0.3,0.9375,
260 -2.5,0.3,1.125,
261 -1.9,0.3,0.6,
262 -2,0.3,0.9,
263 1.7,0,1.425,
264 1.7,-0.66,1.425,
265 1.7,-0.66,0.6,
266 1.7,0,0.6,
267 2.6,0,1.425,
268 2.6,-0.66,1.425,
269 3.1,-0.66,0.825,
270 3.1,0,0.825,
271 2.3,0,2.1,
272 2.3,-0.25,2.1,
273 2.4,-0.25,2.025,
274 2.4,0,2.025,
275 2.7,0,2.4,
276 2.7,-0.25,2.4,
277 3.3,-0.25,2.4,
278 3.3,0,2.4,
279 1.7,0.66,0.6,
280 1.7,0.66,1.425,
281 3.1,0.66,0.825,
282 2.6,0.66,1.425,
283 2.4,0.25,2.025,
284 2.3,0.25,2.1,
285 3.3,0.25,2.4,
286 2.7,0.25,2.4,
287 2.8,0,2.475,
288 2.8,-0.25,2.475,
289 3.525,-0.25,2.49375,
290 3.525,0,2.49375,
291 2.9,0,2.475,
292 2.9,-0.15,2.475,
293 3.45,-0.15,2.5125,
294 3.45,0,2.5125,
295 2.8,0,2.4,
296 2.8,-0.15,2.4,
297 3.2,-0.15,2.4,
298 3.2,0,2.4,
299 3.525,0.25,2.49375,
300 2.8,0.25,2.475,
301 3.45,0.15,2.5125,
302 2.9,0.15,2.475,
303 3.2,0.15,2.4,
304 2.8,0.15,2.4,
305 0,0,3.15,
306 0.8,0,3.15,
307 0.8,-0.45,3.15,
308 0.45,-0.8,3.15,
309 0,-0.8,3.15,
310 0,0,2.85,
311 0.2,0,2.7,
312 0.2,-0.112,2.7,
313 0.112,-0.2,2.7,
314 0,-0.2,2.7,
315 -0.45,-0.8,3.15,
316 -0.8,-0.45,3.15,
317 -0.8,0,3.15,
318 -0.112,-0.2,2.7,
319 -0.2,-0.112,2.7,
320 -0.2,0,2.7,
321 -0.8,0.45,3.15,
322 -0.45,0.8,3.15,
323 0,0.8,3.15,
324 -0.2,0.112,2.7,
325 -0.112,0.2,2.7,
326 0,0.2,2.7,
327 0.45,0.8,3.15,
328 0.8,0.45,3.15,
329 0.112,0.2,2.7,
330 0.2,0.112,2.7,
331 0.4,0,2.55,
332 0.4,-0.224,2.55,
333 0.224,-0.4,2.55,
334 0,-0.4,2.55,
335 1.3,0,2.55,
336 1.3,-0.728,2.55,
337 0.728,-1.3,2.55,
338 0,-1.3,2.55,
339 1.3,0,2.4,
340 1.3,-0.728,2.4,
341 0.728,-1.3,2.4,
342 0,-1.3,2.4,
343 -0.224,-0.4,2.55,
344 -0.4,-0.224,2.55,
345 -0.4,0,2.55,
346 -0.728,-1.3,2.55,
347 -1.3,-0.728,2.55,
348 -1.3,0,2.55,
349 -0.728,-1.3,2.4,
350 -1.3,-0.728,2.4,
351 -1.3,0,2.4,
352 -0.4,0.224,2.55,
353 -0.224,0.4,2.55,
354 0,0.4,2.55,
355 -1.3,0.728,2.55,
356 -0.728,1.3,2.55,
357 0,1.3,2.55,
358 -1.3,0.728,2.4,
359 -0.728,1.3,2.4,
360 0,1.3,2.4,
361 0.224,0.4,2.55,
362 0.4,0.224,2.55,
363 0.728,1.3,2.55,
364 1.3,0.728,2.55,
365 0.728,1.3,2.4,
366 1.3,0.728,2.4,
367 0,0,0,
368 1.425,0,0,
369 1.425,0.798,0,
370 0.798,1.425,0,
371 0,1.425,0,
372 1.5,0,0.075,
373 1.5,0.84,0.075,
374 0.84,1.5,0.075,
375 0,1.5,0.075,
376 -0.798,1.425,0,
377 -1.425,0.798,0,
378 -1.425,0,0,
379 -0.84,1.5,0.075,
380 -1.5,0.84,0.075,
381 -1.5,0,0.075,
382 -1.425,-0.798,0,
383 -0.798,-1.425,0,
384 0,-1.425,0,
385 -1.5,-0.84,0.075,
386 -0.84,-1.5,0.075,
387 0,-1.5,0.075,
388 0.798,-1.425,0,
389 1.425,-0.798,0,
390 0.84,-1.5,0.075,
391 1.5,-0.84,0.075
392         ] ;
393
394         THREE.BufferGeometry.call( this );
395
396         this.type = 'TeapotBufferGeometry';
397
398         this.parameters = {
399                 size: size,
400                 segments: segments,
401                 bottom: bottom,
402                 lid: lid,
403                 body: body,
404                 fitLid: fitLid,
405                 blinn: blinn
406         };
407
408         size = size || 50;
409
410         // number of segments per patch
411         segments = segments !== undefined ? Math.max( 2, Math.floor( segments ) || 10 ) : 10;
412
413         // which parts should be visible
414         bottom = bottom === undefined ? true : bottom;
415         lid = lid === undefined ? true : lid;
416         body = body === undefined ? true : body;
417
418         // Should the lid be snug? It's not traditional, but we make it snug by default
419         fitLid = fitLid === undefined ? true : fitLid;
420
421         // Jim Blinn scaled the teapot down in size by about 1.3 for
422         // some rendering tests. He liked the new proportions that he kept
423         // the data in this form. The model was distributed with these new
424         // proportions and became the norm. Trivia: comparing images of the
425         // real teapot and the computer model, the ratio for the bowl of the
426         // real teapot is more like 1.25, but since 1.3 is the traditional
427         // value given, we use it here.
428         var blinnScale = 1.3;
429         blinn = blinn === undefined ? true : blinn;
430
431         // scale the size to be the real scaling factor
432         var maxHeight = 3.15 * ( blinn ? 1 : blinnScale );
433
434         var maxHeight2 = maxHeight / 2;
435         var trueSize = size / maxHeight2;
436
437         // Number of elements depends on what is needed. Subtract degenerate
438         // triangles at tip of bottom and lid out in advance.
439         var numTriangles = bottom ? ( 8 * segments - 4 ) * segments : 0;
440         numTriangles += lid ? ( 16 * segments - 4 ) * segments : 0;
441         numTriangles += body ? 40 * segments * segments : 0;
442
443         var indices = new Uint32Array( numTriangles * 3 );
444
445         var numVertices = bottom ? 4 : 0;
446         numVertices += lid ? 8 : 0;
447         numVertices += body ? 20 : 0;
448         numVertices *= ( segments + 1 ) * ( segments + 1 );
449
450         var vertices = new Float32Array( numVertices * 3 );
451         var normals = new Float32Array( numVertices * 3 );
452         var uvs = new Float32Array( numVertices * 2 );
453
454         // Bezier form
455         var ms = new THREE.Matrix4();
456         ms.set( -1.0,  3.0, -3.0,  1.0,
457                          3.0, -6.0,  3.0,  0.0,
458                         -3.0,  3.0,  0.0,  0.0,
459                          1.0,  0.0,  0.0,  0.0 ) ;
460
461         var g = [];
462         var i, r, c;
463
464         var sp = [];
465         var tp = [];
466         var dsp = [];
467         var dtp = [];
468
469         // M * G * M matrix, sort of see
470         // http://www.cs.helsinki.fi/group/goa/mallinnus/curves/surfaces.html
471         var mgm = [];
472
473         var vert = [];
474         var sdir = [];
475         var tdir = [];
476
477         var norm = new THREE.Vector3();
478
479         var tcoord;
480
481         var sstep, tstep;
482         var vertPerRow;
483
484         var s, t, sval, tval, p;
485         var dsval = 0;
486         var dtval = 0;
487
488         var normOut = new THREE.Vector3();
489         var v1, v2, v3, v4;
490
491         var gmx = new THREE.Matrix4();
492         var tmtx = new THREE.Matrix4();
493
494         var vsp = new THREE.Vector4();
495         var vtp = new THREE.Vector4();
496         var vdsp = new THREE.Vector4();
497         var vdtp = new THREE.Vector4();
498
499         var vsdir = new THREE.Vector3();
500         var vtdir = new THREE.Vector3();
501
502         var mst = ms.clone();
503         mst.transpose();
504
505         // internal function: test if triangle has any matching vertices;
506         // if so, don't save triangle, since it won't display anything.
507         var notDegenerate = function ( vtx1, vtx2, vtx3 ) {
508
509                 // if any vertex matches, return false
510                 return ! ( ( ( vertices[ vtx1 * 3 ]     === vertices[ vtx2 * 3 ] ) &&
511                                          ( vertices[ vtx1 * 3 + 1 ] === vertices[ vtx2 * 3 + 1 ] ) &&
512                                          ( vertices[ vtx1 * 3 + 2 ] === vertices[ vtx2 * 3 + 2 ] ) ) ||
513                                    ( ( vertices[ vtx1 * 3 ]     === vertices[ vtx3 * 3 ] ) &&
514                                          ( vertices[ vtx1 * 3 + 1 ] === vertices[ vtx3 * 3 + 1 ] ) &&
515                                          ( vertices[ vtx1 * 3 + 2 ] === vertices[ vtx3 * 3 + 2 ] ) ) ||
516                                    ( ( vertices[ vtx2 * 3 ]     === vertices[ vtx3 * 3 ] ) &&
517                                          ( vertices[ vtx2 * 3 + 1 ] === vertices[ vtx3 * 3 + 1 ] ) &&
518                                          ( vertices[ vtx2 * 3 + 2 ] === vertices[ vtx3 * 3 + 2 ] ) ) );
519
520         };
521
522
523         for ( i = 0; i < 3; i ++ )
524         {
525
526                 mgm[ i ] = new THREE.Matrix4();
527
528         }
529
530         var minPatches = body ? 0 : 20;
531         var maxPatches = bottom ? 32 : 28;
532
533         vertPerRow = segments + 1;
534
535         var surfCount = 0;
536
537         var vertCount = 0;
538         var normCount = 0;
539         var uvCount = 0;
540
541         var indexCount = 0;
542
543         for ( var surf = minPatches ; surf < maxPatches ; surf ++ ) {
544
545                 // lid is in the middle of the data, patches 20-27,
546                 // so ignore it for this part of the loop if the lid is not desired
547                 if ( lid || ( surf < 20 || surf >= 28 ) ) {
548
549                         // get M * G * M matrix for x,y,z
550                         for ( i = 0 ; i < 3 ; i ++ ) {
551
552                                 // get control patches
553                                 for ( r = 0 ; r < 4 ; r ++ ) {
554
555                                         for ( c = 0 ; c < 4 ; c ++ ) {
556
557                                                 // transposed
558                                                 g[ c * 4 + r ] = teapotVertices[ teapotPatches[ surf * 16 + r * 4 + c ] * 3 + i ] ;
559
560                                                 // is the lid to be made larger, and is this a point on the lid
561                                                 // that is X or Y?
562                                                 if ( fitLid && ( surf >= 20 && surf < 28 ) && ( i !== 2 ) ) {
563
564                                                         // increase XY size by 7.7%, found empirically. I don't
565                                                         // increase Z so that the teapot will continue to fit in the
566                                                         // space -1 to 1 for Y (Y is up for the final model).
567                                                         g[ c * 4 + r ] *= 1.077;
568
569                                                 }
570
571                                                 // Blinn "fixed" the teapot by dividing Z by blinnScale, and that's the
572                                                 // data we now use. The original teapot is taller. Fix it:
573                                                 if ( ! blinn && ( i === 2 ) ) {
574
575                                                         g[ c * 4 + r ] *= blinnScale;
576
577                                                 }
578
579                                         }
580
581                                 }
582
583                                 gmx.set( g[ 0 ], g[ 1 ], g[ 2 ], g[ 3 ], g[ 4 ], g[ 5 ], g[ 6 ], g[ 7 ], g[ 8 ], g[ 9 ], g[ 10 ], g[ 11 ], g[ 12 ], g[ 13 ], g[ 14 ], g[ 15 ] );
584
585                                 tmtx.multiplyMatrices( gmx, ms );
586                                 mgm[ i ].multiplyMatrices( mst, tmtx );
587
588                         }
589
590                         // step along, get points, and output
591                         for ( sstep = 0 ; sstep <= segments ; sstep ++ ) {
592
593                                 s = sstep / segments;
594
595                                 for ( tstep = 0 ; tstep <= segments ; tstep ++ ) {
596
597                                         t = tstep / segments;
598
599                                         // point from basis
600                                         // get power vectors and their derivatives
601                                         for ( p = 4, sval = tval = 1.0 ; p -- ; ) {
602
603                                                 sp[ p ] = sval ;
604                                                 tp[ p ] = tval ;
605                                                 sval *= s ;
606                                                 tval *= t ;
607
608                                                 if ( p === 3 ) {
609
610                                                         dsp[ p ] = dtp[ p ] = 0.0 ;
611                                                         dsval = dtval = 1.0 ;
612
613                                                 } else {
614
615                                                         dsp[ p ] = dsval * ( 3 - p ) ;
616                                                         dtp[ p ] = dtval * ( 3 - p ) ;
617                                                         dsval *= s ;
618                                                         dtval *= t ;
619
620                                                 }
621
622                                         }
623
624                                         vsp.fromArray( sp );
625                                         vtp.fromArray( tp );
626                                         vdsp.fromArray( dsp );
627                                         vdtp.fromArray( dtp );
628
629                                         // do for x,y,z
630                                         for ( i = 0 ; i < 3 ; i ++ ) {
631
632                                                 // multiply power vectors times matrix to get value
633                                                 tcoord = vsp.clone();
634                                                 tcoord.applyMatrix4( mgm[ i ] );
635                                                 vert[ i ] = tcoord.dot( vtp );
636
637                                                 // get s and t tangent vectors
638                                                 tcoord = vdsp.clone();
639                                                 tcoord.applyMatrix4( mgm[ i ] );
640                                                 sdir[ i ] = tcoord.dot( vtp ) ;
641
642                                                 tcoord = vsp.clone();
643                                                 tcoord.applyMatrix4( mgm[ i ] );
644                                                 tdir[ i ] = tcoord.dot( vdtp ) ;
645
646                                         }
647
648                                         // find normal
649                                         vsdir.fromArray( sdir );
650                                         vtdir.fromArray( tdir );
651                                         norm.crossVectors( vtdir, vsdir );
652                                         norm.normalize();
653
654                                         // if X and Z length is 0, at the cusp, so point the normal up or down, depending on patch number
655                                         if ( vert[ 0 ] === 0 && vert[ 1 ] === 0 )
656                                         {
657
658                                                 // if above the middle of the teapot, normal points up, else down
659                                                 normOut.set( 0, vert[ 2 ] > maxHeight2 ? 1 : - 1, 0 );
660
661                                         }
662                                         else
663                                         {
664
665                                                 // standard output: rotate on X axis
666                                                 normOut.set( norm.x, norm.z, - norm.y );
667
668                                         }
669
670                                         // store it all
671                                         vertices[ vertCount ++ ] = trueSize * vert[ 0 ];
672                                         vertices[ vertCount ++ ] = trueSize * ( vert[ 2 ] - maxHeight2 );
673                                         vertices[ vertCount ++ ] = - trueSize * vert[ 1 ];
674
675                                         normals[ normCount ++ ] = normOut.x;
676                                         normals[ normCount ++ ] = normOut.y;
677                                         normals[ normCount ++ ] = normOut.z;
678
679                                         uvs[ uvCount ++ ] = 1 - t;
680                                         uvs[ uvCount ++ ] = 1 - s;
681
682                                 }
683
684                         }
685
686                         // save the faces
687                         for ( sstep = 0 ; sstep < segments ; sstep ++ ) {
688
689                                 for ( tstep = 0 ; tstep < segments ; tstep ++ ) {
690
691                                         v1 = surfCount * vertPerRow * vertPerRow + sstep * vertPerRow + tstep;
692                                         v2 = v1 + 1;
693                                         v3 = v2 + vertPerRow;
694                                         v4 = v1 + vertPerRow;
695
696                                         // Normals and UVs cannot be shared. Without clone(), you can see the consequences
697                                         // of sharing if you call geometry.applyMatrix( matrix ).
698                                         if ( notDegenerate ( v1, v2, v3 ) ) {
699
700                                                 indices[ indexCount ++ ] = v1;
701                                                 indices[ indexCount ++ ] = v2;
702                                                 indices[ indexCount ++ ] = v3;
703
704                                         }
705                                         if ( notDegenerate ( v1, v3, v4 ) ) {
706
707                                                 indices[ indexCount ++ ] = v1;
708                                                 indices[ indexCount ++ ] = v3;
709                                                 indices[ indexCount ++ ] = v4;
710
711                                         }
712
713                                 }
714
715                         }
716
717                         // increment only if a surface was used
718                         surfCount ++;
719
720                 }
721
722         }
723
724         this.setIndex( new THREE.BufferAttribute( indices, 1 ) );
725         this.addAttribute( 'position', new THREE.BufferAttribute( vertices, 3 ) );
726         this.addAttribute( 'normal', new THREE.BufferAttribute( normals, 3 ) );
727         this.addAttribute( 'uv', new THREE.BufferAttribute( uvs, 2 ) );
728
729         this.computeBoundingSphere();
730
731 };
732
733
734 THREE.TeapotBufferGeometry.prototype = Object.create( THREE.BufferGeometry.prototype );
735 THREE.TeapotBufferGeometry.prototype.constructor = THREE.TeapotBufferGeometry;
736
737 THREE.TeapotBufferGeometry.prototype.clone = function () {
738
739         var bufferGeometry = new THREE.TeapotBufferGeometry(
740                 this.parameters.size,
741                 this.parameters.segments,
742                 this.parameters.bottom,
743                 this.parameters.lid,
744                 this.parameters.body,
745                 this.parameters.fitLid,
746                 this.parameters.blinn
747         );
748
749         return bufferGeometry;
750
751 };