Making DALi public API typesafe using guaranteed types; uint8_t, uint32_t
[platform/core/uifw/dali-core.git] / dali / public-api / object / type-registry.h
1 #ifndef __DALI_TYPE_REGISTRY_H__
2 #define __DALI_TYPE_REGISTRY_H__
3
4 /*
5  * Copyright (c) 2018 Samsung Electronics Co., Ltd.
6  *
7  * Licensed under the Apache License, Version 2.0 (the "License");
8  * you may not use this file except in compliance with the License.
9  * You may obtain a copy of the License at
10  *
11  * http://www.apache.org/licenses/LICENSE-2.0
12  *
13  * Unless required by applicable law or agreed to in writing, software
14  * distributed under the License is distributed on an "AS IS" BASIS,
15  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
16  * See the License for the specific language governing permissions and
17  * limitations under the License.
18  *
19  */
20
21
22 // EXTERNAL INCLUDES
23 #include <typeinfo>
24 #include <cstdint> // uint32_t
25
26 // INTERNAL INCLUDES
27 #include <dali/public-api/object/base-handle.h>
28 #include <dali/public-api/object/type-info.h>
29
30 namespace Dali
31 {
32 /**
33  * @addtogroup dali_core_object
34  * @{
35  */
36
37 namespace Internal DALI_INTERNAL
38 {
39 class TypeRegistry;
40 }
41
42 /**
43  * @brief The TypeRegistry allows registration of type instance creation functions.
44  *
45  * These can then be created later by name and down cast to the appropriate type.
46  *
47  * Usage: (Registering)
48  *
49  * In my-actor.cpp
50  * @code
51  * // Note: object construction in namespace scope is defined in a translation unit as being
52  * //       in appearance order (C++ standard 3.6/2). So TypeRegistration is declared first in
53  * //       the cpp file below. Signal, action and property declarations follow in any order.
54  * namespace
55  * {
56  *   TypeRegistration myActorType(typeid(MyActor), typeid(Actor), CreateMyActor );
57  *
58  *   SignalConnectorType( myActorType, "highlighted", ConnectSignalForMyActor );
59  *   TypeAction( myActorType, "open", DoMyActorAction );
60  *   TypeAction( myActorType, "close", DoMyActorAction );
61  *   PropertyRegistration( myActorType, "status", PropertyRegistration::START_INDEX, Property::BOOLEAN, SetPropertyFunction, GetPropertyFunction );
62  * }
63  * @endcode
64  *
65  * Usage: (Creation)
66  *
67  * @code
68  *   TypeRegistry::TypeInfo type = TypeRegistry::Get().GetTypeInfo("MyActor");
69  *   MyActor a = MyActor::DownCast(type.CreateInstance());
70  *   if(a)
71  *   {
72  *     ...
73  *   }
74  * @endcode
75  *
76  * CustomActor
77  *
78  *  Actors that inherit from the CustomActor framework must ensure the implementation
79  *  class has an identical name to the Actor class. This is to ensure the class can be
80  *  found at runtime for signals and actions. Otherwise these will silently fail.
81  *
82  *  As namespaces are discarded the convention is to use a namespace ie
83  *
84  *    'class MyActor {}; namespace Internal { class MyActor {}; }'
85  *
86  *  Warning: this arrangement will silently fail
87  *
88  *    'class MyActor {}; class MyActorImpl {};'
89  *
90  * Naming Conventions
91  *
92  *   Signal and action names follow properties and are by convention lower case hyphen
93  *   separated ie 'next-page'. This maintains consistency with the scripted interface.
94  *
95  * @SINCE_1_0.0
96  */
97 class DALI_CORE_API TypeRegistry : public BaseHandle
98 {
99 public:
100   /**
101    * @brief Gets Type Registry handle.
102    *
103    * @SINCE_1_0.0
104    * @return TypeRegistry handle
105    */
106   static TypeRegistry Get();
107
108   /**
109    * @brief Allows the creation of an empty typeRegistry handle.
110    * @SINCE_1_0.0
111    */
112   TypeRegistry();
113
114   /**
115    * @brief Destructor.
116    * @SINCE_1_0.0
117    */
118   ~TypeRegistry();
119
120   /**
121    * @brief This copy constructor is required for (smart) pointer semantics.
122    *
123    * @SINCE_1_0.0
124    * @param[in] handle A reference to the copied handle
125    */
126   TypeRegistry(const TypeRegistry& handle);
127
128   /**
129    * @brief This assignment operator is required for (smart) pointer semantics.
130    *
131    * @SINCE_1_0.0
132    * @param[in] rhs A reference to the copied handle
133    * @return A reference to this
134    */
135   TypeRegistry& operator=(const TypeRegistry& rhs);
136
137   /**
138    * @brief Gets TypeInfo for a registered type.
139    *
140    * @SINCE_1_0.0
141    * @param[in] uniqueTypeName A unique type name
142    * @return TypeInfo if the type exists, otherwise an empty handle
143    */
144   TypeInfo GetTypeInfo( const std::string &uniqueTypeName );
145
146   /**
147    * @brief Gets TypeInfo for a registered type.
148    *
149    * @SINCE_1_0.0
150    * @param[in] registerType The registered type info
151    * @return TypeInfo if the type exists, otherwise an empty handle
152    */
153   TypeInfo GetTypeInfo( const std::type_info& registerType );
154
155   /**
156    * @brief Gets type name count.
157    *
158    * @SINCE_1_0.0
159    * @return The count
160    */
161   size_t GetTypeNameCount() const;
162
163   /**
164    * @brief Gets type names by index.
165    *
166    * @SINCE_1_0.0
167    * @param[in] index The index to get the type name
168    * @return The type name or an empty string when index is not valid
169    */
170   std::string GetTypeName(size_t index) const;
171
172 public: // Not intended for application developers
173
174   /// @cond internal
175   /**
176    * @brief This constructor is used by Dali Get() method.
177    *
178    * @SINCE_1_0.0
179    * @param[in] typeRegistry A pointer to a Dali resource
180    */
181   explicit DALI_INTERNAL TypeRegistry(Internal::TypeRegistry*typeRegistry);
182   /// @endcond
183 };
184
185 /**
186  * @brief Registers a type from type info.
187  * @SINCE_1_0.0
188  */
189 class DALI_CORE_API TypeRegistration
190 {
191 public:
192   /**
193    * @brief Constructor registers the type creation function.
194    *
195    * @SINCE_1_0.0
196    * @param[in] registerType The type info for the type to be registered
197    * @param[in] baseType The base type info of registerType
198    * @param[in] f registerType Instance creation function
199    */
200   TypeRegistration( const std::type_info& registerType, const std::type_info& baseType,
201                     TypeInfo::CreateFunction f );
202
203   /**
204    * @brief Constructor registers the type creation function.
205    *
206    * @SINCE_1_0.0
207    * @param[in] registerType the type info for the type to be registered
208    * @param[in] baseType the base type info of registerType
209    * @param[in] f registerType instance creation function
210    * @param[in] callCreateOnInit If true the creation function is called as part of Dali initialization
211    */
212   TypeRegistration( const std::type_info& registerType, const std::type_info& baseType,
213                     TypeInfo::CreateFunction f, bool callCreateOnInit );
214
215   /**
216    * @brief Constructor registers the type creation function for a named class or type.
217    *
218    * This allows types to be created dynamically from script. The name must be
219    * unique for successful registration.
220    * @SINCE_1_0.0
221    * @param[in] name the name of the type to be registered
222    * @param[in] baseType the base type info of registerType
223    * @param[in] f registerType instance creation function
224    */
225   TypeRegistration( const std::string& name, const std::type_info& baseType,
226                     TypeInfo::CreateFunction f );
227
228   /**
229    * @brief The name the type is registered under (derived from type_info).
230    *
231    * @SINCE_1_0.0
232    * @return The registered name or empty if unregistered
233    */
234   const std::string RegisteredName() const;
235
236 private:
237   TypeRegistry mReference; ///< Reference to the type registry
238   std::string mName;       ///< Name of the type
239 };
240
241 /**
242  * @brief Registers a signal connector function to a registered type.
243  * @SINCE_1_0.0
244  */
245 class DALI_CORE_API SignalConnectorType
246 {
247 public:
248   /**
249    * @brief Constructor registers the type creation function.
250    *
251    * @SINCE_1_0.0
252    * @param[in] typeRegistration The TypeRegistration object
253    * @param[in] name The signal name
254    * @param[in] func The signal connector function
255    */
256   SignalConnectorType( TypeRegistration& typeRegistration, const std::string& name, TypeInfo::SignalConnectorFunction func );
257 };
258
259 /**
260  * @brief Registers an action function.
261  * @SINCE_1_0.0
262  */
263 class DALI_CORE_API TypeAction
264 {
265 public:
266   /**
267    * @brief Constructor registers the type creation function.
268    *
269    * @SINCE_1_0.0
270    * @param[in] registered The TypeRegistration object
271    * @param[in] name The action name
272    * @param[in] f The action function
273    */
274   TypeAction( TypeRegistration &registered, const std::string &name, TypeInfo::ActionFunction f);
275 };
276
277 /**
278  * @brief Registers a property for the given type.
279  * @SINCE_1_0.0
280  */
281 class DALI_CORE_API PropertyRegistration
282 {
283 public:
284
285   /**
286    * @brief This constructor registers the property with the registered type.
287    *
288    * This constructor is for event-thread only properties where the
289    * value of the property can be retrieved and set via specified
290    * functions.
291    *
292    * Functions of the following type may be used for setFunc and getFunc respectively:
293    * @code
294    *   void SetProperty( BaseObject* object, Property::Index index, const Property::Value& value );
295    *   Property::Value GetProperty( BaseObject* object, Property::Index index );
296    * @endcode
297    *
298    * @SINCE_1_0.0
299    * @param[in] registered The TypeRegistration object
300    * @param[in] name The name of the property
301    * @param[in] index The property index. Must be a value between PROPERTY_REGISTRATION_START_INDEX and PROPERTY_REGISTRATION_MAX_INDEX inclusive
302    * @param[in] type The property value type
303    * @param[in] setFunc The function to call when setting the property. If NULL, then the property becomes read-only
304    * @param[in] getFunc The function to call to retrieve the current value of the property. MUST be provided
305    * @pre "registered" must be registered with the TypeRegistry.
306    * @note The "index" value must be between START_INDEX and MAX_INDEX inclusive.
307    * @note If "setFunc" is NULL, then the property becomes a read-only property.
308    * @note "getFunc" MUST be provided.
309    *
310    */
311   PropertyRegistration( TypeRegistration& registered,
312                         const std::string& name, Property::Index index, Property::Type type,
313                         TypeInfo::SetPropertyFunction setFunc, TypeInfo::GetPropertyFunction getFunc );
314 };
315
316 /**
317  * @brief Registers an animatable property for the given type.
318  * @SINCE_1_0.0
319  */
320 class DALI_CORE_API AnimatablePropertyRegistration
321 {
322 public:
323
324   /**
325    * @brief This constructor registers the animatable property with the registered type.
326    *
327    * This constructor is for scene-graph only properties where the
328    * value of the property can be retrieved and set via specified
329    * functions.
330    *
331    * @SINCE_1_0.0
332    * @param[in] registered The TypeRegistration object
333    * @param[in] name The name of the property
334    * @param[in] index The property index. Must be a value between ANIMATABLE_PROPERTY_REGISTRATION_START_INDEX and ANIMATABLE_PROPERTY_REGISTRATION_MAX_INDEX inclusive
335    * @param[in] type The property value type
336    * @pre "registered" must be registered with the TypeRegistry.
337    */
338   AnimatablePropertyRegistration( TypeRegistration& registered, const std::string& name, Property::Index index, Property::Type type );
339
340   /**
341    * @brief This constructor registers the animatable property with the registered default value.
342    *
343    * This constructor is for scene-graph only properties where the
344    * value of the property can be retrieved and set via specified
345    * functions.
346    *
347    * @SINCE_1_1.18
348    * @param[in] registered The TypeRegistration object
349    * @param[in] name The name of the property
350    * @param[in] index The property index. Must be a value between ANIMATABLE_PROPERTY_REGISTRATION_START_INDEX and ANIMATABLE_PROPERTY_REGISTRATION_MAX_INDEX inclusive
351    * @param[in] value The property default value
352    * @pre "registered" must be registered with the TypeRegistry.
353    */
354   AnimatablePropertyRegistration( TypeRegistration& registered, const std::string& name, Property::Index index, const Property::Value& value );
355 };
356
357 /**
358  * @brief Registers a component of animatable property for the given component index.
359  * @SINCE_1_0.0
360  */
361 class DALI_CORE_API AnimatablePropertyComponentRegistration
362 {
363 public:
364
365   /**
366    * @brief This constructor registers a component of an animatable property where
367    * the base animatable property must be a property that supports property component
368    * (i.e. Vector2, Vector3 or Vector4) and the base animatable property must have
369    * been registered.
370    *
371    * This constructor is for a component of scene-graph only properties where the
372    * value of the property can be retrieved and set via specified functions.
373    *
374    * @SINCE_1_0.0
375    * @param[in] registered The TypeRegistration object
376    * @param[in] name The name of the component
377    * @param[in] index The property index. Must be a value between ANIMATABLE_PROPERTY_REGISTRATION_START_INDEX and ANIMATABLE_PROPERTY_REGISTRATION_MAX_INDEX inclusive
378    * @param[in] baseIndex The index of the base animatable property. Must be a value between ANIMATABLE_PROPERTY_REGISTRATION_START_INDEX and ANIMATABLE_PROPERTY_REGISTRATION_MAX_INDEX inclusive
379    * @param[in] componentIndex The index of the component (e.g. 0 for the x component of a Vector2 property and 1 for the y component of a Vector2 property)
380    * @pre "registered" must be registered with the TypeRegistry.
381    */
382   AnimatablePropertyComponentRegistration( TypeRegistration& registered, const std::string& name, Property::Index index, Property::Index baseIndex, uint32_t componentIndex );
383 };
384
385 /**
386  * @brief Registers a child property for the given type.
387  * @SINCE_1_1.35
388  */
389 class DALI_CORE_API ChildPropertyRegistration
390 {
391 public:
392
393   /**
394    * @brief This constructor registers an event-thread only child property (i.e. a property
395    * that the parent supports in its children) with the registered type.
396    *
397    * @SINCE_1_1.35
398    * @param[in] registered The TypeRegistration object
399    * @param[in] name The name of the property
400    * @param[in] index The property index. Must be a value between CHILD_PROPERTY_REGISTRATION_START_INDEX and CHILD_PROPERTY_REGISTRATION_MAX_INDEX inclusive
401    * @param[in] type The property value type
402    * @pre "registered" must be registered with the TypeRegistry.
403    */
404   ChildPropertyRegistration( TypeRegistration& registered, const std::string& name, Property::Index index, Property::Type type );
405
406   /**
407    * @brief This constructor registers an event-thread only child property (i.e. a property
408    * that the parent supports in its children) with the registered type.
409    *
410    * @SINCE_1_3.20
411    * @param[in] registered The name of the registered type
412    * @param[in] name The name of the property
413    * @param[in] index The property index. Must be a value between CHILD_PROPERTY_REGISTRATION_START_INDEX and CHILD_PROPERTY_REGISTRATION_MAX_INDEX inclusive
414    * @param[in] type The property value type
415    * @pre "registered" must be registered with the TypeRegistry.
416    */
417   ChildPropertyRegistration( const std::string& registered, const std::string& name, Property::Index index, Property::Type type );
418 };
419
420
421 /**
422  * @}
423  */
424 } // namespace Dali
425
426 #endif // header