static void DestroyBackground2D(SFNode *node) { M_Background2D *top; Background2DStack *ptr; BackgroundStatus *status; ptr = (Background2DStack *) Node_GetPrivate(node); DeleteDrawableNode(ptr->node); while (ChainGetCount(ptr->surfaces_links)) { status = ChainGetEntry(ptr->surfaces_links, 0); ChainDeleteEntry(ptr->surfaces_links, 0); ChainDeleteItem(status->bind_stack, node); /*force bind - bindable nodes are the only cases where we generate eventIn in the scene graph*/ if (ChainGetCount(status->bind_stack)) { top = ChainGetEntry(status->bind_stack, 0); if (!top->set_bind) { top->set_bind = 1; if (top->on_set_bind) top->on_set_bind((SFNode *) top); } } free(status); } texture_destroy(&ptr->txh); DeleteChain(ptr->surfaces_links); free(ptr); }
static void b2D_set_bind(SFNode *node) { u32 i; Bool isOnTop; M_Background2D *newTop; M_Background2D *bck = (M_Background2D *) node; Background2DStack *bcks = (Background2DStack *)Node_GetPrivate(node); for (i=0; i<ChainGetCount(bcks->surfaces_links); i++) { BackgroundStatus *status = ChainGetEntry(bcks->surfaces_links, i); isOnTop = (ChainGetEntry(status->bind_stack, 0)==node) ? 1 : 0; if (! bck->set_bind) { if (bck->isBound) { bck->isBound = 0; Node_OnEventOutSTR(node, "isBound"); } if (isOnTop && (ChainGetCount(status->bind_stack)>1)) { ChainDeleteEntry(status->bind_stack, 0); ChainAddEntry(status->bind_stack, node); newTop = ChainGetEntry(status->bind_stack, 0); newTop->set_bind = 1; newTop->on_set_bind((SFNode *) newTop); } } else { if (! bck->isBound) { bck->isBound = 1; Node_OnEventOutSTR(node, "isBound"); Node_SetDirty(node, 0); } if (!isOnTop) { newTop = ChainGetEntry(status->bind_stack, 0); ChainDeleteItem(status->bind_stack, node); ChainInsertEntry(status->bind_stack, node, 0); newTop->set_bind = 0; newTop->on_set_bind((SFNode *) newTop); } } } /*and redraw scene*/ SR_Invalidate(bcks->compositor, NULL); }
static void TraverseBackground2D(GF_Node *node, void *rs, Bool is_destroy) { u32 col; BackgroundStatus *status; M_Background2D *bck; Background2DStack *stack = (Background2DStack *) gf_node_get_private(node); GF_TraverseState *tr_state = (GF_TraverseState *)rs; if (is_destroy) { DestroyBackground2D(node); return; } bck = (M_Background2D *)node; /*special case for background in Layer2D: the background is seen as a regular drawable, so RENDER_BINDABLE is not used*/ switch (tr_state->traversing_mode) { case TRAVERSE_DRAW_2D: DrawBackground2D_2D(tr_state->ctx, tr_state); return; case TRAVERSE_PICK: case TRAVERSE_GET_BOUNDS: return; } /*first traverse, bound if needed*/ if (gf_list_find(tr_state->backgrounds, node) < 0) { M_Background2D *top_bck = (M_Background2D *)node; gf_list_add(tr_state->backgrounds, node); assert(gf_list_find(stack->reg_stacks, tr_state->backgrounds)==-1); gf_list_add(stack->reg_stacks, tr_state->backgrounds); b2D_new_status(stack, bck); /*only bound if we're on top*/ top_bck = gf_list_get(tr_state->backgrounds, 0); if (!bck->isBound) { if (top_bck== bck) { Bindable_SetIsBound(node, 1); } else if (!top_bck->isBound) { bck->set_bind = 1; bck->on_set_bind(node, NULL); } } /*open the stream if any*/ if (back_use_texture(bck) && !stack->txh.is_open) gf_sc_texture_play(&stack->txh, &bck->url); /*in any case don't draw the first time (since the background could have been declared last)*/ gf_sc_invalidate(stack->txh.compositor, NULL); return; } if (!bck->isBound) return; status = b2d_get_status(stack, tr_state->backgrounds); if (!status) return; if (gf_node_dirty_get(node)) { stack->flags |= CTX_APP_DIRTY; gf_node_dirty_clear(node, 0); col = GF_COL_ARGB_FIXED(FIX_ONE, bck->backColor.red, bck->backColor.green, bck->backColor.blue); if (col != status->ctx.aspect.fill_color) { status->ctx.aspect.fill_color = col; stack->flags |= CTX_APP_DIRTY; } } if (back_use_texture(bck) ) { if (stack->txh.tx_io && !(status->ctx.flags & CTX_APP_DIRTY) && stack->txh.needs_refresh) stack->flags |= CTX_TEXTURE_DIRTY; } status->ctx.flags = stack->flags; if (tr_state->traversing_mode != TRAVERSE_BINDABLE) return; /*3D mode*/ #ifndef GPAC_DISABLE_3D if (tr_state->visual->type_3d) { DrawBackground2D_3D(bck, stack, tr_state); } else #endif DrawBackground2D_2D(&status->ctx, tr_state); }