1 /**
2  * @file lv_group.h
3  *
4  */
5 
6 #ifndef LV_GROUP_H
7 #define LV_GROUP_H
8 
9 #ifdef __cplusplus
10 extern "C" {
11 #endif
12 
13 /*********************
14  *      INCLUDES
15  *********************/
16 
17 #include "../lv_conf_internal.h"
18 
19 #include <stdint.h>
20 #include <stdbool.h>
21 #include "../misc/lv_ll.h"
22 #include "../misc/lv_types.h"
23 
24 /*********************
25  *      DEFINES
26  *********************/
27 /*Predefined keys to control the focused object via lv_group_send(group, c)*/
28 
29 enum {
30     LV_KEY_UP        = 17,  /*0x11*/
31     LV_KEY_DOWN      = 18,  /*0x12*/
32     LV_KEY_RIGHT     = 19,  /*0x13*/
33     LV_KEY_LEFT      = 20,  /*0x14*/
34     LV_KEY_ESC       = 27,  /*0x1B*/
35     LV_KEY_DEL       = 127, /*0x7F*/
36     LV_KEY_BACKSPACE = 8,   /*0x08*/
37     LV_KEY_ENTER     = 10,  /*0x0A, '\n'*/
38     LV_KEY_NEXT      = 9,   /*0x09, '\t'*/
39     LV_KEY_PREV      = 11,  /*0x0B, '*/
40     LV_KEY_HOME      = 2,   /*0x02, STX*/
41     LV_KEY_END       = 3,   /*0x03, ETX*/
42 };
43 typedef uint8_t lv_key_t;
44 
45 /**********************
46  *      TYPEDEFS
47  **********************/
48 
49 struct _lv_obj_t;
50 struct _lv_group_t;
51 
52 typedef void (*lv_group_focus_cb_t)(struct _lv_group_t *);
53 typedef void (*lv_group_edge_cb_t)(struct _lv_group_t *, bool);
54 
55 /**
56  * Groups can be used to logically hold objects so that they can be individually focused.
57  * They are NOT for laying out objects on a screen (try layouts for that).
58  */
59 typedef struct _lv_group_t {
60     lv_ll_t obj_ll;        /**< Linked list to store the objects in the group*/
61     struct _lv_obj_t ** obj_focus; /**< The object in focus*/
62 
63     lv_group_focus_cb_t focus_cb;              /**< A function to call when a new object is focused (optional)*/
64     lv_group_edge_cb_t  edge_cb;               /**< A function to call when an edge is reached, no more focus
65                                                     targets are available in this direction (to allow edge feedback
66                                                     like a sound or a scroll bounce) */
67 
68 #if LV_USE_USER_DATA
69     void * user_data;
70 #endif
71 
72     uint8_t frozen : 1;         /**< 1: can't focus to new object*/
73     uint8_t editing : 1;        /**< 1: Edit mode, 0: Navigate mode*/
74     uint8_t refocus_policy : 1; /**< 1: Focus prev if focused on deletion. 0: Focus next if focused on
75                                    deletion.*/
76     uint8_t wrap : 1;           /**< 1: Focus next/prev can wrap at end of list. 0: Focus next/prev stops at end
77                                    of list.*/
78 } lv_group_t;
79 
80 
81 typedef enum {
82     LV_GROUP_REFOCUS_POLICY_NEXT = 0,
83     LV_GROUP_REFOCUS_POLICY_PREV = 1
84 } lv_group_refocus_policy_t;
85 
86 /**********************
87  * GLOBAL PROTOTYPES
88  **********************/
89 
90 /**
91  * Init. the group module
92  * @remarks Internal function, do not call directly.
93  */
94 void _lv_group_init(void);
95 
96 /**
97  * Create a new object group
98  * @return          pointer to the new object group
99  */
100 lv_group_t * lv_group_create(void);
101 
102 /**
103  * Delete a group object
104  * @param group     pointer to a group
105  */
106 void lv_group_del(lv_group_t * group);
107 
108 /**
109  * Set a default group. New object are added to this group if it's enabled in their class with `add_to_def_group = true`
110  * @param group     pointer to a group (can be `NULL`)
111  */
112 void lv_group_set_default(lv_group_t * group);
113 
114 /**
115  * Get the default group
116  * @return          pointer to the default group
117  */
118 lv_group_t * lv_group_get_default(void);
119 
120 /**
121  * Add an object to a group
122  * @param group     pointer to a group
123  * @param obj       pointer to an object to add
124  */
125 void lv_group_add_obj(lv_group_t * group, struct _lv_obj_t * obj);
126 
127 /**
128  * Swap 2 object in a group. The object must be in the same group
129  * @param obj1  pointer to an object
130  * @param obj2  pointer to an other object
131  */
132 void lv_group_swap_obj(struct _lv_obj_t * obj1, struct _lv_obj_t * obj2);
133 
134 /**
135  * Remove an object from its group
136  * @param obj       pointer to an object to remove
137  */
138 void lv_group_remove_obj(struct _lv_obj_t * obj);
139 
140 /**
141  * Remove all objects from a group
142  * @param group     pointer to a group
143  */
144 void lv_group_remove_all_objs(lv_group_t * group);
145 
146 /**
147  * Focus on an object (defocus the current)
148  * @param obj       pointer to an object to focus on
149  */
150 void lv_group_focus_obj(struct _lv_obj_t * obj);
151 
152 /**
153  * Focus the next object in a group (defocus the current)
154  * @param group     pointer to a group
155  */
156 void lv_group_focus_next(lv_group_t * group);
157 
158 /**
159  * Focus the previous object in a group (defocus the current)
160  * @param group     pointer to a group
161  */
162 void lv_group_focus_prev(lv_group_t * group);
163 
164 /**
165  * Do not let to change the focus from the current object
166  * @param group     pointer to a group
167  * @param en        true: freeze, false: release freezing (normal mode)
168  */
169 void lv_group_focus_freeze(lv_group_t * group, bool en);
170 
171 /**
172  * Send a control character to the focuses object of a group
173  * @param group     pointer to a group
174  * @param c         a character (use LV_KEY_.. to navigate)
175  * @return          result of focused object in group.
176  */
177 lv_res_t lv_group_send_data(lv_group_t * group, uint32_t c);
178 
179 /**
180  * Set a function for a group which will be called when a new object is focused
181  * @param group         pointer to a group
182  * @param focus_cb      the call back function or NULL if unused
183  */
184 void lv_group_set_focus_cb(lv_group_t * group, lv_group_focus_cb_t focus_cb);
185 
186 /**
187  * Set a function for a group which will be called when a focus edge is reached
188  * @param group         pointer to a group
189  * @param edge_cb      the call back function or NULL if unused
190  */
191 void lv_group_set_edge_cb(lv_group_t * group, lv_group_edge_cb_t edge_cb);
192 
193 
194 /**
195  * Set whether the next or previous item in a group is focused if the currently focused obj is
196  * deleted.
197  * @param group         pointer to a group
198  * @param policy        new refocus policy enum
199  */
200 void lv_group_set_refocus_policy(lv_group_t * group, lv_group_refocus_policy_t policy);
201 
202 /**
203  * Manually set the current mode (edit or navigate).
204  * @param group         pointer to group
205  * @param edit          true: edit mode; false: navigate mode
206  */
207 void lv_group_set_editing(lv_group_t * group, bool edit);
208 
209 /**
210  * Set whether focus next/prev will allow wrapping from first->last or last->first object.
211  * @param group         pointer to group
212  * @param               en true: wrapping enabled; false: wrapping disabled
213  */
214 void lv_group_set_wrap(lv_group_t * group, bool en);
215 
216 /**
217  * Get the focused object or NULL if there isn't one
218  * @param group         pointer to a group
219  * @return              pointer to the focused object
220  */
221 struct _lv_obj_t * lv_group_get_focused(const lv_group_t * group);
222 
223 /**
224  * Get the focus callback function of a group
225  * @param group pointer to a group
226  * @return the call back function or NULL if not set
227  */
228 lv_group_focus_cb_t lv_group_get_focus_cb(const lv_group_t * group);
229 
230 /**
231  * Get the edge callback function of a group
232  * @param group pointer to a group
233  * @return the call back function or NULL if not set
234  */
235 lv_group_edge_cb_t lv_group_get_edge_cb(const lv_group_t * group);
236 
237 /**
238  * Get the current mode (edit or navigate).
239  * @param group         pointer to group
240  * @return              true: edit mode; false: navigate mode
241  */
242 bool lv_group_get_editing(const lv_group_t * group);
243 
244 /**
245  * Get whether focus next/prev will allow wrapping from first->last or last->first object.
246  * @param group         pointer to group
247  * @param               en true: wrapping enabled; false: wrapping disabled
248  */
249 bool lv_group_get_wrap(lv_group_t * group);
250 
251 /**
252  * Get the number of object in the group
253  * @param group         pointer to a group
254  * @return              number of objects in the group
255  */
256 uint32_t lv_group_get_obj_count(lv_group_t * group);
257 
258 /**********************
259  *      MACROS
260  **********************/
261 
262 #ifdef __cplusplus
263 } /*extern "C"*/
264 #endif
265 
266 #endif /*LV_GROUP_H*/
267