Line data Source code
1 : /* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
2 : /*************************************************************************
3 : *
4 : * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
5 : *
6 : * Copyright 2008 by Sun Microsystems, Inc.
7 : *
8 : * OpenOffice.org - a multi-platform office productivity suite
9 : *
10 : * This file is part of OpenOffice.org.
11 : *
12 : * OpenOffice.org is free software: you can redistribute it and/or modify
13 : * it under the terms of the GNU Lesser General Public License version 3
14 : * only, as published by the Free Software Foundation.
15 : *
16 : * OpenOffice.org is distributed in the hope that it will be useful,
17 : * but WITHOUT ANY WARRANTY; without even the implied warranty of
18 : * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
19 : * GNU Lesser General Public License version 3 for more details
20 : * (a copy is included in the LICENSE file that accompanied this code).
21 : *
22 : * You should have received a copy of the GNU Lesser General Public License
23 : * version 3 along with OpenOffice.org. If not, see
24 : * <http://www.openoffice.org/license.html>
25 : * for a copy of the LGPLv3 License.
26 : *
27 : ************************************************************************/
28 :
29 : #include <utility>
30 :
31 : #include <boost/make_shared.hpp>
32 :
33 : #include "OGLTrans_TransitionImpl.hxx"
34 : #include "OGLTrans_Shaders.hxx"
35 : #include <GL/gl.h>
36 : #include <math.h>
37 :
38 : using boost::make_shared;
39 : using boost::shared_ptr;
40 :
41 : using std::max;
42 : using std::min;
43 : using std::vector;
44 :
45 0 : TransitionScene::TransitionScene(TransitionScene const& rOther)
46 : : maLeavingSlidePrimitives(rOther.maLeavingSlidePrimitives)
47 : , maEnteringSlidePrimitives(rOther.maEnteringSlidePrimitives)
48 : , maOverallOperations(rOther.maOverallOperations)
49 0 : , maSceneObjects(rOther.maSceneObjects)
50 : {
51 0 : }
52 :
53 0 : TransitionScene& TransitionScene::operator=(const TransitionScene& rOther)
54 : {
55 0 : TransitionScene aTmp(rOther);
56 0 : swap(aTmp);
57 0 : return *this;
58 : }
59 :
60 0 : void TransitionScene::swap(TransitionScene& rOther)
61 : {
62 : using std::swap;
63 :
64 0 : swap(maLeavingSlidePrimitives, rOther.maLeavingSlidePrimitives);
65 0 : swap(maEnteringSlidePrimitives, rOther.maEnteringSlidePrimitives);
66 0 : swap(maOverallOperations, rOther.maOverallOperations);
67 0 : swap(maSceneObjects, rOther.maSceneObjects);
68 0 : }
69 :
70 0 : OGLTransitionImpl::~OGLTransitionImpl()
71 : {
72 0 : }
73 :
74 0 : void OGLTransitionImpl::setScene(TransitionScene const& rScene)
75 : {
76 0 : maScene = rScene;
77 0 : }
78 :
79 0 : void OGLTransitionImpl::prepare( ::sal_Int32 glLeavingSlideTex, ::sal_Int32 glEnteringSlideTex )
80 : {
81 0 : const SceneObjects_t& rSceneObjects(maScene.getSceneObjects());
82 0 : for(unsigned int i(0); i != rSceneObjects.size(); ++i) {
83 0 : rSceneObjects[i]->prepare();
84 : }
85 :
86 0 : prepareTransition_( glLeavingSlideTex, glEnteringSlideTex );
87 0 : }
88 :
89 0 : void OGLTransitionImpl::finish()
90 : {
91 0 : const SceneObjects_t& rSceneObjects(maScene.getSceneObjects());
92 0 : for(unsigned int i(0); i != rSceneObjects.size(); ++i) {
93 0 : rSceneObjects[i]->finish();
94 : }
95 :
96 0 : finishTransition_();
97 0 : }
98 :
99 0 : static void blendSlide( double depth )
100 : {
101 0 : double showHeight = -1 + depth*2;
102 0 : GLfloat reflectionColor[] = {0, 0, 0, 0.25};
103 :
104 0 : glDisable( GL_DEPTH_TEST );
105 0 : glBegin( GL_QUADS );
106 0 : glColor4fv( reflectionColor );
107 0 : glVertex3f( -1, -1, 0 );
108 0 : glColor4f( 0, 0, 0, 1 );
109 0 : glVertex3f(-1, showHeight, 0 );
110 0 : glVertex3f( 1, showHeight, 0 );
111 0 : glColor4fv( reflectionColor );
112 0 : glVertex3f( 1, -1, 0 );
113 0 : glEnd();
114 :
115 0 : glBegin( GL_QUADS );
116 0 : glColor4f( 0, 0, 0, 1 );
117 0 : glVertex3f( -1, showHeight, 0 );
118 0 : glVertex3f( -1, 1, 0 );
119 0 : glVertex3f( 1, 1, 0 );
120 0 : glVertex3f( 1, showHeight, 0 );
121 0 : glEnd();
122 0 : glEnable( GL_DEPTH_TEST );
123 0 : }
124 :
125 0 : static void slideShadow( double nTime, const Primitive& primitive, double sw, double sh )
126 : {
127 0 : double reflectionDepth = 0.3;
128 :
129 0 : glEnable(GL_BLEND);
130 0 : glBlendFunc(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA);
131 0 : glDisable(GL_LIGHTING);
132 :
133 0 : glPushMatrix();
134 0 : primitive.applyOperations( nTime, sw, sh );
135 0 : blendSlide( reflectionDepth );
136 0 : glPopMatrix();
137 :
138 0 : glDisable(GL_BLEND);
139 0 : glEnable(GL_LIGHTING);
140 0 : }
141 :
142 0 : void OGLTransitionImpl::prepare_( double, double, double, double, double )
143 : {
144 0 : }
145 :
146 0 : void OGLTransitionImpl::prepareTransition_( ::sal_Int32, ::sal_Int32 )
147 : {
148 0 : }
149 :
150 0 : void OGLTransitionImpl::finishTransition_()
151 : {
152 0 : }
153 :
154 0 : void OGLTransitionImpl::displaySlides_( double nTime, ::sal_Int32 glLeavingSlideTex, ::sal_Int32 glEnteringSlideTex, double SlideWidthScale, double SlideHeightScale )
155 : {
156 0 : applyOverallOperations( nTime, SlideWidthScale, SlideHeightScale );
157 :
158 0 : glEnable(GL_TEXTURE_2D);
159 0 : displaySlide( nTime, glLeavingSlideTex, maScene.getLeavingSlide(), SlideWidthScale, SlideHeightScale );
160 0 : displaySlide( nTime, glEnteringSlideTex, maScene.getEnteringSlide(), SlideWidthScale, SlideHeightScale );
161 0 : }
162 :
163 0 : void OGLTransitionImpl::display( double nTime, ::sal_Int32 glLeavingSlideTex, ::sal_Int32 glEnteringSlideTex,
164 : double SlideWidth, double SlideHeight, double DispWidth, double DispHeight )
165 : {
166 0 : const double SlideWidthScale = SlideWidth/DispWidth;
167 0 : const double SlideHeightScale = SlideHeight/DispHeight;
168 :
169 0 : prepare_( nTime, SlideWidth, SlideHeight, DispWidth, DispHeight );
170 :
171 0 : glPushMatrix();
172 0 : displaySlides_( nTime, glLeavingSlideTex, glEnteringSlideTex, SlideWidthScale, SlideHeightScale );
173 0 : displayScene( nTime, SlideWidth, SlideHeight, DispWidth, DispHeight );
174 0 : glPopMatrix();
175 0 : }
176 :
177 0 : void OGLTransitionImpl::applyOverallOperations( double nTime, double SlideWidthScale, double SlideHeightScale )
178 : {
179 0 : const Operations_t& rOverallOperations(maScene.getOperations());
180 0 : for(unsigned int i(0); i != rOverallOperations.size(); ++i)
181 0 : rOverallOperations[i]->interpolate(nTime,SlideWidthScale,SlideHeightScale);
182 0 : }
183 :
184 : void
185 0 : OGLTransitionImpl::displaySlide(
186 : const double nTime,
187 : const ::sal_Int32 glSlideTex, const Primitives_t& primitives,
188 : double SlideWidthScale, double SlideHeightScale )
189 : {
190 : //TODO change to foreach
191 0 : glBindTexture(GL_TEXTURE_2D, glSlideTex);
192 :
193 : // display slide reflection
194 : // note that depth test is turned off while blending the shadow
195 : // so the slides has to be rendered in right order, see rochade as example
196 0 : if( maSettings.mbReflectSlides ) {
197 0 : double surfaceLevel = -0.04;
198 :
199 : /* reflected slides */
200 0 : glPushMatrix();
201 :
202 0 : glScaled( 1, -1, 1 );
203 0 : glTranslated( 0, 2 - surfaceLevel, 0 );
204 :
205 0 : glCullFace(GL_FRONT);
206 0 : for(unsigned int i(0); i < primitives.size(); ++i)
207 0 : primitives[i].display(nTime, SlideWidthScale, SlideHeightScale);
208 0 : glCullFace(GL_BACK);
209 :
210 0 : slideShadow( nTime, primitives[0], SlideWidthScale, SlideHeightScale );
211 :
212 0 : glPopMatrix();
213 : }
214 :
215 0 : for(unsigned int i(0); i < primitives.size(); ++i)
216 0 : primitives[i].display(nTime, SlideWidthScale, SlideHeightScale);
217 0 : }
218 :
219 0 : void OGLTransitionImpl::displayScene( double nTime, double SlideWidth, double SlideHeight, double DispWidth, double DispHeight )
220 : {
221 0 : const SceneObjects_t& rSceneObjects(maScene.getSceneObjects());
222 0 : glEnable(GL_TEXTURE_2D);
223 0 : for(unsigned int i(0); i != rSceneObjects.size(); ++i)
224 0 : rSceneObjects[i]->display(nTime, SlideWidth, SlideHeight, DispWidth, DispHeight);
225 0 : }
226 :
227 0 : void Primitive::display(double nTime, double WidthScale, double HeightScale) const
228 : {
229 0 : glPushMatrix();
230 :
231 0 : applyOperations( nTime, WidthScale, HeightScale );
232 :
233 0 : glEnableClientState( GL_VERTEX_ARRAY );
234 0 : if(!Normals.empty())
235 : {
236 0 : glNormalPointer( GL_DOUBLE , 0 , &Normals[0] );
237 0 : glEnableClientState( GL_NORMAL_ARRAY );
238 : }
239 0 : glEnableClientState( GL_TEXTURE_COORD_ARRAY );
240 0 : glTexCoordPointer( 2, GL_DOUBLE, 0, &TexCoords[0] );
241 0 : glVertexPointer( 3, GL_DOUBLE, 0, &Vertices[0] );
242 0 : glDrawArrays( GL_TRIANGLES, 0, Vertices.size() );
243 0 : glPopMatrix();
244 0 : }
245 :
246 0 : void Primitive::applyOperations(double nTime, double WidthScale, double HeightScale) const
247 : {
248 0 : for(unsigned int i(0); i < Operations.size(); ++i)
249 0 : Operations[i]->interpolate( nTime ,WidthScale,HeightScale);
250 0 : glScaled(WidthScale,HeightScale,1);
251 0 : }
252 :
253 0 : void SceneObject::display(double nTime, double /* SlideWidth */, double /* SlideHeight */, double DispWidth, double DispHeight ) const
254 : {
255 0 : for(unsigned int i(0); i < maPrimitives.size(); ++i) {
256 : // fixme: allow various model spaces, now we make it so that
257 : // it is regular -1,-1 to 1,1, where the whole display fits in
258 0 : glPushMatrix();
259 0 : if (DispHeight > DispWidth)
260 0 : glScaled(DispHeight/DispWidth, 1, 1);
261 : else
262 0 : glScaled(1, DispWidth/DispHeight, 1);
263 0 : maPrimitives[i].display(nTime, 1, 1);
264 0 : glPopMatrix();
265 : }
266 0 : }
267 :
268 0 : void SceneObject::pushPrimitive(const Primitive &p)
269 : {
270 0 : maPrimitives.push_back(p);
271 0 : }
272 :
273 0 : SceneObject::SceneObject()
274 0 : : maPrimitives()
275 : {
276 0 : }
277 :
278 0 : SceneObject::~SceneObject()
279 : {
280 0 : }
281 :
282 0 : Iris::Iris()
283 : : SceneObject()
284 0 : , maTexture(0)
285 : {
286 0 : }
287 :
288 0 : void Iris::display(double nTime, double SlideWidth, double SlideHeight, double DispWidth, double DispHeight ) const
289 : {
290 0 : glBindTexture(GL_TEXTURE_2D, maTexture);
291 0 : SceneObject::display(nTime, SlideWidth, SlideHeight, DispWidth, DispHeight);
292 0 : }
293 :
294 0 : void Iris::prepare()
295 : {
296 : static const GLubyte img[3] = { 80, 80, 80 };
297 :
298 0 : glGenTextures(1, &maTexture);
299 0 : glBindTexture(GL_TEXTURE_2D, maTexture);
300 0 : glTexImage2D(GL_TEXTURE_2D, 0, 3, 1, 1, 0, GL_RGB, GL_UNSIGNED_BYTE, img);
301 0 : glTexParameteri(GL_TEXTURE_2D,GL_TEXTURE_WRAP_S,GL_REPEAT);
302 0 : glTexParameteri(GL_TEXTURE_2D,GL_TEXTURE_WRAP_T,GL_REPEAT);
303 0 : glTexParameteri(GL_TEXTURE_2D,GL_TEXTURE_MAG_FILTER,GL_LINEAR);
304 0 : glTexParameteri(GL_TEXTURE_2D,GL_TEXTURE_MIN_FILTER,GL_LINEAR);
305 0 : }
306 :
307 0 : void Iris::finish()
308 : {
309 0 : glDeleteTextures(1, &maTexture);
310 0 : }
311 :
312 : namespace
313 : {
314 :
315 0 : class SimpleTransition : public OGLTransitionImpl
316 : {
317 : public:
318 0 : SimpleTransition()
319 0 : : OGLTransitionImpl()
320 : {
321 0 : }
322 :
323 0 : SimpleTransition(const TransitionScene& rScene, const TransitionSettings& rSettings)
324 0 : : OGLTransitionImpl(rScene, rSettings)
325 : {
326 0 : }
327 : };
328 :
329 : shared_ptr<OGLTransitionImpl>
330 0 : makeSimpleTransition()
331 : {
332 0 : return make_shared<SimpleTransition>();
333 : }
334 :
335 : shared_ptr<OGLTransitionImpl>
336 0 : makeSimpleTransition(
337 : const Primitives_t& rLeavingSlidePrimitives,
338 : const Primitives_t& rEnteringSlidePrimitives,
339 : const Operations_t& rOverallOperations,
340 : const SceneObjects_t& rSceneObjects,
341 : const TransitionSettings& rSettings = TransitionSettings())
342 : {
343 : return make_shared<SimpleTransition>(
344 : TransitionScene(rLeavingSlidePrimitives, rEnteringSlidePrimitives, rOverallOperations, rSceneObjects),
345 0 : rSettings)
346 : ;
347 : }
348 :
349 : shared_ptr<OGLTransitionImpl>
350 0 : makeSimpleTransition(
351 : const Primitives_t& rLeavingSlidePrimitives,
352 : const Primitives_t& rEnteringSlidePrimitives,
353 : const Operations_t& rOverallOperations,
354 : const TransitionSettings& rSettings = TransitionSettings())
355 : {
356 0 : return makeSimpleTransition(rLeavingSlidePrimitives, rEnteringSlidePrimitives, rOverallOperations, SceneObjects_t(), rSettings);
357 : }
358 :
359 : shared_ptr<OGLTransitionImpl>
360 0 : makeSimpleTransition(
361 : const Primitives_t& rLeavingSlidePrimitives,
362 : const Primitives_t& rEnteringSlidePrimitives,
363 : const SceneObjects_t& rSceneObjects,
364 : const TransitionSettings& rSettings = TransitionSettings())
365 : {
366 0 : return makeSimpleTransition(rLeavingSlidePrimitives, rEnteringSlidePrimitives, Operations_t(), rSceneObjects, rSettings);
367 : }
368 :
369 : shared_ptr<OGLTransitionImpl>
370 0 : makeSimpleTransition(
371 : const Primitives_t& rLeavingSlidePrimitives,
372 : const Primitives_t& rEnteringSlidePrimitives,
373 : const TransitionSettings& rSettings = TransitionSettings())
374 : {
375 0 : return makeSimpleTransition(rLeavingSlidePrimitives, rEnteringSlidePrimitives, Operations_t(), SceneObjects_t(), rSettings);
376 : }
377 :
378 : }
379 :
380 0 : boost::shared_ptr<OGLTransitionImpl> makeOutsideCubeFaceToLeft()
381 : {
382 0 : Primitive Slide;
383 :
384 0 : Slide.pushTriangle(basegfx::B2DVector(0,0),basegfx::B2DVector(1,0),basegfx::B2DVector(0,1));
385 0 : Slide.pushTriangle(basegfx::B2DVector(1,0),basegfx::B2DVector(0,1),basegfx::B2DVector(1,1));
386 :
387 0 : Primitives_t aLeavingPrimitives;
388 0 : aLeavingPrimitives.push_back(Slide);
389 :
390 0 : Slide.Operations.push_back(makeRotateAndScaleDepthByWidth(basegfx::B3DVector(0,1,0),basegfx::B3DVector(0,0,-1),90,false,0.0,1.0));
391 :
392 0 : Primitives_t aEnteringPrimitives;
393 0 : aEnteringPrimitives.push_back(Slide);
394 :
395 0 : Operations_t aOperations;
396 0 : aOperations.push_back(makeRotateAndScaleDepthByWidth(basegfx::B3DVector(0,1,0),basegfx::B3DVector(0,0,-1),-90,true,0.0,1.0));
397 :
398 0 : return makeSimpleTransition(aLeavingPrimitives, aEnteringPrimitives, aOperations);
399 : }
400 :
401 0 : boost::shared_ptr<OGLTransitionImpl> makeInsideCubeFaceToLeft()
402 : {
403 0 : Primitive Slide;
404 :
405 0 : Slide.pushTriangle(basegfx::B2DVector(0,0),basegfx::B2DVector(1,0),basegfx::B2DVector(0,1));
406 0 : Slide.pushTriangle(basegfx::B2DVector(1,0),basegfx::B2DVector(0,1),basegfx::B2DVector(1,1));
407 :
408 0 : Primitives_t aLeavingPrimitives;
409 0 : aLeavingPrimitives.push_back(Slide);
410 :
411 0 : Slide.Operations.push_back(makeRotateAndScaleDepthByWidth(basegfx::B3DVector(0,1,0),basegfx::B3DVector(0,0,1),-90,false,0.0,1.0));
412 :
413 0 : Primitives_t aEnteringPrimitives;
414 0 : aEnteringPrimitives.push_back(Slide);
415 :
416 0 : Operations_t aOperations;
417 0 : aOperations.push_back(makeRotateAndScaleDepthByWidth(basegfx::B3DVector(0,1,0),basegfx::B3DVector(0,0,1),90,true,0.0,1.0));
418 :
419 0 : return makeSimpleTransition(aLeavingPrimitives, aEnteringPrimitives, aOperations);
420 : }
421 :
422 0 : boost::shared_ptr<OGLTransitionImpl> makeFallLeaving()
423 : {
424 0 : Primitive Slide;
425 :
426 0 : Slide.pushTriangle(basegfx::B2DVector(0,0),basegfx::B2DVector(1,0),basegfx::B2DVector(0,1));
427 0 : Slide.pushTriangle(basegfx::B2DVector(1,0),basegfx::B2DVector(0,1),basegfx::B2DVector(1,1));
428 :
429 0 : Primitives_t aEnteringPrimitives;
430 0 : aEnteringPrimitives.push_back(Slide);
431 :
432 0 : Slide.Operations.push_back(makeRotateAndScaleDepthByWidth(basegfx::B3DVector(1,0,0),basegfx::B3DVector(0,-1,0), 90,true,0.0,1.0));
433 0 : Primitives_t aLeavingPrimitives;
434 0 : aLeavingPrimitives.push_back(Slide);
435 :
436 0 : TransitionSettings aSettings;
437 0 : aSettings.mbUseMipMapEntering = false;
438 :
439 0 : return makeSimpleTransition(aLeavingPrimitives, aEnteringPrimitives, aSettings);
440 : }
441 :
442 0 : boost::shared_ptr<OGLTransitionImpl> makeTurnAround()
443 : {
444 0 : Primitive Slide;
445 :
446 0 : TransitionSettings aSettings;
447 0 : aSettings.mbReflectSlides = true;
448 :
449 0 : Slide.pushTriangle(basegfx::B2DVector(0,0),basegfx::B2DVector(1,0),basegfx::B2DVector(0,1));
450 0 : Slide.pushTriangle(basegfx::B2DVector(1,0),basegfx::B2DVector(0,1),basegfx::B2DVector(1,1));
451 0 : Primitives_t aLeavingPrimitives;
452 0 : aLeavingPrimitives.push_back(Slide);
453 :
454 0 : Slide.Operations.push_back(makeRotateAndScaleDepthByWidth(basegfx::B3DVector(0,1,0),basegfx::B3DVector(0,0,0),-180,false,0.0,1.0));
455 0 : Primitives_t aEnteringPrimitives;
456 0 : aEnteringPrimitives.push_back(Slide);
457 :
458 0 : Operations_t aOperations;
459 0 : aOperations.push_back(makeSTranslate(basegfx::B3DVector(0, 0, -1.5),true, 0, 0.5));
460 0 : aOperations.push_back(makeSTranslate(basegfx::B3DVector(0, 0, 1.5), true, 0.5, 1));
461 0 : aOperations.push_back(makeRotateAndScaleDepthByWidth(basegfx::B3DVector(0, 1, 0),basegfx::B3DVector(0, 0, 0), -180, true, 0.0, 1.0));
462 :
463 0 : return makeSimpleTransition(aLeavingPrimitives, aEnteringPrimitives, aOperations, aSettings);
464 : }
465 :
466 0 : boost::shared_ptr<OGLTransitionImpl> makeTurnDown()
467 : {
468 0 : Primitive Slide;
469 :
470 0 : Slide.pushTriangle(basegfx::B2DVector(0,0),basegfx::B2DVector(1,0),basegfx::B2DVector(0,1));
471 0 : Slide.pushTriangle(basegfx::B2DVector(1,0),basegfx::B2DVector(0,1),basegfx::B2DVector(1,1));
472 0 : Primitives_t aLeavingPrimitives;
473 0 : aLeavingPrimitives.push_back(Slide);
474 :
475 0 : Slide.Operations.push_back(makeSTranslate(basegfx::B3DVector(0, 0, 0.0001), false, -1.0, 0.0));
476 0 : Slide.Operations.push_back(makeSRotate (basegfx::B3DVector(0, 0, 1), basegfx::B3DVector(-1, 1, 0), -90, true, 0.0, 1.0));
477 0 : Slide.Operations.push_back(makeSRotate (basegfx::B3DVector(0, 0, 1), basegfx::B3DVector(-1, 1, 0), 90, false, -1.0, 0.0));
478 0 : Primitives_t aEnteringPrimitives;
479 0 : aEnteringPrimitives.push_back(Slide);
480 :
481 0 : TransitionSettings aSettings;
482 0 : aSettings.mbUseMipMapLeaving = false;
483 :
484 0 : return makeSimpleTransition(aLeavingPrimitives, aEnteringPrimitives, aSettings);
485 : }
486 :
487 0 : boost::shared_ptr<OGLTransitionImpl> makeIris()
488 : {
489 0 : Primitive Slide;
490 :
491 0 : Slide.pushTriangle (basegfx::B2DVector (0,0), basegfx::B2DVector (1,0), basegfx::B2DVector (0,1));
492 0 : Slide.pushTriangle (basegfx::B2DVector (1,0), basegfx::B2DVector (0,1), basegfx::B2DVector (1,1));
493 0 : Primitives_t aEnteringPrimitives;
494 0 : aEnteringPrimitives.push_back (Slide);
495 :
496 0 : Slide.Operations.push_back (makeSTranslate (basegfx::B3DVector (0, 0, 0.000001), false, -1, 0));
497 0 : Slide.Operations.push_back (makeSTranslate (basegfx::B3DVector (0, 0, -0.000002), false, 0.5, 1));
498 0 : Primitives_t aLeavingPrimitives;
499 0 : aLeavingPrimitives.push_back (Slide);
500 :
501 :
502 0 : Primitive irisPart, part;
503 0 : int i, nSteps = 24, nParts = 7;
504 0 : double t = 1.0/nSteps, cx, cy, lcx, lcy, lx = 1, ly = 0, x, y, cxo, cyo, lcxo, lcyo, of=2.2, f=1.42;
505 :
506 0 : for (i=1; i<=nSteps; i++) {
507 0 : x = cos ((3*2*M_PI*t)/nParts);
508 0 : y = -sin ((3*2*M_PI*t)/nParts);
509 0 : cx = (f*x + 1)/2;
510 0 : cy = (f*y + 1)/2;
511 0 : lcx = (f*lx + 1)/2;
512 0 : lcy = (f*ly + 1)/2;
513 0 : cxo = (of*x + 1)/2;
514 0 : cyo = (of*y + 1)/2;
515 0 : lcxo = (of*lx + 1)/2;
516 0 : lcyo = (of*ly + 1)/2;
517 : irisPart.pushTriangle (basegfx::B2DVector (lcx, lcy),
518 : basegfx::B2DVector (lcxo, lcyo),
519 0 : basegfx::B2DVector (cx, cy));
520 : irisPart.pushTriangle (basegfx::B2DVector (cx, cy),
521 : basegfx::B2DVector (lcxo, lcyo),
522 0 : basegfx::B2DVector (cxo, cyo));
523 0 : lx = x;
524 0 : ly = y;
525 0 : t += 1.0/nSteps;
526 : }
527 :
528 0 : shared_ptr<Iris> pIris = make_shared<Iris>();
529 0 : double angle = 87;
530 :
531 0 : for (i = 0; i < nParts; i++) {
532 0 : irisPart.Operations.clear ();
533 : double rx, ry;
534 :
535 0 : rx = cos ((2*M_PI*i)/nParts);
536 0 : ry = sin ((2*M_PI*i)/nParts);
537 0 : irisPart.Operations.push_back (makeSRotate (basegfx::B3DVector(0, 0, 1), basegfx::B3DVector(rx, ry, 0), angle, true, 0.0, 0.5));
538 0 : irisPart.Operations.push_back (makeSRotate (basegfx::B3DVector(0, 0, 1), basegfx::B3DVector(rx, ry, 0), -angle, true, 0.5, 1));
539 0 : if (i > 0) {
540 0 : irisPart.Operations.push_back (makeSTranslate (basegfx::B3DVector(rx, ry, 0), false, -1, 0));
541 0 : irisPart.Operations.push_back (makeSRotate (basegfx::B3DVector(0, 0, 1), basegfx::B3DVector(0, 0, 0), i*360.0/nParts, false, -1, 0));
542 0 : irisPart.Operations.push_back (makeSTranslate (basegfx::B3DVector(-1, 0, 0), false, -1, 0));
543 : }
544 0 : irisPart.Operations.push_back(makeSTranslate(basegfx::B3DVector(0, 0, 1), false, -2, 0.0));
545 0 : irisPart.Operations.push_back (makeSRotate (basegfx::B3DVector(1, .5, 0), basegfx::B3DVector(1, 0, 0), -30, false, -1, 0));
546 0 : pIris->pushPrimitive (irisPart);
547 : }
548 :
549 0 : SceneObjects_t aSceneObjects;
550 0 : aSceneObjects.push_back (pIris);
551 :
552 0 : TransitionSettings aSettings;
553 0 : aSettings.mbUseMipMapLeaving = aSettings.mbUseMipMapEntering = false;
554 :
555 0 : return makeSimpleTransition(aLeavingPrimitives, aEnteringPrimitives, aSceneObjects, aSettings);
556 : }
557 :
558 : namespace
559 : {
560 :
561 0 : class RochadeTransition : public OGLTransitionImpl
562 : {
563 : public:
564 0 : RochadeTransition(const TransitionScene& rScene, const TransitionSettings& rSettings)
565 0 : : OGLTransitionImpl(rScene, rSettings)
566 0 : {}
567 :
568 : private:
569 : virtual void displaySlides_( double nTime, ::sal_Int32 glLeavingSlideTex, ::sal_Int32 glEnteringSlideTex, double SlideWidthScale, double SlideHeightScale ) SAL_OVERRIDE;
570 : };
571 :
572 0 : void RochadeTransition::displaySlides_( double nTime, ::sal_Int32 glLeavingSlideTex, ::sal_Int32 glEnteringSlideTex, double SlideWidthScale, double SlideHeightScale )
573 : {
574 0 : applyOverallOperations( nTime, SlideWidthScale, SlideHeightScale );
575 :
576 0 : glEnable(GL_TEXTURE_2D);
577 :
578 0 : if( nTime > .5) {
579 0 : displaySlide( nTime, glLeavingSlideTex, getScene().getLeavingSlide(), SlideWidthScale, SlideHeightScale );
580 0 : displaySlide( nTime, glEnteringSlideTex, getScene().getEnteringSlide(), SlideWidthScale, SlideHeightScale );
581 : } else {
582 0 : displaySlide( nTime, glEnteringSlideTex, getScene().getEnteringSlide(), SlideWidthScale, SlideHeightScale );
583 0 : displaySlide( nTime, glLeavingSlideTex, getScene().getLeavingSlide(), SlideWidthScale, SlideHeightScale );
584 : }
585 0 : }
586 :
587 : shared_ptr<OGLTransitionImpl>
588 0 : makeRochadeTransition(
589 : const Primitives_t& rLeavingSlidePrimitives,
590 : const Primitives_t& rEnteringSlidePrimitives,
591 : const TransitionSettings& rSettings)
592 : {
593 : return make_shared<RochadeTransition>(
594 : TransitionScene(rLeavingSlidePrimitives, rEnteringSlidePrimitives),
595 0 : rSettings)
596 : ;
597 :
598 : }
599 : }
600 :
601 0 : boost::shared_ptr<OGLTransitionImpl> makeRochade()
602 : {
603 0 : Primitive Slide;
604 :
605 0 : TransitionSettings aSettings;
606 0 : aSettings.mbReflectSlides = true;
607 :
608 : double w, h;
609 :
610 0 : w = 2.2;
611 0 : h = 10;
612 :
613 0 : Slide.pushTriangle(basegfx::B2DVector(0,0),basegfx::B2DVector(1,0),basegfx::B2DVector(0,1));
614 0 : Slide.pushTriangle(basegfx::B2DVector(1,0),basegfx::B2DVector(0,1),basegfx::B2DVector(1,1));
615 :
616 0 : Slide.Operations.push_back(makeSEllipseTranslate(w, h, 0.25, -0.25, true, 0, 1));
617 0 : Slide.Operations.push_back(makeRotateAndScaleDepthByWidth(basegfx::B3DVector(0,1,0),basegfx::B3DVector(0,0,0), -45, true, 0, 1));
618 0 : Primitives_t aLeavingSlide;
619 0 : aLeavingSlide.push_back(Slide);
620 :
621 0 : Slide.Operations.clear();
622 0 : Slide.Operations.push_back(makeSEllipseTranslate(w, h, 0.75, 0.25, true, 0, 1));
623 0 : Slide.Operations.push_back(makeSTranslate(basegfx::B3DVector(0, 0, -h), false, -1, 0));
624 0 : Slide.Operations.push_back(makeRotateAndScaleDepthByWidth(basegfx::B3DVector(0,1,0),basegfx::B3DVector(0,0,0), -45, true, 0, 1));
625 0 : Slide.Operations.push_back(makeRotateAndScaleDepthByWidth(basegfx::B3DVector(0,1,0),basegfx::B3DVector(0,0,0), 45, false, -1, 0));
626 0 : Primitives_t aEnteringSlide;
627 0 : aEnteringSlide.push_back(Slide);
628 :
629 0 : return makeRochadeTransition(aLeavingSlide, aEnteringSlide, aSettings);
630 : }
631 :
632 : // TODO(Q3): extract to basegfx
633 0 : inline basegfx::B2DVector clamp(const basegfx::B2DVector& v)
634 : {
635 0 : return basegfx::B2DVector(min(max(v.getX(),-1.0),1.0),
636 0 : min(max(v.getY(),-1.0),1.0));
637 : }
638 :
639 : // TODO(Q3): extract to basegfx
640 : inline basegfx::B3DVector clamp(const basegfx::B3DVector& v)
641 : {
642 : return basegfx::B3DVector(min(max(v.getX(),-1.0),1.0),
643 : min(max(v.getY(),-1.0),1.0),
644 : min(max(v.getZ(),-1.0),1.0));
645 : }
646 :
647 0 : inline double randFromNeg1to1()
648 : {
649 0 : return ( ( static_cast<double>( rand() ) / static_cast<double>( RAND_MAX ) ) * 2.0 ) - 1.0;
650 : }
651 :
652 : // TODO(Q3): extract to basegfx
653 0 : inline basegfx::B3DVector randNormVectorInXYPlane()
654 : {
655 0 : basegfx::B3DVector toReturn(randFromNeg1to1(),randFromNeg1to1(),0.0);
656 0 : return toReturn/toReturn.getLength();
657 : }
658 :
659 0 : boost::shared_ptr<OGLTransitionImpl> makeRevolvingCircles( ::sal_uInt16 nCircles , ::sal_uInt16 nPointsOnCircles )
660 : {
661 0 : double dAngle(2*3.1415926/static_cast<double>( nPointsOnCircles ));
662 0 : if(nCircles < 2 || nPointsOnCircles < 4)
663 : {
664 0 : makeNByMTileFlip(1,1);
665 0 : return makeSimpleTransition();
666 : }
667 0 : double Radius(1.0/static_cast<double>( nCircles ));
668 0 : double dRadius(Radius);
669 0 : double LastRadius(0.0);
670 0 : double NextRadius(2*Radius);
671 :
672 : /// now we know there is at least two circles
673 : /// the first will always be a full circle
674 : /// the last will always be the outer shell of the slide with a circle hole
675 :
676 : //add the full circle
677 0 : vector<basegfx::B2DVector> unScaledTexCoords;
678 0 : double TempAngle(0.0);
679 0 : for(unsigned int Point(0); Point < nPointsOnCircles; ++Point)
680 : {
681 0 : unScaledTexCoords.push_back( basegfx::B2DVector( cos(TempAngle - 3.1415926/2.0) , sin(TempAngle- 3.1415926/2.0) ) );
682 :
683 0 : TempAngle += dAngle;
684 : }
685 :
686 0 : Primitives_t aLeavingSlide;
687 0 : Primitives_t aEnteringSlide;
688 : {
689 0 : Primitive EnteringSlide;
690 0 : Primitive LeavingSlide;
691 0 : for(int Point(0); Point + 1 < nPointsOnCircles; ++Point)
692 : {
693 0 : EnteringSlide.pushTriangle( basegfx::B2DVector( 0.5 , 0.5 ) , Radius * unScaledTexCoords[ Point + 1 ] / 2.0 + basegfx::B2DVector( 0.5 , 0.5 ) , Radius * unScaledTexCoords[ Point ] / 2.0 + basegfx::B2DVector( 0.5 , 0.5 ) );
694 0 : LeavingSlide.pushTriangle( basegfx::B2DVector( 0.5 , 0.5 ) , Radius * unScaledTexCoords[ Point + 1 ] / 2.0 + basegfx::B2DVector( 0.5 , 0.5 ) , Radius * unScaledTexCoords[ Point ] / 2.0 + basegfx::B2DVector( 0.5, 0.5) );
695 : }
696 0 : EnteringSlide.pushTriangle( basegfx::B2DVector(0.5,0.5) , Radius * unScaledTexCoords[ 0 ] / 2.0 + basegfx::B2DVector( 0.5 , 0.5 ) , Radius * unScaledTexCoords[ nPointsOnCircles - 1 ] / 2.0 + basegfx::B2DVector( 0.5 , 0.5 ) );
697 0 : LeavingSlide.pushTriangle( basegfx::B2DVector(0.5,0.5) , Radius*unScaledTexCoords[0]/2.0 + basegfx::B2DVector(0.5,0.5) , Radius*unScaledTexCoords[nPointsOnCircles - 1]/2.0 + basegfx::B2DVector(0.5,0.5) );
698 :
699 0 : basegfx::B3DVector axis(randNormVectorInXYPlane());
700 0 : EnteringSlide.Operations.push_back( makeSRotate( axis , basegfx::B3DVector(0,0,0) , 180, true, Radius/2.0 , (NextRadius + 1)/2.0 ) );
701 0 : LeavingSlide.Operations.push_back( makeSRotate( axis , basegfx::B3DVector(0,0,0) , 180, true, Radius/2.0 , (NextRadius + 1)/2.0 ) );
702 0 : EnteringSlide.Operations.push_back( makeSRotate( axis , basegfx::B3DVector(0,0,0) , -180, false,0.0,1.0) );
703 :
704 0 : aEnteringSlide.push_back(EnteringSlide);
705 0 : aLeavingSlide.push_back(LeavingSlide);
706 0 : LastRadius = Radius;
707 0 : Radius = NextRadius;
708 0 : NextRadius += dRadius;
709 : }
710 :
711 0 : for(int i(1); i < nCircles - 1; ++i)
712 : {
713 0 : Primitive LeavingSlide;
714 0 : Primitive EnteringSlide;
715 0 : for(int Side(0); Side < nPointsOnCircles - 1; ++Side)
716 : {
717 0 : EnteringSlide.pushTriangle(Radius*unScaledTexCoords[Side]/2.0 + basegfx::B2DVector(0.5,0.5) , LastRadius*unScaledTexCoords[Side]/2.0 + basegfx::B2DVector(0.5,0.5) , LastRadius*unScaledTexCoords[Side + 1]/2.0 + basegfx::B2DVector(0.5,0.5) );
718 0 : EnteringSlide.pushTriangle(Radius*unScaledTexCoords[Side]/2.0 + basegfx::B2DVector(0.5,0.5) , LastRadius*unScaledTexCoords[Side + 1]/2.0 + basegfx::B2DVector(0.5,0.5) , Radius*unScaledTexCoords[Side + 1]/2.0 + basegfx::B2DVector(0.5,0.5) );
719 :
720 0 : LeavingSlide.pushTriangle(Radius*unScaledTexCoords[Side]/2.0 + basegfx::B2DVector(0.5,0.5) , LastRadius*unScaledTexCoords[Side]/2.0 + basegfx::B2DVector(0.5,0.5) , LastRadius*unScaledTexCoords[Side + 1]/2.0 + basegfx::B2DVector(0.5,0.5) );
721 0 : LeavingSlide.pushTriangle(Radius*unScaledTexCoords[Side]/2.0 + basegfx::B2DVector(0.5,0.5) , LastRadius*unScaledTexCoords[Side + 1]/2.0 + basegfx::B2DVector(0.5,0.5) , Radius*unScaledTexCoords[Side + 1]/2.0 + basegfx::B2DVector(0.5,0.5) );
722 : }
723 :
724 0 : EnteringSlide.pushTriangle(Radius*unScaledTexCoords[nPointsOnCircles - 1]/2.0 + basegfx::B2DVector(0.5,0.5) , LastRadius*unScaledTexCoords[nPointsOnCircles - 1]/2.0 + basegfx::B2DVector(0.5,0.5) , LastRadius*unScaledTexCoords[0]/2.0 + basegfx::B2DVector(0.5,0.5) );
725 0 : EnteringSlide.pushTriangle(Radius*unScaledTexCoords[nPointsOnCircles - 1]/2.0 + basegfx::B2DVector(0.5,0.5) , LastRadius*unScaledTexCoords[0]/2.0 + basegfx::B2DVector(0.5,0.5) , Radius*unScaledTexCoords[0]/2.0 + basegfx::B2DVector(0.5,0.5) );
726 :
727 0 : LeavingSlide.pushTriangle(Radius*unScaledTexCoords[nPointsOnCircles - 1]/2.0 + basegfx::B2DVector(0.5,0.5) , LastRadius*unScaledTexCoords[nPointsOnCircles - 1]/2.0 + basegfx::B2DVector(0.5,0.5) , LastRadius*unScaledTexCoords[0]/2.0 + basegfx::B2DVector(0.5,0.5) );
728 0 : LeavingSlide.pushTriangle(Radius*unScaledTexCoords[nPointsOnCircles - 1]/2.0 + basegfx::B2DVector(0.5,0.5) , LastRadius*unScaledTexCoords[0]/2.0 + basegfx::B2DVector(0.5,0.5) , Radius*unScaledTexCoords[0]/2.0 + basegfx::B2DVector(0.5,0.5) );
729 :
730 0 : basegfx::B3DVector axis(randNormVectorInXYPlane());
731 0 : EnteringSlide.Operations.push_back( makeSRotate( axis , basegfx::B3DVector(0,0,0) , 180, true, Radius/2.0 , (NextRadius + 1)/2.0 ) );
732 0 : LeavingSlide.Operations.push_back( makeSRotate( axis , basegfx::B3DVector(0,0,0) , 180, true, Radius/2.0 , (NextRadius + 1)/2.0 ) );
733 0 : EnteringSlide.Operations.push_back( makeSRotate( axis , basegfx::B3DVector(0,0,0) , -180, false,0.0,1.0) );
734 :
735 0 : aEnteringSlide.push_back(EnteringSlide);
736 0 : aLeavingSlide.push_back(LeavingSlide);
737 :
738 0 : LastRadius = Radius;
739 0 : Radius = NextRadius;
740 0 : NextRadius += dRadius;
741 0 : }
742 : {
743 0 : Radius = sqrt(2.0);
744 0 : Primitive LeavingSlide;
745 0 : Primitive EnteringSlide;
746 0 : for(int Side(0); Side < nPointsOnCircles - 1; ++Side)
747 : {
748 :
749 0 : EnteringSlide.pushTriangle(clamp(Radius*unScaledTexCoords[Side])/2.0 + basegfx::B2DVector(0.5,0.5) , LastRadius*unScaledTexCoords[Side]/2.0 + basegfx::B2DVector(0.5,0.5) , LastRadius*unScaledTexCoords[Side + 1]/2.0 + basegfx::B2DVector(0.5,0.5) );
750 0 : EnteringSlide.pushTriangle(clamp(Radius*unScaledTexCoords[Side])/2.0 + basegfx::B2DVector(0.5,0.5) , LastRadius*unScaledTexCoords[Side + 1]/2.0 + basegfx::B2DVector(0.5,0.5) , clamp(Radius*unScaledTexCoords[Side + 1])/2.0 + basegfx::B2DVector(0.5,0.5) );
751 :
752 0 : LeavingSlide.pushTriangle(clamp(Radius*unScaledTexCoords[Side])/2.0 + basegfx::B2DVector(0.5,0.5) , LastRadius*unScaledTexCoords[Side]/2.0 + basegfx::B2DVector(0.5,0.5) , LastRadius*unScaledTexCoords[Side + 1]/2.0 + basegfx::B2DVector(0.5,0.5) );
753 0 : LeavingSlide.pushTriangle(clamp(Radius*unScaledTexCoords[Side])/2.0 + basegfx::B2DVector(0.5,0.5) , LastRadius*unScaledTexCoords[Side + 1]/2.0 + basegfx::B2DVector(0.5,0.5) , clamp(Radius*unScaledTexCoords[Side + 1])/2.0 + basegfx::B2DVector(0.5,0.5) );
754 : }
755 :
756 0 : EnteringSlide.pushTriangle(clamp(Radius*unScaledTexCoords[nPointsOnCircles - 1])/2.0 + basegfx::B2DVector(0.5,0.5) , LastRadius*unScaledTexCoords[nPointsOnCircles - 1]/2.0 + basegfx::B2DVector(0.5,0.5) , LastRadius*unScaledTexCoords[0]/2.0 + basegfx::B2DVector(0.5,0.5) );
757 0 : EnteringSlide.pushTriangle(clamp(Radius*unScaledTexCoords[nPointsOnCircles - 1])/2.0 + basegfx::B2DVector(0.5,0.5) , LastRadius*unScaledTexCoords[0]/2.0 + basegfx::B2DVector(0.5,0.5) , clamp(Radius*unScaledTexCoords[0])/2.0 + basegfx::B2DVector(0.5,0.5) );
758 :
759 0 : LeavingSlide.pushTriangle(clamp(Radius*unScaledTexCoords[nPointsOnCircles - 1])/2.0 + basegfx::B2DVector(0.5,0.5) , LastRadius*unScaledTexCoords[nPointsOnCircles - 1]/2.0 + basegfx::B2DVector(0.5,0.5) , LastRadius*unScaledTexCoords[0]/2.0 + basegfx::B2DVector(0.5,0.5) );
760 0 : LeavingSlide.pushTriangle(clamp(Radius*unScaledTexCoords[nPointsOnCircles - 1])/2.0 + basegfx::B2DVector(0.5,0.5) , LastRadius*unScaledTexCoords[0]/2.0 + basegfx::B2DVector(0.5,0.5) , clamp(Radius*unScaledTexCoords[0])/2.0 + basegfx::B2DVector(0.5,0.5) );
761 :
762 0 : basegfx::B3DVector axis(randNormVectorInXYPlane());
763 0 : EnteringSlide.Operations.push_back( makeSRotate( axis , basegfx::B3DVector(0,0,0) , 180, true, (LastRadius + dRadius)/2.0 , 1.0 ) );
764 0 : LeavingSlide.Operations.push_back( makeSRotate( axis , basegfx::B3DVector(0,0,0) , 180, true, (LastRadius + dRadius)/2.0 , 1.0 ) );
765 0 : EnteringSlide.Operations.push_back( makeSRotate( axis , basegfx::B3DVector(0,0,0) , -180, false,0.0,1.0) );
766 :
767 0 : aEnteringSlide.push_back(EnteringSlide);
768 0 : aLeavingSlide.push_back(LeavingSlide);
769 : }
770 :
771 0 : return makeSimpleTransition(aLeavingSlide, aEnteringSlide);
772 : }
773 :
774 0 : boost::shared_ptr<OGLTransitionImpl> makeHelix( ::sal_uInt16 nRows )
775 : {
776 0 : double invN(1.0/static_cast<double>(nRows));
777 0 : double iDn = 0.0;
778 0 : double iPDn = invN;
779 0 : Primitives_t aLeavingSlide;
780 0 : Primitives_t aEnteringSlide;
781 0 : for(unsigned int i(0); i < nRows; ++i)
782 : {
783 0 : Primitive Tile;
784 :
785 0 : Tile.pushTriangle(basegfx::B2DVector( 1.0 , iDn ) , basegfx::B2DVector( 0.0 , iDn ) , basegfx::B2DVector( 0.0 , iPDn ));
786 :
787 0 : Tile.pushTriangle(basegfx::B2DVector( 1.0 , iPDn ) , basegfx::B2DVector( 1.0 , iDn ) , basegfx::B2DVector( 0.0 , iPDn ));
788 :
789 0 : Tile.Operations.push_back( makeSRotate( basegfx::B3DVector( 0 , 1 , 0 ) , ( Tile.getVertices()[1] + Tile.getVertices()[3] )/2.0 , 180 ,
790 0 : true,min(max(static_cast<double>(i - nRows/2.0)*invN/2.0,0.0),1.0),
791 0 : min(max(static_cast<double>(i + nRows/2.0)*invN/2.0,0.0),1.0) ) );
792 :
793 0 : aLeavingSlide.push_back(Tile);
794 :
795 0 : Tile.Operations.push_back( makeSRotate( basegfx::B3DVector( 0 , 1 , 0 ) , ( Tile.getVertices()[1] + Tile.getVertices()[3] )/2.0 , -180 , false,0.0,1.0) );
796 :
797 0 : aEnteringSlide.push_back(Tile);
798 :
799 0 : iDn += invN;
800 0 : iPDn += invN;
801 0 : }
802 :
803 0 : return makeSimpleTransition(aLeavingSlide, aEnteringSlide);
804 : }
805 :
806 0 : boost::shared_ptr<OGLTransitionImpl> makeNByMTileFlip( ::sal_uInt16 n, ::sal_uInt16 m )
807 : {
808 0 : double invN(1.0/static_cast<double>(n));
809 0 : double invM(1.0/static_cast<double>(m));
810 0 : double iDn = 0.0;
811 0 : double iPDn = invN;
812 0 : Primitives_t aLeavingSlide;
813 0 : Primitives_t aEnteringSlide;
814 0 : for(unsigned int i(0); i < n; ++i)
815 : {
816 0 : double jDm = 0.0;
817 0 : double jPDm = invM;
818 0 : for(unsigned int j(0); j < m; ++j)
819 : {
820 0 : Primitive Tile;
821 :
822 0 : Tile.pushTriangle(basegfx::B2DVector( iPDn , jDm ) , basegfx::B2DVector( iDn , jDm ) , basegfx::B2DVector( iDn , jPDm ));
823 :
824 0 : Tile.pushTriangle(basegfx::B2DVector( iPDn , jPDm ) , basegfx::B2DVector( iPDn , jDm ) , basegfx::B2DVector( iDn , jPDm ));//bottom left corner of tile
825 :
826 0 : Tile.Operations.push_back( makeSRotate( basegfx::B3DVector( 1 , 1 , 0 ) , ( Tile.getVertices()[1] + Tile.getVertices()[3] )/2.0 , 180 , true, iDn*jDm/2.0 , ((iPDn*jPDm)+1.0)/2.0 ) );
827 0 : aLeavingSlide.push_back(Tile);
828 0 : Tile.Operations.push_back( makeSRotate( basegfx::B3DVector( 1 , 1 , 0 ) , ( Tile.getVertices()[1] + Tile.getVertices()[3] )/2.0 , -180, false, iDn*jDm/2.0 , ((iPDn*jPDm)+1.0)/2.0 ) );
829 :
830 0 : aEnteringSlide.push_back(Tile);
831 :
832 0 : jDm += invM;
833 0 : jPDm += invM;
834 0 : }
835 0 : iDn += invN;
836 0 : iPDn += invN;
837 : }
838 :
839 0 : return makeSimpleTransition(aLeavingSlide, aEnteringSlide);
840 : }
841 :
842 0 : SRotate::SRotate(const basegfx::B3DVector& Axis,const basegfx::B3DVector& Origin,double Angle, bool bInter, double T0, double T1):axis(Axis),origin(Origin),angle(Angle)
843 : {
844 0 : nT0 = T0;
845 0 : nT1 = T1;
846 0 : bInterpolate = bInter;
847 0 : }
848 :
849 0 : SScale::SScale(const basegfx::B3DVector& Scale,const basegfx::B3DVector& Origin, bool bInter, double T0, double T1):scale(Scale),origin(Origin)
850 : {
851 0 : nT0 = T0;
852 0 : nT1 = T1;
853 0 : bInterpolate = bInter;
854 0 : }
855 :
856 0 : RotateAndScaleDepthByWidth::RotateAndScaleDepthByWidth(const basegfx::B3DVector& Axis,const basegfx::B3DVector& Origin,double Angle, bool bInter, double T0, double T1):axis(Axis),origin(Origin),angle(Angle)
857 : {
858 0 : nT0 = T0;
859 0 : nT1 = T1;
860 0 : bInterpolate = bInter;
861 0 : }
862 :
863 0 : RotateAndScaleDepthByHeight::RotateAndScaleDepthByHeight(const basegfx::B3DVector& Axis,const basegfx::B3DVector& Origin,double Angle, bool bInter, double T0, double T1):axis(Axis),origin(Origin),angle(Angle)
864 : {
865 0 : nT0 = T0;
866 0 : nT1 = T1;
867 0 : bInterpolate = bInter;
868 0 : }
869 :
870 :
871 0 : STranslate::STranslate(const basegfx::B3DVector& Vector, bool bInter, double T0, double T1):vector(Vector)
872 : {
873 0 : nT0 = T0;
874 0 : nT1 = T1;
875 0 : bInterpolate = bInter;
876 0 : }
877 :
878 : boost::shared_ptr<SRotate>
879 0 : makeSRotate(const basegfx::B3DVector& Axis,const basegfx::B3DVector& Origin,double Angle,bool bInter, double T0, double T1)
880 : {
881 0 : return make_shared<SRotate>(Axis, Origin, Angle, bInter, T0, T1);
882 : }
883 :
884 : boost::shared_ptr<SScale>
885 0 : makeSScale(const basegfx::B3DVector& Scale, const basegfx::B3DVector& Origin,bool bInter, double T0, double T1)
886 : {
887 0 : return make_shared<SScale>(Scale, Origin, bInter, T0, T1);
888 : }
889 :
890 : boost::shared_ptr<STranslate>
891 0 : makeSTranslate(const basegfx::B3DVector& Vector,bool bInter, double T0, double T1)
892 : {
893 0 : return make_shared<STranslate>(Vector, bInter, T0, T1);
894 : }
895 :
896 : boost::shared_ptr<SEllipseTranslate>
897 0 : makeSEllipseTranslate(double dWidth, double dHeight, double dStartPosition, double dEndPosition, bool bInter, double T0, double T1)
898 : {
899 0 : return make_shared<SEllipseTranslate>(dWidth, dHeight, dStartPosition, dEndPosition, bInter, T0, T1);
900 : }
901 :
902 : boost::shared_ptr<RotateAndScaleDepthByWidth>
903 0 : makeRotateAndScaleDepthByWidth(const basegfx::B3DVector& Axis,const basegfx::B3DVector& Origin,double Angle,bool bInter, double T0, double T1)
904 : {
905 0 : return make_shared<RotateAndScaleDepthByWidth>(Axis, Origin, Angle, bInter, T0, T1);
906 : }
907 :
908 : boost::shared_ptr<RotateAndScaleDepthByHeight>
909 0 : makeRotateAndScaleDepthByHeight(const basegfx::B3DVector& Axis,const basegfx::B3DVector& Origin,double Angle,bool bInter, double T0, double T1)
910 : {
911 0 : return make_shared<RotateAndScaleDepthByHeight>(Axis, Origin, Angle, bInter, T0, T1);
912 : }
913 :
914 0 : inline double intervalInter(double t, double T0, double T1)
915 : {
916 0 : return ( t - T0 ) / ( T1 - T0 );
917 : }
918 :
919 0 : void STranslate::interpolate(double t,double SlideWidthScale,double SlideHeightScale) const
920 : {
921 0 : if(t <= nT0)
922 0 : return;
923 0 : if(!bInterpolate || t > nT1)
924 0 : t = nT1;
925 0 : t = intervalInter(t,nT0,nT1);
926 0 : glTranslated(SlideWidthScale*t*vector.getX(),SlideHeightScale*t*vector.getY(),t*vector.getZ());
927 : }
928 :
929 0 : void SRotate::interpolate(double t,double SlideWidthScale,double SlideHeightScale) const
930 : {
931 0 : if(t <= nT0)
932 0 : return;
933 0 : if(!bInterpolate || t > nT1)
934 0 : t = nT1;
935 0 : t = intervalInter(t,nT0,nT1);
936 0 : glTranslated(SlideWidthScale*origin.getX(),SlideHeightScale*origin.getY(),origin.getZ());
937 0 : glScaled(SlideWidthScale,SlideHeightScale,1);
938 0 : glRotated(t*angle,axis.getX(),axis.getY(),axis.getZ());
939 0 : glScaled(1/SlideWidthScale,1/SlideHeightScale,1);
940 0 : glTranslated(-SlideWidthScale*origin.getX(),-SlideHeightScale*origin.getY(),-origin.getZ());
941 : }
942 :
943 0 : void SScale::interpolate(double t,double SlideWidthScale,double SlideHeightScale) const
944 : {
945 0 : if(t <= nT0)
946 0 : return;
947 0 : if(!bInterpolate || t > nT1)
948 0 : t = nT1;
949 0 : t = intervalInter(t,nT0,nT1);
950 0 : glTranslated(SlideWidthScale*origin.getX(),SlideHeightScale*origin.getY(),origin.getZ());
951 0 : glScaled((1-t) + t*scale.getX(),(1-t) + t*scale.getY(),(1-t) + t*scale.getZ());
952 0 : glTranslated(-SlideWidthScale*origin.getX(),-SlideHeightScale*origin.getY(),-origin.getZ());
953 : }
954 :
955 0 : void RotateAndScaleDepthByWidth::interpolate(double t,double SlideWidthScale,double SlideHeightScale) const
956 : {
957 0 : if(t <= nT0)
958 0 : return;
959 0 : if(!bInterpolate || t > nT1)
960 0 : t = nT1;
961 0 : t = intervalInter(t,nT0,nT1);
962 0 : glTranslated(SlideWidthScale*origin.getX(),SlideHeightScale*origin.getY(),SlideWidthScale*origin.getZ());
963 0 : glRotated(t*angle,axis.getX(),axis.getY(),axis.getZ());
964 0 : glTranslated(-SlideWidthScale*origin.getX(),-SlideHeightScale*origin.getY(),-SlideWidthScale*origin.getZ());
965 : }
966 :
967 0 : void RotateAndScaleDepthByHeight::interpolate(double t,double SlideWidthScale,double SlideHeightScale) const
968 : {
969 0 : if(t <= nT0)
970 0 : return;
971 0 : if(!bInterpolate || t > nT1)
972 0 : t = nT1;
973 0 : t = intervalInter(t,nT0,nT1);
974 0 : glTranslated(SlideWidthScale*origin.getX(),SlideHeightScale*origin.getY(),SlideHeightScale*origin.getZ());
975 0 : glRotated(t*angle,axis.getX(),axis.getY(),axis.getZ());
976 0 : glTranslated(-SlideWidthScale*origin.getX(),-SlideHeightScale*origin.getY(),-SlideHeightScale*origin.getZ());
977 : }
978 :
979 0 : SEllipseTranslate::SEllipseTranslate(double dWidth, double dHeight, double dStartPosition, double dEndPosition, bool bInter, double T0, double T1)
980 : {
981 0 : nT0 = T0;
982 0 : nT1 = T1;
983 0 : bInterpolate = bInter;
984 0 : width = dWidth;
985 0 : height = dHeight;
986 0 : startPosition = dStartPosition;
987 0 : endPosition = dEndPosition;
988 0 : }
989 :
990 0 : void SEllipseTranslate::interpolate(double t,double /* SlideWidthScale */,double /* SlideHeightScale */) const
991 : {
992 0 : if(t <= nT0)
993 0 : return;
994 0 : if(!bInterpolate || t > nT1)
995 0 : t = nT1;
996 0 : t = intervalInter(t,nT0,nT1);
997 :
998 : double a1, a2, x, y;
999 0 : a1 = startPosition*2*M_PI;
1000 0 : a2 = (startPosition + t*(endPosition - startPosition))*2*M_PI;
1001 0 : x = width*(cos (a2) - cos (a1))/2;
1002 0 : y = height*(sin (a2) - sin (a1))/2;
1003 :
1004 0 : glTranslated(x, 0, y);
1005 : }
1006 :
1007 0 : Primitive& Primitive::operator=(const Primitive& rvalue)
1008 : {
1009 0 : Primitive aTmp(rvalue);
1010 0 : swap(aTmp);
1011 0 : return *this;
1012 : }
1013 :
1014 0 : Primitive::Primitive(const Primitive& rvalue)
1015 : : Operations(rvalue.Operations)
1016 : , Vertices(rvalue.Vertices)
1017 : , Normals(rvalue.Normals)
1018 0 : , TexCoords(rvalue.TexCoords)
1019 : {
1020 0 : }
1021 :
1022 0 : void Primitive::swap(Primitive& rOther)
1023 : {
1024 : using std::swap;
1025 :
1026 0 : swap(Operations, rOther.Operations);
1027 0 : swap(Vertices, rOther.Vertices);
1028 0 : swap(Normals, rOther.Normals);
1029 0 : swap(TexCoords, rOther.TexCoords);
1030 0 : }
1031 :
1032 0 : void Primitive::pushTriangle(const basegfx::B2DVector& SlideLocation0,const basegfx::B2DVector& SlideLocation1,const basegfx::B2DVector& SlideLocation2)
1033 : {
1034 0 : vector<basegfx::B3DVector> Verts;
1035 0 : vector<basegfx::B2DVector> Texs;
1036 0 : Verts.reserve(3);
1037 0 : Texs.reserve(3);
1038 :
1039 0 : Verts.push_back(basegfx::B3DVector( 2*SlideLocation0.getX() - 1, -2*SlideLocation0.getY() + 1 , 0.0 ));
1040 0 : Verts.push_back(basegfx::B3DVector( 2*SlideLocation1.getX() - 1, -2*SlideLocation1.getY() + 1 , 0.0 ));
1041 0 : Verts.push_back(basegfx::B3DVector( 2*SlideLocation2.getX() - 1, -2*SlideLocation2.getY() + 1 , 0.0 ));
1042 :
1043 : //figure out if they're facing the correct way, and make them face the correct way.
1044 0 : basegfx::B3DVector Normal( basegfx::cross( Verts[0] - Verts[1] , Verts[1] - Verts[2] ) );
1045 0 : if(Normal.getZ() >= 0.0)//if the normal is facing us
1046 : {
1047 0 : Texs.push_back(SlideLocation0);
1048 0 : Texs.push_back(SlideLocation1);
1049 0 : Texs.push_back(SlideLocation2);
1050 : }
1051 : else // if the normal is facing away from us, make it face us
1052 : {
1053 0 : Texs.push_back(SlideLocation0);
1054 0 : Texs.push_back(SlideLocation2);
1055 0 : Texs.push_back(SlideLocation1);
1056 0 : Verts.clear();
1057 0 : Verts.push_back(basegfx::B3DVector( 2*SlideLocation0.getX() - 1, -2*SlideLocation0.getY() + 1 , 0.0 ));
1058 0 : Verts.push_back(basegfx::B3DVector( 2*SlideLocation2.getX() - 1, -2*SlideLocation2.getY() + 1 , 0.0 ));
1059 0 : Verts.push_back(basegfx::B3DVector( 2*SlideLocation1.getX() - 1, -2*SlideLocation1.getY() + 1 , 0.0 ));
1060 : }
1061 :
1062 0 : Vertices.push_back(Verts[0]);
1063 0 : Vertices.push_back(Verts[1]);
1064 0 : Vertices.push_back(Verts[2]);
1065 :
1066 0 : TexCoords.push_back(Texs[0]);
1067 0 : TexCoords.push_back(Texs[1]);
1068 0 : TexCoords.push_back(Texs[2]);
1069 :
1070 0 : Normals.push_back(basegfx::B3DVector(0,0,1));//all normals always face the screen when untransformed.
1071 0 : Normals.push_back(basegfx::B3DVector(0,0,1));//all normals always face the screen when untransformed.
1072 0 : Normals.push_back(basegfx::B3DVector(0,0,1));//all normals always face the screen when untransformed.
1073 0 : }
1074 :
1075 : namespace
1076 : {
1077 :
1078 0 : class DiamondTransition : public OGLTransitionImpl
1079 : {
1080 : public:
1081 0 : DiamondTransition(const TransitionScene& rScene, const TransitionSettings& rSettings)
1082 0 : : OGLTransitionImpl(rScene, rSettings)
1083 0 : {}
1084 :
1085 : private:
1086 : virtual void prepare_( double nTime, double SlideWidth, double SlideHeight, double DispWidth, double DispHeight ) SAL_OVERRIDE;
1087 : // mmPrepare = &OGLTransitionImpl::prepareDiamond;
1088 : };
1089 :
1090 0 : void DiamondTransition::prepare_( double nTime, double /* SlideWidth */, double /* SlideHeight */, double /* DispWidth */, double /* DispHeight */ )
1091 : {
1092 0 : Primitive Slide1, Slide2;
1093 :
1094 0 : Slide1.pushTriangle (basegfx::B2DVector (0,0), basegfx::B2DVector (1,0), basegfx::B2DVector (0,1));
1095 0 : Slide1.pushTriangle (basegfx::B2DVector (1,0), basegfx::B2DVector (0,1), basegfx::B2DVector (1,1));
1096 0 : Primitives_t aEnteringSlidePrimitives;
1097 0 : aEnteringSlidePrimitives.push_back (Slide1);
1098 :
1099 0 : if( nTime >= 0.5 ) {
1100 0 : double m = 1 - nTime;
1101 :
1102 0 : Slide2.pushTriangle (basegfx::B2DVector (0,0), basegfx::B2DVector (m,0), basegfx::B2DVector (0,m));
1103 0 : Slide2.pushTriangle (basegfx::B2DVector (nTime,0), basegfx::B2DVector (1,0), basegfx::B2DVector (1,m));
1104 0 : Slide2.pushTriangle (basegfx::B2DVector (1,nTime), basegfx::B2DVector (1,1), basegfx::B2DVector (nTime,1));
1105 0 : Slide2.pushTriangle (basegfx::B2DVector (0,nTime), basegfx::B2DVector (m,1), basegfx::B2DVector (0,1));
1106 : } else {
1107 0 : double l = 0.5 - nTime;
1108 0 : double h = 0.5 + nTime;
1109 :
1110 0 : Slide2.pushTriangle (basegfx::B2DVector (0,0), basegfx::B2DVector (1,0), basegfx::B2DVector (0.5,l));
1111 0 : Slide2.pushTriangle (basegfx::B2DVector (0.5,l), basegfx::B2DVector (1,0), basegfx::B2DVector (h,0.5));
1112 0 : Slide2.pushTriangle (basegfx::B2DVector (1,0), basegfx::B2DVector (1,1), basegfx::B2DVector (h,0.5));
1113 0 : Slide2.pushTriangle (basegfx::B2DVector (h,0.5), basegfx::B2DVector (1,1), basegfx::B2DVector (0.5,h));
1114 0 : Slide2.pushTriangle (basegfx::B2DVector (0.5,h), basegfx::B2DVector (1,1), basegfx::B2DVector (0,1));
1115 0 : Slide2.pushTriangle (basegfx::B2DVector (l,0.5), basegfx::B2DVector (0.5,h), basegfx::B2DVector (0,1));
1116 0 : Slide2.pushTriangle (basegfx::B2DVector (0,0), basegfx::B2DVector (l,0.5), basegfx::B2DVector (0,1));
1117 0 : Slide2.pushTriangle (basegfx::B2DVector (0,0), basegfx::B2DVector (0.5,l), basegfx::B2DVector (l,0.5));
1118 : }
1119 0 : Slide2.Operations.push_back (makeSTranslate (basegfx::B3DVector (0, 0, 0.00000001), false, -1, 0));
1120 0 : Primitives_t aLeavingSlidePrimitives;
1121 0 : aLeavingSlidePrimitives.push_back (Slide2);
1122 :
1123 0 : setScene(TransitionScene(aLeavingSlidePrimitives, aEnteringSlidePrimitives));
1124 0 : }
1125 :
1126 : shared_ptr<OGLTransitionImpl>
1127 0 : makeDiamondTransition(const TransitionSettings& rSettings)
1128 : {
1129 0 : return make_shared<DiamondTransition>(TransitionScene(), rSettings);
1130 : }
1131 :
1132 : }
1133 :
1134 0 : boost::shared_ptr<OGLTransitionImpl> makeDiamond()
1135 : {
1136 0 : TransitionSettings aSettings;
1137 0 : aSettings.mbUseMipMapLeaving = aSettings.mbUseMipMapEntering = false;
1138 :
1139 0 : return makeDiamondTransition(aSettings);
1140 : }
1141 :
1142 0 : boost::shared_ptr<OGLTransitionImpl> makeVenetianBlinds( bool vertical, int parts )
1143 : {
1144 : static double t30 = tan( M_PI/6.0 );
1145 0 : double n, ln = 0;
1146 0 : double p = 1.0/parts;
1147 :
1148 0 : Primitives_t aLeavingSlide;
1149 0 : Primitives_t aEnteringSlide;
1150 0 : for( int i=0; i<parts; i++ ) {
1151 0 : Primitive Slide;
1152 0 : n = (i + 1)/(double)parts;
1153 0 : if( vertical ) {
1154 0 : Slide.pushTriangle (basegfx::B2DVector (ln,0), basegfx::B2DVector (n,0), basegfx::B2DVector (ln,1));
1155 0 : Slide.pushTriangle (basegfx::B2DVector (n,0), basegfx::B2DVector (ln,1), basegfx::B2DVector (n,1));
1156 0 : Slide.Operations.push_back(makeRotateAndScaleDepthByWidth(basegfx::B3DVector(0, 1, 0), basegfx::B3DVector(n + ln - 1, 0, -t30*p), -120, true, 0.0, 1.0));
1157 : } else {
1158 0 : Slide.pushTriangle (basegfx::B2DVector (0,ln), basegfx::B2DVector (1,ln), basegfx::B2DVector (0,n));
1159 0 : Slide.pushTriangle (basegfx::B2DVector (1,ln), basegfx::B2DVector (0,n), basegfx::B2DVector (1,n));
1160 0 : Slide.Operations.push_back(makeRotateAndScaleDepthByHeight(basegfx::B3DVector(1, 0, 0), basegfx::B3DVector(0, 1 - n - ln, -t30*p), -120, true, 0.0, 1.0));
1161 : }
1162 0 : aLeavingSlide.push_back (Slide);
1163 :
1164 0 : if( vertical ) {
1165 0 : Slide.Operations.push_back(makeSRotate(basegfx::B3DVector(0, 1, 0), basegfx::B3DVector(2*n - 1, 0, 0), -60, false, -1, 0));
1166 0 : Slide.Operations.push_back(makeSRotate(basegfx::B3DVector(0, 1, 0), basegfx::B3DVector(n + ln - 1, 0, 0), 180, false, -1, 0));
1167 : } else {
1168 0 : Slide.Operations.push_back(makeSRotate(basegfx::B3DVector(1, 0, 0), basegfx::B3DVector(0, 1 - 2*n, 0), -60, false, -1, 0));
1169 0 : Slide.Operations.push_back(makeSRotate(basegfx::B3DVector(1, 0, 0), basegfx::B3DVector(0, 1 - n - ln, 0), 180, false, -1, 0));
1170 : }
1171 0 : aEnteringSlide.push_back (Slide);
1172 0 : ln = n;
1173 0 : }
1174 :
1175 0 : return makeSimpleTransition(aLeavingSlide, aEnteringSlide);
1176 : }
1177 :
1178 : namespace
1179 : {
1180 :
1181 0 : class FadeSmoothlyTransition : public OGLTransitionImpl
1182 : {
1183 : public:
1184 0 : FadeSmoothlyTransition(const TransitionScene& rScene, const TransitionSettings& rSettings)
1185 0 : : OGLTransitionImpl(rScene, rSettings)
1186 0 : {}
1187 :
1188 : private:
1189 : virtual void displaySlides_( double nTime, ::sal_Int32 glLeavingSlideTex, ::sal_Int32 glEnteringSlideTex, double SlideWidthScale, double SlideHeightScale ) SAL_OVERRIDE;
1190 : };
1191 :
1192 0 : void FadeSmoothlyTransition::displaySlides_( double nTime, ::sal_Int32 glLeavingSlideTex, ::sal_Int32 glEnteringSlideTex, double SlideWidthScale, double SlideHeightScale )
1193 : {
1194 0 : applyOverallOperations( nTime, SlideWidthScale, SlideHeightScale );
1195 :
1196 0 : glDisable(GL_DEPTH_TEST);
1197 :
1198 0 : displaySlide( nTime, glLeavingSlideTex, getScene().getLeavingSlide(), SlideWidthScale, SlideHeightScale );
1199 :
1200 0 : glDisable(GL_LIGHTING);
1201 0 : glEnable(GL_BLEND);
1202 0 : glBlendFunc(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA);
1203 0 : glTexEnvi(GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_MODULATE);
1204 0 : glColor4f( 1, 1, 1, nTime );
1205 0 : displaySlide( nTime, glEnteringSlideTex, getScene().getEnteringSlide(), SlideWidthScale, SlideHeightScale );
1206 0 : glDisable(GL_BLEND);
1207 0 : glTexEnvi(GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_REPLACE);
1208 0 : glEnable(GL_LIGHTING);
1209 :
1210 0 : glEnable(GL_DEPTH_TEST);
1211 0 : }
1212 :
1213 : shared_ptr<OGLTransitionImpl>
1214 0 : makeFadeSmoothlyTransition(
1215 : const Primitives_t& rLeavingSlidePrimitives,
1216 : const Primitives_t& rEnteringSlidePrimitives,
1217 : const TransitionSettings& rSettings)
1218 : {
1219 : return make_shared<FadeSmoothlyTransition>(
1220 : TransitionScene(rLeavingSlidePrimitives, rEnteringSlidePrimitives),
1221 0 : rSettings)
1222 : ;
1223 : }
1224 :
1225 : }
1226 :
1227 0 : boost::shared_ptr<OGLTransitionImpl> makeFadeSmoothly()
1228 : {
1229 0 : Primitive Slide;
1230 :
1231 0 : Slide.pushTriangle (basegfx::B2DVector (0,0), basegfx::B2DVector (1,0), basegfx::B2DVector (0,1));
1232 0 : Slide.pushTriangle (basegfx::B2DVector (1,0), basegfx::B2DVector (0,1), basegfx::B2DVector (1,1));
1233 0 : Primitives_t aLeavingSlide;
1234 0 : aLeavingSlide.push_back (Slide);
1235 0 : Primitives_t aEnteringSlide;
1236 0 : aEnteringSlide.push_back (Slide);
1237 :
1238 0 : TransitionSettings aSettings;
1239 0 : aSettings.mbUseMipMapLeaving = aSettings.mbUseMipMapEntering = false;
1240 :
1241 0 : return makeFadeSmoothlyTransition(aLeavingSlide, aEnteringSlide, aSettings);
1242 : }
1243 :
1244 : namespace
1245 : {
1246 :
1247 0 : class FadeThroughBlackTransition : public OGLTransitionImpl
1248 : {
1249 : public:
1250 0 : FadeThroughBlackTransition(const TransitionScene& rScene, const TransitionSettings& rSettings)
1251 0 : : OGLTransitionImpl(rScene, rSettings)
1252 0 : {}
1253 :
1254 : private:
1255 : virtual void displaySlides_( double nTime, ::sal_Int32 glLeavingSlideTex, ::sal_Int32 glEnteringSlideTex, double SlideWidthScale, double SlideHeightScale ) SAL_OVERRIDE;
1256 : };
1257 :
1258 0 : void FadeThroughBlackTransition::displaySlides_( double nTime, ::sal_Int32 glLeavingSlideTex, ::sal_Int32 glEnteringSlideTex, double SlideWidthScale, double SlideHeightScale )
1259 : {
1260 0 : applyOverallOperations( nTime, SlideWidthScale, SlideHeightScale );
1261 :
1262 0 : glDisable(GL_DEPTH_TEST);
1263 :
1264 0 : glDisable(GL_LIGHTING);
1265 0 : glEnable(GL_BLEND);
1266 0 : glBlendFunc(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA);
1267 0 : glTexEnvi(GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_MODULATE);
1268 0 : if( nTime < 0.5 ) {
1269 0 : glColor4f( 1, 1, 1, 1 - nTime*2 );
1270 0 : displaySlide( nTime, glLeavingSlideTex, getScene().getLeavingSlide(), SlideWidthScale, SlideHeightScale );
1271 : } else {
1272 0 : glColor4f( 1, 1, 1, (nTime - 0.5)*2 );
1273 0 : displaySlide( nTime, glEnteringSlideTex, getScene().getEnteringSlide(), SlideWidthScale, SlideHeightScale );
1274 : }
1275 0 : glDisable(GL_BLEND);
1276 0 : glTexEnvi(GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_REPLACE);
1277 0 : glEnable(GL_LIGHTING);
1278 :
1279 0 : glEnable(GL_DEPTH_TEST);
1280 0 : }
1281 :
1282 : shared_ptr<OGLTransitionImpl>
1283 0 : makeFadeThroughBlackTransition(
1284 : const Primitives_t& rLeavingSlidePrimitives,
1285 : const Primitives_t& rEnteringSlidePrimitives,
1286 : const TransitionSettings& rSettings)
1287 : {
1288 : return make_shared<FadeThroughBlackTransition>(
1289 : TransitionScene(rLeavingSlidePrimitives, rEnteringSlidePrimitives),
1290 0 : rSettings)
1291 : ;
1292 : }
1293 :
1294 : }
1295 :
1296 0 : boost::shared_ptr<OGLTransitionImpl> makeFadeThroughBlack()
1297 : {
1298 0 : Primitive Slide;
1299 :
1300 0 : Slide.pushTriangle (basegfx::B2DVector (0,0), basegfx::B2DVector (1,0), basegfx::B2DVector (0,1));
1301 0 : Slide.pushTriangle (basegfx::B2DVector (1,0), basegfx::B2DVector (0,1), basegfx::B2DVector (1,1));
1302 0 : Primitives_t aLeavingSlide;
1303 0 : aLeavingSlide.push_back (Slide);
1304 0 : Primitives_t aEnteringSlide;
1305 0 : aEnteringSlide.push_back (Slide);
1306 :
1307 0 : TransitionSettings aSettings;
1308 0 : aSettings.mbUseMipMapLeaving = aSettings.mbUseMipMapEntering = false;
1309 :
1310 0 : return makeFadeThroughBlackTransition(aLeavingSlide, aEnteringSlide, aSettings);
1311 : }
1312 :
1313 : static const char* basicVertexShader = "\n\
1314 : varying vec2 v_texturePosition;\n\
1315 : \n\
1316 : void main( void )\n\
1317 : {\n\
1318 : gl_Position = ftransform();\n\
1319 : v_texturePosition = gl_MultiTexCoord0.xy;\n\
1320 : }\n\
1321 : ";
1322 :
1323 : static const char* staticFragmentShader = "\n\
1324 : uniform sampler2D leavingSlideTexture;\n\
1325 : uniform sampler2D enteringSlideTexture;\n\
1326 : uniform sampler2D permTexture;\n\
1327 : uniform float time;\n\
1328 : varying vec2 v_texturePosition;\n\
1329 : \n\
1330 : float snoise(vec2 P) {\n\
1331 : \n\
1332 : return texture2D(permTexture, P).r;\n\
1333 : }\n\
1334 : \n\
1335 : \n\
1336 : #define PART 0.5\n\
1337 : #define START 0.4\n\
1338 : #define END 0.9\n\
1339 : \n\
1340 : void main() {\n\
1341 : float sn = snoise(10.0*v_texturePosition+time*0.07);\n\
1342 : if( time < PART ) {\n\
1343 : float sn1 = snoise(vec2(time*15.0, 20.0*v_texturePosition.y));\n\
1344 : float sn2 = snoise(v_texturePosition);\n\
1345 : if (sn1 > 1.0 - time*time && sn2 < 2.0*time+0.1)\n\
1346 : gl_FragColor = vec4(sn, sn, sn, 1.0);\n\
1347 : else if (time > START )\n\
1348 : gl_FragColor = ((time-START)/(PART - START))*vec4(sn, sn, sn, 1.0) + (1.0 - (time - START)/(PART - START))*texture2D(leavingSlideTexture, v_texturePosition);\n\
1349 : else\n\
1350 : gl_FragColor = texture2D(leavingSlideTexture, v_texturePosition);\n\
1351 : } else if ( time < PART ) {\n\
1352 : gl_FragColor = texture2D(leavingSlideTexture, v_texturePosition);\n\
1353 : } else if ( time > END ) {\n\
1354 : gl_FragColor = ((1.0 - time)/(1.0 - END))*vec4(sn, sn, sn, 1.0) + ((time - END)/(1.0 - END))*texture2D(enteringSlideTexture, v_texturePosition);\n\
1355 : } else \n\
1356 : gl_FragColor = vec4(sn, sn, sn, 1.0);\n\
1357 : }\n\
1358 : ";
1359 :
1360 : static const char* dissolveFragmentShader = "\n\
1361 : uniform sampler2D leavingSlideTexture;\n\
1362 : uniform sampler2D enteringSlideTexture;\n\
1363 : uniform sampler2D permTexture;\n\
1364 : uniform float time;\n\
1365 : varying vec2 v_texturePosition;\n\
1366 : \n\
1367 : float snoise(vec2 P) {\n\
1368 : \n\
1369 : return texture2D(permTexture, P).r;\n\
1370 : }\n\
1371 : \n\
1372 : void main() {\n\
1373 : float sn = snoise(10.0*v_texturePosition);\n\
1374 : if( sn < time)\n\
1375 : gl_FragColor = texture2D(enteringSlideTexture, v_texturePosition);\n\
1376 : else\n\
1377 : gl_FragColor = texture2D(leavingSlideTexture, v_texturePosition);\n\
1378 : }\n\
1379 : ";
1380 :
1381 : namespace
1382 : {
1383 :
1384 0 : class ShaderTransition : public OGLTransitionImpl
1385 : {
1386 : protected:
1387 0 : ShaderTransition(const TransitionScene& rScene, const TransitionSettings& rSettings)
1388 : : OGLTransitionImpl(rScene, rSettings)
1389 : , m_nProgramObject(0)
1390 0 : , m_nHelperTexture(0)
1391 0 : {}
1392 :
1393 : private:
1394 : virtual void displaySlides_( double nTime, ::sal_Int32 glLeavingSlideTex, ::sal_Int32 glEnteringSlideTex, double SlideWidthScale, double SlideHeightScale ) SAL_OVERRIDE;
1395 : virtual void prepareTransition_( ::sal_Int32 glLeavingSlideTex, ::sal_Int32 glEnteringSlideTex ) SAL_OVERRIDE;
1396 : virtual void finishTransition_() SAL_OVERRIDE;
1397 : virtual GLuint makeShader_() = 0;
1398 :
1399 : void impl_preparePermShader();
1400 :
1401 : private:
1402 : /** GLSL program object
1403 : */
1404 : GLuint m_nProgramObject;
1405 :
1406 : /** various data */
1407 : GLuint m_nHelperTexture;
1408 : };
1409 :
1410 0 : void ShaderTransition::displaySlides_( double nTime, ::sal_Int32 glLeavingSlideTex, ::sal_Int32 glEnteringSlideTex,
1411 : double SlideWidthScale, double SlideHeightScale )
1412 : {
1413 0 : applyOverallOperations( nTime, SlideWidthScale, SlideHeightScale );
1414 :
1415 : #ifdef GL_VERSION_2_0
1416 0 : if( m_nProgramObject ) {
1417 0 : GLint location = OGLShaders::glGetUniformLocation( m_nProgramObject, "time" );
1418 0 : if( location != -1 ) {
1419 0 : OGLShaders::glUniform1f( location, nTime );
1420 : }
1421 : }
1422 :
1423 0 : OGLShaders::glActiveTexture( GL_TEXTURE2 );
1424 0 : glBindTexture( GL_TEXTURE_2D, glEnteringSlideTex );
1425 0 : OGLShaders::glActiveTexture( GL_TEXTURE0 );
1426 : #endif
1427 :
1428 0 : displaySlide( nTime, glLeavingSlideTex, getScene().getLeavingSlide(), SlideWidthScale, SlideHeightScale );
1429 0 : }
1430 :
1431 0 : void ShaderTransition::prepareTransition_( ::sal_Int32 /* glLeavingSlideTex */, ::sal_Int32 /* glEnteringSlideTex */ )
1432 : {
1433 0 : m_nProgramObject = makeShader_();
1434 :
1435 0 : impl_preparePermShader();
1436 0 : }
1437 :
1438 0 : void ShaderTransition::finishTransition_()
1439 : {
1440 : #ifdef GL_VERSION_2_0
1441 0 : if( m_nProgramObject ) {
1442 0 : OGLShaders::glDeleteProgram( m_nProgramObject );
1443 0 : m_nProgramObject = 0;
1444 : }
1445 0 : if ( m_nHelperTexture )
1446 : {
1447 0 : glDeleteTextures( 1, &m_nHelperTexture );
1448 0 : m_nHelperTexture = 0;
1449 : }
1450 : #endif
1451 0 : }
1452 :
1453 : int permutation256 [256]= {
1454 : 215, 100, 200, 204, 233, 50, 85, 196,
1455 : 71, 141, 122, 160, 93, 131, 243, 234,
1456 : 162, 183, 36, 155, 4, 62, 35, 205,
1457 : 40, 102, 33, 27, 255, 55, 214, 156,
1458 : 75, 163, 134, 126, 249, 74, 197, 228,
1459 : 72, 90, 206, 235, 17, 22, 49, 169,
1460 : 227, 89, 16, 5, 117, 60, 248, 230,
1461 : 217, 68, 138, 96, 194, 170, 136, 10,
1462 : 112, 238, 184, 189, 176, 42, 225, 212,
1463 : 84, 58, 175, 244, 150, 168, 219, 236,
1464 : 101, 208, 123, 37, 164, 110, 158, 201,
1465 : 78, 114, 57, 48, 70, 142, 106, 43,
1466 : 232, 26, 32, 252, 239, 98, 191, 94,
1467 : 59, 149, 39, 187, 203, 190, 19, 13,
1468 : 133, 45, 61, 247, 23, 34, 20, 52,
1469 : 118, 209, 146, 193, 222, 18, 1, 152,
1470 : 46, 41, 91, 148, 115, 25, 135, 77,
1471 : 254, 147, 224, 161, 9, 213, 223, 250,
1472 : 231, 251, 127, 166, 63, 179, 81, 130,
1473 : 139, 28, 120, 151, 241, 86, 111, 0,
1474 : 88, 153, 172, 182, 159, 105, 178, 47,
1475 : 51, 167, 65, 66, 92, 73, 198, 211,
1476 : 245, 195, 31, 220, 140, 76, 221, 186,
1477 : 154, 185, 56, 83, 38, 165, 109, 67,
1478 : 124, 226, 132, 53, 229, 29, 12, 181,
1479 : 121, 24, 207, 199, 177, 113, 30, 80,
1480 : 3, 97, 188, 79, 216, 173, 8, 145,
1481 : 87, 128, 180, 237, 240, 137, 125, 104,
1482 : 15, 242, 119, 246, 103, 143, 95, 144,
1483 : 2, 44, 69, 157, 192, 174, 14, 54,
1484 : 218, 82, 64, 210, 11, 6, 129, 21,
1485 : 116, 171, 99, 202, 7, 107, 253, 108
1486 : };
1487 :
1488 0 : void initPermTexture(GLuint *texID)
1489 : {
1490 0 : glGenTextures(1, texID);
1491 0 : glBindTexture(GL_TEXTURE_2D, *texID);
1492 :
1493 : static bool initialized = false;
1494 : static unsigned char permutation2D[256*256*4];
1495 0 : if( !initialized ) {
1496 : int x, y;
1497 :
1498 0 : for( y=0; y < 256; y++ )
1499 0 : for( x=0; x < 256; x++ )
1500 0 : permutation2D[x*4 + y*1024] = permutation256[(y + permutation256[x]) & 0xff];
1501 :
1502 0 : initialized = true;
1503 : }
1504 :
1505 0 : glTexImage2D( GL_TEXTURE_2D, 0, GL_RGBA, 256, 256, 0, GL_RGBA, GL_UNSIGNED_BYTE, permutation2D );
1506 0 : glTexParameteri( GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_NEAREST );
1507 0 : glTexParameteri( GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_NEAREST );
1508 0 : }
1509 :
1510 0 : void ShaderTransition::impl_preparePermShader()
1511 : {
1512 : #ifdef GL_VERSION_2_0
1513 0 : if( m_nProgramObject ) {
1514 0 : OGLShaders::glUseProgram( m_nProgramObject );
1515 :
1516 0 : GLint location = OGLShaders::glGetUniformLocation( m_nProgramObject, "leavingSlideTexture" );
1517 0 : if( location != -1 ) {
1518 0 : OGLShaders::glUniform1i( location, 0 ); // texture unit 0
1519 : }
1520 :
1521 0 : OGLShaders::glActiveTexture(GL_TEXTURE1);
1522 0 : if( !m_nHelperTexture )
1523 0 : initPermTexture( &m_nHelperTexture );
1524 0 : OGLShaders::glActiveTexture(GL_TEXTURE0);
1525 :
1526 0 : location = OGLShaders::glGetUniformLocation( m_nProgramObject, "permTexture" );
1527 0 : if( location != -1 ) {
1528 0 : OGLShaders::glUniform1i( location, 1 ); // texture unit 1
1529 : }
1530 :
1531 0 : location = OGLShaders::glGetUniformLocation( m_nProgramObject, "enteringSlideTexture" );
1532 0 : if( location != -1 ) {
1533 0 : OGLShaders::glUniform1i( location, 2 ); // texture unit 2
1534 : }
1535 : }
1536 : #endif
1537 0 : }
1538 :
1539 : }
1540 :
1541 : namespace
1542 : {
1543 :
1544 0 : class StaticNoiseTransition : public ShaderTransition
1545 : {
1546 : public:
1547 0 : StaticNoiseTransition(const TransitionScene& rScene, const TransitionSettings& rSettings)
1548 0 : : ShaderTransition(rScene, rSettings)
1549 0 : {}
1550 :
1551 : private:
1552 : virtual GLuint makeShader_() SAL_OVERRIDE;
1553 : };
1554 :
1555 0 : GLuint StaticNoiseTransition::makeShader_()
1556 : {
1557 0 : return OGLShaders::LinkProgram( basicVertexShader, staticFragmentShader );
1558 : }
1559 :
1560 : shared_ptr<OGLTransitionImpl>
1561 0 : makeStaticNoiseTransition(
1562 : const Primitives_t& rLeavingSlidePrimitives,
1563 : const Primitives_t& rEnteringSlidePrimitives,
1564 : const TransitionSettings& rSettings)
1565 : {
1566 : return make_shared<StaticNoiseTransition>(
1567 : TransitionScene(rLeavingSlidePrimitives, rEnteringSlidePrimitives),
1568 0 : rSettings)
1569 : ;
1570 : }
1571 :
1572 : }
1573 :
1574 0 : boost::shared_ptr<OGLTransitionImpl> makeStatic()
1575 : {
1576 0 : Primitive Slide;
1577 :
1578 0 : Slide.pushTriangle (basegfx::B2DVector (0,0), basegfx::B2DVector (1,0), basegfx::B2DVector (0,1));
1579 0 : Slide.pushTriangle (basegfx::B2DVector (1,0), basegfx::B2DVector (0,1), basegfx::B2DVector (1,1));
1580 0 : Primitives_t aLeavingSlide;
1581 0 : aLeavingSlide.push_back (Slide);
1582 0 : Primitives_t aEnteringSlide;
1583 0 : aEnteringSlide.push_back (Slide);
1584 :
1585 0 : TransitionSettings aSettings;
1586 0 : aSettings.mbUseMipMapLeaving = aSettings.mbUseMipMapEntering = false;
1587 0 : aSettings.mnRequiredGLVersion = 2.0;
1588 :
1589 0 : return makeStaticNoiseTransition(aLeavingSlide, aEnteringSlide, aSettings);
1590 : }
1591 :
1592 : namespace
1593 : {
1594 :
1595 0 : class DissolveTransition : public ShaderTransition
1596 : {
1597 : public:
1598 0 : DissolveTransition(const TransitionScene& rScene, const TransitionSettings& rSettings)
1599 0 : : ShaderTransition(rScene, rSettings)
1600 0 : {}
1601 :
1602 : private:
1603 : virtual GLuint makeShader_() SAL_OVERRIDE;
1604 : };
1605 :
1606 0 : GLuint DissolveTransition::makeShader_()
1607 : {
1608 0 : return OGLShaders::LinkProgram( basicVertexShader, dissolveFragmentShader );
1609 : }
1610 :
1611 : shared_ptr<OGLTransitionImpl>
1612 0 : makeDissolveTransition(
1613 : const Primitives_t& rLeavingSlidePrimitives,
1614 : const Primitives_t& rEnteringSlidePrimitives,
1615 : const TransitionSettings& rSettings)
1616 : {
1617 : return make_shared<DissolveTransition>(
1618 : TransitionScene(rLeavingSlidePrimitives, rEnteringSlidePrimitives),
1619 0 : rSettings)
1620 : ;
1621 : }
1622 :
1623 : }
1624 :
1625 0 : boost::shared_ptr<OGLTransitionImpl> makeDissolve()
1626 : {
1627 0 : Primitive Slide;
1628 :
1629 0 : Slide.pushTriangle (basegfx::B2DVector (0,0), basegfx::B2DVector (1,0), basegfx::B2DVector (0,1));
1630 0 : Slide.pushTriangle (basegfx::B2DVector (1,0), basegfx::B2DVector (0,1), basegfx::B2DVector (1,1));
1631 0 : Primitives_t aLeavingSlide;
1632 0 : aLeavingSlide.push_back (Slide);
1633 0 : Primitives_t aEnteringSlide;
1634 0 : aEnteringSlide.push_back (Slide);
1635 :
1636 0 : TransitionSettings aSettings;
1637 0 : aSettings.mbUseMipMapLeaving = aSettings.mbUseMipMapEntering = false;
1638 0 : aSettings.mnRequiredGLVersion = 2.0;
1639 :
1640 0 : return makeDissolveTransition(aLeavingSlide, aEnteringSlide, aSettings);
1641 : }
1642 :
1643 0 : boost::shared_ptr<OGLTransitionImpl> makeNewsflash()
1644 : {
1645 0 : Primitive Slide;
1646 :
1647 0 : Slide.pushTriangle(basegfx::B2DVector(0,0),basegfx::B2DVector(1,0),basegfx::B2DVector(0,1));
1648 0 : Slide.pushTriangle(basegfx::B2DVector(1,0),basegfx::B2DVector(0,1),basegfx::B2DVector(1,1));
1649 0 : Slide.Operations.push_back(makeSRotate(basegfx::B3DVector(0,0,1),basegfx::B3DVector(0,0,0),3000,true,0,0.5));
1650 0 : Slide.Operations.push_back(makeSScale(basegfx::B3DVector(0.01,0.01,0.01),basegfx::B3DVector(0,0,0),true,0,0.5));
1651 0 : Slide.Operations.push_back(makeSTranslate(basegfx::B3DVector(-10000, 0, 0),false, 0.5, 2));
1652 0 : Primitives_t aLeavingSlide;
1653 0 : aLeavingSlide.push_back(Slide);
1654 :
1655 0 : Slide.Operations.clear();
1656 0 : Slide.Operations.push_back(makeSRotate(basegfx::B3DVector(0,0,1),basegfx::B3DVector(0,0,0),-3000,true,0.5,1));
1657 0 : Slide.Operations.push_back(makeSTranslate(basegfx::B3DVector(-100, 0, 0),false, -1, 1));
1658 0 : Slide.Operations.push_back(makeSTranslate(basegfx::B3DVector(100, 0, 0),false, 0.5, 1));
1659 0 : Slide.Operations.push_back(makeSScale(basegfx::B3DVector(0.01,0.01,0.01),basegfx::B3DVector(0,0,0),false,-1,1));
1660 0 : Slide.Operations.push_back(makeSScale(basegfx::B3DVector(100,100,100),basegfx::B3DVector(0,0,0),true,0.5,1));
1661 0 : Primitives_t aEnteringSlide;
1662 0 : aEnteringSlide.push_back(Slide);
1663 :
1664 0 : Operations_t aOverallOperations;
1665 0 : aOverallOperations.push_back(makeSRotate(basegfx::B3DVector(0,0,1),basegfx::B3DVector(0.2,0.2,0),1080,true,0,1));
1666 :
1667 0 : return makeSimpleTransition(aLeavingSlide, aEnteringSlide, aOverallOperations);
1668 : }
1669 :
1670 : /* vim:set shiftwidth=4 softtabstop=4 expandtab: */
|