blob: fe7b497152d1e32a1fae3ba82f10a6c75e0426da [file] [log] [blame]
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +09001/*
2 * Copyright (C) 2013 DENSO CORPORATION
3 *
Bryce Harringtonaf637c22015-06-11 12:55:55 -07004 * Permission is hereby granted, free of charge, to any person obtaining
5 * a copy of this software and associated documentation files (the
6 * "Software"), to deal in the Software without restriction, including
7 * without limitation the rights to use, copy, modify, merge, publish,
8 * distribute, sublicense, and/or sell copies of the Software, and to
9 * permit persons to whom the Software is furnished to do so, subject to
10 * the following conditions:
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +090011 *
Bryce Harringtonaf637c22015-06-11 12:55:55 -070012 * The above copyright notice and this permission notice (including the
13 * next paragraph) shall be included in all copies or substantial
14 * portions of the Software.
15 *
16 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
17 * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
18 * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
19 * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS
20 * BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN
21 * ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
22 * CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
23 * SOFTWARE.
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +090024 */
25
26/**
27 * Implementation of ivi-layout library. The actual view on ivi_screen is
28 * not updated till calling ivi_layout_commit_changes. A overview from
29 * calling API for updating properties of ivi_surface/ivi_layer to asking
30 * compositor to compose them by using weston_compositor_schedule_repaint,
31 * 0/ initialize this library by ivi_layout_init_with_compositor
32 * with (struct weston_compositor *ec) from ivi-shell.
33 * 1/ When a API for updating properties of ivi_surface/ivi_layer, it updates
34 * pending prop of ivi_surface/ivi_layer/ivi_screen which are structure to
35 * store properties.
36 * 2/ Before calling commitChanges, in case of calling a API to get a property,
37 * return current property, not pending property.
38 * 3/ At the timing of calling ivi_layout_commitChanges, pending properties
39 * are applied to properties.
40 *
41 * *) ivi_layout_commitChanges is also called by transition animation
42 * per each frame. See ivi-layout-transition.c in details. Transition
43 * animation interpolates frames between previous properties of ivi_surface
44 * and new ones.
45 * For example, when a property of ivi_surface is changed from invisibility
46 * to visibility, it behaves like fade-in. When ivi_layout_commitChange is
47 * called during transition animation, it cancels the transition and
48 * re-start transition to new properties from current properties of final
49 * frame just before the the cancellation.
50 *
51 * 4/ According properties, set transformation by using weston_matrix and
52 * weston_view per ivi_surfaces and ivi_layers in while loop.
53 * 5/ Set damage and trigger transform by using weston_view_geometry_dirty.
54 * 6/ Notify update of properties.
55 * 7/ Trigger composition by weston_compositor_schedule_repaint.
56 *
57 */
Nobuhiko Tanibataee8e5832014-12-15 13:25:39 +090058#include "config.h"
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +090059
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +090060#include <string.h>
Ucan, Emre (ADITG/SW1)38fcf382015-08-20 14:13:29 +000061#include <assert.h>
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +090062
63#include "compositor.h"
64#include "ivi-layout-export.h"
65#include "ivi-layout-private.h"
66
Jon Cruz867d50e2015-06-15 15:37:10 -070067#include "shared/helpers.h"
Jon Cruz4678bab2015-06-15 15:37:07 -070068#include "shared/os-compatibility.h"
Nobuhiko Tanibataee8e5832014-12-15 13:25:39 +090069
Nobuhiko Tanibataacbcc6c2015-08-24 10:24:15 +090070#define max(a, b) ((a) > (b) ? (a) : (b))
71
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +090072struct listener_layout_notification {
73 void *userdata;
74 struct wl_listener listener;
75};
76
77struct ivi_layout;
78
79struct ivi_layout_screen {
80 struct wl_list link;
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +090081 uint32_t id_screen;
82
83 struct ivi_layout *layout;
84 struct weston_output *output;
85
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +090086 struct {
87 struct wl_list layer_list;
88 struct wl_list link;
89 } pending;
90
91 struct {
Ucan, Emre (ADITG/SW1)174257b2015-08-20 14:13:30 +000092 int dirty;
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +090093 struct wl_list layer_list;
94 struct wl_list link;
95 } order;
96};
97
98struct ivi_layout_notification_callback {
99 void *callback;
100 void *data;
101};
102
Nobuhiko Tanibata21deb282015-07-15 14:05:32 +0900103struct ivi_rectangle
104{
105 int32_t x;
106 int32_t y;
107 int32_t width;
108 int32_t height;
109};
110
Nobuhiko Tanibata82051702015-06-22 15:31:26 +0900111static void
112remove_notification(struct wl_list *listener_list, void *callback, void *userdata);
113
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +0900114static struct ivi_layout ivilayout = {0};
115
116struct ivi_layout *
117get_instance(void)
118{
119 return &ivilayout;
120}
121
122/**
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +0900123 * Internal API to add/remove a ivi_layer to/from ivi_screen.
124 */
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +0900125static struct ivi_layout_surface *
126get_surface(struct wl_list *surf_list, uint32_t id_surface)
127{
128 struct ivi_layout_surface *ivisurf;
129
130 wl_list_for_each(ivisurf, surf_list, link) {
131 if (ivisurf->id_surface == id_surface) {
132 return ivisurf;
133 }
134 }
135
136 return NULL;
137}
138
139static struct ivi_layout_layer *
140get_layer(struct wl_list *layer_list, uint32_t id_layer)
141{
142 struct ivi_layout_layer *ivilayer;
143
144 wl_list_for_each(ivilayer, layer_list, link) {
145 if (ivilayer->id_layer == id_layer) {
146 return ivilayer;
147 }
148 }
149
150 return NULL;
151}
152
Ucan, Emre (ADITG/SW1)64635ee2015-08-28 12:59:06 +0000153static struct weston_view *
154get_weston_view(struct ivi_layout_surface *ivisurf)
155{
156 struct weston_view *view = NULL;
157
158 assert(ivisurf->surface != NULL);
159
160 /* One view per surface */
161 if(wl_list_empty(&ivisurf->surface->views))
162 view = NULL;
163 else
164 view = wl_container_of(ivisurf->surface->views.next, view, surface_link);
165
166 return view;
167}
168
Nobuhiko Tanibataef6c7862014-12-15 13:20:44 +0900169static void
170remove_configured_listener(struct ivi_layout_surface *ivisurf)
171{
172 struct wl_listener *link = NULL;
173 struct wl_listener *next = NULL;
174
175 wl_list_for_each_safe(link, next, &ivisurf->configured.listener_list, link) {
176 wl_list_remove(&link->link);
177 }
178}
179
Nobuhiko Tanibataef6c7862014-12-15 13:20:44 +0900180static void
181remove_all_notification(struct wl_list *listener_list)
182{
183 struct wl_listener *listener = NULL;
184 struct wl_listener *next = NULL;
185
186 wl_list_for_each_safe(listener, next, listener_list, link) {
187 struct listener_layout_notification *notification = NULL;
Ucan, Emre (ADITG/SW1)cf34dc22015-08-20 14:13:33 +0000188 wl_list_remove(&listener->link);
Nobuhiko Tanibataef6c7862014-12-15 13:20:44 +0900189
190 notification =
191 container_of(listener,
192 struct listener_layout_notification,
193 listener);
194
195 free(notification->userdata);
196 free(notification);
197 }
198}
199
Nobuhiko Tanibataee8e5832014-12-15 13:25:39 +0900200static void
Nobuhiko Tanibataef6c7862014-12-15 13:20:44 +0900201ivi_layout_surface_remove_notification(struct ivi_layout_surface *ivisurf)
202{
203 if (ivisurf == NULL) {
204 weston_log("ivi_layout_surface_remove_notification: invalid argument\n");
205 return;
206 }
207
208 remove_all_notification(&ivisurf->property_changed.listener_list);
209}
210
Nobuhiko Tanibata82051702015-06-22 15:31:26 +0900211static void
212ivi_layout_surface_remove_notification_by_callback(struct ivi_layout_surface *ivisurf,
213 surface_property_notification_func callback,
214 void *userdata)
215{
216 if (ivisurf == NULL) {
217 weston_log("ivi_layout_surface_remove_notification_by_callback: invalid argument\n");
218 return;
219 }
220
221 remove_notification(&ivisurf->property_changed.listener_list, callback, userdata);
222}
223
Nobuhiko Tanibataee8e5832014-12-15 13:25:39 +0900224/**
Nobuhiko Tanibata6f6c9382015-06-22 15:30:53 +0900225 * Called at destruction of wl_surface/ivi_surface
Nobuhiko Tanibataee8e5832014-12-15 13:25:39 +0900226 */
Nobuhiko Tanibata6f6c9382015-06-22 15:30:53 +0900227void
228ivi_layout_surface_destroy(struct ivi_layout_surface *ivisurf)
Nobuhiko Tanibataef6c7862014-12-15 13:20:44 +0900229{
230 struct ivi_layout *layout = get_instance();
231
232 if (ivisurf == NULL) {
Nobuhiko Tanibata6f6c9382015-06-22 15:30:53 +0900233 weston_log("%s: invalid argument\n", __func__);
Nobuhiko Tanibataef6c7862014-12-15 13:20:44 +0900234 return;
235 }
236
Nobuhiko Tanibata21deb282015-07-15 14:05:32 +0900237 wl_list_remove(&ivisurf->transform.link);
Nobuhiko Tanibata6f6c9382015-06-22 15:30:53 +0900238 wl_list_remove(&ivisurf->pending.link);
239 wl_list_remove(&ivisurf->order.link);
240 wl_list_remove(&ivisurf->link);
Nobuhiko Tanibataef6c7862014-12-15 13:20:44 +0900241
242 wl_signal_emit(&layout->surface_notification.removed, ivisurf);
243
244 remove_configured_listener(ivisurf);
245
246 ivi_layout_surface_remove_notification(ivisurf);
247
Nobuhiko Tanibata6f6c9382015-06-22 15:30:53 +0900248 free(ivisurf);
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +0900249}
250
251/**
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +0900252 * Internal API to initialize ivi_screens found from output_list of weston_compositor.
253 * Called by ivi_layout_init_with_compositor.
254 */
255static void
256create_screen(struct weston_compositor *ec)
257{
258 struct ivi_layout *layout = get_instance();
259 struct ivi_layout_screen *iviscrn = NULL;
260 struct weston_output *output = NULL;
261 int32_t count = 0;
262
263 wl_list_for_each(output, &ec->output_list, link) {
264 iviscrn = calloc(1, sizeof *iviscrn);
265 if (iviscrn == NULL) {
266 weston_log("fails to allocate memory\n");
267 continue;
268 }
269
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +0900270 iviscrn->layout = layout;
271
272 iviscrn->id_screen = count;
273 count++;
274
275 iviscrn->output = output;
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +0900276
277 wl_list_init(&iviscrn->pending.layer_list);
278 wl_list_init(&iviscrn->pending.link);
279
280 wl_list_init(&iviscrn->order.layer_list);
281 wl_list_init(&iviscrn->order.link);
282
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +0900283 wl_list_insert(&layout->screen_list, &iviscrn->link);
284 }
285}
286
287/**
288 * Internal APIs to initialize properties of ivi_surface/ivi_layer when they are created.
289 */
290static void
291init_layer_properties(struct ivi_layout_layer_properties *prop,
292 int32_t width, int32_t height)
293{
294 memset(prop, 0, sizeof *prop);
295 prop->opacity = wl_fixed_from_double(1.0);
296 prop->source_width = width;
297 prop->source_height = height;
298 prop->dest_width = width;
299 prop->dest_height = height;
300}
301
302static void
303init_surface_properties(struct ivi_layout_surface_properties *prop)
304{
305 memset(prop, 0, sizeof *prop);
306 prop->opacity = wl_fixed_from_double(1.0);
Nobuhiko Tanibatae259a7a2015-04-27 17:02:54 +0900307 /*
308 * FIXME: this shall be finxed by ivi-layout-transition.
309 */
310 prop->dest_width = 1;
311 prop->dest_height = 1;
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +0900312}
313
314/**
315 * Internal APIs to be called from ivi_layout_commit_changes.
316 */
317static void
318update_opacity(struct ivi_layout_layer *ivilayer,
319 struct ivi_layout_surface *ivisurf)
320{
Ucan, Emre (ADITG/SW1)64635ee2015-08-28 12:59:06 +0000321 struct weston_view *tmpview = NULL;
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +0900322 double layer_alpha = wl_fixed_to_double(ivilayer->prop.opacity);
323 double surf_alpha = wl_fixed_to_double(ivisurf->prop.opacity);
324
Nobuhiko Tanibata90c27892015-12-26 23:52:51 +0900325 tmpview = get_weston_view(ivisurf);
326 assert(tmpview != NULL);
327 tmpview->alpha = layer_alpha * surf_alpha;
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +0900328}
329
330static void
Nobuhiko Tanibata21deb282015-07-15 14:05:32 +0900331get_rotate_values(enum wl_output_transform orientation,
332 float *v_sin,
333 float *v_cos)
334{
335 switch (orientation) {
336 case WL_OUTPUT_TRANSFORM_90:
337 *v_sin = 1.0f;
338 *v_cos = 0.0f;
339 break;
340 case WL_OUTPUT_TRANSFORM_180:
341 *v_sin = 0.0f;
342 *v_cos = -1.0f;
343 break;
344 case WL_OUTPUT_TRANSFORM_270:
345 *v_sin = -1.0f;
346 *v_cos = 0.0f;
347 break;
348 case WL_OUTPUT_TRANSFORM_NORMAL:
349 default:
350 *v_sin = 0.0f;
351 *v_cos = 1.0f;
352 break;
353 }
354}
355
356static void
357get_scale(enum wl_output_transform orientation,
358 float dest_width,
359 float dest_height,
360 float source_width,
361 float source_height,
362 float *scale_x,
363 float *scale_y)
364{
365 switch (orientation) {
366 case WL_OUTPUT_TRANSFORM_90:
367 *scale_x = dest_width / source_height;
368 *scale_y = dest_height / source_width;
369 break;
370 case WL_OUTPUT_TRANSFORM_180:
371 *scale_x = dest_width / source_width;
372 *scale_y = dest_height / source_height;
373 break;
374 case WL_OUTPUT_TRANSFORM_270:
375 *scale_x = dest_width / source_height;
376 *scale_y = dest_height / source_width;
377 break;
378 case WL_OUTPUT_TRANSFORM_NORMAL:
379 default:
380 *scale_x = dest_width / source_width;
381 *scale_y = dest_height / source_height;
382 break;
383 }
384}
385
386static void
387calc_transformation_matrix(struct ivi_rectangle *source_rect,
388 struct ivi_rectangle *dest_rect,
389 enum wl_output_transform orientation,
390 struct weston_matrix *m)
391{
392 float source_center_x;
393 float source_center_y;
394 float vsin;
395 float vcos;
396 float scale_x;
397 float scale_y;
398 float translate_x;
399 float translate_y;
400
401 source_center_x = source_rect->x + source_rect->width * 0.5f;
402 source_center_y = source_rect->y + source_rect->height * 0.5f;
403 weston_matrix_translate(m, -source_center_x, -source_center_y, 0.0f);
404
405 get_rotate_values(orientation, &vsin, &vcos);
406 weston_matrix_rotate_xy(m, vcos, vsin);
407
408 get_scale(orientation,
409 dest_rect->width,
410 dest_rect->height,
411 source_rect->width,
412 source_rect->height,
413 &scale_x,
414 &scale_y);
415 weston_matrix_scale(m, scale_x, scale_y, 1.0f);
416
417 translate_x = dest_rect->width * 0.5f + dest_rect->x;
418 translate_y = dest_rect->height * 0.5f + dest_rect->y;
419 weston_matrix_translate(m, translate_x, translate_y, 0.0f);
420}
421
Nobuhiko Tanibataacbcc6c2015-08-24 10:24:15 +0900422/*
423 * This computes intersected rect_output from two ivi_rectangles
Nobuhiko Tanibata21deb282015-07-15 14:05:32 +0900424 */
425static void
Nobuhiko Tanibataacbcc6c2015-08-24 10:24:15 +0900426ivi_rectangle_intersect(const struct ivi_rectangle *rect1,
427 const struct ivi_rectangle *rect2,
428 struct ivi_rectangle *rect_output)
429{
430 int32_t rect1_right = rect1->x + rect1->width;
431 int32_t rect1_bottom = rect1->y + rect1->height;
432 int32_t rect2_right = rect2->x + rect2->width;
433 int32_t rect2_bottom = rect2->y + rect2->height;
434
435 rect_output->x = max(rect1->x, rect2->x);
436 rect_output->y = max(rect1->y, rect2->y);
437 rect_output->width = rect1_right < rect2_right ?
438 rect1_right - rect_output->x :
439 rect2_right - rect_output->x;
440 rect_output->height = rect1_bottom < rect2_bottom ?
441 rect1_bottom - rect_output->y :
442 rect2_bottom - rect_output->y;
443
444 if (rect_output->width < 0 || rect_output->height < 0) {
445 rect_output->width = 0;
446 rect_output->height = 0;
447 }
448}
449
450/*
451 * Transform rect_input by the inverse of matrix, intersect with boundingbox,
452 * and store the result in rect_output.
453 * The boundingbox must be given in the same coordinate space as rect_output.
454 * Additionally, there are the following restrictions on the matrix:
455 * - no projective transformations
456 * - no skew
457 * - only multiples of 90-degree rotations supported
458 *
459 * In failure case of weston_matrix_invert, rect_output is set to boundingbox
460 * as a fail-safe with log.
461 */
462static void
463calc_inverse_matrix_transform(const struct weston_matrix *matrix,
464 const struct ivi_rectangle *rect_input,
465 const struct ivi_rectangle *boundingbox,
466 struct ivi_rectangle *rect_output)
467{
468 struct weston_matrix m;
469 struct weston_vector top_left;
470 struct weston_vector bottom_right;
471
472 assert(boundingbox != rect_output);
473
474 if (weston_matrix_invert(&m, matrix) < 0) {
475 weston_log("ivi-shell: calc_inverse_matrix_transform fails to invert a matrix.\n");
476 weston_log("ivi-shell: boundingbox is set to the rect_output.\n");
477 rect_output->x = boundingbox->x;
478 rect_output->y = boundingbox->y;
479 rect_output->width = boundingbox->width;
480 rect_output->height = boundingbox->height;
481 }
482
483 /* The vectors and matrices involved will always produce f[3] == 1.0. */
484 top_left.f[0] = rect_input->x;
485 top_left.f[1] = rect_input->y;
486 top_left.f[2] = 0.0f;
487 top_left.f[3] = 1.0f;
488
489 bottom_right.f[0] = rect_input->x + rect_input->width;
490 bottom_right.f[1] = rect_input->y + rect_input->height;
491 bottom_right.f[2] = 0.0f;
492 bottom_right.f[3] = 1.0f;
493
494 weston_matrix_transform(&m, &top_left);
495 weston_matrix_transform(&m, &bottom_right);
496
497 if (top_left.f[0] < bottom_right.f[0]) {
498 rect_output->x = top_left.f[0];
499 rect_output->width = bottom_right.f[0] - rect_output->x;
500 } else {
501 rect_output->x = bottom_right.f[0];
502 rect_output->width = top_left.f[0] - rect_output->x;
503 }
504
505 if (top_left.f[1] < bottom_right.f[1]) {
506 rect_output->y = top_left.f[1];
507 rect_output->height = bottom_right.f[1] - rect_output->y;
508 } else {
509 rect_output->y = bottom_right.f[1];
510 rect_output->height = top_left.f[1] - rect_output->y;
511 }
512
513 ivi_rectangle_intersect(rect_output, boundingbox, rect_output);
514}
515
516/**
517 * This computes the whole transformation matrix:m from surface-local
Nobuhiko Tanibata1c2618e2015-12-09 15:39:26 +0900518 * coordinates to multi screens coordinate, which is global coordinates.
519 * It is assumed that weston_view::geometry.{x,y} are zero.
Nobuhiko Tanibataacbcc6c2015-08-24 10:24:15 +0900520 *
521 * Additionally, this computes the mask on surface-local coordinates as a
522 * ivi_rectangle. This can be set to weston_view_set_mask.
523 *
524 * The mask is computed by following steps
Nobuhiko Tanibata1c2618e2015-12-09 15:39:26 +0900525 * - destination rectangle of layer is tansformed to multi screen coordinate,
526 * global coordinates. This is done by adding weston_output.{x,y} in simple
527 * because there is no scaled and rotated transformation.
528 * - destination rectangle of layer in multi screens coordinate needs to be
529 * intersected inside of a screen the layer is assigned to. This is because
530 * overlapped region of weston surface in another screen shall not be
531 * displayed according to ivi use case.
532 * - destination rectangle of layer
533 * - in multi screen coordinates,
534 * - and intersected inside of an assigned screen,
535 * is inversed to surface-local cooodinates by inversed matrix:m.
Nobuhiko Tanibataacbcc6c2015-08-24 10:24:15 +0900536 * - the area is intersected by intersected area between weston_surface and
537 * source rectangle of ivi_surface.
538 */
539static void
540calc_surface_to_global_matrix_and_mask_to_weston_surface(
Nobuhiko Tanibata29babdf2015-12-09 15:38:41 +0900541 struct ivi_layout_screen *iviscrn,
Nobuhiko Tanibataacbcc6c2015-08-24 10:24:15 +0900542 struct ivi_layout_layer *ivilayer,
543 struct ivi_layout_surface *ivisurf,
544 struct weston_matrix *m,
545 struct ivi_rectangle *result)
Nobuhiko Tanibata21deb282015-07-15 14:05:32 +0900546{
547 const struct ivi_layout_surface_properties *sp = &ivisurf->prop;
548 const struct ivi_layout_layer_properties *lp = &ivilayer->prop;
Nobuhiko Tanibata29babdf2015-12-09 15:38:41 +0900549 struct weston_output *output = iviscrn->output;
Nobuhiko Tanibataacbcc6c2015-08-24 10:24:15 +0900550 struct ivi_rectangle weston_surface_rect = { 0,
551 0,
552 ivisurf->surface->width,
553 ivisurf->surface->height };
Nobuhiko Tanibata21deb282015-07-15 14:05:32 +0900554 struct ivi_rectangle surface_source_rect = { sp->source_x,
555 sp->source_y,
556 sp->source_width,
557 sp->source_height };
558 struct ivi_rectangle surface_dest_rect = { sp->dest_x,
559 sp->dest_y,
560 sp->dest_width,
561 sp->dest_height };
562 struct ivi_rectangle layer_source_rect = { lp->source_x,
563 lp->source_y,
564 lp->source_width,
565 lp->source_height };
566 struct ivi_rectangle layer_dest_rect = { lp->dest_x,
567 lp->dest_y,
568 lp->dest_width,
569 lp->dest_height };
Nobuhiko Tanibata1c2618e2015-12-09 15:39:26 +0900570 struct ivi_rectangle screen_dest_rect = { output->x,
571 output->y,
572 output->width,
573 output->height };
574 struct ivi_rectangle layer_dest_rect_in_global =
575 { lp->dest_x + output->x,
576 lp->dest_y + output->y,
577 lp->dest_width,
578 lp->dest_height };
Nobuhiko Tanibataacbcc6c2015-08-24 10:24:15 +0900579 struct ivi_rectangle surface_result;
Nobuhiko Tanibata1c2618e2015-12-09 15:39:26 +0900580 struct ivi_rectangle layer_dest_rect_in_global_intersected;
Nobuhiko Tanibata21deb282015-07-15 14:05:32 +0900581
Nobuhiko Tanibataacbcc6c2015-08-24 10:24:15 +0900582 /*
583 * the whole transformation matrix:m from surface-local
584 * coordinates to global coordinates, which is computed by
585 * two steps,
586 * - surface-local coordinates to layer-local coordinates
Nobuhiko Tanibata29babdf2015-12-09 15:38:41 +0900587 * - layer-local coordinates to a single screen-local coordinates
588 * - a single screen-local coordinates to multi screen coordinates,
589 * which is global coordinates.
Nobuhiko Tanibataacbcc6c2015-08-24 10:24:15 +0900590 */
Nobuhiko Tanibata21deb282015-07-15 14:05:32 +0900591 calc_transformation_matrix(&surface_source_rect,
592 &surface_dest_rect,
593 sp->orientation, m);
594
595 calc_transformation_matrix(&layer_source_rect,
596 &layer_dest_rect,
597 lp->orientation, m);
Nobuhiko Tanibataacbcc6c2015-08-24 10:24:15 +0900598
Nobuhiko Tanibata29babdf2015-12-09 15:38:41 +0900599 weston_matrix_translate(m, output->x, output->y, 0.0f);
600
Nobuhiko Tanibataacbcc6c2015-08-24 10:24:15 +0900601 /* this intersected ivi_rectangle would be used for masking
602 * weston_surface
603 */
604 ivi_rectangle_intersect(&surface_source_rect, &weston_surface_rect,
605 &surface_result);
606
Nobuhiko Tanibata1c2618e2015-12-09 15:39:26 +0900607 /*
608 * destination rectangle of layer in multi screens coordinate
609 * is intersected to avoid displaying outside of an assigned screen.
610 */
611 ivi_rectangle_intersect(&layer_dest_rect_in_global, &screen_dest_rect,
612 &layer_dest_rect_in_global_intersected);
613
Nobuhiko Tanibataacbcc6c2015-08-24 10:24:15 +0900614 /* calc masking area of weston_surface from m */
615 calc_inverse_matrix_transform(m,
Nobuhiko Tanibata1c2618e2015-12-09 15:39:26 +0900616 &layer_dest_rect_in_global_intersected,
Nobuhiko Tanibataacbcc6c2015-08-24 10:24:15 +0900617 &surface_result,
618 result);
Nobuhiko Tanibata21deb282015-07-15 14:05:32 +0900619}
620
621static void
Nobuhiko Tanibatab4cb25d2015-12-09 15:36:58 +0900622update_prop(struct ivi_layout_screen *iviscrn,
623 struct ivi_layout_layer *ivilayer,
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +0900624 struct ivi_layout_surface *ivisurf)
625{
Nobuhiko Tanibata4c1dbf72015-07-15 13:55:50 +0900626 struct weston_view *tmpview;
Nobuhiko Tanibataacbcc6c2015-08-24 10:24:15 +0900627 struct ivi_rectangle r;
Nobuhiko Tanibata21deb282015-07-15 14:05:32 +0900628 bool can_calc = true;
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +0900629
Nobuhiko Tanibatab4cb25d2015-12-09 15:36:58 +0900630 /*In case of no prop change, this just returns*/
631 if (!ivilayer->event_mask && !ivisurf->event_mask)
Nobuhiko Tanibata4c1dbf72015-07-15 13:55:50 +0900632 return;
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +0900633
Nobuhiko Tanibata4c1dbf72015-07-15 13:55:50 +0900634 update_opacity(ivilayer, ivisurf);
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +0900635
Ucan, Emre (ADITG/SW1)64635ee2015-08-28 12:59:06 +0000636 tmpview = get_weston_view(ivisurf);
637 assert(tmpview != NULL);
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +0900638
Nobuhiko Tanibata21deb282015-07-15 14:05:32 +0900639 if (ivisurf->prop.source_width == 0 || ivisurf->prop.source_height == 0) {
640 weston_log("ivi-shell: source rectangle is not yet set by ivi_layout_surface_set_source_rectangle\n");
641 can_calc = false;
642 }
643
644 if (ivisurf->prop.dest_width == 0 || ivisurf->prop.dest_height == 0) {
645 weston_log("ivi-shell: destination rectangle is not yet set by ivi_layout_surface_set_destination_rectangle\n");
646 can_calc = false;
647 }
648
649 if (can_calc) {
650 wl_list_remove(&ivisurf->transform.link);
651 weston_matrix_init(&ivisurf->transform.matrix);
652
Nobuhiko Tanibataacbcc6c2015-08-24 10:24:15 +0900653 calc_surface_to_global_matrix_and_mask_to_weston_surface(
Nobuhiko Tanibata29babdf2015-12-09 15:38:41 +0900654 iviscrn, ivilayer, ivisurf, &ivisurf->transform.matrix, &r);
Nobuhiko Tanibata21deb282015-07-15 14:05:32 +0900655
Ucan, Emre (ADITG/SW1)64635ee2015-08-28 12:59:06 +0000656 weston_view_set_mask(tmpview, r.x, r.y, r.width, r.height);
657 wl_list_insert(&tmpview->geometry.transformation_list,
658 &ivisurf->transform.link);
Nobuhiko Tanibata21deb282015-07-15 14:05:32 +0900659
Ucan, Emre (ADITG/SW1)64635ee2015-08-28 12:59:06 +0000660 weston_view_set_transform_parent(tmpview, NULL);
Nobuhiko Tanibata21deb282015-07-15 14:05:32 +0900661 }
662
663 ivisurf->update_count++;
664
Ucan, Emre (ADITG/SW1)64635ee2015-08-28 12:59:06 +0000665 weston_view_geometry_dirty(tmpview);
Nobuhiko Tanibata4c1dbf72015-07-15 13:55:50 +0900666
Ucan, Emre (ADITG/SW1)64635ee2015-08-28 12:59:06 +0000667 weston_surface_damage(ivisurf->surface);
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +0900668}
669
670static void
671commit_changes(struct ivi_layout *layout)
672{
673 struct ivi_layout_screen *iviscrn = NULL;
674 struct ivi_layout_layer *ivilayer = NULL;
675 struct ivi_layout_surface *ivisurf = NULL;
676
677 wl_list_for_each(iviscrn, &layout->screen_list, link) {
678 wl_list_for_each(ivilayer, &iviscrn->order.layer_list, order.link) {
Nobuhiko Tanibatab4cb25d2015-12-09 15:36:58 +0900679 /*
680 * If ivilayer is invisible, weston_view of ivisurf doesn't
681 * need to be modified.
682 */
683 if (ivilayer->prop.visibility == false)
684 continue;
685
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +0900686 wl_list_for_each(ivisurf, &ivilayer->order.surface_list, order.link) {
Nobuhiko Tanibatab4cb25d2015-12-09 15:36:58 +0900687 /*
688 * If ivilayer is invisible, weston_view of ivisurf doesn't
689 * need to be modified.
690 */
691 if (ivisurf->prop.visibility == false)
692 continue;
693
694 update_prop(iviscrn, ivilayer, ivisurf);
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +0900695 }
696 }
697 }
698}
699
700static void
701commit_surface_list(struct ivi_layout *layout)
702{
703 struct ivi_layout_surface *ivisurf = NULL;
704 int32_t dest_x = 0;
705 int32_t dest_y = 0;
706 int32_t dest_width = 0;
707 int32_t dest_height = 0;
708 int32_t configured = 0;
709
710 wl_list_for_each(ivisurf, &layout->surface_list, link) {
Dawid Gajownik74a635b2015-08-06 17:12:19 -0300711 if (ivisurf->pending.prop.transition_type == IVI_LAYOUT_TRANSITION_VIEW_DEFAULT) {
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +0900712 dest_x = ivisurf->prop.dest_x;
713 dest_y = ivisurf->prop.dest_y;
714 dest_width = ivisurf->prop.dest_width;
715 dest_height = ivisurf->prop.dest_height;
716
717 ivi_layout_transition_move_resize_view(ivisurf,
718 ivisurf->pending.prop.dest_x,
719 ivisurf->pending.prop.dest_y,
720 ivisurf->pending.prop.dest_width,
721 ivisurf->pending.prop.dest_height,
722 ivisurf->pending.prop.transition_duration);
723
Dawid Gajownik74a635b2015-08-06 17:12:19 -0300724 if (ivisurf->pending.prop.visibility) {
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +0900725 ivi_layout_transition_visibility_on(ivisurf, ivisurf->pending.prop.transition_duration);
726 } else {
727 ivi_layout_transition_visibility_off(ivisurf, ivisurf->pending.prop.transition_duration);
728 }
729
730 ivisurf->prop = ivisurf->pending.prop;
731 ivisurf->prop.dest_x = dest_x;
732 ivisurf->prop.dest_y = dest_y;
733 ivisurf->prop.dest_width = dest_width;
734 ivisurf->prop.dest_height = dest_height;
735 ivisurf->prop.transition_type = IVI_LAYOUT_TRANSITION_NONE;
736 ivisurf->pending.prop.transition_type = IVI_LAYOUT_TRANSITION_NONE;
737
Dawid Gajownik74a635b2015-08-06 17:12:19 -0300738 } else if (ivisurf->pending.prop.transition_type == IVI_LAYOUT_TRANSITION_VIEW_DEST_RECT_ONLY) {
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +0900739 dest_x = ivisurf->prop.dest_x;
740 dest_y = ivisurf->prop.dest_y;
741 dest_width = ivisurf->prop.dest_width;
742 dest_height = ivisurf->prop.dest_height;
743
744 ivi_layout_transition_move_resize_view(ivisurf,
745 ivisurf->pending.prop.dest_x,
746 ivisurf->pending.prop.dest_y,
747 ivisurf->pending.prop.dest_width,
748 ivisurf->pending.prop.dest_height,
749 ivisurf->pending.prop.transition_duration);
750
751 ivisurf->prop = ivisurf->pending.prop;
752 ivisurf->prop.dest_x = dest_x;
753 ivisurf->prop.dest_y = dest_y;
754 ivisurf->prop.dest_width = dest_width;
755 ivisurf->prop.dest_height = dest_height;
756
757 ivisurf->prop.transition_type = IVI_LAYOUT_TRANSITION_NONE;
758 ivisurf->pending.prop.transition_type = IVI_LAYOUT_TRANSITION_NONE;
759
Dawid Gajownik74a635b2015-08-06 17:12:19 -0300760 } else if (ivisurf->pending.prop.transition_type == IVI_LAYOUT_TRANSITION_VIEW_FADE_ONLY) {
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +0900761 configured = 0;
Dawid Gajownik74a635b2015-08-06 17:12:19 -0300762 if (ivisurf->pending.prop.visibility) {
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +0900763 ivi_layout_transition_visibility_on(ivisurf, ivisurf->pending.prop.transition_duration);
764 } else {
765 ivi_layout_transition_visibility_off(ivisurf, ivisurf->pending.prop.transition_duration);
766 }
767
768 if (ivisurf->prop.dest_width != ivisurf->pending.prop.dest_width ||
769 ivisurf->prop.dest_height != ivisurf->pending.prop.dest_height) {
770 configured = 1;
771 }
772
773 ivisurf->prop = ivisurf->pending.prop;
774 ivisurf->prop.transition_type = IVI_LAYOUT_TRANSITION_NONE;
775 ivisurf->pending.prop.transition_type = IVI_LAYOUT_TRANSITION_NONE;
776
777 if (configured && !is_surface_transition(ivisurf))
778 wl_signal_emit(&ivisurf->configured, ivisurf);
779 } else {
780 configured = 0;
781 if (ivisurf->prop.dest_width != ivisurf->pending.prop.dest_width ||
782 ivisurf->prop.dest_height != ivisurf->pending.prop.dest_height) {
783 configured = 1;
784 }
785
786 ivisurf->prop = ivisurf->pending.prop;
787 ivisurf->prop.transition_type = IVI_LAYOUT_TRANSITION_NONE;
788 ivisurf->pending.prop.transition_type = IVI_LAYOUT_TRANSITION_NONE;
789
790 if (configured && !is_surface_transition(ivisurf))
791 wl_signal_emit(&ivisurf->configured, ivisurf);
792 }
793 }
794}
795
796static void
797commit_layer_list(struct ivi_layout *layout)
798{
799 struct ivi_layout_layer *ivilayer = NULL;
800 struct ivi_layout_surface *ivisurf = NULL;
801 struct ivi_layout_surface *next = NULL;
802
803 wl_list_for_each(ivilayer, &layout->layer_list, link) {
Dawid Gajownik74a635b2015-08-06 17:12:19 -0300804 if (ivilayer->pending.prop.transition_type == IVI_LAYOUT_TRANSITION_LAYER_MOVE) {
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +0900805 ivi_layout_transition_move_layer(ivilayer, ivilayer->pending.prop.dest_x, ivilayer->pending.prop.dest_y, ivilayer->pending.prop.transition_duration);
Dawid Gajownik74a635b2015-08-06 17:12:19 -0300806 } else if (ivilayer->pending.prop.transition_type == IVI_LAYOUT_TRANSITION_LAYER_FADE) {
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +0900807 ivi_layout_transition_fade_layer(ivilayer,ivilayer->pending.prop.is_fade_in,
808 ivilayer->pending.prop.start_alpha,ivilayer->pending.prop.end_alpha,
809 NULL, NULL,
810 ivilayer->pending.prop.transition_duration);
811 }
812 ivilayer->pending.prop.transition_type = IVI_LAYOUT_TRANSITION_NONE;
813
814 ivilayer->prop = ivilayer->pending.prop;
815
Ucan, Emre (ADITG/SW1)38fcf382015-08-20 14:13:29 +0000816 if (!ivilayer->order.dirty) {
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +0900817 continue;
818 }
819
Ucan, Emre (ADITG/SW1)38fcf382015-08-20 14:13:29 +0000820 wl_list_for_each_safe(ivisurf, next, &ivilayer->order.surface_list,
821 order.link) {
Ucan, Emre (ADITG/SW1)dfac3752015-08-28 12:58:58 +0000822 ivisurf->on_layer = NULL;
Ucan, Emre (ADITG/SW1)38fcf382015-08-20 14:13:29 +0000823 wl_list_remove(&ivisurf->order.link);
824 wl_list_init(&ivisurf->order.link);
825 ivisurf->event_mask |= IVI_NOTIFICATION_REMOVE;
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +0900826 }
827
Ucan, Emre (ADITG/SW1)38fcf382015-08-20 14:13:29 +0000828 assert(wl_list_empty(&ivilayer->order.surface_list));
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +0900829
Ucan, Emre (ADITG/SW1)38fcf382015-08-20 14:13:29 +0000830 wl_list_for_each(ivisurf, &ivilayer->pending.surface_list,
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +0900831 pending.link) {
Ucan, Emre (ADITG/SW1)38fcf382015-08-20 14:13:29 +0000832 wl_list_remove(&ivisurf->order.link);
833 wl_list_insert(&ivilayer->order.surface_list,
834 &ivisurf->order.link);
Ucan, Emre (ADITG/SW1)dfac3752015-08-28 12:58:58 +0000835 ivisurf->on_layer = ivilayer;
Ucan, Emre (ADITG/SW1)38fcf382015-08-20 14:13:29 +0000836 ivisurf->event_mask |= IVI_NOTIFICATION_ADD;
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +0900837 }
Ucan, Emre (ADITG/SW1)38fcf382015-08-20 14:13:29 +0000838
839 ivilayer->order.dirty = 0;
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +0900840 }
841}
842
843static void
844commit_screen_list(struct ivi_layout *layout)
845{
846 struct ivi_layout_screen *iviscrn = NULL;
847 struct ivi_layout_layer *ivilayer = NULL;
848 struct ivi_layout_layer *next = NULL;
849 struct ivi_layout_surface *ivisurf = NULL;
Ucan, Emre (ADITG/SW1)64635ee2015-08-28 12:59:06 +0000850 struct weston_view *tmpview = NULL;
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +0900851
Nobuhiko Tanibatafbfa8f22015-11-25 23:36:57 +0900852 /* Clear view list of layout ivi_layer */
853 wl_list_init(&layout->layout_layer.view_list.link);
854
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +0900855 wl_list_for_each(iviscrn, &layout->screen_list, link) {
Ucan, Emre (ADITG/SW1)174257b2015-08-20 14:13:30 +0000856 if (iviscrn->order.dirty) {
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +0900857 wl_list_for_each_safe(ivilayer, next,
858 &iviscrn->order.layer_list, order.link) {
Ucan, Emre (ADITG/SW1)8a223672015-08-28 12:58:55 +0000859 ivilayer->on_screen = NULL;
Ucan, Emre (ADITG/SW1)174257b2015-08-20 14:13:30 +0000860 wl_list_remove(&ivilayer->order.link);
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +0900861 wl_list_init(&ivilayer->order.link);
862 ivilayer->event_mask |= IVI_NOTIFICATION_REMOVE;
863 }
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +0900864
Ucan, Emre (ADITG/SW1)174257b2015-08-20 14:13:30 +0000865 assert(wl_list_empty(&iviscrn->order.layer_list));
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +0900866
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +0900867 wl_list_for_each(ivilayer, &iviscrn->pending.layer_list,
868 pending.link) {
Nobuhiko Tanibata77b0ee12015-11-25 23:36:46 +0900869 /* FIXME: avoid to insert order.link to multiple screens */
870 wl_list_remove(&ivilayer->order.link);
871
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +0900872 wl_list_insert(&iviscrn->order.layer_list,
873 &ivilayer->order.link);
Ucan, Emre (ADITG/SW1)8a223672015-08-28 12:58:55 +0000874 ivilayer->on_screen = iviscrn;
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +0900875 ivilayer->event_mask |= IVI_NOTIFICATION_ADD;
876 }
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +0900877
Ucan, Emre (ADITG/SW1)174257b2015-08-20 14:13:30 +0000878 iviscrn->order.dirty = 0;
879 }
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +0900880
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +0900881 wl_list_for_each(ivilayer, &iviscrn->order.layer_list, order.link) {
882 if (ivilayer->prop.visibility == false)
883 continue;
884
885 wl_list_for_each(ivisurf, &ivilayer->order.surface_list, order.link) {
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +0900886 if (ivisurf->prop.visibility == false)
887 continue;
Ucan, Emre (ADITG/SW1)64635ee2015-08-28 12:59:06 +0000888
889 tmpview = get_weston_view(ivisurf);
890 assert(tmpview != NULL);
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +0900891
892 weston_layer_entry_insert(&layout->layout_layer.view_list,
893 &tmpview->layer_link);
894
895 ivisurf->surface->output = iviscrn->output;
896 }
897 }
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +0900898 }
899}
900
901static void
902commit_transition(struct ivi_layout* layout)
903{
Dawid Gajownik74a635b2015-08-06 17:12:19 -0300904 if (wl_list_empty(&layout->pending_transition_list)) {
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +0900905 return;
906 }
907
908 wl_list_insert_list(&layout->transitions->transition_list,
909 &layout->pending_transition_list);
910
911 wl_list_init(&layout->pending_transition_list);
912
913 wl_event_source_timer_update(layout->transitions->event_source, 1);
914}
915
916static void
917send_surface_prop(struct ivi_layout_surface *ivisurf)
918{
919 wl_signal_emit(&ivisurf->property_changed, ivisurf);
920 ivisurf->event_mask = 0;
921}
922
923static void
924send_layer_prop(struct ivi_layout_layer *ivilayer)
925{
926 wl_signal_emit(&ivilayer->property_changed, ivilayer);
927 ivilayer->event_mask = 0;
928}
929
930static void
931send_prop(struct ivi_layout *layout)
932{
933 struct ivi_layout_layer *ivilayer = NULL;
934 struct ivi_layout_surface *ivisurf = NULL;
935
936 wl_list_for_each_reverse(ivilayer, &layout->layer_list, link) {
Nobuhiko Tanibata6ce3ef82015-06-22 15:32:06 +0900937 if (ivilayer->event_mask)
938 send_layer_prop(ivilayer);
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +0900939 }
940
941 wl_list_for_each_reverse(ivisurf, &layout->surface_list, link) {
Nobuhiko Tanibata6ce3ef82015-06-22 15:32:06 +0900942 if (ivisurf->event_mask)
943 send_surface_prop(ivisurf);
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +0900944 }
945}
946
947static void
948clear_surface_pending_list(struct ivi_layout_layer *ivilayer)
949{
950 struct ivi_layout_surface *surface_link = NULL;
951 struct ivi_layout_surface *surface_next = NULL;
952
953 wl_list_for_each_safe(surface_link, surface_next,
954 &ivilayer->pending.surface_list, pending.link) {
Ucan, Emre (ADITG/SW1)cf34dc22015-08-20 14:13:33 +0000955 wl_list_remove(&surface_link->pending.link);
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +0900956 wl_list_init(&surface_link->pending.link);
957 }
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +0900958}
959
960static void
961clear_surface_order_list(struct ivi_layout_layer *ivilayer)
962{
963 struct ivi_layout_surface *surface_link = NULL;
964 struct ivi_layout_surface *surface_next = NULL;
965
966 wl_list_for_each_safe(surface_link, surface_next,
967 &ivilayer->order.surface_list, order.link) {
Ucan, Emre (ADITG/SW1)cf34dc22015-08-20 14:13:33 +0000968 wl_list_remove(&surface_link->order.link);
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +0900969 wl_list_init(&surface_link->order.link);
970 }
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +0900971}
972
973static void
974layer_created(struct wl_listener *listener, void *data)
975{
976 struct ivi_layout_layer *ivilayer = data;
977
978 struct listener_layout_notification *notification =
979 container_of(listener,
980 struct listener_layout_notification,
981 listener);
982
983 struct ivi_layout_notification_callback *created_callback =
984 notification->userdata;
985
986 ((layer_create_notification_func)created_callback->callback)
987 (ivilayer, created_callback->data);
988}
989
990static void
991layer_removed(struct wl_listener *listener, void *data)
992{
993 struct ivi_layout_layer *ivilayer = data;
994
995 struct listener_layout_notification *notification =
996 container_of(listener,
997 struct listener_layout_notification,
998 listener);
999
1000 struct ivi_layout_notification_callback *removed_callback =
1001 notification->userdata;
1002
1003 ((layer_remove_notification_func)removed_callback->callback)
1004 (ivilayer, removed_callback->data);
1005}
1006
1007static void
1008layer_prop_changed(struct wl_listener *listener, void *data)
1009{
1010 struct ivi_layout_layer *ivilayer = data;
1011
1012 struct listener_layout_notification *layout_listener =
1013 container_of(listener,
1014 struct listener_layout_notification,
1015 listener);
1016
1017 struct ivi_layout_notification_callback *prop_callback =
1018 layout_listener->userdata;
1019
1020 ((layer_property_notification_func)prop_callback->callback)
1021 (ivilayer, &ivilayer->prop, ivilayer->event_mask, prop_callback->data);
1022}
1023
1024static void
1025surface_created(struct wl_listener *listener, void *data)
1026{
1027 struct ivi_layout_surface *ivisurface = data;
1028
1029 struct listener_layout_notification *notification =
1030 container_of(listener,
1031 struct listener_layout_notification,
1032 listener);
1033
1034 struct ivi_layout_notification_callback *created_callback =
1035 notification->userdata;
1036
1037 ((surface_create_notification_func)created_callback->callback)
1038 (ivisurface, created_callback->data);
1039}
1040
1041static void
1042surface_removed(struct wl_listener *listener, void *data)
1043{
1044 struct ivi_layout_surface *ivisurface = data;
1045
1046 struct listener_layout_notification *notification =
1047 container_of(listener,
1048 struct listener_layout_notification,
1049 listener);
1050
1051 struct ivi_layout_notification_callback *removed_callback =
1052 notification->userdata;
1053
1054 ((surface_remove_notification_func)removed_callback->callback)
1055 (ivisurface, removed_callback->data);
1056}
1057
1058static void
1059surface_prop_changed(struct wl_listener *listener, void *data)
1060{
1061 struct ivi_layout_surface *ivisurf = data;
1062
1063 struct listener_layout_notification *layout_listener =
1064 container_of(listener,
1065 struct listener_layout_notification,
1066 listener);
1067
1068 struct ivi_layout_notification_callback *prop_callback =
1069 layout_listener->userdata;
1070
1071 ((surface_property_notification_func)prop_callback->callback)
1072 (ivisurf, &ivisurf->prop, ivisurf->event_mask, prop_callback->data);
1073
1074 ivisurf->event_mask = 0;
1075}
1076
1077static void
1078surface_configure_changed(struct wl_listener *listener,
1079 void *data)
1080{
1081 struct ivi_layout_surface *ivisurface = data;
1082
1083 struct listener_layout_notification *notification =
1084 container_of(listener,
1085 struct listener_layout_notification,
1086 listener);
1087
1088 struct ivi_layout_notification_callback *configure_changed_callback =
1089 notification->userdata;
1090
1091 ((surface_configure_notification_func)configure_changed_callback->callback)
1092 (ivisurface, configure_changed_callback->data);
1093}
1094
1095static int32_t
1096add_notification(struct wl_signal *signal,
1097 wl_notify_func_t callback,
1098 void *userdata)
1099{
1100 struct listener_layout_notification *notification = NULL;
1101
1102 notification = malloc(sizeof *notification);
1103 if (notification == NULL) {
1104 weston_log("fails to allocate memory\n");
1105 free(userdata);
1106 return IVI_FAILED;
1107 }
1108
1109 notification->listener.notify = callback;
1110 notification->userdata = userdata;
1111
1112 wl_signal_add(signal, &notification->listener);
1113
1114 return IVI_SUCCEEDED;
1115}
1116
1117static void
1118remove_notification(struct wl_list *listener_list, void *callback, void *userdata)
1119{
1120 struct wl_listener *listener = NULL;
1121 struct wl_listener *next = NULL;
1122
1123 wl_list_for_each_safe(listener, next, listener_list, link) {
1124 struct listener_layout_notification *notification =
1125 container_of(listener,
1126 struct listener_layout_notification,
1127 listener);
1128
1129 struct ivi_layout_notification_callback *notification_callback =
1130 notification->userdata;
1131
1132 if ((notification_callback->callback != callback) ||
1133 (notification_callback->data != userdata)) {
1134 continue;
1135 }
1136
Ucan, Emre (ADITG/SW1)cf34dc22015-08-20 14:13:33 +00001137 wl_list_remove(&listener->link);
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +09001138
1139 free(notification->userdata);
1140 free(notification);
1141 }
1142}
1143
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +09001144/**
1145 * Exported APIs of ivi-layout library are implemented from here.
1146 * Brief of APIs is described in ivi-layout-export.h.
1147 */
Nobuhiko Tanibataee8e5832014-12-15 13:25:39 +09001148static int32_t
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +09001149ivi_layout_add_notification_create_layer(layer_create_notification_func callback,
1150 void *userdata)
1151{
1152 struct ivi_layout *layout = get_instance();
1153 struct ivi_layout_notification_callback *created_callback = NULL;
1154
1155 if (callback == NULL) {
1156 weston_log("ivi_layout_add_notification_create_layer: invalid argument\n");
1157 return IVI_FAILED;
1158 }
1159
1160 created_callback = malloc(sizeof *created_callback);
1161 if (created_callback == NULL) {
1162 weston_log("fails to allocate memory\n");
1163 return IVI_FAILED;
1164 }
1165
1166 created_callback->callback = callback;
1167 created_callback->data = userdata;
1168
1169 return add_notification(&layout->layer_notification.created,
1170 layer_created,
1171 created_callback);
1172}
1173
Nobuhiko Tanibataee8e5832014-12-15 13:25:39 +09001174static void
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +09001175ivi_layout_remove_notification_create_layer(layer_create_notification_func callback,
1176 void *userdata)
1177{
1178 struct ivi_layout *layout = get_instance();
1179 remove_notification(&layout->layer_notification.created.listener_list, callback, userdata);
1180}
1181
Nobuhiko Tanibataee8e5832014-12-15 13:25:39 +09001182static int32_t
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +09001183ivi_layout_add_notification_remove_layer(layer_remove_notification_func callback,
1184 void *userdata)
1185{
1186 struct ivi_layout *layout = get_instance();
1187 struct ivi_layout_notification_callback *removed_callback = NULL;
1188
1189 if (callback == NULL) {
1190 weston_log("ivi_layout_add_notification_remove_layer: invalid argument\n");
1191 return IVI_FAILED;
1192 }
1193
1194 removed_callback = malloc(sizeof *removed_callback);
1195 if (removed_callback == NULL) {
1196 weston_log("fails to allocate memory\n");
1197 return IVI_FAILED;
1198 }
1199
1200 removed_callback->callback = callback;
1201 removed_callback->data = userdata;
1202 return add_notification(&layout->layer_notification.removed,
1203 layer_removed,
1204 removed_callback);
1205}
1206
Nobuhiko Tanibataee8e5832014-12-15 13:25:39 +09001207static void
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +09001208ivi_layout_remove_notification_remove_layer(layer_remove_notification_func callback,
1209 void *userdata)
1210{
1211 struct ivi_layout *layout = get_instance();
1212 remove_notification(&layout->layer_notification.removed.listener_list, callback, userdata);
1213}
1214
Nobuhiko Tanibataee8e5832014-12-15 13:25:39 +09001215static int32_t
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +09001216ivi_layout_add_notification_create_surface(surface_create_notification_func callback,
1217 void *userdata)
1218{
1219 struct ivi_layout *layout = get_instance();
1220 struct ivi_layout_notification_callback *created_callback = NULL;
1221
1222 if (callback == NULL) {
1223 weston_log("ivi_layout_add_notification_create_surface: invalid argument\n");
1224 return IVI_FAILED;
1225 }
1226
1227 created_callback = malloc(sizeof *created_callback);
1228 if (created_callback == NULL) {
1229 weston_log("fails to allocate memory\n");
1230 return IVI_FAILED;
1231 }
1232
1233 created_callback->callback = callback;
1234 created_callback->data = userdata;
1235
1236 return add_notification(&layout->surface_notification.created,
1237 surface_created,
1238 created_callback);
1239}
1240
Nobuhiko Tanibataee8e5832014-12-15 13:25:39 +09001241static void
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +09001242ivi_layout_remove_notification_create_surface(surface_create_notification_func callback,
1243 void *userdata)
1244{
1245 struct ivi_layout *layout = get_instance();
1246 remove_notification(&layout->surface_notification.created.listener_list, callback, userdata);
1247}
1248
Nobuhiko Tanibataee8e5832014-12-15 13:25:39 +09001249static int32_t
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +09001250ivi_layout_add_notification_remove_surface(surface_remove_notification_func callback,
1251 void *userdata)
1252{
1253 struct ivi_layout *layout = get_instance();
1254 struct ivi_layout_notification_callback *removed_callback = NULL;
1255
1256 if (callback == NULL) {
1257 weston_log("ivi_layout_add_notification_remove_surface: invalid argument\n");
1258 return IVI_FAILED;
1259 }
1260
1261 removed_callback = malloc(sizeof *removed_callback);
1262 if (removed_callback == NULL) {
1263 weston_log("fails to allocate memory\n");
1264 return IVI_FAILED;
1265 }
1266
1267 removed_callback->callback = callback;
1268 removed_callback->data = userdata;
1269
1270 return add_notification(&layout->surface_notification.removed,
1271 surface_removed,
1272 removed_callback);
1273}
1274
Nobuhiko Tanibataee8e5832014-12-15 13:25:39 +09001275static void
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +09001276ivi_layout_remove_notification_remove_surface(surface_remove_notification_func callback,
1277 void *userdata)
1278{
1279 struct ivi_layout *layout = get_instance();
1280 remove_notification(&layout->surface_notification.removed.listener_list, callback, userdata);
1281}
1282
Nobuhiko Tanibataee8e5832014-12-15 13:25:39 +09001283static int32_t
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +09001284ivi_layout_add_notification_configure_surface(surface_configure_notification_func callback,
1285 void *userdata)
1286{
1287 struct ivi_layout *layout = get_instance();
1288 struct ivi_layout_notification_callback *configure_changed_callback = NULL;
1289 if (callback == NULL) {
1290 weston_log("ivi_layout_add_notification_configure_surface: invalid argument\n");
1291 return IVI_FAILED;
1292 }
1293
1294 configure_changed_callback = malloc(sizeof *configure_changed_callback);
1295 if (configure_changed_callback == NULL) {
1296 weston_log("fails to allocate memory\n");
1297 return IVI_FAILED;
1298 }
1299
1300 configure_changed_callback->callback = callback;
1301 configure_changed_callback->data = userdata;
1302
1303 return add_notification(&layout->surface_notification.configure_changed,
1304 surface_configure_changed,
1305 configure_changed_callback);
1306}
1307
Nobuhiko Tanibataee8e5832014-12-15 13:25:39 +09001308static void
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +09001309ivi_layout_remove_notification_configure_surface(surface_configure_notification_func callback,
1310 void *userdata)
1311{
1312 struct ivi_layout *layout = get_instance();
1313 remove_notification(&layout->surface_notification.configure_changed.listener_list, callback, userdata);
1314}
1315
Nobuhiko Tanibataee8e5832014-12-15 13:25:39 +09001316uint32_t
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +09001317ivi_layout_get_id_of_surface(struct ivi_layout_surface *ivisurf)
1318{
1319 return ivisurf->id_surface;
1320}
1321
Nobuhiko Tanibataee8e5832014-12-15 13:25:39 +09001322static uint32_t
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +09001323ivi_layout_get_id_of_layer(struct ivi_layout_layer *ivilayer)
1324{
1325 return ivilayer->id_layer;
1326}
1327
Nobuhiko Tanibata4d0116e2015-06-22 15:31:57 +09001328static uint32_t
1329ivi_layout_get_id_of_screen(struct ivi_layout_screen *iviscrn)
1330{
1331 return iviscrn->id_screen;
1332}
1333
Nobuhiko Tanibataee8e5832014-12-15 13:25:39 +09001334static struct ivi_layout_layer *
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +09001335ivi_layout_get_layer_from_id(uint32_t id_layer)
1336{
1337 struct ivi_layout *layout = get_instance();
1338 struct ivi_layout_layer *ivilayer = NULL;
1339
1340 wl_list_for_each(ivilayer, &layout->layer_list, link) {
1341 if (ivilayer->id_layer == id_layer) {
1342 return ivilayer;
1343 }
1344 }
1345
1346 return NULL;
1347}
1348
Nobuhiko Tanibataee8e5832014-12-15 13:25:39 +09001349struct ivi_layout_surface *
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +09001350ivi_layout_get_surface_from_id(uint32_t id_surface)
1351{
1352 struct ivi_layout *layout = get_instance();
1353 struct ivi_layout_surface *ivisurf = NULL;
1354
1355 wl_list_for_each(ivisurf, &layout->surface_list, link) {
1356 if (ivisurf->id_surface == id_surface) {
1357 return ivisurf;
1358 }
1359 }
1360
1361 return NULL;
1362}
1363
Nobuhiko Tanibataee8e5832014-12-15 13:25:39 +09001364static struct ivi_layout_screen *
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +09001365ivi_layout_get_screen_from_id(uint32_t id_screen)
1366{
1367 struct ivi_layout *layout = get_instance();
1368 struct ivi_layout_screen *iviscrn = NULL;
1369
1370 wl_list_for_each(iviscrn, &layout->screen_list, link) {
Nobuhiko Tanibata3e710d12015-11-25 23:36:09 +09001371 if (iviscrn->id_screen == id_screen)
1372 return iviscrn;
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +09001373 }
1374
1375 return NULL;
1376}
1377
Nobuhiko Tanibataee8e5832014-12-15 13:25:39 +09001378static int32_t
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +09001379ivi_layout_get_screen_resolution(struct ivi_layout_screen *iviscrn,
1380 int32_t *pWidth, int32_t *pHeight)
1381{
1382 struct weston_output *output = NULL;
1383
Nobuhiko Tanibata0c217cb2015-06-22 15:30:32 +09001384 if (iviscrn == NULL || pWidth == NULL || pHeight == NULL) {
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +09001385 weston_log("ivi_layout_get_screen_resolution: invalid argument\n");
1386 return IVI_FAILED;
1387 }
1388
1389 output = iviscrn->output;
1390 *pWidth = output->current_mode->width;
1391 *pHeight = output->current_mode->height;
1392
1393 return IVI_SUCCEEDED;
1394}
1395
Nobuhiko Tanibataee8e5832014-12-15 13:25:39 +09001396static int32_t
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +09001397ivi_layout_surface_add_notification(struct ivi_layout_surface *ivisurf,
1398 surface_property_notification_func callback,
1399 void *userdata)
1400{
1401 struct listener_layout_notification* notification = NULL;
1402 struct ivi_layout_notification_callback *prop_callback = NULL;
1403
1404 if (ivisurf == NULL || callback == NULL) {
1405 weston_log("ivi_layout_surface_add_notification: invalid argument\n");
1406 return IVI_FAILED;
1407 }
1408
1409 notification = malloc(sizeof *notification);
1410 if (notification == NULL) {
1411 weston_log("fails to allocate memory\n");
1412 return IVI_FAILED;
1413 }
1414
1415 prop_callback = malloc(sizeof *prop_callback);
1416 if (prop_callback == NULL) {
1417 weston_log("fails to allocate memory\n");
Lucas Tanure193c7a52015-09-19 18:24:58 -03001418 free(notification);
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +09001419 return IVI_FAILED;
1420 }
1421
1422 prop_callback->callback = callback;
1423 prop_callback->data = userdata;
1424
1425 notification->listener.notify = surface_prop_changed;
1426 notification->userdata = prop_callback;
1427
1428 wl_signal_add(&ivisurf->property_changed, &notification->listener);
1429
1430 return IVI_SUCCEEDED;
1431}
1432
Nobuhiko Tanibataee8e5832014-12-15 13:25:39 +09001433static const struct ivi_layout_layer_properties *
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +09001434ivi_layout_get_properties_of_layer(struct ivi_layout_layer *ivilayer)
1435{
1436 if (ivilayer == NULL) {
1437 weston_log("ivi_layout_get_properties_of_layer: invalid argument\n");
1438 return NULL;
1439 }
1440
1441 return &ivilayer->prop;
1442}
1443
Nobuhiko Tanibataee8e5832014-12-15 13:25:39 +09001444static int32_t
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +09001445ivi_layout_get_screens(int32_t *pLength, struct ivi_layout_screen ***ppArray)
1446{
1447 struct ivi_layout *layout = get_instance();
1448 struct ivi_layout_screen *iviscrn = NULL;
1449 int32_t length = 0;
1450 int32_t n = 0;
1451
1452 if (pLength == NULL || ppArray == NULL) {
1453 weston_log("ivi_layout_get_screens: invalid argument\n");
1454 return IVI_FAILED;
1455 }
1456
1457 length = wl_list_length(&layout->screen_list);
1458
Dawid Gajownik74a635b2015-08-06 17:12:19 -03001459 if (length != 0) {
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +09001460 /* the Array must be free by module which called this function */
1461 *ppArray = calloc(length, sizeof(struct ivi_layout_screen *));
1462 if (*ppArray == NULL) {
1463 weston_log("fails to allocate memory\n");
1464 return IVI_FAILED;
1465 }
1466
1467 wl_list_for_each(iviscrn, &layout->screen_list, link) {
1468 (*ppArray)[n++] = iviscrn;
1469 }
1470 }
1471
1472 *pLength = length;
1473
1474 return IVI_SUCCEEDED;
1475}
1476
Nobuhiko Tanibataee8e5832014-12-15 13:25:39 +09001477static int32_t
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +09001478ivi_layout_get_screens_under_layer(struct ivi_layout_layer *ivilayer,
1479 int32_t *pLength,
1480 struct ivi_layout_screen ***ppArray)
1481{
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +09001482 int32_t length = 0;
1483 int32_t n = 0;
1484
1485 if (ivilayer == NULL || pLength == NULL || ppArray == NULL) {
1486 weston_log("ivi_layout_get_screens_under_layer: invalid argument\n");
1487 return IVI_FAILED;
1488 }
1489
Ucan, Emre (ADITG/SW1)8a223672015-08-28 12:58:55 +00001490 if (ivilayer->on_screen != NULL)
1491 length = 1;
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +09001492
Dawid Gajownik74a635b2015-08-06 17:12:19 -03001493 if (length != 0) {
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +09001494 /* the Array must be free by module which called this function */
1495 *ppArray = calloc(length, sizeof(struct ivi_layout_screen *));
1496 if (*ppArray == NULL) {
1497 weston_log("fails to allocate memory\n");
1498 return IVI_FAILED;
1499 }
1500
Ucan, Emre (ADITG/SW1)8a223672015-08-28 12:58:55 +00001501 (*ppArray)[n++] = ivilayer->on_screen;
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +09001502 }
1503
1504 *pLength = length;
1505
1506 return IVI_SUCCEEDED;
1507}
1508
Nobuhiko Tanibataee8e5832014-12-15 13:25:39 +09001509static int32_t
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +09001510ivi_layout_get_layers(int32_t *pLength, struct ivi_layout_layer ***ppArray)
1511{
1512 struct ivi_layout *layout = get_instance();
1513 struct ivi_layout_layer *ivilayer = NULL;
1514 int32_t length = 0;
1515 int32_t n = 0;
1516
1517 if (pLength == NULL || ppArray == NULL) {
1518 weston_log("ivi_layout_get_layers: invalid argument\n");
1519 return IVI_FAILED;
1520 }
1521
1522 length = wl_list_length(&layout->layer_list);
1523
Dawid Gajownik74a635b2015-08-06 17:12:19 -03001524 if (length != 0) {
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +09001525 /* the Array must be free by module which called this function */
1526 *ppArray = calloc(length, sizeof(struct ivi_layout_layer *));
1527 if (*ppArray == NULL) {
1528 weston_log("fails to allocate memory\n");
1529 return IVI_FAILED;
1530 }
1531
1532 wl_list_for_each(ivilayer, &layout->layer_list, link) {
1533 (*ppArray)[n++] = ivilayer;
1534 }
1535 }
1536
1537 *pLength = length;
1538
1539 return IVI_SUCCEEDED;
1540}
1541
Nobuhiko Tanibataee8e5832014-12-15 13:25:39 +09001542static int32_t
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +09001543ivi_layout_get_layers_on_screen(struct ivi_layout_screen *iviscrn,
1544 int32_t *pLength,
1545 struct ivi_layout_layer ***ppArray)
1546{
1547 struct ivi_layout_layer *ivilayer = NULL;
1548 int32_t length = 0;
1549 int32_t n = 0;
1550
1551 if (iviscrn == NULL || pLength == NULL || ppArray == NULL) {
1552 weston_log("ivi_layout_get_layers_on_screen: invalid argument\n");
1553 return IVI_FAILED;
1554 }
1555
1556 length = wl_list_length(&iviscrn->order.layer_list);
1557
Dawid Gajownik74a635b2015-08-06 17:12:19 -03001558 if (length != 0) {
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +09001559 /* the Array must be free by module which called this function */
1560 *ppArray = calloc(length, sizeof(struct ivi_layout_layer *));
1561 if (*ppArray == NULL) {
1562 weston_log("fails to allocate memory\n");
1563 return IVI_FAILED;
1564 }
1565
Nobuhiko Tanibatae2b82142015-06-22 15:30:19 +09001566 wl_list_for_each(ivilayer, &iviscrn->order.layer_list, order.link) {
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +09001567 (*ppArray)[n++] = ivilayer;
1568 }
1569 }
1570
1571 *pLength = length;
1572
1573 return IVI_SUCCEEDED;
1574}
1575
Nobuhiko Tanibataee8e5832014-12-15 13:25:39 +09001576static int32_t
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +09001577ivi_layout_get_layers_under_surface(struct ivi_layout_surface *ivisurf,
1578 int32_t *pLength,
1579 struct ivi_layout_layer ***ppArray)
1580{
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +09001581 int32_t length = 0;
1582 int32_t n = 0;
1583
1584 if (ivisurf == NULL || pLength == NULL || ppArray == NULL) {
1585 weston_log("ivi_layout_getLayers: invalid argument\n");
1586 return IVI_FAILED;
1587 }
1588
Ucan, Emre (ADITG/SW1)dfac3752015-08-28 12:58:58 +00001589 if (ivisurf->on_layer != NULL) {
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +09001590 /* the Array must be free by module which called this function */
Ucan, Emre (ADITG/SW1)dfac3752015-08-28 12:58:58 +00001591 length = 1;
1592 *ppArray = calloc(length, sizeof(struct ivi_layout_screen *));
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +09001593 if (*ppArray == NULL) {
1594 weston_log("fails to allocate memory\n");
1595 return IVI_FAILED;
1596 }
1597
Ucan, Emre (ADITG/SW1)dfac3752015-08-28 12:58:58 +00001598 (*ppArray)[n++] = ivisurf->on_layer;
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +09001599 }
1600
1601 *pLength = length;
1602
1603 return IVI_SUCCEEDED;
1604}
1605
Nobuhiko Tanibataee8e5832014-12-15 13:25:39 +09001606static
1607int32_t
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +09001608ivi_layout_get_surfaces(int32_t *pLength, struct ivi_layout_surface ***ppArray)
1609{
1610 struct ivi_layout *layout = get_instance();
1611 struct ivi_layout_surface *ivisurf = NULL;
1612 int32_t length = 0;
1613 int32_t n = 0;
1614
1615 if (pLength == NULL || ppArray == NULL) {
1616 weston_log("ivi_layout_get_surfaces: invalid argument\n");
1617 return IVI_FAILED;
1618 }
1619
1620 length = wl_list_length(&layout->surface_list);
1621
Dawid Gajownik74a635b2015-08-06 17:12:19 -03001622 if (length != 0) {
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +09001623 /* the Array must be free by module which called this function */
1624 *ppArray = calloc(length, sizeof(struct ivi_layout_surface *));
1625 if (*ppArray == NULL) {
1626 weston_log("fails to allocate memory\n");
1627 return IVI_FAILED;
1628 }
1629
1630 wl_list_for_each(ivisurf, &layout->surface_list, link) {
1631 (*ppArray)[n++] = ivisurf;
1632 }
1633 }
1634
1635 *pLength = length;
1636
1637 return IVI_SUCCEEDED;
1638}
1639
Nobuhiko Tanibataee8e5832014-12-15 13:25:39 +09001640static int32_t
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +09001641ivi_layout_get_surfaces_on_layer(struct ivi_layout_layer *ivilayer,
1642 int32_t *pLength,
1643 struct ivi_layout_surface ***ppArray)
1644{
1645 struct ivi_layout_surface *ivisurf = NULL;
1646 int32_t length = 0;
1647 int32_t n = 0;
1648
1649 if (ivilayer == NULL || pLength == NULL || ppArray == NULL) {
1650 weston_log("ivi_layout_getSurfaceIDsOnLayer: invalid argument\n");
1651 return IVI_FAILED;
1652 }
1653
1654 length = wl_list_length(&ivilayer->order.surface_list);
1655
1656 if (length != 0) {
1657 /* the Array must be free by module which called this function */
1658 *ppArray = calloc(length, sizeof(struct ivi_layout_surface *));
1659 if (*ppArray == NULL) {
1660 weston_log("fails to allocate memory\n");
1661 return IVI_FAILED;
1662 }
1663
1664 wl_list_for_each(ivisurf, &ivilayer->order.surface_list, order.link) {
1665 (*ppArray)[n++] = ivisurf;
1666 }
1667 }
1668
1669 *pLength = length;
1670
1671 return IVI_SUCCEEDED;
1672}
1673
Nobuhiko Tanibataee8e5832014-12-15 13:25:39 +09001674static struct ivi_layout_layer *
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +09001675ivi_layout_layer_create_with_dimension(uint32_t id_layer,
1676 int32_t width, int32_t height)
1677{
1678 struct ivi_layout *layout = get_instance();
1679 struct ivi_layout_layer *ivilayer = NULL;
1680
1681 ivilayer = get_layer(&layout->layer_list, id_layer);
1682 if (ivilayer != NULL) {
1683 weston_log("id_layer is already created\n");
Nobuhiko Tanibata4b601e12015-06-22 15:31:16 +09001684 ++ivilayer->ref_count;
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +09001685 return ivilayer;
1686 }
1687
1688 ivilayer = calloc(1, sizeof *ivilayer);
1689 if (ivilayer == NULL) {
1690 weston_log("fails to allocate memory\n");
1691 return NULL;
1692 }
1693
Nobuhiko Tanibata4b601e12015-06-22 15:31:16 +09001694 ivilayer->ref_count = 1;
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +09001695 wl_signal_init(&ivilayer->property_changed);
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +09001696 ivilayer->layout = layout;
1697 ivilayer->id_layer = id_layer;
1698
1699 init_layer_properties(&ivilayer->prop, width, height);
1700 ivilayer->event_mask = 0;
1701
1702 wl_list_init(&ivilayer->pending.surface_list);
1703 wl_list_init(&ivilayer->pending.link);
1704 ivilayer->pending.prop = ivilayer->prop;
1705
1706 wl_list_init(&ivilayer->order.surface_list);
1707 wl_list_init(&ivilayer->order.link);
1708
1709 wl_list_insert(&layout->layer_list, &ivilayer->link);
1710
1711 wl_signal_emit(&layout->layer_notification.created, ivilayer);
1712
1713 return ivilayer;
1714}
1715
Nobuhiko Tanibataee8e5832014-12-15 13:25:39 +09001716static void
Nobuhiko Tanibataef6c7862014-12-15 13:20:44 +09001717ivi_layout_layer_remove_notification(struct ivi_layout_layer *ivilayer)
1718{
1719 if (ivilayer == NULL) {
1720 weston_log("ivi_layout_layer_remove_notification: invalid argument\n");
1721 return;
1722 }
1723
1724 remove_all_notification(&ivilayer->property_changed.listener_list);
1725}
1726
Nobuhiko Tanibataee8e5832014-12-15 13:25:39 +09001727static void
Nobuhiko Tanibatadb8efd12015-06-22 15:31:39 +09001728ivi_layout_layer_remove_notification_by_callback(struct ivi_layout_layer *ivilayer,
1729 layer_property_notification_func callback,
1730 void *userdata)
1731{
1732 if (ivilayer == NULL) {
1733 weston_log("ivi_layout_layer_remove_notification_by_callback: invalid argument\n");
1734 return;
1735 }
1736
1737 remove_notification(&ivilayer->property_changed.listener_list, callback, userdata);
1738}
1739
1740static void
Nobuhiko Tanibata3aa8aed2015-06-22 15:32:23 +09001741ivi_layout_layer_destroy(struct ivi_layout_layer *ivilayer)
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +09001742{
1743 struct ivi_layout *layout = get_instance();
1744
1745 if (ivilayer == NULL) {
1746 weston_log("ivi_layout_layer_remove: invalid argument\n");
1747 return;
1748 }
1749
Nobuhiko Tanibata4b601e12015-06-22 15:31:16 +09001750 if (--ivilayer->ref_count > 0)
1751 return;
1752
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +09001753 wl_signal_emit(&layout->layer_notification.removed, ivilayer);
1754
1755 clear_surface_pending_list(ivilayer);
1756 clear_surface_order_list(ivilayer);
1757
Ucan, Emre (ADITG/SW1)cf34dc22015-08-20 14:13:33 +00001758 wl_list_remove(&ivilayer->pending.link);
1759 wl_list_remove(&ivilayer->order.link);
1760 wl_list_remove(&ivilayer->link);
1761
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +09001762 ivi_layout_layer_remove_notification(ivilayer);
1763
1764 free(ivilayer);
1765}
1766
Nobuhiko Tanibataee8e5832014-12-15 13:25:39 +09001767int32_t
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +09001768ivi_layout_layer_set_visibility(struct ivi_layout_layer *ivilayer,
1769 bool newVisibility)
1770{
1771 struct ivi_layout_layer_properties *prop = NULL;
1772
1773 if (ivilayer == NULL) {
1774 weston_log("ivi_layout_layer_set_visibility: invalid argument\n");
1775 return IVI_FAILED;
1776 }
1777
1778 prop = &ivilayer->pending.prop;
1779 prop->visibility = newVisibility;
1780
Nobuhiko Tanibata5d4a3232015-06-22 15:32:14 +09001781 if (ivilayer->prop.visibility != newVisibility)
1782 ivilayer->event_mask |= IVI_NOTIFICATION_VISIBILITY;
1783 else
1784 ivilayer->event_mask &= ~IVI_NOTIFICATION_VISIBILITY;
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +09001785
1786 return IVI_SUCCEEDED;
1787}
1788
Nobuhiko Tanibataee8e5832014-12-15 13:25:39 +09001789static bool
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +09001790ivi_layout_layer_get_visibility(struct ivi_layout_layer *ivilayer)
1791{
1792 if (ivilayer == NULL) {
1793 weston_log("ivi_layout_layer_get_visibility: invalid argument\n");
1794 return false;
1795 }
1796
1797 return ivilayer->prop.visibility;
1798}
1799
Nobuhiko Tanibataee8e5832014-12-15 13:25:39 +09001800int32_t
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +09001801ivi_layout_layer_set_opacity(struct ivi_layout_layer *ivilayer,
1802 wl_fixed_t opacity)
1803{
1804 struct ivi_layout_layer_properties *prop = NULL;
1805
Nobuhiko Tanibata7bbacc62015-06-22 15:30:09 +09001806 if (ivilayer == NULL ||
1807 opacity < wl_fixed_from_double(0.0) ||
1808 wl_fixed_from_double(1.0) < opacity) {
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +09001809 weston_log("ivi_layout_layer_set_opacity: invalid argument\n");
1810 return IVI_FAILED;
1811 }
1812
1813 prop = &ivilayer->pending.prop;
1814 prop->opacity = opacity;
1815
Nobuhiko Tanibata5d4a3232015-06-22 15:32:14 +09001816 if (ivilayer->prop.opacity != opacity)
1817 ivilayer->event_mask |= IVI_NOTIFICATION_OPACITY;
1818 else
1819 ivilayer->event_mask &= ~IVI_NOTIFICATION_OPACITY;
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +09001820
1821 return IVI_SUCCEEDED;
1822}
1823
Nobuhiko Tanibataee8e5832014-12-15 13:25:39 +09001824wl_fixed_t
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +09001825ivi_layout_layer_get_opacity(struct ivi_layout_layer *ivilayer)
1826{
1827 if (ivilayer == NULL) {
1828 weston_log("ivi_layout_layer_get_opacity: invalid argument\n");
1829 return wl_fixed_from_double(0.0);
1830 }
1831
1832 return ivilayer->prop.opacity;
1833}
1834
Nobuhiko Tanibataee8e5832014-12-15 13:25:39 +09001835static int32_t
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +09001836ivi_layout_layer_set_source_rectangle(struct ivi_layout_layer *ivilayer,
1837 int32_t x, int32_t y,
1838 int32_t width, int32_t height)
1839{
1840 struct ivi_layout_layer_properties *prop = NULL;
1841
1842 if (ivilayer == NULL) {
1843 weston_log("ivi_layout_layer_set_source_rectangle: invalid argument\n");
1844 return IVI_FAILED;
1845 }
1846
1847 prop = &ivilayer->pending.prop;
1848 prop->source_x = x;
1849 prop->source_y = y;
1850 prop->source_width = width;
1851 prop->source_height = height;
1852
Nobuhiko Tanibata5d4a3232015-06-22 15:32:14 +09001853 if (ivilayer->prop.source_x != x || ivilayer->prop.source_y != y ||
1854 ivilayer->prop.source_width != width ||
1855 ivilayer->prop.source_height != height)
1856 ivilayer->event_mask |= IVI_NOTIFICATION_SOURCE_RECT;
1857 else
1858 ivilayer->event_mask &= ~IVI_NOTIFICATION_SOURCE_RECT;
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +09001859
1860 return IVI_SUCCEEDED;
1861}
1862
Nobuhiko Tanibataee8e5832014-12-15 13:25:39 +09001863static int32_t
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +09001864ivi_layout_layer_set_destination_rectangle(struct ivi_layout_layer *ivilayer,
1865 int32_t x, int32_t y,
1866 int32_t width, int32_t height)
1867{
1868 struct ivi_layout_layer_properties *prop = NULL;
1869
1870 if (ivilayer == NULL) {
1871 weston_log("ivi_layout_layer_set_destination_rectangle: invalid argument\n");
1872 return IVI_FAILED;
1873 }
1874
1875 prop = &ivilayer->pending.prop;
1876 prop->dest_x = x;
1877 prop->dest_y = y;
1878 prop->dest_width = width;
1879 prop->dest_height = height;
1880
Nobuhiko Tanibata5d4a3232015-06-22 15:32:14 +09001881 if (ivilayer->prop.dest_x != x || ivilayer->prop.dest_y != y ||
1882 ivilayer->prop.dest_width != width ||
1883 ivilayer->prop.dest_height != height)
1884 ivilayer->event_mask |= IVI_NOTIFICATION_DEST_RECT;
1885 else
1886 ivilayer->event_mask &= ~IVI_NOTIFICATION_DEST_RECT;
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +09001887
1888 return IVI_SUCCEEDED;
1889}
1890
Nobuhiko Tanibataee8e5832014-12-15 13:25:39 +09001891static int32_t
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +09001892ivi_layout_layer_get_dimension(struct ivi_layout_layer *ivilayer,
1893 int32_t *dest_width, int32_t *dest_height)
1894{
1895 if (ivilayer == NULL || dest_width == NULL || dest_height == NULL) {
1896 weston_log("ivi_layout_layer_get_dimension: invalid argument\n");
1897 return IVI_FAILED;
1898 }
1899
1900 *dest_width = ivilayer->prop.dest_width;
1901 *dest_height = ivilayer->prop.dest_height;
1902
1903 return IVI_SUCCEEDED;
1904}
1905
Nobuhiko Tanibataee8e5832014-12-15 13:25:39 +09001906static int32_t
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +09001907ivi_layout_layer_set_dimension(struct ivi_layout_layer *ivilayer,
1908 int32_t dest_width, int32_t dest_height)
1909{
1910 struct ivi_layout_layer_properties *prop = NULL;
1911
1912 if (ivilayer == NULL) {
1913 weston_log("ivi_layout_layer_set_dimension: invalid argument\n");
1914 return IVI_FAILED;
1915 }
1916
1917 prop = &ivilayer->pending.prop;
1918
1919 prop->dest_width = dest_width;
1920 prop->dest_height = dest_height;
1921
Nobuhiko Tanibata5d4a3232015-06-22 15:32:14 +09001922 if (ivilayer->prop.dest_width != dest_width ||
1923 ivilayer->prop.dest_height != dest_height)
1924 ivilayer->event_mask |= IVI_NOTIFICATION_DIMENSION;
1925 else
1926 ivilayer->event_mask &= ~IVI_NOTIFICATION_DIMENSION;
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +09001927
1928 return IVI_SUCCEEDED;
1929}
1930
Nobuhiko Tanibataee8e5832014-12-15 13:25:39 +09001931int32_t
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +09001932ivi_layout_layer_get_position(struct ivi_layout_layer *ivilayer,
1933 int32_t *dest_x, int32_t *dest_y)
1934{
1935 if (ivilayer == NULL || dest_x == NULL || dest_y == NULL) {
1936 weston_log("ivi_layout_layer_get_position: invalid argument\n");
1937 return IVI_FAILED;
1938 }
1939
1940 *dest_x = ivilayer->prop.dest_x;
1941 *dest_y = ivilayer->prop.dest_y;
1942
1943 return IVI_SUCCEEDED;
1944}
1945
Nobuhiko Tanibataee8e5832014-12-15 13:25:39 +09001946int32_t
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +09001947ivi_layout_layer_set_position(struct ivi_layout_layer *ivilayer,
1948 int32_t dest_x, int32_t dest_y)
1949{
1950 struct ivi_layout_layer_properties *prop = NULL;
1951
1952 if (ivilayer == NULL) {
1953 weston_log("ivi_layout_layer_set_position: invalid argument\n");
1954 return IVI_FAILED;
1955 }
1956
1957 prop = &ivilayer->pending.prop;
1958 prop->dest_x = dest_x;
1959 prop->dest_y = dest_y;
1960
Nobuhiko Tanibata5d4a3232015-06-22 15:32:14 +09001961 if (ivilayer->prop.dest_x != dest_x || ivilayer->prop.dest_y != dest_y)
1962 ivilayer->event_mask |= IVI_NOTIFICATION_POSITION;
1963 else
1964 ivilayer->event_mask &= ~IVI_NOTIFICATION_POSITION;
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +09001965
1966 return IVI_SUCCEEDED;
1967}
1968
Nobuhiko Tanibataee8e5832014-12-15 13:25:39 +09001969static int32_t
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +09001970ivi_layout_layer_set_orientation(struct ivi_layout_layer *ivilayer,
1971 enum wl_output_transform orientation)
1972{
1973 struct ivi_layout_layer_properties *prop = NULL;
1974
1975 if (ivilayer == NULL) {
1976 weston_log("ivi_layout_layer_set_orientation: invalid argument\n");
1977 return IVI_FAILED;
1978 }
1979
1980 prop = &ivilayer->pending.prop;
1981 prop->orientation = orientation;
1982
Nobuhiko Tanibata5d4a3232015-06-22 15:32:14 +09001983 if (ivilayer->prop.orientation != orientation)
1984 ivilayer->event_mask |= IVI_NOTIFICATION_ORIENTATION;
1985 else
1986 ivilayer->event_mask &= ~IVI_NOTIFICATION_ORIENTATION;
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +09001987
1988 return IVI_SUCCEEDED;
1989}
1990
Nobuhiko Tanibataee8e5832014-12-15 13:25:39 +09001991static enum wl_output_transform
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +09001992ivi_layout_layer_get_orientation(struct ivi_layout_layer *ivilayer)
1993{
1994 if (ivilayer == NULL) {
1995 weston_log("ivi_layout_layer_get_orientation: invalid argument\n");
1996 return 0;
1997 }
1998
1999 return ivilayer->prop.orientation;
2000}
2001
Nobuhiko Tanibataee8e5832014-12-15 13:25:39 +09002002int32_t
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +09002003ivi_layout_layer_set_render_order(struct ivi_layout_layer *ivilayer,
2004 struct ivi_layout_surface **pSurface,
2005 int32_t number)
2006{
2007 struct ivi_layout *layout = get_instance();
2008 struct ivi_layout_surface *ivisurf = NULL;
2009 struct ivi_layout_surface *next = NULL;
2010 uint32_t *id_surface = NULL;
2011 int32_t i = 0;
2012
2013 if (ivilayer == NULL) {
2014 weston_log("ivi_layout_layer_set_render_order: invalid argument\n");
2015 return IVI_FAILED;
2016 }
2017
Ucan, Emre (ADITG/SW1)c2be6382015-08-19 11:25:01 +00002018 clear_surface_pending_list(ivilayer);
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +09002019
2020 for (i = 0; i < number; i++) {
2021 id_surface = &pSurface[i]->id_surface;
2022
2023 wl_list_for_each_safe(ivisurf, next, &layout->surface_list, link) {
2024 if (*id_surface != ivisurf->id_surface) {
2025 continue;
2026 }
2027
Ucan, Emre (ADITG/SW1)cf34dc22015-08-20 14:13:33 +00002028 wl_list_remove(&ivisurf->pending.link);
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +09002029 wl_list_insert(&ivilayer->pending.surface_list,
2030 &ivisurf->pending.link);
2031 break;
2032 }
2033 }
2034
Ucan, Emre (ADITG/SW1)38fcf382015-08-20 14:13:29 +00002035 ivilayer->order.dirty = 1;
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +09002036
2037 return IVI_SUCCEEDED;
2038}
2039
Nobuhiko Tanibataee8e5832014-12-15 13:25:39 +09002040int32_t
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +09002041ivi_layout_surface_set_visibility(struct ivi_layout_surface *ivisurf,
2042 bool newVisibility)
2043{
2044 struct ivi_layout_surface_properties *prop = NULL;
2045
2046 if (ivisurf == NULL) {
2047 weston_log("ivi_layout_surface_set_visibility: invalid argument\n");
2048 return IVI_FAILED;
2049 }
2050
2051 prop = &ivisurf->pending.prop;
2052 prop->visibility = newVisibility;
2053
Nobuhiko Tanibata5d4a3232015-06-22 15:32:14 +09002054 if (ivisurf->prop.visibility != newVisibility)
2055 ivisurf->event_mask |= IVI_NOTIFICATION_VISIBILITY;
2056 else
2057 ivisurf->event_mask &= ~IVI_NOTIFICATION_VISIBILITY;
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +09002058
2059 return IVI_SUCCEEDED;
2060}
2061
Nobuhiko Tanibataee8e5832014-12-15 13:25:39 +09002062bool
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +09002063ivi_layout_surface_get_visibility(struct ivi_layout_surface *ivisurf)
2064{
2065 if (ivisurf == NULL) {
2066 weston_log("ivi_layout_surface_get_visibility: invalid argument\n");
2067 return false;
2068 }
2069
2070 return ivisurf->prop.visibility;
2071}
2072
Nobuhiko Tanibataee8e5832014-12-15 13:25:39 +09002073int32_t
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +09002074ivi_layout_surface_set_opacity(struct ivi_layout_surface *ivisurf,
2075 wl_fixed_t opacity)
2076{
2077 struct ivi_layout_surface_properties *prop = NULL;
2078
Nobuhiko Tanibataa86226c2015-06-22 15:29:20 +09002079 if (ivisurf == NULL ||
2080 opacity < wl_fixed_from_double(0.0) ||
2081 wl_fixed_from_double(1.0) < opacity) {
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +09002082 weston_log("ivi_layout_surface_set_opacity: invalid argument\n");
2083 return IVI_FAILED;
2084 }
2085
2086 prop = &ivisurf->pending.prop;
2087 prop->opacity = opacity;
2088
Nobuhiko Tanibata5d4a3232015-06-22 15:32:14 +09002089 if (ivisurf->prop.opacity != opacity)
2090 ivisurf->event_mask |= IVI_NOTIFICATION_OPACITY;
2091 else
2092 ivisurf->event_mask &= ~IVI_NOTIFICATION_OPACITY;
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +09002093
2094 return IVI_SUCCEEDED;
2095}
2096
Nobuhiko Tanibataee8e5832014-12-15 13:25:39 +09002097wl_fixed_t
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +09002098ivi_layout_surface_get_opacity(struct ivi_layout_surface *ivisurf)
2099{
2100 if (ivisurf == NULL) {
2101 weston_log("ivi_layout_surface_get_opacity: invalid argument\n");
2102 return wl_fixed_from_double(0.0);
2103 }
2104
2105 return ivisurf->prop.opacity;
2106}
2107
Nobuhiko Tanibataee8e5832014-12-15 13:25:39 +09002108int32_t
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +09002109ivi_layout_surface_set_destination_rectangle(struct ivi_layout_surface *ivisurf,
2110 int32_t x, int32_t y,
2111 int32_t width, int32_t height)
2112{
2113 struct ivi_layout_surface_properties *prop = NULL;
2114
2115 if (ivisurf == NULL) {
2116 weston_log("ivi_layout_surface_set_destination_rectangle: invalid argument\n");
2117 return IVI_FAILED;
2118 }
2119
2120 prop = &ivisurf->pending.prop;
2121 prop->start_x = prop->dest_x;
2122 prop->start_y = prop->dest_y;
2123 prop->dest_x = x;
2124 prop->dest_y = y;
2125 prop->start_width = prop->dest_width;
2126 prop->start_height = prop->dest_height;
2127 prop->dest_width = width;
2128 prop->dest_height = height;
2129
Nobuhiko Tanibata5d4a3232015-06-22 15:32:14 +09002130 if (ivisurf->prop.dest_x != x || ivisurf->prop.dest_y != y ||
2131 ivisurf->prop.dest_width != width ||
2132 ivisurf->prop.dest_height != height)
2133 ivisurf->event_mask |= IVI_NOTIFICATION_DEST_RECT;
2134 else
2135 ivisurf->event_mask &= ~IVI_NOTIFICATION_DEST_RECT;
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +09002136
2137 return IVI_SUCCEEDED;
2138}
2139
Nobuhiko Tanibataee8e5832014-12-15 13:25:39 +09002140static int32_t
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +09002141ivi_layout_surface_set_dimension(struct ivi_layout_surface *ivisurf,
2142 int32_t dest_width, int32_t dest_height)
2143{
2144 struct ivi_layout_surface_properties *prop = NULL;
2145
2146 if (ivisurf == NULL) {
2147 weston_log("ivi_layout_surface_set_dimension: invalid argument\n");
2148 return IVI_FAILED;
2149 }
2150
2151 prop = &ivisurf->pending.prop;
2152 prop->dest_width = dest_width;
2153 prop->dest_height = dest_height;
2154
Nobuhiko Tanibata5d4a3232015-06-22 15:32:14 +09002155 if (ivisurf->prop.dest_width != dest_width ||
2156 ivisurf->prop.dest_height != dest_height)
2157 ivisurf->event_mask |= IVI_NOTIFICATION_DIMENSION;
2158 else
2159 ivisurf->event_mask &= ~IVI_NOTIFICATION_DIMENSION;
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +09002160
2161 return IVI_SUCCEEDED;
2162}
2163
2164int32_t
2165ivi_layout_surface_get_dimension(struct ivi_layout_surface *ivisurf,
2166 int32_t *dest_width, int32_t *dest_height)
2167{
2168 if (ivisurf == NULL || dest_width == NULL || dest_height == NULL) {
2169 weston_log("ivi_layout_surface_get_dimension: invalid argument\n");
2170 return IVI_FAILED;
2171 }
2172
2173 *dest_width = ivisurf->prop.dest_width;
2174 *dest_height = ivisurf->prop.dest_height;
2175
2176 return IVI_SUCCEEDED;
2177}
2178
Nobuhiko Tanibataee8e5832014-12-15 13:25:39 +09002179static int32_t
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +09002180ivi_layout_surface_set_position(struct ivi_layout_surface *ivisurf,
2181 int32_t dest_x, int32_t dest_y)
2182{
2183 struct ivi_layout_surface_properties *prop = NULL;
2184
2185 if (ivisurf == NULL) {
2186 weston_log("ivi_layout_surface_set_position: invalid argument\n");
2187 return IVI_FAILED;
2188 }
2189
2190 prop = &ivisurf->pending.prop;
2191 prop->dest_x = dest_x;
2192 prop->dest_y = dest_y;
2193
Nobuhiko Tanibata5d4a3232015-06-22 15:32:14 +09002194 if (ivisurf->prop.dest_x != dest_x || ivisurf->prop.dest_y != dest_y)
2195 ivisurf->event_mask |= IVI_NOTIFICATION_POSITION;
2196 else
2197 ivisurf->event_mask &= ~IVI_NOTIFICATION_POSITION;
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +09002198
2199 return IVI_SUCCEEDED;
2200}
2201
Nobuhiko Tanibataee8e5832014-12-15 13:25:39 +09002202static int32_t
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +09002203ivi_layout_surface_get_position(struct ivi_layout_surface *ivisurf,
2204 int32_t *dest_x, int32_t *dest_y)
2205{
2206 if (ivisurf == NULL || dest_x == NULL || dest_y == NULL) {
2207 weston_log("ivi_layout_surface_get_position: invalid argument\n");
2208 return IVI_FAILED;
2209 }
2210
2211 *dest_x = ivisurf->prop.dest_x;
2212 *dest_y = ivisurf->prop.dest_y;
2213
2214 return IVI_SUCCEEDED;
2215}
2216
Nobuhiko Tanibataee8e5832014-12-15 13:25:39 +09002217static int32_t
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +09002218ivi_layout_surface_set_orientation(struct ivi_layout_surface *ivisurf,
2219 enum wl_output_transform orientation)
2220{
2221 struct ivi_layout_surface_properties *prop = NULL;
2222
2223 if (ivisurf == NULL) {
2224 weston_log("ivi_layout_surface_set_orientation: invalid argument\n");
2225 return IVI_FAILED;
2226 }
2227
2228 prop = &ivisurf->pending.prop;
2229 prop->orientation = orientation;
2230
Nobuhiko Tanibata5d4a3232015-06-22 15:32:14 +09002231 if (ivisurf->prop.orientation != orientation)
2232 ivisurf->event_mask |= IVI_NOTIFICATION_ORIENTATION;
2233 else
2234 ivisurf->event_mask &= ~IVI_NOTIFICATION_ORIENTATION;
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +09002235
2236 return IVI_SUCCEEDED;
2237}
2238
Nobuhiko Tanibataee8e5832014-12-15 13:25:39 +09002239static enum wl_output_transform
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +09002240ivi_layout_surface_get_orientation(struct ivi_layout_surface *ivisurf)
2241{
2242 if (ivisurf == NULL) {
2243 weston_log("ivi_layout_surface_get_orientation: invalid argument\n");
2244 return 0;
2245 }
2246
2247 return ivisurf->prop.orientation;
2248}
2249
Nobuhiko Tanibataee8e5832014-12-15 13:25:39 +09002250static int32_t
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +09002251ivi_layout_screen_add_layer(struct ivi_layout_screen *iviscrn,
2252 struct ivi_layout_layer *addlayer)
2253{
2254 struct ivi_layout *layout = get_instance();
2255 struct ivi_layout_layer *ivilayer = NULL;
2256 struct ivi_layout_layer *next = NULL;
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +09002257
2258 if (iviscrn == NULL || addlayer == NULL) {
2259 weston_log("ivi_layout_screen_add_layer: invalid argument\n");
2260 return IVI_FAILED;
2261 }
2262
Ucan, Emre (ADITG/SW1)bb4ec0a2015-08-28 12:59:01 +00002263 if (addlayer->on_screen == iviscrn) {
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +09002264 weston_log("ivi_layout_screen_add_layer: addlayer is already available\n");
2265 return IVI_SUCCEEDED;
2266 }
2267
2268 wl_list_for_each_safe(ivilayer, next, &layout->layer_list, link) {
2269 if (ivilayer->id_layer == addlayer->id_layer) {
Ucan, Emre (ADITG/SW1)cf34dc22015-08-20 14:13:33 +00002270 wl_list_remove(&ivilayer->pending.link);
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +09002271 wl_list_insert(&iviscrn->pending.layer_list,
2272 &ivilayer->pending.link);
2273 break;
2274 }
2275 }
2276
Ucan, Emre (ADITG/SW1)174257b2015-08-20 14:13:30 +00002277 iviscrn->order.dirty = 1;
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +09002278
2279 return IVI_SUCCEEDED;
2280}
2281
Nobuhiko Tanibataee8e5832014-12-15 13:25:39 +09002282static int32_t
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +09002283ivi_layout_screen_set_render_order(struct ivi_layout_screen *iviscrn,
2284 struct ivi_layout_layer **pLayer,
2285 const int32_t number)
2286{
2287 struct ivi_layout *layout = get_instance();
2288 struct ivi_layout_layer *ivilayer = NULL;
2289 struct ivi_layout_layer *next = NULL;
2290 uint32_t *id_layer = NULL;
2291 int32_t i = 0;
2292
2293 if (iviscrn == NULL) {
2294 weston_log("ivi_layout_screen_set_render_order: invalid argument\n");
2295 return IVI_FAILED;
2296 }
2297
2298 wl_list_for_each_safe(ivilayer, next,
2299 &iviscrn->pending.layer_list, pending.link) {
Ucan, Emre (ADITG/SW1)174257b2015-08-20 14:13:30 +00002300 wl_list_remove(&ivilayer->pending.link);
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +09002301 wl_list_init(&ivilayer->pending.link);
2302 }
2303
Ucan, Emre (ADITG/SW1)174257b2015-08-20 14:13:30 +00002304 assert(wl_list_empty(&iviscrn->pending.layer_list));
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +09002305
2306 for (i = 0; i < number; i++) {
2307 id_layer = &pLayer[i]->id_layer;
2308 wl_list_for_each(ivilayer, &layout->layer_list, link) {
2309 if (*id_layer != ivilayer->id_layer) {
2310 continue;
2311 }
2312
Ucan, Emre (ADITG/SW1)174257b2015-08-20 14:13:30 +00002313 wl_list_remove(&ivilayer->pending.link);
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +09002314 wl_list_insert(&iviscrn->pending.layer_list,
2315 &ivilayer->pending.link);
2316 break;
2317 }
2318 }
2319
Ucan, Emre (ADITG/SW1)174257b2015-08-20 14:13:30 +00002320 iviscrn->order.dirty = 1;
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +09002321
2322 return IVI_SUCCEEDED;
2323}
2324
Nobuhiko Tanibataee8e5832014-12-15 13:25:39 +09002325static struct weston_output *
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +09002326ivi_layout_screen_get_output(struct ivi_layout_screen *iviscrn)
2327{
2328 return iviscrn->output;
2329}
2330
2331/**
2332 * This function is used by the additional ivi-module because of dumping ivi_surface sceenshot.
2333 * The ivi-module, e.g. ivi-controller.so, is in wayland-ivi-extension of Genivi's Layer Management.
2334 * This function is used to get the result of drawing by clients.
2335 */
Nobuhiko Tanibataee8e5832014-12-15 13:25:39 +09002336static struct weston_surface *
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +09002337ivi_layout_surface_get_weston_surface(struct ivi_layout_surface *ivisurf)
2338{
2339 return ivisurf != NULL ? ivisurf->surface : NULL;
2340}
2341
Nobuhiko Tanibataee8e5832014-12-15 13:25:39 +09002342static int32_t
Nobuhiko Tanibatac3fd6242015-04-21 02:13:15 +09002343ivi_layout_surface_get_size(struct ivi_layout_surface *ivisurf,
2344 int32_t *width, int32_t *height,
2345 int32_t *stride)
2346{
2347 int32_t w;
2348 int32_t h;
2349 const size_t bytespp = 4; /* PIXMAN_a8b8g8r8 */
2350
2351 if (ivisurf == NULL || ivisurf->surface == NULL) {
2352 weston_log("%s: invalid argument\n", __func__);
2353 return IVI_FAILED;
2354 }
2355
2356 weston_surface_get_content_size(ivisurf->surface, &w, &h);
2357
2358 if (width != NULL)
2359 *width = w;
2360
2361 if (height != NULL)
2362 *height = h;
2363
2364 if (stride != NULL)
2365 *stride = w * bytespp;
2366
2367 return IVI_SUCCEEDED;
2368}
2369
2370static int32_t
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +09002371ivi_layout_layer_add_notification(struct ivi_layout_layer *ivilayer,
2372 layer_property_notification_func callback,
2373 void *userdata)
2374{
2375 struct ivi_layout_notification_callback *prop_callback = NULL;
2376
2377 if (ivilayer == NULL || callback == NULL) {
2378 weston_log("ivi_layout_layer_add_notification: invalid argument\n");
2379 return IVI_FAILED;
2380 }
2381
2382 prop_callback = malloc(sizeof *prop_callback);
2383 if (prop_callback == NULL) {
2384 weston_log("fails to allocate memory\n");
2385 return IVI_FAILED;
2386 }
2387
2388 prop_callback->callback = callback;
2389 prop_callback->data = userdata;
2390
2391 return add_notification(&ivilayer->property_changed,
2392 layer_prop_changed,
2393 prop_callback);
2394}
2395
Nobuhiko Tanibataee8e5832014-12-15 13:25:39 +09002396static const struct ivi_layout_surface_properties *
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +09002397ivi_layout_get_properties_of_surface(struct ivi_layout_surface *ivisurf)
2398{
2399 if (ivisurf == NULL) {
2400 weston_log("ivi_layout_get_properties_of_surface: invalid argument\n");
2401 return NULL;
2402 }
2403
2404 return &ivisurf->prop;
2405}
2406
Nobuhiko Tanibataee8e5832014-12-15 13:25:39 +09002407static int32_t
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +09002408ivi_layout_layer_add_surface(struct ivi_layout_layer *ivilayer,
2409 struct ivi_layout_surface *addsurf)
2410{
2411 struct ivi_layout *layout = get_instance();
2412 struct ivi_layout_surface *ivisurf = NULL;
2413 struct ivi_layout_surface *next = NULL;
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +09002414
2415 if (ivilayer == NULL || addsurf == NULL) {
2416 weston_log("ivi_layout_layer_add_surface: invalid argument\n");
2417 return IVI_FAILED;
2418 }
2419
Wataru Natsume9c926fe2016-03-03 19:56:09 +09002420 if (addsurf->on_layer == ivilayer)
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +09002421 return IVI_SUCCEEDED;
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +09002422
2423 wl_list_for_each_safe(ivisurf, next, &layout->surface_list, link) {
2424 if (ivisurf->id_surface == addsurf->id_surface) {
Ucan, Emre (ADITG/SW1)cf34dc22015-08-20 14:13:33 +00002425 wl_list_remove(&ivisurf->pending.link);
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +09002426 wl_list_insert(&ivilayer->pending.surface_list,
2427 &ivisurf->pending.link);
2428 break;
2429 }
2430 }
2431
Ucan, Emre (ADITG/SW1)38fcf382015-08-20 14:13:29 +00002432 ivilayer->order.dirty = 1;
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +09002433
2434 return IVI_SUCCEEDED;
2435}
2436
Nobuhiko Tanibataee8e5832014-12-15 13:25:39 +09002437static void
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +09002438ivi_layout_layer_remove_surface(struct ivi_layout_layer *ivilayer,
2439 struct ivi_layout_surface *remsurf)
2440{
2441 struct ivi_layout_surface *ivisurf = NULL;
2442 struct ivi_layout_surface *next = NULL;
2443
2444 if (ivilayer == NULL || remsurf == NULL) {
2445 weston_log("ivi_layout_layer_remove_surface: invalid argument\n");
2446 return;
2447 }
2448
2449 wl_list_for_each_safe(ivisurf, next,
2450 &ivilayer->pending.surface_list, pending.link) {
2451 if (ivisurf->id_surface == remsurf->id_surface) {
Ucan, Emre (ADITG/SW1)cf34dc22015-08-20 14:13:33 +00002452 wl_list_remove(&ivisurf->pending.link);
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +09002453 wl_list_init(&ivisurf->pending.link);
2454 break;
2455 }
2456 }
2457
Ucan, Emre (ADITG/SW1)38fcf382015-08-20 14:13:29 +00002458 ivilayer->order.dirty = 1;
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +09002459}
2460
Nobuhiko Tanibataee8e5832014-12-15 13:25:39 +09002461static int32_t
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +09002462ivi_layout_surface_set_source_rectangle(struct ivi_layout_surface *ivisurf,
2463 int32_t x, int32_t y,
2464 int32_t width, int32_t height)
2465{
2466 struct ivi_layout_surface_properties *prop = NULL;
2467
2468 if (ivisurf == NULL) {
2469 weston_log("ivi_layout_surface_set_source_rectangle: invalid argument\n");
2470 return IVI_FAILED;
2471 }
2472
2473 prop = &ivisurf->pending.prop;
2474 prop->source_x = x;
2475 prop->source_y = y;
2476 prop->source_width = width;
2477 prop->source_height = height;
2478
Nobuhiko Tanibata5d4a3232015-06-22 15:32:14 +09002479 if (ivisurf->prop.source_x != x || ivisurf->prop.source_y != y ||
2480 ivisurf->prop.source_width != width ||
2481 ivisurf->prop.source_height != height)
2482 ivisurf->event_mask |= IVI_NOTIFICATION_SOURCE_RECT;
2483 else
2484 ivisurf->event_mask &= ~IVI_NOTIFICATION_SOURCE_RECT;
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +09002485
2486 return IVI_SUCCEEDED;
2487}
2488
Nobuhiko Tanibataee8e5832014-12-15 13:25:39 +09002489int32_t
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +09002490ivi_layout_commit_changes(void)
2491{
2492 struct ivi_layout *layout = get_instance();
2493
2494 commit_surface_list(layout);
2495 commit_layer_list(layout);
2496 commit_screen_list(layout);
2497
2498 commit_transition(layout);
2499
2500 commit_changes(layout);
2501 send_prop(layout);
2502 weston_compositor_schedule_repaint(layout->compositor);
2503
2504 return IVI_SUCCEEDED;
2505}
2506
Nobuhiko Tanibataee8e5832014-12-15 13:25:39 +09002507static int32_t
Nobuhiko Tanibata3c6796f2014-12-15 13:20:58 +09002508ivi_layout_layer_set_transition(struct ivi_layout_layer *ivilayer,
2509 enum ivi_layout_transition_type type,
2510 uint32_t duration)
2511{
2512 if (ivilayer == NULL) {
2513 weston_log("%s: invalid argument\n", __func__);
2514 return -1;
2515 }
2516
2517 ivilayer->pending.prop.transition_type = type;
2518 ivilayer->pending.prop.transition_duration = duration;
2519
2520 return 0;
2521}
2522
Nobuhiko Tanibataee8e5832014-12-15 13:25:39 +09002523static int32_t
Nobuhiko Tanibata3c6796f2014-12-15 13:20:58 +09002524ivi_layout_layer_set_fade_info(struct ivi_layout_layer* ivilayer,
2525 uint32_t is_fade_in,
2526 double start_alpha, double end_alpha)
2527{
2528 if (ivilayer == NULL) {
2529 weston_log("%s: invalid argument\n", __func__);
2530 return -1;
2531 }
2532
2533 ivilayer->pending.prop.is_fade_in = is_fade_in;
2534 ivilayer->pending.prop.start_alpha = start_alpha;
2535 ivilayer->pending.prop.end_alpha = end_alpha;
2536
2537 return 0;
2538}
2539
Nobuhiko Tanibataee8e5832014-12-15 13:25:39 +09002540static int32_t
Nobuhiko Tanibata3c6796f2014-12-15 13:20:58 +09002541ivi_layout_surface_set_transition_duration(struct ivi_layout_surface *ivisurf,
2542 uint32_t duration)
2543{
2544 struct ivi_layout_surface_properties *prop;
2545
2546 if (ivisurf == NULL) {
2547 weston_log("%s: invalid argument\n", __func__);
2548 return -1;
2549 }
2550
2551 prop = &ivisurf->pending.prop;
2552 prop->transition_duration = duration*10;
2553 return 0;
2554}
2555
Nobuhiko Tanibataee8e5832014-12-15 13:25:39 +09002556static int32_t
Nobuhiko Tanibata3c6796f2014-12-15 13:20:58 +09002557ivi_layout_surface_set_transition(struct ivi_layout_surface *ivisurf,
2558 enum ivi_layout_transition_type type,
2559 uint32_t duration)
2560{
2561 struct ivi_layout_surface_properties *prop;
2562
2563 if (ivisurf == NULL) {
2564 weston_log("%s: invalid argument\n", __func__);
2565 return -1;
2566 }
2567
2568 prop = &ivisurf->pending.prop;
2569 prop->transition_type = type;
2570 prop->transition_duration = duration;
2571 return 0;
2572}
2573
Nobuhiko Tanibatac3fd6242015-04-21 02:13:15 +09002574static int32_t
2575ivi_layout_surface_dump(struct weston_surface *surface,
2576 void *target, size_t size,int32_t x, int32_t y,
2577 int32_t width, int32_t height)
2578{
2579 int result = 0;
2580
2581 if (surface == NULL) {
2582 weston_log("%s: invalid argument\n", __func__);
2583 return IVI_FAILED;
2584 }
2585
2586 result = weston_surface_copy_content(
2587 surface, target, size,
2588 x, y, width, height);
2589
2590 return result == 0 ? IVI_SUCCEEDED : IVI_FAILED;
2591}
2592
Nobuhiko Tanibata28dc18c2014-12-15 13:22:31 +09002593/**
2594 * methods of interaction between ivi-shell with ivi-layout
2595 */
2596struct weston_view *
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +09002597ivi_layout_get_weston_view(struct ivi_layout_surface *surface)
2598{
Dawid Gajownik74a635b2015-08-06 17:12:19 -03002599 if (surface == NULL)
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +09002600 return NULL;
2601
Ucan, Emre (ADITG/SW1)64635ee2015-08-28 12:59:06 +00002602 return get_weston_view(surface);
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +09002603}
2604
Nobuhiko Tanibata28dc18c2014-12-15 13:22:31 +09002605void
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +09002606ivi_layout_surface_configure(struct ivi_layout_surface *ivisurf,
2607 int32_t width, int32_t height)
2608{
2609 struct ivi_layout *layout = get_instance();
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +09002610
Nobuhiko Tanibatae6cc9972015-04-27 16:54:01 +09002611 /* emit callback which is set by ivi-layout api user */
2612 wl_signal_emit(&layout->surface_notification.configure_changed,
2613 ivisurf);
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +09002614}
2615
Nobuhiko Tanibataee8e5832014-12-15 13:25:39 +09002616static int32_t
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +09002617ivi_layout_surface_set_content_observer(struct ivi_layout_surface *ivisurf,
2618 ivi_controller_surface_content_callback callback,
2619 void* userdata)
2620{
2621 int32_t ret = IVI_FAILED;
2622
2623 if (ivisurf != NULL) {
2624 ivisurf->content_observer.callback = callback;
2625 ivisurf->content_observer.userdata = userdata;
2626 ret = IVI_SUCCEEDED;
2627 }
2628 return ret;
2629}
2630
Nobuhiko Tanibata28dc18c2014-12-15 13:22:31 +09002631struct ivi_layout_surface*
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +09002632ivi_layout_surface_create(struct weston_surface *wl_surface,
2633 uint32_t id_surface)
2634{
2635 struct ivi_layout *layout = get_instance();
2636 struct ivi_layout_surface *ivisurf = NULL;
2637 struct weston_view *tmpview = NULL;
2638
2639 if (wl_surface == NULL) {
2640 weston_log("ivi_layout_surface_create: invalid argument\n");
2641 return NULL;
2642 }
2643
2644 ivisurf = get_surface(&layout->surface_list, id_surface);
2645 if (ivisurf != NULL) {
2646 if (ivisurf->surface != NULL) {
2647 weston_log("id_surface(%d) is already created\n", id_surface);
2648 return NULL;
2649 }
2650 }
2651
2652 ivisurf = calloc(1, sizeof *ivisurf);
2653 if (ivisurf == NULL) {
2654 weston_log("fails to allocate memory\n");
2655 return NULL;
2656 }
2657
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +09002658 wl_signal_init(&ivisurf->property_changed);
2659 wl_signal_init(&ivisurf->configured);
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +09002660 ivisurf->id_surface = id_surface;
2661 ivisurf->layout = layout;
2662
2663 ivisurf->surface = wl_surface;
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +09002664
2665 tmpview = weston_view_create(wl_surface);
2666 if (tmpview == NULL) {
2667 weston_log("fails to allocate memory\n");
2668 }
2669
2670 ivisurf->surface->width_from_buffer = 0;
2671 ivisurf->surface->height_from_buffer = 0;
2672
Nobuhiko Tanibata21deb282015-07-15 14:05:32 +09002673 weston_matrix_init(&ivisurf->transform.matrix);
2674 wl_list_init(&ivisurf->transform.link);
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +09002675
2676 init_surface_properties(&ivisurf->prop);
2677 ivisurf->event_mask = 0;
2678
2679 ivisurf->pending.prop = ivisurf->prop;
2680 wl_list_init(&ivisurf->pending.link);
2681
2682 wl_list_init(&ivisurf->order.link);
2683 wl_list_init(&ivisurf->order.layer_list);
2684
2685 wl_list_insert(&layout->surface_list, &ivisurf->link);
2686
2687 wl_signal_emit(&layout->surface_notification.created, ivisurf);
2688
2689 return ivisurf;
2690}
2691
Nobuhiko Tanibata28dc18c2014-12-15 13:22:31 +09002692void
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +09002693ivi_layout_init_with_compositor(struct weston_compositor *ec)
2694{
2695 struct ivi_layout *layout = get_instance();
2696
2697 layout->compositor = ec;
2698
2699 wl_list_init(&layout->surface_list);
2700 wl_list_init(&layout->layer_list);
2701 wl_list_init(&layout->screen_list);
2702
2703 wl_signal_init(&layout->layer_notification.created);
2704 wl_signal_init(&layout->layer_notification.removed);
2705
2706 wl_signal_init(&layout->surface_notification.created);
2707 wl_signal_init(&layout->surface_notification.removed);
2708 wl_signal_init(&layout->surface_notification.configure_changed);
2709
2710 /* Add layout_layer at the last of weston_compositor.layer_list */
2711 weston_layer_init(&layout->layout_layer, ec->layer_list.prev);
2712
2713 create_screen(ec);
2714
2715 layout->transitions = ivi_layout_transition_set_create(ec);
2716 wl_list_init(&layout->pending_transition_list);
2717}
2718
2719
Nobuhiko Tanibata28dc18c2014-12-15 13:22:31 +09002720void
Nobuhiko Tanibata6f9df652014-11-27 13:22:00 +09002721ivi_layout_surface_add_configured_listener(struct ivi_layout_surface* ivisurf,
2722 struct wl_listener* listener)
2723{
2724 wl_signal_add(&ivisurf->configured, listener);
2725}
2726
Ucan, Emre \(ADITG/SW1\)0c0e51e2015-10-15 14:51:41 +00002727static struct ivi_layout_interface ivi_layout_interface = {
Nobuhiko Tanibataee8e5832014-12-15 13:25:39 +09002728 /**
2729 * commit all changes
2730 */
2731 .commit_changes = ivi_layout_commit_changes,
2732
2733 /**
2734 * surface controller interfaces
2735 */
2736 .add_notification_create_surface = ivi_layout_add_notification_create_surface,
2737 .remove_notification_create_surface = ivi_layout_remove_notification_create_surface,
2738 .add_notification_remove_surface = ivi_layout_add_notification_remove_surface,
2739 .remove_notification_remove_surface = ivi_layout_remove_notification_remove_surface,
2740 .add_notification_configure_surface = ivi_layout_add_notification_configure_surface,
2741 .remove_notification_configure_surface = ivi_layout_remove_notification_configure_surface,
2742 .get_surfaces = ivi_layout_get_surfaces,
2743 .get_id_of_surface = ivi_layout_get_id_of_surface,
2744 .get_surface_from_id = ivi_layout_get_surface_from_id,
2745 .get_properties_of_surface = ivi_layout_get_properties_of_surface,
2746 .get_surfaces_on_layer = ivi_layout_get_surfaces_on_layer,
2747 .surface_set_visibility = ivi_layout_surface_set_visibility,
2748 .surface_get_visibility = ivi_layout_surface_get_visibility,
2749 .surface_set_opacity = ivi_layout_surface_set_opacity,
2750 .surface_get_opacity = ivi_layout_surface_get_opacity,
2751 .surface_set_source_rectangle = ivi_layout_surface_set_source_rectangle,
2752 .surface_set_destination_rectangle = ivi_layout_surface_set_destination_rectangle,
2753 .surface_set_position = ivi_layout_surface_set_position,
2754 .surface_get_position = ivi_layout_surface_get_position,
2755 .surface_set_dimension = ivi_layout_surface_set_dimension,
2756 .surface_get_dimension = ivi_layout_surface_get_dimension,
2757 .surface_set_orientation = ivi_layout_surface_set_orientation,
2758 .surface_get_orientation = ivi_layout_surface_get_orientation,
2759 .surface_set_content_observer = ivi_layout_surface_set_content_observer,
2760 .surface_add_notification = ivi_layout_surface_add_notification,
2761 .surface_remove_notification = ivi_layout_surface_remove_notification,
2762 .surface_get_weston_surface = ivi_layout_surface_get_weston_surface,
2763 .surface_set_transition = ivi_layout_surface_set_transition,
2764 .surface_set_transition_duration = ivi_layout_surface_set_transition_duration,
2765
2766 /**
2767 * layer controller interfaces
2768 */
2769 .add_notification_create_layer = ivi_layout_add_notification_create_layer,
2770 .remove_notification_create_layer = ivi_layout_remove_notification_create_layer,
2771 .add_notification_remove_layer = ivi_layout_add_notification_remove_layer,
2772 .remove_notification_remove_layer = ivi_layout_remove_notification_remove_layer,
2773 .layer_create_with_dimension = ivi_layout_layer_create_with_dimension,
Nobuhiko Tanibata3aa8aed2015-06-22 15:32:23 +09002774 .layer_destroy = ivi_layout_layer_destroy,
Nobuhiko Tanibataee8e5832014-12-15 13:25:39 +09002775 .get_layers = ivi_layout_get_layers,
2776 .get_id_of_layer = ivi_layout_get_id_of_layer,
2777 .get_layer_from_id = ivi_layout_get_layer_from_id,
2778 .get_properties_of_layer = ivi_layout_get_properties_of_layer,
2779 .get_layers_under_surface = ivi_layout_get_layers_under_surface,
2780 .get_layers_on_screen = ivi_layout_get_layers_on_screen,
2781 .layer_set_visibility = ivi_layout_layer_set_visibility,
2782 .layer_get_visibility = ivi_layout_layer_get_visibility,
2783 .layer_set_opacity = ivi_layout_layer_set_opacity,
2784 .layer_get_opacity = ivi_layout_layer_get_opacity,
2785 .layer_set_source_rectangle = ivi_layout_layer_set_source_rectangle,
2786 .layer_set_destination_rectangle = ivi_layout_layer_set_destination_rectangle,
2787 .layer_set_position = ivi_layout_layer_set_position,
2788 .layer_get_position = ivi_layout_layer_get_position,
2789 .layer_set_dimension = ivi_layout_layer_set_dimension,
2790 .layer_get_dimension = ivi_layout_layer_get_dimension,
2791 .layer_set_orientation = ivi_layout_layer_set_orientation,
2792 .layer_get_orientation = ivi_layout_layer_get_orientation,
2793 .layer_add_surface = ivi_layout_layer_add_surface,
2794 .layer_remove_surface = ivi_layout_layer_remove_surface,
2795 .layer_set_render_order = ivi_layout_layer_set_render_order,
2796 .layer_add_notification = ivi_layout_layer_add_notification,
2797 .layer_remove_notification = ivi_layout_layer_remove_notification,
2798 .layer_set_transition = ivi_layout_layer_set_transition,
2799
2800 /**
Nobuhiko Tanibata4d0116e2015-06-22 15:31:57 +09002801 * screen controller interfaces part1
Nobuhiko Tanibataee8e5832014-12-15 13:25:39 +09002802 */
2803 .get_screen_from_id = ivi_layout_get_screen_from_id,
2804 .get_screen_resolution = ivi_layout_get_screen_resolution,
2805 .get_screens = ivi_layout_get_screens,
2806 .get_screens_under_layer = ivi_layout_get_screens_under_layer,
2807 .screen_add_layer = ivi_layout_screen_add_layer,
2808 .screen_set_render_order = ivi_layout_screen_set_render_order,
2809 .screen_get_output = ivi_layout_screen_get_output,
2810
2811 /**
2812 * animation
2813 */
2814 .transition_move_layer_cancel = ivi_layout_transition_move_layer_cancel,
Nobuhiko Tanibatac3fd6242015-04-21 02:13:15 +09002815 .layer_set_fade_info = ivi_layout_layer_set_fade_info,
2816
2817 /**
2818 * surface content dumping for debugging
2819 */
2820 .surface_get_size = ivi_layout_surface_get_size,
2821 .surface_dump = ivi_layout_surface_dump,
Nobuhiko Tanibata82051702015-06-22 15:31:26 +09002822
2823 /**
Nobuhiko Tanibatadb8efd12015-06-22 15:31:39 +09002824 * remove notification by callback on property changes of ivi_surface/layer
Nobuhiko Tanibata82051702015-06-22 15:31:26 +09002825 */
Nobuhiko Tanibatadb8efd12015-06-22 15:31:39 +09002826 .surface_remove_notification_by_callback = ivi_layout_surface_remove_notification_by_callback,
Nobuhiko Tanibata4d0116e2015-06-22 15:31:57 +09002827 .layer_remove_notification_by_callback = ivi_layout_layer_remove_notification_by_callback,
2828
2829 /**
2830 * screen controller interfaces part2
2831 */
2832 .get_id_of_screen = ivi_layout_get_id_of_screen
Nobuhiko Tanibataee8e5832014-12-15 13:25:39 +09002833};
2834
2835int
2836load_controller_modules(struct weston_compositor *compositor, const char *modules,
2837 int *argc, char *argv[])
2838{
2839 const char *p, *end;
2840 char buffer[256];
2841 int (*controller_module_init)(struct weston_compositor *compositor,
2842 int *argc, char *argv[],
Ucan, Emre \(ADITG/SW1\)0c0e51e2015-10-15 14:51:41 +00002843 const struct ivi_layout_interface *interface,
Nobuhiko Tanibataee8e5832014-12-15 13:25:39 +09002844 size_t interface_version);
2845
2846 if (modules == NULL)
2847 return 0;
2848
2849 p = modules;
2850 while (*p) {
2851 end = strchrnul(p, ',');
2852 snprintf(buffer, sizeof buffer, "%.*s", (int)(end - p), p);
2853
2854 controller_module_init = weston_load_module(buffer, "controller_module_init");
Pekka Paalanen97246c02015-03-26 15:47:29 +02002855 if (!controller_module_init)
2856 return -1;
2857
2858 if (controller_module_init(compositor, argc, argv,
Ucan, Emre \(ADITG/SW1\)0c0e51e2015-10-15 14:51:41 +00002859 &ivi_layout_interface,
2860 sizeof(struct ivi_layout_interface)) != 0) {
Pekka Paalanen97246c02015-03-26 15:47:29 +02002861 weston_log("ivi-shell: Initialization of controller module fails");
2862 return -1;
Nobuhiko Tanibataee8e5832014-12-15 13:25:39 +09002863 }
2864
2865 p = end;
2866 while (*p == ',')
2867 p++;
2868 }
2869
2870 return 0;
2871}