/** * @file lv_draw_sdl_refr.c * */ /********************* * INCLUDES *********************/ #include "../../lv_conf_internal.h" #if LV_USE_GPU_SDL #include "../../core/lv_refr.h" #include "lv_draw_sdl.h" #include "lv_draw_sdl_priv.h" #include "lv_draw_sdl_composite.h" #include "lv_draw_sdl_utils.h" #include "lv_draw_sdl_layer.h" /********************* * DEFINES *********************/ /********************** * TYPEDEFS **********************/ /********************** * STATIC PROTOTYPES **********************/ /********************** * STATIC VARIABLES **********************/ /********************** * MACROS **********************/ /********************** * GLOBAL FUNCTIONS **********************/ lv_draw_layer_ctx_t * lv_draw_sdl_layer_init(lv_draw_ctx_t * draw_ctx, lv_draw_layer_ctx_t * layer_ctx, lv_draw_layer_flags_t flags) { lv_draw_sdl_ctx_t * ctx = (lv_draw_sdl_ctx_t *) draw_ctx; SDL_Renderer * renderer = ctx->renderer; lv_draw_sdl_layer_ctx_t * transform_ctx = (lv_draw_sdl_layer_ctx_t *) layer_ctx; transform_ctx->flags = flags; transform_ctx->orig_target = SDL_GetRenderTarget(renderer); lv_coord_t target_w = lv_area_get_width(&layer_ctx->area_full); lv_coord_t target_h = lv_area_get_height(&layer_ctx->area_full); enum lv_draw_sdl_composite_texture_id_t texture_id = LV_DRAW_SDL_COMPOSITE_TEXTURE_ID_TRANSFORM0 + ctx->internals->transform_count; transform_ctx->target = lv_draw_sdl_composite_texture_obtain(ctx, texture_id, target_w, target_h, &transform_ctx->target_in_cache); transform_ctx->target_rect.x = 0; transform_ctx->target_rect.y = 0; transform_ctx->target_rect.w = target_w; transform_ctx->target_rect.h = target_h; layer_ctx->max_row_with_alpha = target_h; layer_ctx->max_row_with_no_alpha = target_h; SDL_SetTextureBlendMode(transform_ctx->target, SDL_BLENDMODE_BLEND); SDL_SetRenderTarget(renderer, transform_ctx->target); /* SDL_RenderClear is not working properly, so we overwrite the target with solid color */ SDL_SetRenderDrawBlendMode(renderer, SDL_BLENDMODE_NONE); SDL_SetRenderDrawColor(renderer, 0, 0, 0, 0); SDL_RenderFillRect(renderer, NULL); SDL_SetRenderDrawBlendMode(renderer, SDL_BLENDMODE_BLEND); /* Set proper drawing context for transform layer */ ctx->internals->transform_count += 1; draw_ctx->buf_area = &layer_ctx->area_full; draw_ctx->clip_area = &layer_ctx->area_full; return layer_ctx; } void lv_draw_sdl_layer_blend(lv_draw_ctx_t * draw_ctx, lv_draw_layer_ctx_t * layer_ctx, const lv_draw_img_dsc_t * draw_dsc) { lv_draw_sdl_ctx_t * ctx = (lv_draw_sdl_ctx_t *) draw_ctx; lv_draw_sdl_layer_ctx_t * transform_ctx = (lv_draw_sdl_layer_ctx_t *) layer_ctx; SDL_Renderer * renderer = ctx->renderer; SDL_Rect trans_rect; if(transform_ctx->flags & LV_DRAW_LAYER_FLAG_CAN_SUBDIVIDE) { lv_area_zoom_to_sdl_rect(&layer_ctx->area_act, &trans_rect, draw_dsc->zoom, &draw_dsc->pivot); } else { lv_area_zoom_to_sdl_rect(&layer_ctx->area_full, &trans_rect, draw_dsc->zoom, &draw_dsc->pivot); } SDL_SetRenderTarget(renderer, transform_ctx->orig_target); /*Render off-screen texture, transformed*/ SDL_Rect clip_rect; lv_area_to_sdl_rect(layer_ctx->original.clip_area, &clip_rect); SDL_Point center = {.x = draw_dsc->pivot.x, .y = draw_dsc->pivot.y}; SDL_RenderSetClipRect(renderer, &clip_rect); SDL_SetTextureAlphaMod(transform_ctx->target, draw_dsc->opa); SDL_RenderCopyEx(renderer, transform_ctx->target, &transform_ctx->target_rect, &trans_rect, draw_dsc->angle, ¢er, SDL_FLIP_NONE); SDL_RenderSetClipRect(renderer, NULL); } void lv_draw_sdl_layer_destroy(lv_draw_ctx_t * draw_ctx, lv_draw_layer_ctx_t * layer_ctx) { lv_draw_sdl_ctx_t * ctx = (lv_draw_sdl_ctx_t *) draw_ctx; lv_draw_sdl_layer_ctx_t * transform_ctx = (lv_draw_sdl_layer_ctx_t *) layer_ctx; if(!transform_ctx->target_in_cache && transform_ctx->target != NULL) { LV_LOG_WARN("Texture is not cached, this will impact performance."); SDL_DestroyTexture(transform_ctx->target); } ctx->internals->transform_count -= 1; } void lv_draw_sdl_transform_areas_offset(lv_draw_sdl_ctx_t * ctx, bool has_composite, lv_area_t * apply_area, lv_area_t * coords, lv_area_t * clip) { if(ctx->internals->transform_count == 0) { return; } lv_area_t * area = ctx->base_draw.buf_area; lv_area_move(coords, -area->x1, -area->y1); lv_area_move(clip, -area->x1, -area->y1); if(has_composite) { lv_area_move(apply_area, -area->x1, -area->y1); } } /********************** * STATIC FUNCTIONS **********************/ #endif /*LV_USE_GPU_SDL*/