weston-ivi-shell: change order of transmitting notification;
[profile/ivi/wayland-ivi-extension.git] / weston-ivi-shell / src / ivi-controller.c
index 59765cc..e050292 100755 (executable)
@@ -213,6 +213,7 @@ destroy_ivicontroller_layer(struct wl_resource *resource)
 
         wl_list_remove(&ctrllayer->link);
         --ivilayer->controller_layer_count;
+        ivi_controller_layer_send_destroyed(ctrllayer->resource);
         free(ctrllayer);
         ctrllayer = NULL;
         break;
@@ -344,7 +345,8 @@ controller_screen_create(struct ivishell *shell,
 
 static void
 send_surface_add_event(struct ivisurface *ivisurf,
-                       struct wl_resource *resource)
+                       struct wl_resource *resource,
+                       enum ivi_layout_notification_mask mask)
 {
     struct ivi_layout_layer **pArray = NULL;
     uint32_t length = 0;
@@ -356,6 +358,7 @@ send_surface_add_event(struct ivisurface *ivisurf,
     struct ivilayer *ivilayer = NULL;
     struct ivishell *shell = ivisurf->shell;
     uint32_t id_layout_layer = 0;
+    struct wl_client *surface_client = wl_resource_get_client(resource);
     int found = 0;
 
     ans = ivi_layout_getLayersUnderSurface(ivisurf->layout_surface,
@@ -366,69 +369,39 @@ send_surface_add_event(struct ivisurface *ivisurf,
     }
 
     /* Send Null to cancel added surface */
-    wl_list_for_each_safe(link_layer, next, &ivisurf->list_layer, link) {
-        for (i = 0, found = 0; i < (int)length; i++) {
-            if (pArray[i] == link_layer->layer->layout_layer) {
-                /* No need to send event, if new layer doesn't be added. */
-                found = 1;
-                break;
-            }
-        }
-        if (found != 0) {
-            continue;
+    if (mask & IVI_NOTIFICATION_REMOVE) {
+        wl_list_for_each_safe(link_layer, next, &ivisurf->list_layer, link) {
+            ivi_controller_surface_send_layer(resource, NULL);
         }
-
-        ivi_controller_surface_send_layer(resource, NULL);
-        wl_list_remove(&link_layer->link);
-        free(link_layer);
-        link_layer = NULL;
     }
-
-    for (i = 0; i < (int)length; i++) {
-        found = 0;
-        wl_list_for_each(link_layer, &ivisurf->list_layer, link) {
-            if (pArray[i] == link_layer->layer->layout_layer) {
-                /* No need to send event, if new layer doesn't be added. */
-                found = 1;
-                break;
+    else if (mask & IVI_NOTIFICATION_ADD) {
+        for (i = 0; i < (int)length; i++) {
+            /* Send new surface event */
+            ivilayer = NULL;
+            wl_list_for_each(ivilayer, &shell->list_layer, link) {
+                if (ivilayer->layout_layer == pArray[i]) {
+                    break;
+                }
             }
-        }
-        if (found != 0) {
-            continue;
-        }
 
-        /* Create list_layer */
-        link_layer = calloc(1, sizeof(*link_layer));
-        if (NULL == link_layer) {
-            continue;
-        }
-        wl_list_init(&link_layer->link);
-        link_layer->layer = NULL;
-        wl_list_for_each(ivilayer, &shell->list_layer, link) {
-            if (ivilayer->layout_layer == pArray[i]) {
-                link_layer->layer = ivilayer;
-                break;
+            if (ivilayer == NULL) {
+                continue;
             }
-        }
 
-        if (link_layer->layer == NULL) {
-            free(link_layer);
-            link_layer = NULL;
-            continue;
-        }
-        wl_list_insert(&ivisurf->list_layer, &link_layer->link);
+            id_layout_layer =
+                ivi_layout_getIdOfLayer(ivilayer->layout_layer);
+            wl_list_for_each(ctrllayer, &shell->list_controller_layer, link) {
+                if (id_layout_layer != ctrllayer->id_layer) {
+                    continue;
+                }
 
-        /* Send new surface event */
-        id_layout_layer =
-            ivi_layout_getIdOfLayer(link_layer->layer->layout_layer);
-        wl_list_for_each(ctrllayer, &shell->list_controller_layer, link) {
-            if (id_layout_layer != ctrllayer->id_layer) {
-                continue;
-            }
-            if (resource != ctrllayer->resource) {
-                continue;
+                struct wl_client *layer_client = wl_resource_get_client(ctrllayer->resource);
+                if (surface_client != layer_client) {
+                    continue;
+                }
+
+                ivi_controller_surface_send_layer(resource, ctrllayer->resource);
             }
-            ivi_controller_surface_send_layer(resource, ctrllayer->resource);
         }
     }
 
@@ -468,8 +441,66 @@ send_surface_event(struct wl_resource *resource,
         ivi_controller_surface_send_pixelformat(resource,
                                                 prop->pixelformat);
     }
+    if (mask & IVI_NOTIFICATION_REMOVE) {
+        send_surface_add_event(ivisurf, resource, IVI_NOTIFICATION_REMOVE);
+    }
     if (mask & IVI_NOTIFICATION_ADD) {
-        send_surface_add_event(ivisurf, resource);
+        send_surface_add_event(ivisurf, resource, IVI_NOTIFICATION_ADD);
+    }
+}
+
+static void
+update_surface_prop(struct ivisurface *ivisurf,
+                    uint32_t mask)
+{
+    struct ivi_layout_layer **pArray = NULL;
+    uint32_t length = 0;
+    int32_t ans = 0;
+    int i = 0;
+    struct ivishell *shell = ivisurf->shell;
+
+    ans = ivi_layout_getLayersUnderSurface(ivisurf->layout_surface,
+                                          &length, &pArray);
+    if (0 != ans) {
+        weston_log("failed to get layers at send_surface_add_event\n");
+        return;
+    }
+
+    if (mask & IVI_NOTIFICATION_REMOVE) {
+        struct link_layer *link_layer = NULL;
+        struct link_layer *next = NULL;
+
+        wl_list_for_each_safe(link_layer, next, &ivisurf->list_layer, link) {
+            wl_list_remove(&link_layer->link);
+            free(link_layer);
+            link_layer = NULL;
+        }
+    }
+    if (mask & IVI_NOTIFICATION_ADD) {
+        for (i = 0; i < (int)length; ++i) {
+            /* Create list_layer */
+            struct ivilayer *ivilayer = NULL;
+            struct link_layer *link_layer = calloc(1, sizeof(*link_layer));
+            if (NULL == link_layer) {
+                continue;
+            }
+            wl_list_init(&link_layer->link);
+            link_layer->layer = NULL;
+            wl_list_for_each(ivilayer, &shell->list_layer, link) {
+                if (ivilayer->layout_layer == pArray[i]) {
+                    link_layer->layer = ivilayer;
+                    break;
+                }
+            }
+
+            if (link_layer->layer == NULL) {
+                free(link_layer);
+                link_layer = NULL;
+                continue;
+            }
+
+            wl_list_insert(&ivisurf->list_layer, &link_layer->link);
+        }
     }
 }
 
@@ -492,11 +523,14 @@ send_surface_prop(struct ivi_layout_surface *layout_surface,
         }
         send_surface_event(ctrlsurf->resource, ivisurf, prop, mask);
     }
+
+    update_surface_prop(ivisurf, mask);
 }
 
 static void
 send_layer_add_event(struct ivilayer *ivilayer,
-                     struct wl_resource *resource)
+                     struct wl_resource *resource,
+                     enum ivi_layout_notification_mask mask)
 {
     struct ivi_layout_screen **pArray = NULL;
     uint32_t length = 0;
@@ -506,7 +540,6 @@ send_layer_add_event(struct ivilayer *ivilayer,
     struct link_screen *next = NULL;
     struct iviscreen *iviscrn = NULL;
     struct ivishell *shell = ivilayer->shell;
-    int found = 0;
     struct wl_client *client = wl_resource_get_client(resource);
     struct wl_resource *resource_output = NULL;
 
@@ -518,64 +551,31 @@ send_layer_add_event(struct ivilayer *ivilayer,
     }
 
     /* Send Null to cancel added layer */
-    wl_list_for_each_safe(link_scrn, next, &ivilayer->list_screen, link) {
-        for (i = 0, found = 0; i < (int)length; i++) {
-            if (pArray[i] == link_scrn->screen->layout_screen) {
-                /* No need to send event, if new layer doesn't be added. */
-                found = 1;
-                break;
-            }
-        }
-        if (found != 0) {
-            continue;
+    if (mask & IVI_NOTIFICATION_REMOVE) {
+        wl_list_for_each_safe(link_scrn, next, &ivilayer->list_screen, link) {
+            ivi_controller_layer_send_screen(resource, NULL);
         }
-
-        ivi_controller_layer_send_screen(resource, NULL);
-        wl_list_remove(&link_scrn->link);
-        free(link_scrn);
-        link_scrn = NULL;
     }
-
-    for (i = 0; i < (int)length; i++) {
-        found = 0;
-        wl_list_for_each(link_scrn, &ivilayer->list_screen, link) {
-            if (pArray[i] == link_scrn->screen->layout_screen) {
-                /* No need to send event, if new screen doesn't be added. */
-                found = 1;
-                break;
+    else if (mask & IVI_NOTIFICATION_ADD) {
+        for (i = 0; i < (int)length; i++) {
+            /* Send new layer event */
+            iviscrn = NULL;
+            wl_list_for_each(iviscrn, &shell->list_screen, link) {
+                if (iviscrn->layout_screen == pArray[i]) {
+                    break;
+                }
             }
-        }
-        if (found != 0) {
-            continue;
-        }
 
-        /* Create list_screen */
-        link_scrn = calloc(1, sizeof(*link_scrn));
-        if (NULL == link_scrn) {
-            continue;
-        }
-        wl_list_init(&link_scrn->link);
-        link_scrn->screen = NULL;
-        wl_list_for_each(iviscrn, &shell->list_screen, link) {
-            if (iviscrn->layout_screen == pArray[i]) {
-                link_scrn->screen = iviscrn;
-                break;
+            if (iviscrn == NULL) {
+                continue;
             }
-        }
 
-        if (link_scrn->screen == NULL) {
-            free(link_scrn);
-            link_scrn = NULL;
-            continue;
-        }
-        wl_list_insert(&ivilayer->list_screen, &link_scrn->link);
-
-        /* Send new layer event */
-        resource_output =
-            wl_resource_find_for_client(&iviscrn->output->resource_list,
-                                 client);
-        if (resource_output != NULL) {
-            ivi_controller_layer_send_screen(resource, resource_output);
+            resource_output =
+                wl_resource_find_for_client(&iviscrn->output->resource_list,
+                                     client);
+            if (resource_output != NULL) {
+                ivi_controller_layer_send_screen(resource, resource_output);
+            }
         }
     }
 
@@ -615,12 +615,69 @@ send_layer_event(struct wl_resource *resource,
         ivi_controller_layer_send_visibility(resource,
                                           prop->visibility);
     }
+    if (mask & IVI_NOTIFICATION_REMOVE) {
+        send_layer_add_event(ivilayer, resource, IVI_NOTIFICATION_REMOVE);
+    }
     if (mask & IVI_NOTIFICATION_ADD) {
-        send_layer_add_event(ivilayer, resource);
+        send_layer_add_event(ivilayer, resource, IVI_NOTIFICATION_ADD);
+    }
+}
+
+static void
+update_layer_prop(struct ivilayer *ivilayer,
+                  enum ivi_layout_notification_mask mask)
+{
+    struct ivi_layout_screen **pArray = NULL;
+    uint32_t length = 0;
+    int32_t ans = 0;
+    struct link_screen *link_scrn = NULL;
+    struct link_screen *next = NULL;
+
+    ans = ivi_layout_getScreensUnderLayer(ivilayer->layout_layer,
+                                          &length, &pArray);
+    if (0 != ans) {
+        weston_log("failed to get screens at send_layer_add_event\n");
+        return;
     }
+
+    /* Send Null to cancel added layer */
     if (mask & IVI_NOTIFICATION_REMOVE) {
-        send_layer_add_event(ivilayer, resource);
+        wl_list_for_each_safe(link_scrn, next, &ivilayer->list_screen, link) {
+            wl_list_remove(&link_scrn->link);
+            free(link_scrn);
+            link_scrn = NULL;
+        }
     }
+    if (mask & IVI_NOTIFICATION_ADD) {
+        int i = 0;
+        for (i = 0; i < (int)length; i++) {
+            struct ivishell *shell = ivilayer->shell;
+            struct iviscreen *iviscrn = NULL;
+            /* Create list_screen */
+            link_scrn = calloc(1, sizeof(*link_scrn));
+            if (NULL == link_scrn) {
+                continue;
+            }
+            wl_list_init(&link_scrn->link);
+            link_scrn->screen = NULL;
+            wl_list_for_each(iviscrn, &shell->list_screen, link) {
+                if (iviscrn->layout_screen == pArray[i]) {
+                    link_scrn->screen = iviscrn;
+                    break;
+                }
+            }
+
+            if (link_scrn->screen == NULL) {
+                free(link_scrn);
+                link_scrn = NULL;
+                continue;
+            }
+            wl_list_insert(&ivilayer->list_screen, &link_scrn->link);
+        }
+    }
+
+    free(pArray);
+    pArray = NULL;
 }
 
 static void
@@ -641,6 +698,8 @@ send_layer_prop(struct ivi_layout_layer *layer,
         }
         send_layer_event(ctrllayer->resource, ivilayer, prop, mask);
     }
+
+    update_layer_prop(ivilayer, mask);
 }
 
 static void
@@ -927,12 +986,11 @@ controller_layer_destroy(struct wl_client *client,
 
     ivilayer->layer_canbe_removed = 1;
     wl_list_for_each_safe(ctrllayer, next, &shell->list_controller_layer, link) {
-        if (ctrllayer->resource != resource) {
+        if (ctrllayer->id_layer != id_layer) {
             continue;
-    }
+        }
 
-        wl_resource_destroy(resource);
-        break;
+        wl_resource_destroy(ctrllayer->resource);
     }
 }
 
@@ -1210,22 +1268,6 @@ add_client_to_resources(struct ivishell *shell,
     uint32_t id_layout_surface = 0;
     uint32_t id_layout_layer = 0;
 
-    wl_list_for_each(ivisurf, &shell->list_surface, link) {
-        id_layout_surface =
-            ivi_layout_getIdOfSurface(ivisurf->layout_surface);
-
-        ivi_controller_send_surface(controller->resource,
-                                    id_layout_surface);
-    }
-
-    wl_list_for_each(ivilayer, &shell->list_layer, link) {
-        id_layout_layer =
-            ivi_layout_getIdOfLayer(ivilayer->layout_layer);
-
-        ivi_controller_send_layer(controller->resource,
-                                  id_layout_layer);
-    }
-
     wl_list_for_each(iviscrn, &shell->list_screen, link) {
         resource_output = wl_resource_find_for_client(
                 &iviscrn->output->resource_list, client);
@@ -1242,6 +1284,20 @@ add_client_to_resources(struct ivishell *shell,
                                    wl_resource_get_id(resource_output),
                                    ctrlscrn->resource);
     }
+    wl_list_for_each_reverse(ivilayer, &shell->list_layer, link) {
+        id_layout_layer =
+            ivi_layout_getIdOfLayer(ivilayer->layout_layer);
+
+        ivi_controller_send_layer(controller->resource,
+                                  id_layout_layer);
+    }
+    wl_list_for_each_reverse(ivisurf, &shell->list_surface, link) {
+        id_layout_surface =
+            ivi_layout_getIdOfSurface(ivisurf->layout_surface);
+
+        ivi_controller_send_surface(controller->resource,
+                                    id_layout_surface);
+    }
 }
 
 static void