Updated non-capi public API documentation to new style.
[platform/core/uifw/dali-core.git] / dali / public-api / events / hit-test-algorithm.h
1 #ifndef  __DALI_HIT_TEST_ALGORITHM_H__
2 #define  __DALI_HIT_TEST_ALGORITHM_H__
3
4 //
5 // Copyright (c) 2014 Samsung Electronics Co., Ltd.
6 //
7 // Licensed under the Flora License, Version 1.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://floralicense.org/license/
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 #include <dali/public-api/actors/actor.h>
21 #include <dali/public-api/common/stage.h>
22
23
24 namespace Dali DALI_IMPORT_API
25 {
26
27 class RenderTask;
28
29 /**
30  * @brief This namespace is provided for application developers to do hit-test for the actors.
31  *
32  * <h3>Hit Test Algorithm:</h3>
33  *
34  * Hit testing is dependent on the camera used, which is specific to each RenderTask. For each RenderTask,
35  * hit testing starts from the top-most layer and we go through all the layers until we have a hit or there
36  * are none left. Before we perform a hit test within a layer, we check if all the layer's parents meet the
37  * conditions defined by the function ((e.g. whether it is visible)). If they are not, we skip hit testing
38  * the actors in that layer altogether. Otherwise, we walk through the actor tree within a layer to check
39  * whether the actors within the actor tree should be hit-tested.
40  *
41  * The following pseudocode gives an example of what the function can typically check, which should normally
42  * be provided by the application code:
43  *
44  *   @code
45  *   HIT-TEST-FUNCTION( ACTOR, TRAVERSE-TYPE )
46  *   {
47  *     if( TRAVERSE-TYPE == CHECK_ACTOR ) // Check whether current actor should be hit-tested
48  *     {
49  *       if( ACTOR-IS-VISIBLE &&
50  *           ACTOR-WORLD-COLOR-IS-NOT-TRANSPARENT )
51  *       {
52  *         HITTABLE = TRUE
53  *       }
54  *     }
55  *     else if( TRAVERSE-TYPE == DESCEND_ACTOR_TREE ) ///< Check whether the actor tree should be descended to hit-test its children.
56  *     {
57  *       if( ACTOR-IS-VISIBLE )
58  *       {
59  *         HITTABLE = TRUE
60  *       }
61  *     }
62  *   }
63  *   @endcode
64  *
65  * The following pseudocode explains how the algorithm performs the hit-test with the above functor:
66  *
67  *   @code
68  *   HIT-TEST-WITHIN-LAYER( ACTOR )
69  *   {
70  *     // Depth-first traversal within current layer, visiting parent first
71  *
72  *     // Check whether current actor should be hit-tested
73  *     IF ( HIT-TEST-FUNCTION( ACTOR, CHECK_ACTOR ) &&
74  *          ACTOR-HAS-NON-ZERO-SIZE )
75  *     {
76  *       // Hit-test current actor
77  *       IF ( ACTOR-HIT )
78  *       {
79  *         IF ( DISTANCE-TO-ACTOR < DISTANCE-TO-LAST-HIT-ACTOR )
80  *         {
81  *           // The current actor is the closest actor that was underneath the touch
82  *           LAST-HIT-ACTOR = CURRENT-ACTOR
83  *         }
84  *       }
85  *     }
86  *
87  *     // Keep checking children, in case we hit something closer
88  *     FOR-EACH CHILD (in order)
89  *     {
90  *       IF ( HIT-TEST-FUNCTION( ACTOR, DESCEND_ACTOR_TREE ) &&
91  *            ACTOR-IS-NOT-A-LAYER )
92  *       {
93  *         // Continue traversal for this child's sub-tree
94  *         HIT-TEST-WITHIN-LAYER ( CHILD )
95  *       }
96  *       // else we skip the sub-tree with from this child
97  *     }
98  *   }
99  *   @endcode
100  */
101 namespace HitTestAlgorithm
102 {
103
104 /**
105  * @brief How the actor tree should be traversed.
106  */
107 enum TraverseType
108 {
109   CHECK_ACTOR,            ///< Hit test the given actor.
110   DESCEND_ACTOR_TREE      ///< Check whether the actor tree should be descended to hit-test its children.
111 };
112
113 /**
114  * @brief Results structure containing the hit actor and where it was hit.
115  */
116 struct Results
117 {
118   Actor      actor;            ///< The hit actor.
119   Vector2    actorCoordinates; ///< The actor coordinates.
120 };
121
122 /**
123  * @brief Definition of a hit-test function to use in HitTest() method to check if the actor is hittable (e.g. touchable or focusable).
124  *
125  * @return true, if the actor is hittable, false otherwise.
126  */
127 typedef bool (*HitTestFunction)(Actor actor, TraverseType type);
128
129 /**
130  * @brief Given screen coordinates, this method returns the hit actor & the local coordinates relative to
131  * the top-left (0.0f, 0.0f, 0.5f) of the actor.
132  *
133  * An actor is only hittable if the actor meets all the conditions
134  * defined by the given function (see HitTestAlgorithm).
135  *
136  * Typically, if an actor has a zero size or its world color is fully transparent, it should not be
137  * hittable; and if an actor's visibility flag is unset, its children should not be hittable either.
138  *
139  * @param[in] stage The stage.
140  * @param[in] screenCoordinates The screen coordinates.
141  * @param[out] results The results of the hit-test.
142  * @param[in] func The function to use in the hit-test algorithm.
143  */
144 void HitTest( Stage stage, const Vector2& screenCoordinates, Results& results, HitTestFunction func );
145
146 /**
147  * @brief Hit test specific to a given RenderTask.
148  *
149  * @param[in] renderTask The render task for hit test
150  * @param[in] screenCoordinates The screen coordinates.
151  * @param[out] results The results of the hit-test.
152  * @param[in] func The function to use in the hit-test algorithm.
153  */
154 void HitTest( RenderTask& renderTask, const Vector2& screenCoordinates, Results& results, HitTestFunction func );
155
156 } // namespace HitTestAlgorithm
157
158 } // namespace Dali
159
160 #endif // __DALI_HIT_TEST_ALGORITHM_H__