boot-animation can be build on TEST_APP mode
[apps/native/boot-animation.git] / src / animation.c
1 /*
2  * Copyright (c) 2009-2015 Samsung Electronics Co., Ltd All Rights Reserved
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 #include <stdio.h>
19 #include <stdlib.h>
20 #include <string.h>
21 #include <errno.h>
22 #include <fcntl.h>
23 #include <sys/types.h>
24 #include <sys/stat.h>
25 #include <sys/wait.h>
26 #include <sys/time.h>
27 #include <unistd.h>
28 #include <dirent.h>
29
30 #include <vconf.h>
31 #include <efl_util.h>
32
33 #include "boot.h"
34 #include "animation.h"
35 #include "app_log.h"
36
37 #define OVER_COUNT 19
38
39 static struct animation {
40         Evas_Object *win;
41         Evas_Object *layout;
42         Evas_Object *txt;
43         Evas_Object *display_block;
44         Evas_Coord w;
45         Evas_Coord h;
46         int state;
47         int t;
48 } s_animation = {
49         .win = NULL,
50         .layout = NULL,
51         .txt = NULL,
52         .display_block = NULL,
53         .w = 0,
54         .h = 0,
55         .state = 0,
56         .t = 0,
57 };
58
59 static void win_del(void *data, Evas_Object * obj, void *event_info)
60 {
61         __D("Window delete event received");
62         elm_exit();
63 }
64
65 static void __block_display(void)
66 {
67         Evas_Object *display_block = NULL;
68         display_block = evas_object_rectangle_add(evas_object_evas_get(s_animation.win));
69         elm_win_resize_object_add(s_animation.win, display_block);
70         evas_object_color_set(display_block, 0, 0, 0, 255);
71         evas_object_show(display_block);
72
73         s_animation.display_block = display_block;
74 }
75
76 static Eina_Bool __end_cb(void *data)
77 {
78         int type = (int) data;
79
80         if (type == TYPE_OFF) {
81                 __D("EXIT on SHUTDOWN");
82                 /* Delete Previous Layout */
83                 if (s_animation.layout) {
84                         evas_object_del(s_animation.layout);
85                         s_animation.layout = NULL;
86                 }
87
88                 /* boot-animation do not terminate on shutdown, so flush log now */
89                 fflush(stdout);
90                 close(1);
91
92                 __block_display();
93         } else {
94                 __D("EXIT on BOOTING");
95                 if (vconf_set_int(VCONFKEY_BOOT_ANIMATION_FINISHED, 1) != 0) {
96                         __E("Failed to set finished set");
97                 }
98                 boot_exit();
99         }
100         return ECORE_CALLBACK_CANCEL;
101 }
102
103 static void __animation_finished_cb(void *d, Evas_Object * obj, const char *e, const char *s)
104 {
105         if (s_animation.state == TYPE_OFF) {
106                 __D("TYPE OFF");
107                 if (vconf_set_int(VCONFKEY_BOOT_ANIMATION_FINISHED, 1) != 0) {
108                         __E("Failed to set finished set");
109                 }
110                 ecore_timer_add(1, __end_cb, (void *)TYPE_OFF);
111         } else {
112                 __D("TYPE_ON");
113                 __end_cb((void *)TYPE_ON);
114         }
115 }
116
117 static void __fini_layout(void)
118 {
119         if (s_animation.display_block) {
120                 evas_object_del(s_animation.display_block);
121                 s_animation.display_block = NULL;
122         }
123
124         if (s_animation.layout) {
125                 evas_object_del(s_animation.layout);
126                 s_animation.layout = NULL;
127         }
128
129         if (s_animation.txt) {
130                 evas_object_del(s_animation.txt);
131                 s_animation.txt = NULL;
132         }
133 }
134
135 Evas_Object *create_window(void)
136 {
137         __D("Create Window");
138
139         Evas_Object *win;
140
141         win = elm_win_add(NULL, "BOOT_ANIMATION", ELM_WIN_NOTIFICATION);
142         if (!win) {
143                 __E("Failed to create a new window");
144                 return NULL;
145         }
146         elm_win_aux_hint_add(win, "wm.comp.win.always.selective.mode", "1");
147         elm_win_role_set(win, "alert");
148         efl_util_set_notification_window_level(win, EFL_UTIL_NOTIFICATION_LEVEL_HIGH);
149         evas_object_smart_callback_add(win, "delete-request", win_del, NULL);
150
151         elm_win_screen_size_get(win, NULL, NULL, &s_animation.w, &s_animation.h);
152         elm_win_borderless_set(win, EINA_TRUE);
153         elm_win_indicator_mode_set(win, ELM_WIN_INDICATOR_HIDE);
154         evas_object_move(win, 0, 0);
155         evas_object_show(win);
156
157         return win;
158 }
159
160 char *get_layout_file_name(int state, int w, int h)
161 {
162         char file_name[1024];
163         int ret = 0;
164
165         if (state == TYPE_OFF) {
166                 snprintf(file_name, sizeof(file_name), FILE_PATH"%dx%d_PowerOff.edj", w, h);
167         } else {
168                 snprintf(file_name, sizeof(file_name), FILE_PATH"%dx%d_PowerOn.edj", w, h);
169         }
170         __D("File name for Animation is: %s", file_name);
171
172         ret = access(file_name, 0);
173         if (ret == 0) {
174         } else {
175                 __E("There's no Image same with [%s], So set Default[720x1280] image", file_name);
176                 if (state == TYPE_OFF) {
177                         snprintf(file_name, sizeof(file_name), "%s", DEFAULT_OFF);
178                 } else {
179                         snprintf(file_name, sizeof(file_name), "%s", DEFAULT_ON);
180                 }
181
182                 ret = access(file_name, 0);
183                 if (ret) {
184                         __E("There's no Image file[%s] on target", file_name);
185                         return NULL;
186                 }
187         }
188
189         return strdup(file_name);
190 }
191
192 Eina_Bool is_layout_file_exist(const char *file_name)
193 {
194         int ret = 0;
195
196         ret = access(file_name, 0);
197         if (ret == 0) {
198                 return EINA_TRUE;
199         } else {
200                 return EINA_FALSE;
201         }
202 }
203
204 Evas_Object *create_layout(Evas_Object *win, const char *file_name)
205 {
206         Evas_Object *layout = elm_layout_add(win);
207         if (!layout) {
208                 __E("Failed to create layout");
209                 return NULL;
210         }
211         evas_object_size_hint_weight_set(layout, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND);
212         elm_win_resize_object_add(s_animation.win, layout);
213         elm_layout_signal_callback_add(layout, "end", "animation", __animation_finished_cb, NULL);
214
215         if (!elm_layout_file_set(layout, file_name, GRP_ANIM)) {
216                 __E("Failed to layout file set");
217                 return NULL;
218         }
219
220         evas_object_show(layout);
221
222         return layout;
223 }
224
225 int init_animation(int state)
226 {
227         __D("Init animation");
228
229         s_animation.state = state;
230
231         s_animation.win = create_window();
232         if (!s_animation.win) {
233                 __E("Failed to create a new window");
234                 return EXIT_FAILURE;
235         }
236
237         char *layout_file_name = NULL;
238         layout_file_name = get_layout_file_name(state, s_animation.w, s_animation.h);
239         if (!layout_file_name) {
240                 __E("Failed to get layout file name");
241                 return EXIT_FAILURE;
242         }
243
244         if (!is_layout_file_exist(layout_file_name)) {
245                 __E("This file is not exist");
246                 free(layout_file_name);
247                 return EXIT_FAILURE;
248         }
249
250         s_animation.layout = create_layout(s_animation.win, layout_file_name);
251         if (!s_animation.layout) {
252                 __E("Failed to create layout");
253                 free(layout_file_name);
254                 evas_object_del(s_animation.win);
255                 return EXIT_FAILURE;
256         }
257
258         free(layout_file_name);
259
260         return EXIT_SUCCESS;
261 }
262
263 int fini_animation(void)
264 {
265         __fini_layout();
266         evas_object_del(s_animation.win);
267         fflush(stdout);
268         close(1);
269         return EXIT_SUCCESS;
270 }
271
272 #include "test.h"
273 #if TEST_MODE
274 Evas_Object *__t__get_window(void)
275 {
276         return s_animation.win;
277 }
278
279 Evas_Object *__t__get_layout(void)
280 {
281         return s_animation.layout;
282 }
283
284 Evas_Object *__t__get_display_block(void)
285 {
286         return s_animation.display_block;
287 }
288 #endif
289