Revert "License conversion from Flora to Apache 2.0"
[platform/core/uifw/dali-core.git] / dali / public-api / scripting / scripting.cpp
1 //
2 // Copyright (c) 2014 Samsung Electronics Co., Ltd.
3 //
4 // Licensed under the Flora License, Version 1.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://floralicense.org/license/
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 // CLASS HEADER
18 #include <dali/public-api/scripting/scripting.h>
19
20 // INTERNAL INCLUDES
21 #include <dali/public-api/actors/actor.h>
22 #include <dali/public-api/images/image.h>
23 #include <dali/public-api/images/image-attributes.h>
24 #include <dali/public-api/object/type-registry.h>
25 #include <dali/internal/event/images/image-impl.h>
26 #include <dali/internal/event/images/frame-buffer-image-impl.h>
27 #include <dali/internal/event/images/bitmap-image-impl.h>
28 #include <dali/internal/event/effects/shader-effect-impl.h>
29
30 namespace Dali
31 {
32
33 namespace Scripting
34 {
35
36 namespace
37 {
38
39 // Helpers for converting strings to the enumerations and vice versa
40
41 template< typename T >
42 struct StringEnum
43 {
44   const std::string string;
45   const T value;
46 };
47
48 const StringEnum< ColorMode > COLOR_MODE_TABLE[] =
49 {
50   { "USE_OWN_COLOR",                    USE_OWN_COLOR                    },
51   { "USE_PARENT_COLOR",                 USE_PARENT_COLOR                 },
52   { "USE_OWN_MULTIPLY_PARENT_COLOR",    USE_OWN_MULTIPLY_PARENT_COLOR    },
53   { "USE_OWN_MULTIPLY_PARENT_ALPHA",    USE_OWN_MULTIPLY_PARENT_ALPHA    },
54 };
55 const unsigned int COLOR_MODE_TABLE_COUNT = sizeof( COLOR_MODE_TABLE ) / sizeof( COLOR_MODE_TABLE[0] );
56
57 const StringEnum< PositionInheritanceMode > POSITION_INHERITANCE_MODE_TABLE[] =
58 {
59   { "INHERIT_PARENT_POSITION",                    INHERIT_PARENT_POSITION                    },
60   { "USE_PARENT_POSITION",                        USE_PARENT_POSITION                        },
61   { "USE_PARENT_POSITION_PLUS_LOCAL_POSITION",    USE_PARENT_POSITION_PLUS_LOCAL_POSITION    },
62   { "DONT_INHERIT_POSITION",                      DONT_INHERIT_POSITION                      },
63 };
64 const unsigned int POSITION_INHERITANCE_MODE_TABLE_COUNT = sizeof( POSITION_INHERITANCE_MODE_TABLE ) / sizeof( POSITION_INHERITANCE_MODE_TABLE[0] );
65
66 const StringEnum< DrawMode::Type > DRAW_MODE_TABLE[] =
67 {
68   { "NORMAL",     DrawMode::NORMAL     },
69   { "OVERLAY",    DrawMode::OVERLAY    },
70   { "STENCIL",    DrawMode::STENCIL    },
71 };
72 const unsigned int DRAW_MODE_TABLE_COUNT = sizeof( DRAW_MODE_TABLE ) / sizeof( DRAW_MODE_TABLE[0] );
73
74 const StringEnum< Vector3 > ANCHOR_CONSTANT_TABLE[] =
75 {
76   { "BACK_TOP_LEFT",          ParentOrigin::BACK_TOP_LEFT          },
77   { "BACK_TOP_CENTER",        ParentOrigin::BACK_TOP_CENTER        },
78   { "BACK_TOP_RIGHT",         ParentOrigin::BACK_TOP_RIGHT         },
79   { "BACK_CENTER_LEFT",       ParentOrigin::BACK_CENTER_LEFT       },
80   { "BACK_CENTER",            ParentOrigin::BACK_CENTER            },
81   { "BACK_CENTER_RIGHT",      ParentOrigin::BACK_CENTER_RIGHT      },
82   { "BACK_BOTTOM_LEFT",       ParentOrigin::BACK_BOTTOM_LEFT       },
83   { "BACK_BOTTOM_CENTER",     ParentOrigin::BACK_BOTTOM_CENTER     },
84   { "BACK_BOTTOM_RIGHT",      ParentOrigin::BACK_BOTTOM_RIGHT      },
85   { "TOP_LEFT",               ParentOrigin::TOP_LEFT               },
86   { "TOP_CENTER",             ParentOrigin::TOP_CENTER             },
87   { "TOP_RIGHT",              ParentOrigin::TOP_RIGHT              },
88   { "CENTER_LEFT",            ParentOrigin::CENTER_LEFT            },
89   { "CENTER",                 ParentOrigin::CENTER                 },
90   { "CENTER_RIGHT",           ParentOrigin::CENTER_RIGHT           },
91   { "BOTTOM_LEFT",            ParentOrigin::BOTTOM_LEFT            },
92   { "BOTTOM_CENTER",          ParentOrigin::BOTTOM_CENTER          },
93   { "BOTTOM_RIGHT",           ParentOrigin::BOTTOM_RIGHT           },
94   { "FRONT_TOP_LEFT",         ParentOrigin::FRONT_TOP_LEFT         },
95   { "FRONT_TOP_CENTER",       ParentOrigin::FRONT_TOP_CENTER       },
96   { "FRONT_TOP_RIGHT",        ParentOrigin::FRONT_TOP_RIGHT        },
97   { "FRONT_CENTER_LEFT",      ParentOrigin::FRONT_CENTER_LEFT      },
98   { "FRONT_CENTER",           ParentOrigin::FRONT_CENTER           },
99   { "FRONT_CENTER_RIGHT",     ParentOrigin::FRONT_CENTER_RIGHT     },
100   { "FRONT_BOTTOM_LEFT",      ParentOrigin::FRONT_BOTTOM_LEFT      },
101   { "FRONT_BOTTOM_CENTER",    ParentOrigin::FRONT_BOTTOM_CENTER    },
102   { "FRONT_BOTTOM_RIGHT",     ParentOrigin::FRONT_BOTTOM_RIGHT     },
103 };
104 const unsigned int ANCHOR_CONSTANT_TABLE_COUNT = sizeof( ANCHOR_CONSTANT_TABLE ) / sizeof( ANCHOR_CONSTANT_TABLE[0] );
105
106 const StringEnum< Image::LoadPolicy > IMAGE_LOAD_POLICY_TABLE[] =
107 {
108   { "IMMEDIATE", Image::Immediate },
109   { "ON_DEMAND", Image::OnDemand  },
110 };
111 const unsigned int IMAGE_LOAD_POLICY_TABLE_COUNT = sizeof( IMAGE_LOAD_POLICY_TABLE ) / sizeof( IMAGE_LOAD_POLICY_TABLE[0] );
112
113 const StringEnum< Image::ReleasePolicy > IMAGE_RELEASE_POLICY_TABLE[] =
114 {
115   { "UNUSED", Image::Unused },
116   { "NEVER",  Image::Never  },
117 };
118 const unsigned int IMAGE_RELEASE_POLICY_TABLE_COUNT = sizeof( IMAGE_RELEASE_POLICY_TABLE ) / sizeof( IMAGE_RELEASE_POLICY_TABLE[0] );
119
120 const StringEnum< Pixel::Format > PIXEL_FORMAT_TABLE[] =
121 {
122   { "A8",                                           Pixel::A8                                           },
123   { "L8",                                           Pixel::L8                                           },
124   { "LA88",                                         Pixel::LA88                                         },
125   { "RGB565",                                       Pixel::RGB565                                       },
126   { "BGR565",                                       Pixel::BGR565                                       },
127   { "RGBA4444",                                     Pixel::RGBA4444                                     },
128   { "BGRA4444",                                     Pixel::BGRA4444                                     },
129   { "RGBA5551",                                     Pixel::RGBA5551                                     },
130   { "BGRA5551",                                     Pixel::BGRA5551                                     },
131   { "RGB888",                                       Pixel::RGB888                                       },
132   { "RGB8888",                                      Pixel::RGB8888                                      },
133   { "BGR8888",                                      Pixel::BGR8888                                      },
134   { "RGBA8888",                                     Pixel::RGBA8888                                     },
135   { "BGRA8888",                                     Pixel::BGRA8888                                     },
136   { "COMPRESSED_R11_EAC",                           Pixel::COMPRESSED_R11_EAC                           },
137   { "COMPRESSED_SIGNED_R11_EAC",                    Pixel::COMPRESSED_SIGNED_R11_EAC                    },
138   { "COMPRESSED_RG11_EAC",                          Pixel::COMPRESSED_RG11_EAC                          },
139   { "COMPRESSED_SIGNED_RG11_EAC",                   Pixel::COMPRESSED_SIGNED_RG11_EAC                   },
140   { "COMPRESSED_RGB8_ETC2",                         Pixel::COMPRESSED_RGB8_ETC2                         },
141   { "COMPRESSED_SRGB8_ETC2",                        Pixel::COMPRESSED_SRGB8_ETC2                        },
142   { "COMPRESSED_RGB8_PUNCHTHROUGH_ALPHA1_ETC2",     Pixel::COMPRESSED_RGB8_PUNCHTHROUGH_ALPHA1_ETC2     },
143   { "COMPRESSED_SRGB8_PUNCHTHROUGH_ALPHA1_ETC2",    Pixel::COMPRESSED_SRGB8_PUNCHTHROUGH_ALPHA1_ETC2    },
144   { "COMPRESSED_RGBA8_ETC2_EAC",                    Pixel::COMPRESSED_RGBA8_ETC2_EAC                    },
145   { "COMPRESSED_SRGB8_ALPHA8_ETC2_EAC",             Pixel::COMPRESSED_SRGB8_ALPHA8_ETC2_EAC             },
146   { "COMPRESSED_RGB8_ETC1",                         Pixel::COMPRESSED_RGB8_ETC1                         },
147   { "COMPRESSED_RGB_PVRTC_4BPPV1",                  Pixel::COMPRESSED_RGB_PVRTC_4BPPV1                  },
148 };
149 const unsigned int PIXEL_FORMAT_TABLE_COUNT = sizeof( PIXEL_FORMAT_TABLE ) / sizeof( PIXEL_FORMAT_TABLE[0] );
150
151 const StringEnum< ImageAttributes::ScalingMode > IMAGE_SCALING_MODE_TABLE[] =
152 {
153   { "SHRINK_TO_FIT", ImageAttributes::ShrinkToFit },
154   { "SCALE_TO_FILL", ImageAttributes::ScaleToFill },
155   { "FIT_WIDTH",     ImageAttributes::FitWidth    },
156   { "FIT_HEIGHT",    ImageAttributes::FitHeight   },
157 };
158 const unsigned int IMAGE_SCALING_MODE_TABLE_COUNT = sizeof( IMAGE_SCALING_MODE_TABLE ) / sizeof( IMAGE_SCALING_MODE_TABLE[0] );
159
160 template< typename T >
161 T GetEnumeration( const std::string& value, const StringEnum< T >* table, const unsigned int tableCount )
162 {
163   T v( table->value );
164   bool set( false );
165
166   for ( unsigned int i = 0; ( i < tableCount ) && ( !set ); ++i )
167   {
168     set = SetIfEqual(value, table->string, v, table->value );
169     ++table;
170   }
171
172   if ( !set )
173   {
174     DALI_ASSERT_ALWAYS( !"Unknown enumeration string" );
175   }
176
177   return v;
178 }
179
180 template< typename T >
181 const std::string& GetEnumerationName( const T& value, const StringEnum< T >* table, const unsigned int tableCount )
182 {
183   for ( unsigned int i = 0; i < tableCount; ++i )
184   {
185     if ( value == table[i].value )
186     {
187       return table[i].string;
188       break;
189     }
190   }
191
192   return String::EMPTY;
193 }
194
195 } // unnamed namespace
196
197 bool CompareEnums(const std::string& a, const std::string& b)
198 {
199   std::string::const_iterator ia = a.begin();
200   std::string::const_iterator ib = b.begin();
201
202   while( (ia != a.end()) && (ib != b.end()) )
203   {
204     char ca = *ia;
205     char cb = *ib;
206
207     if(ca == '-' || ca == '_')
208     {
209       ++ia;
210       continue;
211     }
212
213     if(cb == '-' || cb == '_')
214     {
215       ++ib;
216       continue;
217     }
218
219     if( 'A' <= ca && ca <= 'Z')
220     {
221       ca = ca + ('a' - 'A');
222     }
223
224     if( 'A' <= cb && cb <= 'Z')
225     {
226       cb = cb + ('a' - 'A');
227     }
228
229     if( ca != cb )
230     {
231       return false;
232     }
233
234     ++ia;
235     ++ib;
236   }
237
238   if( (ia == a.end() && ib == b.end() ) )
239   {
240     return true;
241   }
242   else
243   {
244     return false;
245   }
246
247 }
248
249
250 ColorMode GetColorMode( const std::string& value )
251 {
252   return GetEnumeration< ColorMode >( value, COLOR_MODE_TABLE, COLOR_MODE_TABLE_COUNT );
253 }
254
255
256 const std::string& GetColorMode( ColorMode value )
257 {
258   return GetEnumerationName< ColorMode >( value, COLOR_MODE_TABLE, COLOR_MODE_TABLE_COUNT );
259 }
260
261 PositionInheritanceMode GetPositionInheritanceMode( const std::string& value )
262 {
263   return GetEnumeration< PositionInheritanceMode >( value, POSITION_INHERITANCE_MODE_TABLE, POSITION_INHERITANCE_MODE_TABLE_COUNT );
264 }
265
266
267 const std::string& GetPositionInheritanceMode( PositionInheritanceMode value )
268 {
269   return GetEnumerationName< PositionInheritanceMode >( value, POSITION_INHERITANCE_MODE_TABLE, POSITION_INHERITANCE_MODE_TABLE_COUNT );
270 }
271
272
273 DrawMode::Type GetDrawMode( const std::string& value )
274 {
275   return GetEnumeration< DrawMode::Type >( value, DRAW_MODE_TABLE, DRAW_MODE_TABLE_COUNT );
276 }
277
278
279 const std::string& GetDrawMode( DrawMode::Type value )
280 {
281   return GetEnumerationName< DrawMode::Type >( value, DRAW_MODE_TABLE, DRAW_MODE_TABLE_COUNT );
282 }
283
284
285 Vector3 GetAnchorConstant( const std::string& value )
286 {
287   return GetEnumeration< Vector3 >( value, ANCHOR_CONSTANT_TABLE, ANCHOR_CONSTANT_TABLE_COUNT );
288 }
289
290
291 Image NewImage( const Property::Value& map )
292 {
293   Image ret;
294
295   std::string filename;
296   Image::LoadPolicy loadPolicy       = Dali::Internal::ImageLoadPolicyDefault;
297   Image::ReleasePolicy releasePolicy = Dali::Internal::ImageReleasePolicyDefault;
298   ImageAttributes attributes         = ImageAttributes::New();
299
300   if( Property::MAP == map.GetType() )
301   {
302     std::string field = "filename";
303     if( map.HasKey(field) )
304     {
305       DALI_ASSERT_ALWAYS(map.GetValue(field).GetType() == Property::STRING && "Image filename property is not a string" );
306       filename = map.GetValue(field).Get<std::string>();
307     }
308
309     field = "load-policy";
310     if( map.HasKey(field) )
311     {
312       DALI_ASSERT_ALWAYS(map.GetValue(field).GetType() == Property::STRING && "Image load-policy property is not a string" );
313       std::string v(map.GetValue(field).Get<std::string>());
314       loadPolicy = GetEnumeration< Image::LoadPolicy >( v, IMAGE_LOAD_POLICY_TABLE, IMAGE_LOAD_POLICY_TABLE_COUNT );
315     }
316
317     field = "release-policy";
318     if( map.HasKey(field) )
319     {
320       DALI_ASSERT_ALWAYS(map.GetValue(field).GetType() == Property::STRING && "Image release-policy property is not a string" );
321       std::string v(map.GetValue(field).Get<std::string>());
322       releasePolicy = GetEnumeration< Image::ReleasePolicy >( v, IMAGE_RELEASE_POLICY_TABLE, IMAGE_RELEASE_POLICY_TABLE_COUNT );
323     }
324
325     if( map.HasKey("width") && map.HasKey("height") )
326     {
327       Property::Value &value = map.GetValue("width");
328       unsigned int w = 0, h = 0;
329       // handle floats and integer the same for json script
330       if( value.GetType() == Property::FLOAT)
331       {
332         w = static_cast<unsigned int>( value.Get<float>() );
333       }
334       else
335       {
336         DALI_ASSERT_ALWAYS(value.GetType() == Property::INTEGER && "Image width property is not a number" );
337         w = value.Get<int>();
338       }
339
340       value = map.GetValue("height");
341       if( value.GetType() == Property::FLOAT)
342       {
343         h = static_cast<unsigned int>( value.Get<float>() );
344       }
345       else
346       {
347         DALI_ASSERT_ALWAYS(value.GetType() == Property::INTEGER && "Image width property is not a number" );
348         h = value.Get<int>();
349       }
350
351       attributes.SetSize( w, h );
352     }
353
354     field = "pixel-format";
355     if( map.HasKey(field) )
356     {
357       DALI_ASSERT_ALWAYS(map.GetValue(field).GetType() == Property::STRING && "Image release-policy property is not a string" );
358       std::string s(map.GetValue(field).Get<std::string>());
359       attributes.SetPixelFormat( GetEnumeration< Pixel::Format >( s, PIXEL_FORMAT_TABLE, PIXEL_FORMAT_TABLE_COUNT ));
360     }
361
362     field = "scaling-mode";
363     if( map.HasKey(field) )
364     {
365       DALI_ASSERT_ALWAYS(map.GetValue(field).GetType() == Property::STRING && "Image release-policy property is not a string" );
366       std::string s(map.GetValue(field).Get<std::string>());
367       attributes.SetScalingMode( GetEnumeration< ImageAttributes::ScalingMode >( s, IMAGE_SCALING_MODE_TABLE, IMAGE_SCALING_MODE_TABLE_COUNT ) );
368     }
369
370     field = "crop";
371     if( map.HasKey(field) )
372     {
373       DALI_ASSERT_ALWAYS(map.GetValue(field).GetType() == Property::VECTOR4 && "Image release-policy property is not a string" );
374       Vector4 v(map.GetValue(field).Get<Vector4>());
375       attributes.SetCrop( Rect<float>(v.x, v.y, v.z, v.w) );
376     }
377
378     if( map.HasKey("type") )
379     {
380       DALI_ASSERT_ALWAYS( map.GetValue("type").GetType() == Property::STRING );
381       std::string s(map.GetValue("type").Get<std::string>());
382       if("FrameBufferImage" == s)
383       {
384         ret = new Internal::FrameBufferImage(attributes.GetWidth(),
385                                              attributes.GetHeight(),
386                                              attributes.GetPixelFormat(),
387                                              releasePolicy );
388       }
389       else if("BitmapImage" == s)
390       {
391         ret = new Internal::BitmapImage(attributes.GetWidth(),
392                                         attributes.GetHeight(),
393                                         attributes.GetPixelFormat(),
394                                         loadPolicy,
395                                         releasePolicy);
396       }
397       else if("Image" == s)
398       {
399         ret = Image::New(filename, attributes, loadPolicy, releasePolicy);
400       }
401       else
402       {
403         DALI_ASSERT_ALWAYS( !"Unknown image type" );
404       }
405     }
406     else
407     {
408       ret = Image::New(filename, attributes, loadPolicy, releasePolicy);
409     }
410   }
411
412   return ret;
413
414 } // Image NewImage( Property::Value map )
415
416
417 ShaderEffect NewShaderEffect( const Property::Value& map )
418 {
419   Internal::ShaderEffectPtr ret;
420
421   if( map.GetType() == Property::MAP )
422   {
423     ret = Internal::ShaderEffect::New(Dali::ShaderEffect::HINT_NONE); // hint can be reset if in map
424
425     if( map.HasKey("program") )
426     {
427       Property::Index index = ret->GetPropertyIndex("program");
428       DALI_ASSERT_DEBUG( map.GetValue("program").GetType() == Property::MAP );
429       ret->SetProperty(index, map.GetValue("program"));
430     }
431
432     for(int i = 0; i < map.GetSize(); ++i)
433     {
434       const std::string& key = map.GetKey(i);
435       if(key != "program")
436       {
437         Property::Index index = ret->GetPropertyIndex( key );
438
439         if( Property::INVALID_INDEX != index )
440         {
441           ret->SetProperty(index, map.GetItem(i));
442         }
443         else
444         {
445           // if its not a property then register it as a uniform (making a custom property)
446
447           if(map.GetItem(i).GetType() == Property::INTEGER)
448           {
449             // valid uniforms are floats, vec3's etc so we recast if the user accidentally
450             // set as integer. Note the map could have come from json script.
451             Property::Value asFloat( static_cast<float>( map.GetItem(i).Get<int>() ) );
452             ret->SetUniform( key, asFloat, Dali::ShaderEffect::COORDINATE_TYPE_DEFAULT );
453           }
454           else
455           {
456             ret->SetUniform( key, map.GetItem(i), Dali::ShaderEffect::COORDINATE_TYPE_DEFAULT );
457           }
458         }
459       }
460     }
461   }
462
463   return Dali::ShaderEffect(ret.Get());
464 }
465
466
467 Actor NewActor( const Property::Map& map )
468 {
469   BaseHandle handle;
470
471   const Property::Map::const_iterator endIter = map.end();
472
473   // First find type and create Actor
474   Property::Map::const_iterator typeIter = map.begin();
475   for (; typeIter != endIter; ++typeIter )
476   {
477     if ( typeIter->first == "type" )
478     {
479       TypeInfo type = TypeRegistry::Get().GetTypeInfo( typeIter->second.Get< std::string >() );
480       if ( type )
481       {
482         handle = type.CreateInstance();
483       }
484       break;
485     }
486   }
487
488   if ( !handle )
489   {
490     DALI_LOG_ERROR( "Actor type not provided, returning empty handle" );
491     return Actor();
492   }
493
494   Actor actor( Actor::DownCast( handle ) );
495
496   if ( actor )
497   {
498     // Now set the properties, or create children
499     for ( Property::Map::const_iterator iter = map.begin(); iter != endIter; ++iter )
500     {
501       if ( iter == typeIter )
502       {
503         continue;
504       }
505
506       if ( iter->first == "actors" )
507       {
508         // Create children
509
510         Property::Array actorArray = iter->second.Get< Property::Array >();
511         for ( Property::Array::iterator arrayIter = actorArray.begin(), arrayEndIter = actorArray.end(); arrayIter != arrayEndIter; ++arrayIter )
512         {
513           actor.Add( NewActor( arrayIter->Get< Property::Map >() ) );
514         }
515       }
516       else if ( iter->first == "signals" )
517       {
518         DALI_LOG_ERROR( "signals not supported" );
519       }
520       else if( iter->first ==  "parent-origin" )
521       {
522         // Parent Origin can be a string constant as well as a Vector3
523
524         const Property::Type type( iter->second.GetType() );
525         if ( type == Property::VECTOR3 )
526         {
527           actor.SetParentOrigin( iter->second.Get< Vector3 >() );
528         }
529         else if( type == Property::STRING )
530         {
531           actor.SetParentOrigin( GetAnchorConstant( iter->second.Get< std::string >() ) );
532         }
533       }
534       else if( iter->first ==  "anchor-point" )
535       {
536         // Anchor Point can be a string constant as well as a Vector3
537
538         const Property::Type type( iter->second.GetType() );
539         if ( type == Property::VECTOR3 )
540         {
541           actor.SetAnchorPoint( iter->second.Get< Vector3 >() );
542         }
543         else if( type == Property::STRING )
544         {
545           actor.SetAnchorPoint( GetAnchorConstant( iter->second.Get< std::string >() ) );
546         }
547       }
548       else
549       {
550         Property::Index index( actor.GetPropertyIndex( iter->first ) );
551
552         if ( index != Property::INVALID_INDEX )
553         {
554           actor.SetProperty( index, iter->second );
555         }
556       }
557     }
558   }
559
560   return actor;
561 }
562
563 void CreatePropertyMap( Actor actor, Property::Map& map )
564 {
565   map.clear();
566
567   if ( actor )
568   {
569     map.push_back( Property::StringValuePair( "type", actor.GetTypeName() ) );
570
571     // Default properties
572     Property::IndexContainer indices;
573     actor.GetPropertyIndices( indices );
574     const Property::IndexContainer::const_iterator endIter = indices.end();
575     for ( Property::IndexContainer::iterator iter = indices.begin(); iter != endIter; ++iter )
576     {
577       map.push_back( Property::StringValuePair( actor.GetPropertyName( *iter ), actor.GetProperty( *iter ) ) );
578     }
579
580     // Children
581     unsigned int childCount( actor.GetChildCount() );
582     if ( childCount )
583     {
584       Property::Array childArray;
585       for ( unsigned int child = 0; child < childCount; ++child )
586       {
587         Property::Map childMap;
588         CreatePropertyMap( actor.GetChildAt( child ), childMap );
589         childArray.push_back( childMap );
590       }
591       map.push_back( Property::StringValuePair( "actors", childArray ) );
592     }
593   }
594 }
595
596 void CreatePropertyMap( Image image, Property::Map& map )
597 {
598   map.clear();
599
600   if ( image )
601   {
602     std::string imageType( "Image" );
603
604     // Get Type - cannot use TypeRegistry as Image is not a ProxyObject and thus, not registered
605     if ( BitmapImage::DownCast( image ) )
606     {
607       imageType = "BitmapImage";
608     }
609     else if ( FrameBufferImage::DownCast( image ) )
610     {
611       imageType = "FrameBufferImage";
612     }
613
614     map.push_back( Property::StringValuePair( "type", imageType ) );
615     map.push_back( Property::StringValuePair( "filename", image.GetFilename() ) );
616     map.push_back( Property::StringValuePair( "load-policy", GetEnumerationName< Image::LoadPolicy >( image.GetLoadPolicy(), IMAGE_LOAD_POLICY_TABLE, IMAGE_LOAD_POLICY_TABLE_COUNT ) ) );
617     map.push_back( Property::StringValuePair( "release-policy", GetEnumerationName< Image::ReleasePolicy >( image.GetReleasePolicy(), IMAGE_RELEASE_POLICY_TABLE, IMAGE_RELEASE_POLICY_TABLE_COUNT ) ) );
618
619     ImageAttributes attributes( image.GetAttributes() );
620     map.push_back( Property::StringValuePair( "pixel-format", GetEnumerationName< Pixel::Format >( attributes.GetPixelFormat(), PIXEL_FORMAT_TABLE, PIXEL_FORMAT_TABLE_COUNT ) ) );
621     map.push_back( Property::StringValuePair( "scaling-mode", GetEnumerationName< ImageAttributes::ScalingMode >( attributes.GetScalingMode(), IMAGE_SCALING_MODE_TABLE, IMAGE_SCALING_MODE_TABLE_COUNT ) ) );
622
623     Rect< float > crop( attributes.GetCrop() );
624     map.push_back( Property::StringValuePair( "crop", Vector4( crop.x, crop.y, crop.width, crop.height ) ) );
625
626     int width( image.GetWidth() );
627     int height( image.GetHeight() );
628
629     if ( width && height )
630     {
631       map.push_back( Property::StringValuePair( "width", width ) );
632       map.push_back( Property::StringValuePair( "height", height ) );
633     }
634   }
635 }
636
637 } // namespace scripting
638
639 } // namespace Dali
640
641
642
643