Enable -Wold-style-cast to ensure more consideration is given to types and their...
[platform/core/uifw/dali-core.git] / dali / internal / update / gestures / scene-graph-pan-gesture.cpp
1 /*
2  * Copyright (c) 2017 Samsung Electronics Co., Ltd.
3  *
4  * Licensed under the Apache License, Version 2.0 (the "License");
5  * you may not use this file except in compliance with the License.
6  * You may obtain a copy of the License at
7  *
8  * http://www.apache.org/licenses/LICENSE-2.0
9  *
10  * Unless required by applicable law or agreed to in writing, software
11  * distributed under the License is distributed on an "AS IS" BASIS,
12  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13  * See the License for the specific language governing permissions and
14  * limitations under the License.
15  *
16  */
17
18 // CLASS HEADER
19 #include <dali/internal/update/gestures/scene-graph-pan-gesture.h>
20
21 // EXTERNAL INCLUDES
22 #include <cmath>
23
24 // INTERNAL INCLUDES
25 #include <dali/internal/update/gestures/pan-gesture-profiling.h>
26
27 namespace Dali
28 {
29
30 namespace Internal
31 {
32
33 namespace SceneGraph
34 {
35
36 namespace
37 {
38 const int MAX_GESTURE_AGE = 50;                                     ///< maximum age of a gesture before disallowing its use in algorithm TODO: Possibly make this configurable.
39 const float ACCELERATION_THRESHOLD = 0.1f;                          ///< minimum pan velocity change to trigger dynamic change of prediction amount
40 const unsigned int DEFAULT_PREDICTION_INTERPOLATION = 5;            ///< how much to interpolate pan position and displacement from last vsync time (in milliseconds)
41 const unsigned int DEFAULT_MAX_PREDICTION_INTERPOLATION = 32;       ///< the upper bound of the range to clamp the prediction interpolation
42 const unsigned int DEFAULT_MIN_PREDICTION_INTERPOLATION = 0;        ///< the lower bound of the range to clamp the prediction interpolation
43 const unsigned int DEFAULT_PREDICTION_INTERPOLATION_ADJUSTMENT = 2; ///< the amount of prediction interpolation to adjust (in milliseconds) each time when pan velocity changes
44 const float DEFAULT_SMOOTHING_AMOUNT = 0.25f;                       ///< how much to interpolate pan position and displacement from last vsync time
45 } // unnamed namespace
46
47 const PanGesture::PredictionMode PanGesture::DEFAULT_PREDICTION_MODE = PanGesture::PREDICTION_NONE;
48 const int PanGesture::NUM_PREDICTION_MODES = PanGesture::PREDICTION_1 + 1;
49
50 const PanGesture::SmoothingMode PanGesture::DEFAULT_SMOOTHING_MODE = PanGesture::SMOOTHING_LAST_VALUE;
51 const int PanGesture::NUM_SMOOTHING_MODES = PanGesture::SMOOTHING_LAST_VALUE + 1;
52
53 PanGesture* PanGesture::New()
54 {
55   return new PanGesture();
56 }
57
58 PanGesture::~PanGesture()
59 {
60   delete mProfiling;
61 }
62
63 void PanGesture::AddGesture( const Dali::PanGesture& gesture )
64 {
65   mGestures[ mWritePosition ] = gesture;
66
67   // Update our write position.
68   ++mWritePosition;
69   mWritePosition %= PAN_GESTURE_HISTORY;
70 }
71
72 void PanGesture::RemoveOldHistory(PanInfoHistory& panHistory, unsigned int currentTime, unsigned int maxAge, unsigned int minEvents)
73 {
74   PanInfoHistoryConstIter endIter = panHistory.end();
75   PanInfoHistoryIter iter = panHistory.begin();
76   while( iter != endIter && panHistory.size() > minEvents)
77   {
78     PanInfo currentGesture = *iter;
79     if( currentTime < currentGesture.time + maxAge )
80     {
81       break;
82     }
83     iter = panHistory.erase(iter);
84     endIter = panHistory.end();
85   }
86
87   // dont want more than 5 previous predictions for smoothing
88   iter = mPredictionHistory.begin();
89   while( mPredictionHistory.size() > 1 && iter != mPredictionHistory.end() )
90   {
91     iter = mPredictionHistory.erase(iter);
92   }
93 }
94
95 void PanGesture::PredictiveAlgorithm1(int eventsThisFrame, PanInfo& gestureOut, PanInfoHistory& panHistory, unsigned int lastVSyncTime, unsigned int nextVSyncTime)
96 {
97   RemoveOldHistory(panHistory, lastVSyncTime, MAX_GESTURE_AGE, 0);
98   size_t panHistorySize = panHistory.size();
99   if( panHistorySize == 0 )
100   {
101     // cant do any prediction without a history
102     return;
103   }
104
105   PanInfoHistoryConstIter endIter = panHistory.end();
106   PanInfoHistoryIter iter = panHistory.begin();
107   Vector2 screenVelocity = gestureOut.screen.velocity;
108   Vector2 localVelocity = gestureOut.local.velocity;
109   Vector2 screenDisplacement = gestureOut.screen.displacement;
110   Vector2 localDisplacement = gestureOut.local.displacement;
111
112   bool havePreviousAcceleration = false;
113   bool previousVelocity = false;
114   float previousAccel = 0.0f;
115   unsigned int lastTime(0);
116
117   unsigned int interpolationTime = lastVSyncTime + mCurrentPredictionAmount;
118
119   if( interpolationTime > gestureOut.time ) // Guard against the rare case when gestureOut.time > (lastVSyncTime + mCurrentPredictionAmount)
120   {
121     interpolationTime -= gestureOut.time;
122   }
123   else
124   {
125     interpolationTime = 0u;
126   }
127
128   while( iter != endIter )
129   {
130     PanInfo currentGesture = *iter;
131     if( !previousVelocity )
132     {
133       // not yet set a previous velocity
134       screenVelocity = currentGesture.screen.velocity;
135       previousVelocity = true;
136       lastTime = currentGesture.time;
137       ++iter;
138       continue;
139     }
140     float previousValueWeight = ( static_cast< float >( MAX_GESTURE_AGE ) - (lastVSyncTime - lastTime) ) / static_cast< float >( MAX_GESTURE_AGE );
141     float velMag = currentGesture.screen.velocity.Length();
142     float velDiff = velMag - screenVelocity.Length();
143     float acceleration = 0.0f;
144
145     float time(0.f);
146     if (currentGesture.time > lastTime) // Guard against invalid timestamps
147     {
148       time = static_cast<float>( currentGesture.time - lastTime );
149     }
150     if( time > Math::MACHINE_EPSILON_1 )
151     {
152       acceleration = velDiff / time;
153     }
154
155     float newVelMag = 0.0f;
156     int currentInterpolation = interpolationTime;
157     if( !havePreviousAcceleration )
158     {
159       newVelMag =  velMag;
160       havePreviousAcceleration = true;
161     }
162     else
163     {
164       newVelMag = velMag + (((acceleration * (1.0f - previousValueWeight)) + (previousAccel * previousValueWeight)) * currentInterpolation);
165     }
166     float velMod = 1.0f;
167     if( velMag > Math::MACHINE_EPSILON_1 )
168     {
169       velMod = newVelMag / velMag;
170     }
171     gestureOut.screen.velocity = currentGesture.screen.velocity * velMod;
172     gestureOut.local.velocity = currentGesture.local.velocity * velMod;
173     screenDisplacement = gestureOut.screen.displacement + (gestureOut.screen.velocity * interpolationTime);
174     localDisplacement = gestureOut.local.displacement + (gestureOut.local.velocity * interpolationTime);
175     screenVelocity = currentGesture.screen.velocity;
176     localVelocity = currentGesture.local.velocity;
177     previousAccel = acceleration;
178     ++iter;
179   }
180   // gestureOut's position is currently equal to the last event's position and its displacement is equal to last frame's total displacement
181   // add interpolated distance and position to current
182   // work out interpolated velocity
183   gestureOut.screen.position = (gestureOut.screen.position - gestureOut.screen.displacement) + screenDisplacement;
184   gestureOut.local.position = (gestureOut.local.position - gestureOut.local.displacement) + localDisplacement;
185   gestureOut.screen.displacement = screenDisplacement;
186   gestureOut.local.displacement = localDisplacement;
187   gestureOut.time += interpolationTime;
188 }
189
190 void PanGesture::SmoothingAlgorithm1(bool justStarted, PanInfo& gestureOut, unsigned int lastVSyncTime)
191 {
192   if( justStarted )
193   {
194     gestureOut.screen.displacement = Vector2::ZERO;
195     gestureOut.screen.velocity = Vector2::ZERO;
196     gestureOut.local.displacement = Vector2::ZERO;
197     gestureOut.local.velocity = Vector2::ZERO;
198   }
199   else
200   {
201     gestureOut.screen.position -= (gestureOut.screen.position - mLastGesture.screen.position) * 0.5f * (1.0f - mSmoothingAmount);
202     gestureOut.local.position -= (gestureOut.local.position - mLastGesture.local.position) * 0.5f * (1.0f - mSmoothingAmount);
203     // make current displacement relative to previous update-frame now.
204     gestureOut.screen.displacement = gestureOut.screen.position - mLastGesture.screen.position;
205     gestureOut.local.displacement = gestureOut.local.position - mLastGesture.local.position;
206     // calculate velocity relative to previous update-frame
207     float timeDiff( gestureOut.time - mLastGesture.time );
208     gestureOut.screen.velocity = gestureOut.screen.displacement / timeDiff;
209     gestureOut.local.velocity = gestureOut.local.displacement / timeDiff;
210   }
211 }
212
213 void PanGesture::SmoothingAlgorithm2(bool justStarted, PanInfo& gestureOut, unsigned int lastVSyncTime)
214 {
215   // push back result
216   mPredictionHistory.push_back(gestureOut);
217
218   // now smooth current pan event
219   PanInfoHistoryConstIter endIter = mPredictionHistory.end() - 1;
220   PanInfoHistoryIter iter = mPredictionHistory.begin();
221
222   float distanceMod = 1.0f;
223   float weight = 0.8f;
224   while( iter != endIter )
225   {
226     PanInfo currentGesture = *iter;
227     float newDistanceMod = currentGesture.screen.displacement.Length() / gestureOut.screen.displacement.Length();
228     distanceMod = ((distanceMod * weight) + (newDistanceMod * (1.0f - weight)));
229     weight -= 0.15f;
230     ++iter;
231   }
232   gestureOut.screen.position -= gestureOut.screen.displacement;
233   gestureOut.local.position -= gestureOut.local.displacement;
234   gestureOut.screen.displacement *= distanceMod;
235   gestureOut.local.displacement *= distanceMod;
236   gestureOut.screen.position += gestureOut.screen.displacement;
237   gestureOut.local.position += gestureOut.local.displacement;
238 }
239
240 bool PanGesture::ReadGestures( FrameGestureInfo& info, unsigned int currentTimestamp )
241 {
242   unsigned int previousReadPosition = 0;
243   bool eventFound = false;
244   info.frameGesture = mLastUnmodifiedGesture;
245
246   while( mReadPosition != mWritePosition )
247   {
248     // Copy the gesture first
249     PanInfo currentGesture( mGestures[mReadPosition] );
250
251     if( mProfiling )
252     {
253       mProfiling->mRawData.push_back( PanGestureProfiling::Position( currentGesture.time, currentGesture.screen.position, currentGesture.screen.displacement, currentGesture.screen.velocity, currentGesture.state ) );
254     }
255     info.frameGesture.local.position = currentGesture.local.position;
256     info.frameGesture.local.velocity = currentGesture.local.velocity;
257     info.frameGesture.screen.position = currentGesture.screen.position;
258     info.frameGesture.screen.velocity = currentGesture.screen.velocity;
259
260     if( info.eventsThisFrame > 0 )
261     {
262       info.acceleration = currentGesture.screen.velocity.Length() - mGestures[previousReadPosition].screen.velocity.Length();
263     }
264
265     if( !eventFound )
266     {
267       info.frameGesture.local.displacement = currentGesture.local.displacement;
268       info.frameGesture.screen.displacement = currentGesture.screen.displacement;
269       eventFound = true;
270     }
271     else
272     {
273       info.frameGesture.local.displacement += currentGesture.local.displacement;
274       info.frameGesture.screen.displacement += currentGesture.screen.displacement;
275     }
276     info.frameGesture.time = currentGesture.time;
277
278     // add event to history
279     mPanHistory.push_back( currentGesture );
280     if( currentGesture.state == Gesture::Started )
281     {
282       info.justStarted = true;
283       // clear just finished as we have started new pan
284       info.justFinished = false;
285     }
286     info.justFinished |= ( currentGesture.state == Gesture::Finished || currentGesture.state == Gesture::Cancelled );
287
288     // Update our read position.
289     previousReadPosition = mReadPosition;
290     ++info.eventsThisFrame;
291     ++mReadPosition;
292     mReadPosition %= PAN_GESTURE_HISTORY;
293   }
294   // This code does not determine if the data will be used.
295   return false;
296 }
297
298 bool PanGesture::ReadAndResampleGestures( FrameGestureInfo& info, unsigned int currentTimestamp )
299 {
300   PanInfo lastReadGesture;
301   while( mReadPosition != mWritePosition )
302   {
303     // Copy the gesture first
304     lastReadGesture = mGestures[mReadPosition];
305     if( mProfiling )
306     {
307       mProfiling->mRawData.push_back( PanGestureProfiling::Position( lastReadGesture.time, lastReadGesture.screen.position,
308           lastReadGesture.screen.displacement, lastReadGesture.screen.velocity, lastReadGesture.state ) );
309     }
310
311     info.frameGesture.screen.position += lastReadGesture.screen.position;
312     info.frameGesture.local.position += lastReadGesture.local.position;
313     info.frameGesture.screen.velocity += lastReadGesture.screen.velocity;
314     info.frameGesture.local.velocity += lastReadGesture.local.velocity;
315
316     if( lastReadGesture.state == Gesture::Started )
317     {
318       // Clear just finished as we have started new pan.
319       info.justFinished = false;
320       info.justStarted = true;
321     }
322     else
323     {
324       info.justFinished |= ( lastReadGesture.state == Gesture::Finished || lastReadGesture.state == Gesture::Cancelled );
325     }
326
327     // Add event to history
328     mPanHistory.push_back( lastReadGesture );
329
330     // Update our read position.
331     ++info.eventsThisFrame;
332     ++mReadPosition;
333     mReadPosition %= PAN_GESTURE_HISTORY;
334   }
335
336   bool updateProperties = false;
337   if( info.eventsThisFrame > 0 )
338   {
339     // Some events were read this frame.
340     mTargetGesture = lastReadGesture;
341
342     if( info.eventsThisFrame > 1 )
343     {
344       info.frameGesture.screen.position /= info.eventsThisFrame;
345       info.frameGesture.local.position /= info.eventsThisFrame;
346       info.frameGesture.screen.velocity /= info.eventsThisFrame;
347       info.frameGesture.local.velocity /= info.eventsThisFrame;
348
349       info.frameGesture.screen.displacement = info.frameGesture.screen.position - mLastGesture.screen.position;
350       info.frameGesture.local.displacement = info.frameGesture.local.position - mLastGesture.local.position;
351
352       mNotAtTarget = true;
353     }
354     else
355     {
356       info.frameGesture.screen.displacement = lastReadGesture.screen.displacement;
357       info.frameGesture.local.displacement = lastReadGesture.local.displacement;
358     }
359
360     info.frameGesture.time = currentTimestamp;
361
362     updateProperties = true;
363   }
364   else
365   {
366     // 0 Events this frame.
367     if( mNotAtTarget )
368     {
369       mNotAtTarget = false;
370       info.frameGesture = mTargetGesture;
371       updateProperties = true;
372     }
373     else
374     {
375       info.frameGesture = mLastGesture;
376     }
377   }
378
379   return updateProperties;
380 }
381
382 bool PanGesture::UpdateProperties( unsigned int lastVSyncTime, unsigned int nextVSyncTime )
383 {
384   if( !mInGesture )
385   {
386     // clear current pan history
387     mPanHistory.clear();
388     mPredictionHistory.clear();
389   }
390
391   FrameGestureInfo frameInfo;
392   bool updateProperties = false;
393
394   // Read input data.
395   // If we are using a form of prediction, read all the input as-is.
396   if( mPredictionMode != PREDICTION_NONE )
397   {
398     // Read input required for prediction algorithms.
399     updateProperties = ReadGestures( frameInfo, lastVSyncTime );
400   }
401   else
402   {
403     // Read and resample input.
404     updateProperties = ReadAndResampleGestures( frameInfo, lastVSyncTime );
405   }
406
407   PanInfo frameGesture = frameInfo.frameGesture;
408   mLastUnmodifiedGesture = frameGesture;
409
410   // Process input data.
411   mInGesture |= frameInfo.justStarted;
412   if( mInGesture )
413   {
414     // Profiling.
415     if( mProfiling )
416     {
417       mProfiling->mLatestData.push_back( PanGestureProfiling::Position( lastVSyncTime, frameGesture.screen.position,
418           frameGesture.screen.displacement, frameGesture.screen.velocity, frameGesture.state ) );
419     }
420
421     // Perform prediction.
422     switch( mPredictionMode )
423     {
424       case PREDICTION_NONE:
425       {
426         break;
427       }
428       case PREDICTION_1:
429       {
430         // Dynamically change the prediction amount according to the pan velocity acceleration.
431         if( !frameInfo.justStarted )
432         {
433           if( frameInfo.eventsThisFrame <= 1 )
434           {
435             frameInfo.acceleration = frameGesture.screen.velocity.Length() - mLastUnmodifiedGesture.screen.velocity.Length();
436           }
437
438           // Ignore tiny velocity fluctuation to avoid unnecessary prediction amount change
439           if( fabsf( frameInfo.acceleration ) > ACCELERATION_THRESHOLD )
440           {
441             mCurrentPredictionAmount += mPredictionAmountAdjustment * ( frameInfo.acceleration > Math::MACHINE_EPSILON_0 ? 1.0f : -1.0f );
442             if( mCurrentPredictionAmount > mMaxPredictionAmount + mPredictionAmountAdjustment ) // Guard against unsigned int overflow
443             {
444               mCurrentPredictionAmount = 0;
445             }
446           }
447         }
448         else
449         {
450           mCurrentPredictionAmount = mPredictionAmount; // Reset the prediction amount for each new gesture
451         }
452
453         mCurrentPredictionAmount = std::max( mMinPredictionAmount, std::min( mCurrentPredictionAmount, mMaxPredictionAmount ) );
454
455         // Calculate the delta of positions before the prediction
456         Vector2 deltaPosition = frameGesture.screen.position - mLastUnmodifiedGesture.screen.position;
457
458         // Make latest gesture equal to current gesture before interpolation
459         PredictiveAlgorithm1( frameInfo.eventsThisFrame, frameGesture, mPanHistory, lastVSyncTime, nextVSyncTime );
460
461         // Calculate the delta of positions after the prediction.
462         Vector2 deltaPredictedPosition = frameGesture.screen.position - mLastGesture.screen.position;
463
464         // If the change in the prediction has a different sign than the change in the actual position,
465         // there is overshot (i.e. the current prediction is too large). Return the previous prediction
466         // to give the user's finger a chance to catch up with where we have panned to.
467         bool overshotXAxis = false;
468         bool overshotYAxis = false;
469         if( (deltaPosition.x > Math::MACHINE_EPSILON_0 && deltaPredictedPosition.x < Math::MACHINE_EPSILON_0 )
470          || (deltaPosition.x < Math::MACHINE_EPSILON_0 && deltaPredictedPosition.x > Math::MACHINE_EPSILON_0 ) )
471         {
472           overshotXAxis = true;
473           frameGesture.screen.position.x = mLastGesture.screen.position.x;
474         }
475
476         if( (deltaPosition.y > Math::MACHINE_EPSILON_0 && deltaPredictedPosition.y < Math::MACHINE_EPSILON_0 )
477          || (deltaPosition.y < Math::MACHINE_EPSILON_0 && deltaPredictedPosition.y > Math::MACHINE_EPSILON_0 ) )
478         {
479           overshotYAxis = true;
480           frameGesture.screen.position.y = mLastGesture.screen.position.y;
481         }
482
483         // If there is overshot in one axis, reduce the possible overshot in the other axis,
484         // and reduce the prediction amount so that it doesn't overshoot as easily next time.
485         if(overshotXAxis || overshotYAxis)
486         {
487           mCurrentPredictionAmount -= mPredictionAmountAdjustment;
488           if( mCurrentPredictionAmount > mMaxPredictionAmount + mPredictionAmountAdjustment ) // Guard against unsigned int overflow
489           {
490             mCurrentPredictionAmount = 0;
491           }
492           mCurrentPredictionAmount = std::max( mMinPredictionAmount, std::min( mCurrentPredictionAmount, mMaxPredictionAmount ) );
493
494           if( overshotXAxis && !overshotYAxis )
495           {
496             frameGesture.screen.position.y = ( mLastGesture.screen.position.y + frameGesture.screen.position.y ) * 0.5f;
497           }
498
499           if( overshotYAxis && !overshotXAxis )
500           {
501             frameGesture.screen.position.x = ( mLastGesture.screen.position.x + frameGesture.screen.position.x ) * 0.5f;
502           }
503         }
504
505         updateProperties = true;
506         break;
507       }
508     }
509
510     // Perform smoothing.
511     switch( mSmoothingMode )
512     {
513       case SMOOTHING_NONE:
514       {
515         // No smoothing
516         break;
517       }
518       case SMOOTHING_LAST_VALUE:
519       {
520         SmoothingAlgorithm1( frameInfo.justStarted, frameGesture, lastVSyncTime );
521         break;
522       }
523     }
524
525     if( updateProperties )
526     {
527       // only update properties if event received
528       // set latest gesture to raw pan info with unchanged time
529       mPanning.Set( mInGesture & !frameInfo.justFinished );
530       mScreenPosition.Set( frameGesture.screen.position );
531       mScreenDisplacement.Set( frameGesture.screen.displacement );
532       mScreenVelocity.Set( frameGesture.screen.velocity );
533       mLocalPosition.Set( frameGesture.local.position );
534       mLocalDisplacement.Set( frameGesture.local.displacement );
535       mLocalVelocity.Set( frameGesture.local.velocity );
536     }
537
538     if( mProfiling )
539     {
540       mProfiling->mAveragedData.push_back( PanGestureProfiling::Position( frameGesture.time, frameGesture.screen.position,
541           frameGesture.screen.displacement, frameGesture.screen.velocity, frameGesture.state ) );
542     }
543   }
544
545   mLastGesture = frameGesture;
546
547   mInGesture &= ~frameInfo.justFinished;
548   if( mProfiling && frameInfo.justFinished )
549   {
550     mProfiling->PrintData();
551     mProfiling->ClearData();
552   }
553
554   return updateProperties;
555 }
556
557 const GesturePropertyBool& PanGesture::GetPanningProperty() const
558 {
559   return mPanning;
560 }
561
562 const GesturePropertyVector2& PanGesture::GetScreenPositionProperty() const
563 {
564   return mScreenPosition;
565 }
566
567 const GesturePropertyVector2& PanGesture::GetScreenVelocityProperty() const
568 {
569   return mScreenVelocity;
570 }
571
572 const GesturePropertyVector2& PanGesture::GetScreenDisplacementProperty() const
573 {
574   return mScreenDisplacement;
575 }
576
577 const GesturePropertyVector2& PanGesture::GetLocalPositionProperty() const
578 {
579   return mLocalPosition;
580 }
581
582 const GesturePropertyVector2& PanGesture::GetLocalDisplacementProperty() const
583 {
584   return mLocalDisplacement;
585 }
586
587 const GesturePropertyVector2& PanGesture::GetLocalVelocityProperty() const
588 {
589   return mLocalVelocity;
590 }
591
592 void PanGesture::SetPredictionMode(PredictionMode mode)
593 {
594   mPredictionMode = mode;
595 }
596
597 void PanGesture::SetPredictionAmount(unsigned int amount)
598 {
599   mPredictionAmount = amount;
600 }
601
602 void PanGesture::SetMaximumPredictionAmount(unsigned int amount)
603 {
604   mMaxPredictionAmount = amount;
605 }
606
607 void PanGesture::SetMinimumPredictionAmount(unsigned int amount)
608 {
609   mMinPredictionAmount = amount;
610 }
611
612 void PanGesture::SetPredictionAmountAdjustment(unsigned int amount)
613 {
614   mPredictionAmountAdjustment = amount;
615 }
616
617 void PanGesture::SetSmoothingMode(SmoothingMode mode)
618 {
619   mSmoothingMode = mode;
620 }
621
622 void PanGesture::SetSmoothingAmount(float amount)
623 {
624   mSmoothingAmount = amount;
625 }
626
627 void PanGesture::EnableProfiling()
628 {
629   if( !mProfiling )
630   {
631     mProfiling = new PanGestureProfiling();
632   }
633 }
634
635 void PanGesture::ResetDefaultProperties( BufferIndex updateBufferIndex )
636 {
637   mScreenPosition.Reset();
638   mScreenDisplacement.Reset();
639   mLocalPosition.Reset();
640   mLocalDisplacement.Reset();
641   mPanning.Reset();
642 }
643
644 PanGesture::PanGesture()
645 : mPanning(),
646   mGestures(),
647   mWritePosition( 0 ),
648   mReadPosition( 0 ),
649   mNotAtTarget( false ),
650   mInGesture( false ),
651   mPredictionMode( DEFAULT_PREDICTION_MODE ),
652   mPredictionAmount( DEFAULT_PREDICTION_INTERPOLATION ),
653   mCurrentPredictionAmount( DEFAULT_PREDICTION_INTERPOLATION ),
654   mMaxPredictionAmount( DEFAULT_MAX_PREDICTION_INTERPOLATION ),
655   mMinPredictionAmount( DEFAULT_MIN_PREDICTION_INTERPOLATION ),
656   mPredictionAmountAdjustment( DEFAULT_PREDICTION_INTERPOLATION_ADJUSTMENT ),
657   mSmoothingMode( DEFAULT_SMOOTHING_MODE ),
658   mSmoothingAmount( DEFAULT_SMOOTHING_AMOUNT ),
659   mProfiling( NULL )
660 {
661 }
662
663
664 } // namespace SceneGraph
665
666 } // namespace Internal
667
668 } // namespace Dali