Actor's Transformation API Cleanup
[platform/core/uifw/dali-core.git] / dali / internal / event / actors / camera-actor-impl.cpp
1 /*
2  * Copyright (c) 2014 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/event/actors/camera-actor-impl.h>
20
21 // EXTERNAL INCLUDES
22 #include <cmath>
23
24 // INTERNAL INCLUDES
25 #include <dali/public-api/common/stage.h>
26 #include <dali/public-api/object/type-registry.h>
27 #include <dali/internal/event/actor-attachments/camera-attachment-impl.h>
28 #include <dali/internal/event/common/property-helper.h>
29 #include <dali/internal/event/common/stage-impl.h>
30 #include <dali/internal/event/render-tasks/render-task-impl.h>
31 #include <dali/internal/event/render-tasks/render-task-list-impl.h>
32 #include <dali/internal/event/common/projection.h>
33 #include <dali/integration-api/debug.h>
34
35 namespace Dali
36 {
37
38 namespace Internal
39 {
40
41 namespace
42 {
43
44 // Properties
45
46 /**
47  * We want to discourage the use of property strings (minimize string comparisons),
48  * particularly for the default properties.
49  *              Name                     Type   writable animatable constraint-input  enum for index-checking
50  */
51 DALI_PROPERTY_TABLE_BEGIN
52 DALI_PROPERTY( "type",                   STRING,   true,    false,   true,   Dali::CameraActor::Property::TYPE                  )
53 DALI_PROPERTY( "projection-mode",        STRING,   true,    false,   true,   Dali::CameraActor::Property::PROJECTION_MODE       )
54 DALI_PROPERTY( "field-of-view",          FLOAT,    true,    false,   true,   Dali::CameraActor::Property::FIELD_OF_VIEW         )
55 DALI_PROPERTY( "aspect-ratio",           FLOAT,    true,    false,   true,   Dali::CameraActor::Property::ASPECT_RATIO          )
56 DALI_PROPERTY( "near-plane-distance",    FLOAT,    true,    false,   true,   Dali::CameraActor::Property::NEAR_PLANE_DISTANCE   )
57 DALI_PROPERTY( "far-plane-distance",     FLOAT,    true,    false,   true,   Dali::CameraActor::Property::FAR_PLANE_DISTANCE    )
58 DALI_PROPERTY( "left-plane-distance",    FLOAT,    true,    false,   true,   Dali::CameraActor::Property::LEFT_PLANE_DISTANCE   )
59 DALI_PROPERTY( "right-plane-distance",   FLOAT,    true,    false,   true,   Dali::CameraActor::Property::RIGHT_PLANE_DISTANCE  )
60 DALI_PROPERTY( "top-plane-distance",     FLOAT,    true,    false,   true,   Dali::CameraActor::Property::TOP_PLANE_DISTANCE    )
61 DALI_PROPERTY( "bottom-plane-distance",  FLOAT,    true,    false,   true,   Dali::CameraActor::Property::BOTTOM_PLANE_DISTANCE )
62 DALI_PROPERTY( "target-position",        VECTOR3,  true,    false,   true,   Dali::CameraActor::Property::TARGET_POSITION       )
63 DALI_PROPERTY( "projection-matrix",      MATRIX,   false,   false,   true,   Dali::CameraActor::Property::PROJECTION_MATRIX     )
64 DALI_PROPERTY( "view-matrix",            MATRIX,   false,   false,   true,   Dali::CameraActor::Property::VIEW_MATRIX           )
65 DALI_PROPERTY( "invert-y-axis",          BOOLEAN,  true,    false,   true,   Dali::CameraActor::Property::INVERT_Y_AXIS         )
66 DALI_PROPERTY_TABLE_END( DEFAULT_DERIVED_ACTOR_PROPERTY_START_INDEX )
67
68 // calculate the far plane distance for a 16bit depth buffer with 4 bits per unit precision
69 void CalculateClippingAndZ( float width, float height, float& nearClippingPlane, float& farClippingPlane, float& cameraZ )
70 {
71   nearClippingPlane = std::max( width, height );
72   farClippingPlane = nearClippingPlane + static_cast<float>( 0xFFFF >> 4 );
73   cameraZ = 2.0f * nearClippingPlane;
74 }
75
76 BaseHandle Create()
77 {
78   return Dali::CameraActor::New();
79 }
80
81 TypeRegistration mType( typeid( Dali::CameraActor ), typeid( Dali::Actor ), Create );
82
83 /**
84  * Builds the picking ray in the world reference system from an orthographic camera
85  * The ray origin is the screen coordinate in the near plane translated to a parallel
86  * plane at the camera origin. The ray direction is the direction the camera is facing
87  * (i.e. Z=-1 in view space).
88  */
89 void BuildOrthoPickingRay( const Matrix& viewMatrix,
90                            const Matrix& projectionMatrix,
91                            const Viewport& viewport,
92                            float screenX,
93                            float screenY,
94                            Vector4& rayOrigin,
95                            Vector4& rayDir,
96                            float nearPlaneDistance )
97 {
98   //          inv( modelMatrix )          inv( viewMatrix )    inv( projectionMatrix )           normalize
99   //          <-----------------         <-----------------         <--------------           <-------------
100   //  Local                      World                      Camera                 Normalized                 Screen
101   // reference                  reference                  reference                  clip                  coordinates
102   //  system                     system                     system                 coordinates
103   //          ----------------->         ----------------->         -------------->           ------------->
104   //             modelMatrix                 viewMatrix             projectionMatrix             viewport
105
106   // Transforms the touch point from the screen reference system to the world reference system.
107   Matrix invViewProjection( false ); // Don't initialize.
108   Matrix::Multiply( invViewProjection, viewMatrix, projectionMatrix );
109   if( !invViewProjection.Invert() )
110   {
111     DALI_ASSERT_DEBUG( false );
112   }
113
114   Vector4 near( screenX - viewport.x, viewport.height - (screenY - viewport.y), 0.f, 1.f );
115   if( !Unproject( near, invViewProjection, viewport.width, viewport.height, rayOrigin ) )
116   {
117     DALI_ASSERT_DEBUG( false );
118   }
119
120   Matrix invView = viewMatrix;
121   if( !invView.Invert() )
122   {
123     DALI_ASSERT_DEBUG( false );
124   }
125
126   Vector4 cameraOrigin = invView * Vector4( 0.f, 0.f, 0.f, 1.f );
127   Vector4 nearPlaneOrigin = invView * Vector4( 0.0f, 0.0f, -nearPlaneDistance, 1.0f);
128
129   // Vector pointing from the camera to the near plane
130   rayDir = cameraOrigin - nearPlaneOrigin;
131   rayOrigin -= rayDir;
132   rayDir.Normalize();
133   rayDir.w = 1.0f;
134 }
135
136 } // namespace
137
138 CameraActorPtr CameraActor::New( const Size& size )
139 {
140   CameraActorPtr actor(new CameraActor());
141
142   // Second-phase construction
143
144   actor->Initialize();
145
146   actor->SetName("DefaultCamera");
147
148   // Create the attachment
149   actor->mCameraAttachment = CameraAttachment::New( *actor->mNode );
150
151   actor->Attach(*actor->mCameraAttachment);
152
153   actor->SetPerspectiveProjection( size );
154
155   // By default Actors face in the positive Z direction in world space
156   // CameraActors should face in the negative Z direction, towards the other actors
157   actor->SetOrientation( Quaternion( Math::PI, Vector3::YAXIS ) );
158
159   return actor;
160 }
161
162 void CameraActor::OnInitialize()
163 {
164 }
165
166 CameraActor::CameraActor()
167 : Actor( Actor::BASIC )
168 {
169 }
170
171 CameraActor::~CameraActor()
172 {
173 }
174
175 void CameraActor::SetType( Dali::Camera::Type type )
176 {
177   mCameraAttachment->SetType(type);
178 }
179
180 Dali::Camera::Type CameraActor::GetType() const
181 {
182   return mCameraAttachment->GetType();
183 }
184
185 void CameraActor::SetProjectionMode( Dali::Camera::ProjectionMode mode )
186 {
187   mCameraAttachment->SetProjectionMode(mode);
188 }
189
190 Dali::Camera::ProjectionMode CameraActor::GetProjectionMode() const
191 {
192   return mCameraAttachment->GetProjectionMode();
193 }
194
195 void CameraActor::SetFieldOfView( float fieldOfView )
196 {
197   mCameraAttachment->SetFieldOfView(fieldOfView);
198 }
199
200 float CameraActor::GetFieldOfView( ) const
201 {
202   return mCameraAttachment->GetFieldOfView();
203 }
204
205 void CameraActor::SetAspectRatio( float aspectRatio )
206 {
207   mCameraAttachment->SetAspectRatio(aspectRatio);
208 }
209
210 float CameraActor::GetAspectRatio( ) const
211 {
212   return mCameraAttachment->GetAspectRatio();
213 }
214
215 void CameraActor::SetNearClippingPlane( float nearClippingPlane )
216 {
217   mCameraAttachment->SetNearClippingPlane(nearClippingPlane);
218 }
219
220 float CameraActor::GetNearClippingPlane( ) const
221 {
222   return mCameraAttachment->GetNearClippingPlane();
223 }
224
225 void CameraActor::SetFarClippingPlane( float farClippingPlane )
226 {
227   mCameraAttachment->SetFarClippingPlane(farClippingPlane);
228 }
229
230 float CameraActor::GetFarClippingPlane( ) const
231 {
232   return mCameraAttachment->GetFarClippingPlane();
233 }
234
235 void CameraActor::SetTargetPosition(const Vector3& target)
236 {
237   mCameraAttachment->SetTargetPosition(target);
238 }
239
240 Vector3 CameraActor::GetTargetPosition() const
241 {
242   return mCameraAttachment->GetTargetPosition();
243 }
244
245 void CameraActor::SetInvertYAxis(bool invertYAxis)
246 {
247   mCameraAttachment->SetInvertYAxis(invertYAxis);
248 }
249
250 bool CameraActor::GetInvertYAxis() const
251 {
252   return mCameraAttachment->GetInvertYAxis();
253 }
254
255 void CameraActor::SetPerspectiveProjection( const Size& size, const Vector2& stereoBias /* = Vector2::ZERO */ )
256 {
257   float width = size.width;
258   float height = size.height;
259
260   if( Size::ZERO == size )
261   {
262     if( Stage::IsInstalled() )
263     {
264       const Size& stageSize = mStage->GetSize();
265
266       width = stageSize.width;
267       height = stageSize.height;
268     }
269   }
270
271   if( ( width < Math::MACHINE_EPSILON_1000 ) || ( height < Math::MACHINE_EPSILON_1000 ) )
272   {
273     // On the stage initialization this method is called but the size has not been set.
274     // There is no point to set any value if width or height is zero.
275     return;
276   }
277
278   float nearClippingPlane;
279   float farClippingPlane;
280   float cameraZ;
281   CalculateClippingAndZ( width, height, nearClippingPlane, farClippingPlane, cameraZ );
282
283   // calculate the position of the camera to have the desired aspect ratio
284   const float fieldOfView = 2.0f * std::atan( height * 0.5f / cameraZ );
285
286   // unless it is too small, we want at least as much space to the back as we have torwards the front
287   const float minClippingFarPlane = 2.f * nearClippingPlane;
288   if ( farClippingPlane < minClippingFarPlane )
289   {
290     farClippingPlane = minClippingFarPlane;
291   }
292
293   const float aspectRatio = width / height;
294
295   SetProjectionMode(Dali::Camera::PERSPECTIVE_PROJECTION);
296   SetFieldOfView( fieldOfView );
297   SetNearClippingPlane( nearClippingPlane );
298   SetFarClippingPlane( farClippingPlane );
299   SetAspectRatio( aspectRatio );
300   mCameraAttachment->SetStereoBias( stereoBias );
301   SetZ( cameraZ );
302 }
303
304
305 void CameraActor::SetOrthographicProjection( const Vector2& size )
306 {
307   // Choose near, far and Z parameters to match the SetPerspectiveProjection above.
308   float nearClippingPlane;
309   float farClippingPlane;
310   float cameraZ;
311   CalculateClippingAndZ( size.width, size.height, nearClippingPlane, farClippingPlane, cameraZ );
312   SetOrthographicProjection( -size.x*0.5f, size.x*0.5f, size.y*0.5f, -size.y*0.5f,
313                              nearClippingPlane, farClippingPlane );
314   SetZ( cameraZ );
315 }
316
317 void CameraActor::SetOrthographicProjection( float left, float right, float top, float bottom, float near, float far )
318 {
319   mCameraAttachment->SetLeftClippingPlane(left);
320   mCameraAttachment->SetRightClippingPlane(right);
321   mCameraAttachment->SetTopClippingPlane(top);
322   mCameraAttachment->SetBottomClippingPlane(bottom);
323   SetNearClippingPlane( near );
324   SetFarClippingPlane( far );
325   SetProjectionMode(Dali::Camera::ORTHOGRAPHIC_PROJECTION);
326 }
327
328 bool CameraActor::BuildPickingRay( const Vector2& screenCoordinates,
329                                    const Viewport& viewport,
330                                    Vector4& rayOrigin,
331                                    Vector4& rayDirection )
332 {
333   bool success = true;
334   if( GetProjectionMode() == Dali::Camera::PERSPECTIVE_PROJECTION )
335   {
336     // Build a picking ray in the world reference system.
337     // ray starts from the camera world position
338     rayOrigin = mNode->GetWorldPosition( mStage->GetEventBufferIndex() );
339     rayOrigin.w = 1.0f;
340
341     // Transform the touch point from the screen coordinate system to the world coordinates system.
342     Vector4 near( screenCoordinates.x - viewport.x, viewport.height - (screenCoordinates.y - viewport.y), 0.f, 1.f );
343     if( !Unproject( near, mCameraAttachment->GetInverseViewProjectionMatrix(), viewport.width, viewport.height, near ) )
344     {
345       // unproject failed so no picking ray possible
346       success = false;
347     }
348
349     // Compute the ray's director vector.
350     rayDirection.x = near.x - rayOrigin.x;
351     rayDirection.y = near.y - rayOrigin.y;
352     rayDirection.z = near.z - rayOrigin.z;
353     rayDirection.Normalize();
354     rayDirection.w = 1.f;
355   }
356   else
357   {
358     float nearPlaneDistance = GetNearClippingPlane();
359     BuildOrthoPickingRay( GetViewMatrix(),
360                           GetProjectionMatrix(),
361                           viewport, screenCoordinates.x,
362                           screenCoordinates.y,
363                           rayOrigin,
364                           rayDirection,
365                           nearPlaneDistance );
366   }
367
368   return success;
369 }
370
371 const Matrix& CameraActor::GetViewMatrix() const
372 {
373   if ( OnStage() )
374   {
375     return mCameraAttachment->GetViewMatrix();
376   }
377   else
378   {
379     return Matrix::IDENTITY;
380   }
381 }
382
383 const Matrix& CameraActor::GetProjectionMatrix() const
384 {
385   if ( OnStage() )
386   {
387     return mCameraAttachment->GetProjectionMatrix();
388   }
389   else
390   {
391     return Matrix::IDENTITY;
392   }
393 }
394
395 unsigned int CameraActor::GetDefaultPropertyCount() const
396 {
397   return Actor::GetDefaultPropertyCount() + DEFAULT_PROPERTY_COUNT;
398 }
399
400 void CameraActor::GetDefaultPropertyIndices( Property::IndexContainer& indices ) const
401 {
402   Actor::GetDefaultPropertyIndices( indices ); // Actor class properties
403
404   indices.reserve( indices.size() + DEFAULT_PROPERTY_COUNT );
405
406   int index = DEFAULT_DERIVED_ACTOR_PROPERTY_START_INDEX;
407   for ( int i = 0; i < DEFAULT_PROPERTY_COUNT; ++i, ++index )
408   {
409     indices.push_back( index );
410   }
411 }
412
413 bool CameraActor::IsDefaultPropertyWritable( Property::Index index ) const
414 {
415   if( index < DEFAULT_ACTOR_PROPERTY_MAX_COUNT )
416   {
417     return Actor::IsDefaultPropertyWritable( index );
418   }
419
420   return DEFAULT_PROPERTY_DETAILS[index - DEFAULT_DERIVED_ACTOR_PROPERTY_START_INDEX].writable;
421 }
422
423 bool CameraActor::IsDefaultPropertyAnimatable( Property::Index index ) const
424 {
425   if( index < DEFAULT_ACTOR_PROPERTY_MAX_COUNT )
426   {
427     return Actor::IsDefaultPropertyAnimatable( index );
428   }
429
430   return DEFAULT_PROPERTY_DETAILS[index - DEFAULT_DERIVED_ACTOR_PROPERTY_START_INDEX].animatable;
431 }
432
433 bool CameraActor::IsDefaultPropertyAConstraintInput( Property::Index index ) const
434 {
435   if( index < DEFAULT_ACTOR_PROPERTY_MAX_COUNT )
436   {
437     return Actor::IsDefaultPropertyAConstraintInput( index );
438   }
439
440   return DEFAULT_PROPERTY_DETAILS[index - DEFAULT_DERIVED_ACTOR_PROPERTY_START_INDEX].constraintInput;
441 }
442
443 Property::Type CameraActor::GetDefaultPropertyType( Property::Index index ) const
444 {
445   if( index < DEFAULT_ACTOR_PROPERTY_MAX_COUNT )
446   {
447     return Actor::GetDefaultPropertyType( index );
448   }
449   else
450   {
451     index -= DEFAULT_DERIVED_ACTOR_PROPERTY_START_INDEX;
452
453     if ( ( index >= 0 ) && ( index < DEFAULT_PROPERTY_COUNT ) )
454     {
455       return DEFAULT_PROPERTY_DETAILS[index].type;
456     }
457     else
458     {
459       // index out-of-bounds
460       return Property::NONE;
461     }
462   }
463 }
464
465 const char* CameraActor::GetDefaultPropertyName( Property::Index index ) const
466 {
467   if(index < DEFAULT_ACTOR_PROPERTY_MAX_COUNT)
468   {
469     return Actor::GetDefaultPropertyName(index);
470   }
471   else
472   {
473     index -= DEFAULT_DERIVED_ACTOR_PROPERTY_START_INDEX;
474
475     if ( ( index >= 0 ) && ( index < DEFAULT_PROPERTY_COUNT ) )
476     {
477       return DEFAULT_PROPERTY_DETAILS[index].name;
478     }
479     return NULL;
480   }
481 }
482
483 Property::Index CameraActor::GetDefaultPropertyIndex(const std::string& name) const
484 {
485   Property::Index index = Property::INVALID_INDEX;
486
487   // Look for name in current class' default properties
488   for( int i = 0; i < DEFAULT_PROPERTY_COUNT; ++i )
489   {
490     if( 0 == strcmp( name.c_str(), DEFAULT_PROPERTY_DETAILS[i].name ) ) // dont want to convert rhs to string
491     {
492       index = i + DEFAULT_DERIVED_ACTOR_PROPERTY_START_INDEX;
493       break;
494     }
495   }
496
497   // If not found, check in base class
498   if( Property::INVALID_INDEX == index )
499   {
500     index = Actor::GetDefaultPropertyIndex( name );
501   }
502
503   return index;
504 }
505
506 void CameraActor::SetDefaultProperty( Property::Index index, const Property::Value& propertyValue )
507 {
508   if(index < DEFAULT_ACTOR_PROPERTY_MAX_COUNT)
509   {
510     Actor::SetDefaultProperty(index, propertyValue);
511   }
512   else
513   {
514     DALI_ASSERT_DEBUG(mCameraAttachment && "where is the camera?");
515     switch(index)
516     {
517       case Dali::CameraActor::Property::TYPE:
518       {
519         std::string s( propertyValue.Get<std::string>() );
520         if(s == "LOOK_AT_TARGET")
521         {
522           mCameraAttachment->SetType(Dali::Camera::LOOK_AT_TARGET);
523         }
524         else if(s == "FREE_LOOK")
525         {
526           mCameraAttachment->SetType(Dali::Camera::FREE_LOOK);
527         }
528         else
529         {
530           DALI_LOG_WARNING("Unknown camera type\n");
531         }
532         break;
533       }
534       case Dali::CameraActor::Property::PROJECTION_MODE:
535       {
536         std::string s(propertyValue.Get<std::string>());
537         if(s == "PERSPECTIVE_PROJECTION")
538         {
539           mCameraAttachment->SetProjectionMode(Dali::Camera::PERSPECTIVE_PROJECTION);
540         }
541         else if(s == "ORTHOGRAPHIC_PROJECTION")
542         {
543           mCameraAttachment->SetProjectionMode(Dali::Camera::ORTHOGRAPHIC_PROJECTION);
544         }
545         else
546         {
547           DALI_LOG_WARNING("Unknown projection mode\n");
548         }
549         break;
550       }
551       case Dali::CameraActor::Property::FIELD_OF_VIEW:
552       {
553         mCameraAttachment->SetFieldOfView(propertyValue.Get<float>());
554         break;
555       }
556       case Dali::CameraActor::Property::ASPECT_RATIO:
557       {
558         mCameraAttachment->SetAspectRatio(propertyValue.Get<float>());
559         break;
560       }
561       case Dali::CameraActor::Property::LEFT_PLANE_DISTANCE:
562       {
563         mCameraAttachment->SetLeftClippingPlane(propertyValue.Get<float>());
564         break;
565       }
566       case Dali::CameraActor::Property::RIGHT_PLANE_DISTANCE:
567       {
568         mCameraAttachment->SetRightClippingPlane(propertyValue.Get<float>());
569         break;
570       }
571       case Dali::CameraActor::Property::TOP_PLANE_DISTANCE:
572       {
573         mCameraAttachment->SetTopClippingPlane(propertyValue.Get<float>());
574         break;
575       }
576       case Dali::CameraActor::Property::BOTTOM_PLANE_DISTANCE:
577       {
578         mCameraAttachment->SetBottomClippingPlane(propertyValue.Get<float>());
579         break;
580       }
581       case Dali::CameraActor::Property::NEAR_PLANE_DISTANCE:
582       {
583         mCameraAttachment->SetNearClippingPlane(propertyValue.Get<float>());
584         break;
585       }
586       case Dali::CameraActor::Property::FAR_PLANE_DISTANCE:
587       {
588         mCameraAttachment->SetFarClippingPlane(propertyValue.Get<float>());
589         break;
590       }
591       case Dali::CameraActor::Property::TARGET_POSITION:
592       {
593         mCameraAttachment->SetTargetPosition(propertyValue.Get<Vector3>());
594         break;
595       }
596       case Dali::CameraActor::Property::PROJECTION_MATRIX:
597       {
598         DALI_LOG_WARNING("projection-matrix property is not animatable \n");
599         break;
600       }
601       case Dali::CameraActor::Property::VIEW_MATRIX:
602       {
603         DALI_LOG_WARNING("view-matrix property is not animatable \n");
604         break;
605       }
606       case Dali::CameraActor::Property::INVERT_Y_AXIS:
607       {
608         mCameraAttachment->SetInvertYAxis(propertyValue.Get<bool>());
609         break;
610       }
611       default:
612       {
613         DALI_LOG_WARNING("Unknown property (%d)\n", index);
614         break;
615       }
616     } // switch(index)
617
618   } // else
619 }
620
621 Property::Value CameraActor::GetDefaultProperty( Property::Index index ) const
622 {
623   Property::Value ret;
624   if(index < DEFAULT_ACTOR_PROPERTY_MAX_COUNT)
625   {
626     ret = Actor::GetDefaultProperty(index);
627   }
628   else
629   {
630     DALI_ASSERT_DEBUG(mCameraAttachment && "where is the camera?");
631     switch(index)
632     {
633       case Dali::CameraActor::Property::TYPE:
634       {
635         if(mCameraAttachment->GetType() == Dali::Camera::LOOK_AT_TARGET)
636         {
637           ret = "LOOK_AT_TARGET";
638         }
639         else if(mCameraAttachment->GetType() == Dali::Camera::FREE_LOOK)
640         {
641           ret = "FREE_LOOK";
642         }
643         else
644         {
645           ret = "";
646           DALI_ASSERT_DEBUG("Unknown camera type\n");
647         }
648         break;
649       }
650       case Dali::CameraActor::Property::PROJECTION_MODE:
651       {
652         if(mCameraAttachment->GetProjectionMode() == Dali::Camera::PERSPECTIVE_PROJECTION)
653         {
654           ret = "PERSPECTIVE_PROJECTION";
655         }
656         else if(mCameraAttachment->GetProjectionMode() == Dali::Camera::ORTHOGRAPHIC_PROJECTION)
657         {
658           ret = "ORTHOGRAPHIC_PROJECTION";
659         }
660         else
661         {
662           ret = "";
663           DALI_ASSERT_DEBUG("Unknown projection mode\n");
664         }
665         break;
666       }
667       case Dali::CameraActor::Property::FIELD_OF_VIEW:
668       {
669         ret = mCameraAttachment->GetFieldOfView();
670         break;
671       }
672       case Dali::CameraActor::Property::ASPECT_RATIO:
673       {
674         ret = mCameraAttachment->GetAspectRatio();
675         break;
676       }
677       case Dali::CameraActor::Property::LEFT_PLANE_DISTANCE:
678       {
679         ret = mCameraAttachment->GetLeftClippingPlane();
680         break;
681       }
682       case Dali::CameraActor::Property::RIGHT_PLANE_DISTANCE:
683       {
684         ret = mCameraAttachment->GetRightClippingPlane();
685         break;
686       }
687       case Dali::CameraActor::Property::TOP_PLANE_DISTANCE:
688       {
689         ret = mCameraAttachment->GetTopClippingPlane();
690         break;
691       }
692       case Dali::CameraActor::Property::BOTTOM_PLANE_DISTANCE:
693       {
694         ret = mCameraAttachment->GetBottomClippingPlane();
695         break;
696       }
697       case Dali::CameraActor::Property::NEAR_PLANE_DISTANCE:
698       {
699         ret = mCameraAttachment->GetNearClippingPlane();
700         break;
701       }
702       case Dali::CameraActor::Property::FAR_PLANE_DISTANCE:
703       {
704         ret = mCameraAttachment->GetFarClippingPlane();
705         break;
706       }
707       case Dali::CameraActor::Property::TARGET_POSITION:
708       {
709         ret = mCameraAttachment->GetTargetPosition();
710         break;
711       }
712       case Dali::CameraActor::Property::PROJECTION_MATRIX:
713       {
714         ret = mCameraAttachment->GetProjectionMatrix();
715         break;
716       }
717       case Dali::CameraActor::Property::VIEW_MATRIX:
718       {
719         ret = mCameraAttachment->GetViewMatrix();
720         break;
721       }
722       case Dali::CameraActor::Property::INVERT_Y_AXIS:
723       {
724         ret = mCameraAttachment->GetInvertYAxis();
725         break;
726       }
727       default:
728       {
729         DALI_LOG_WARNING("Unknown property (%d)\n", index);
730         break;
731       }
732     } // switch(index)
733   }
734
735   return ret;
736 }
737
738 const SceneGraph::PropertyBase* CameraActor::GetSceneObjectAnimatableProperty( Property::Index index ) const
739 {
740   DALI_ASSERT_ALWAYS( IsPropertyAnimatable(index) && "Property is not animatable" );
741
742   const SceneGraph::PropertyBase* property( NULL );
743
744   // This method should only return a property of an object connected to the scene-graph
745   if ( !OnStage() )
746   {
747     return property;
748   }
749
750   // let actor handle animatable properties, we have no animatable properties
751   if( index < DEFAULT_ACTOR_PROPERTY_MAX_COUNT )
752   {
753     property = Actor::GetSceneObjectAnimatableProperty(index);
754   }
755
756   return property;
757 }
758
759 const PropertyInputImpl* CameraActor::GetSceneObjectInputProperty( Property::Index index ) const
760 {
761   const PropertyInputImpl* property( NULL );
762
763   // This method should only return a property of an object connected to the scene-graph
764   if ( !OnStage() )
765   {
766     return property;
767   }
768
769   // if its an actor default property or a custom property (actor already handles custom properties)
770   if( ( index < DEFAULT_ACTOR_PROPERTY_MAX_COUNT ) || ( index >= DEFAULT_PROPERTY_MAX_COUNT ) )
771   {
772     property = Actor::GetSceneObjectInputProperty(index);
773   }
774   else
775   {
776     switch( index )
777     {
778       case Dali::CameraActor::Property::PROJECTION_MATRIX:
779       {
780         property = mCameraAttachment->GetProjectionMatrixProperty();
781         break;
782       }
783       case Dali::CameraActor::Property::VIEW_MATRIX:
784       {
785         property = mCameraAttachment->GetViewMatrixProperty();
786         break;
787       }
788       default:
789         DALI_LOG_WARNING("Not an input property (%d)\n", index);
790         break;
791     }
792   }
793
794   return property;
795 }
796
797
798 } // namespace Internal
799
800 } // namespace Dali