mirror of
https://gitee.com/zlgopen/awtk.git
synced 2024-11-29 18:48:09 +08:00
add lcd_profile to help find performance issues
This commit is contained in:
parent
b8366b06e8
commit
a4592c4242
@ -51,6 +51,7 @@ NANOVG_BACKEND_PROJS=[];
|
||||
|
||||
COMMON_CCFLAGS=' -DTK_ROOT=\\\"'+TK_ROOT+'\\\" '
|
||||
COMMON_CCFLAGS=COMMON_CCFLAGS+' -DWITH_STB_FONT '
|
||||
#COMMON_CCFLAGS=COMMON_CCFLAGS+' -DENABLE_PERFORMANCE_PROFILE=1 '
|
||||
#COMMON_CCFLAGS=COMMON_CCFLAGS+' -DWITH_FT_FONT '
|
||||
COMMON_CCFLAGS=COMMON_CCFLAGS+' -DSTBTT_STATIC -DSTB_IMAGE_STATIC -DWITH_STB_IMAGE '
|
||||
COMMON_CCFLAGS=COMMON_CCFLAGS+' -DWITH_VGCANVAS -DWITH_UNICODE_BREAK -DWITH_DESKTOP_STYLE '
|
||||
|
@ -1,4 +1,7 @@
|
||||
# 最新动态
|
||||
* 2019/03/21
|
||||
* 增加lcd\_profile用于对绘制函数进行profile。
|
||||
|
||||
* 2019/03/20
|
||||
* 支持编译Windows 32 位版本(感谢陈谭提供补丁)
|
||||
* 修改资源生成脚本,对于data数据,不限制文件名(DATA类型的资源需带扩展名才能访问)。
|
||||
|
@ -1,5 +1,7 @@
|
||||
## 优化技巧
|
||||
|
||||
### 一、优化提示
|
||||
|
||||
* memcpy是最快的贴图方式,所以对于不透明的图片,尽量保持与Framebuffer一致的格式,这样可以直接使用memcpy贴图。
|
||||
|
||||
> 比如FrameBuffer的格式是BGR565,请定义宏WITH\_BITMAP\_BGR565。
|
||||
@ -41,3 +43,56 @@
|
||||
* 使用3个framebuffer可以避免GUI等待和拷贝,能够有效提高帧率,有条件时尽量启用。
|
||||
|
||||
* 猜测往往是错误的,请用函数time\_now\_ms去度量你怀疑的地方。
|
||||
|
||||
### 二、工具
|
||||
|
||||
如果定义全局的宏(在工程中定义)ENABLE\_PERFORMANCE\_PROFILE,会使用lcd\_profile对全部绘制函数(图片、文字和填充等等)进行时间统计。当绘制一帧需要的时间超过25ms,会打印一些信息:
|
||||
|
||||
```
|
||||
#####################################
|
||||
src/base/lcd_profile.c:326
|
||||
-------------------------------------
|
||||
total_cost=30
|
||||
draw_image_cost=18 times=1
|
||||
draw_text_cost=0 times=15
|
||||
fill_cost=0 times=15
|
||||
stroke_cost=0 times=15
|
||||
end_frame_cost=10
|
||||
-------------------------------------
|
||||
```
|
||||
|
||||
|
||||
也可以在lcd\_profile\_end\_frame函数里设置一个断点,从profile对象上能查看到更详细的统计信息:
|
||||
|
||||
```
|
||||
uint32_t total_cost;
|
||||
uint32_t swap_cost;
|
||||
uint32_t flush_cost;
|
||||
|
||||
uint32_t draw_image_cost;
|
||||
uint32_t draw_image_times;
|
||||
uint32_t draw_image_pixels;
|
||||
|
||||
uint32_t draw_text_cost;
|
||||
uint32_t draw_text_times;
|
||||
uint32_t draw_text_chars;
|
||||
|
||||
uint32_t fill_cost;
|
||||
uint32_t fill_times;
|
||||
uint32_t fill_pixels;
|
||||
|
||||
uint32_t stroke_cost;
|
||||
uint32_t stroke_times;
|
||||
uint32_t stroke_pixels;
|
||||
```
|
||||
|
||||
>参考[lcd_profile.c](https://github.com/zlgopen/awtk/blob/master/src/base/lcd_profile.c)
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
@ -28,6 +28,8 @@
|
||||
#include "base/wuxiaolin.inc"
|
||||
#include "base/system_info.h"
|
||||
|
||||
#include "base/lcd_profile.h"
|
||||
|
||||
static ret_t canvas_draw_fps(canvas_t* c);
|
||||
|
||||
static rect_t* canvas_fix_rect(const rect_t* r, rect_t* o) {
|
||||
@ -71,7 +73,7 @@ canvas_t* canvas_init(canvas_t* c, lcd_t* lcd, font_manager_t* font_manager) {
|
||||
|
||||
memset(c, 0x00, sizeof(canvas_t));
|
||||
|
||||
c->lcd = lcd;
|
||||
c->lcd = lcd_profile_create(lcd);
|
||||
c->font_manager = font_manager;
|
||||
|
||||
return c;
|
||||
@ -205,6 +207,7 @@ ret_t canvas_set_stroke_color(canvas_t* c, color_t color) {
|
||||
ret_t canvas_set_global_alpha(canvas_t* c, uint8_t alpha) {
|
||||
return_value_if_fail(c != NULL, RET_BAD_PARAMS);
|
||||
|
||||
c->global_alpha = alpha;
|
||||
lcd_set_global_alpha(c->lcd, alpha);
|
||||
|
||||
return RET_OK;
|
||||
|
@ -65,6 +65,7 @@ struct _canvas_t {
|
||||
align_v_t text_align_v;
|
||||
align_h_t text_align_h;
|
||||
font_manager_t* font_manager;
|
||||
uint8_t global_alpha;
|
||||
};
|
||||
|
||||
/**
|
||||
|
@ -138,6 +138,7 @@ typedef enum _lcd_type_t {
|
||||
*/
|
||||
LCD_VGCANVAS
|
||||
} lcd_type_t;
|
||||
|
||||
/**
|
||||
* @class lcd_t
|
||||
* 显示设备抽象基类。
|
||||
@ -258,7 +259,7 @@ struct _lcd_t {
|
||||
* 准备绘制。
|
||||
* @param {lcd_t*} lcd lcd对象。
|
||||
* @param {rect_t*} dirty_rect 需要绘制的区域。
|
||||
* @param {bool_t} anim_mode 动画模式,如果可能,直接画到显存而不是离线的framebuffer。
|
||||
* @param {lcd_draw_mode_t} anim_mode 动画模式,如果可能,直接画到显存而不是离线的framebuffer。
|
||||
*
|
||||
* @return {ret_t} 返回RET_OK表示成功,否则表示失败。
|
||||
*/
|
||||
@ -361,9 +362,9 @@ ret_t lcd_set_font_size(lcd_t* lcd, uint32_t font_size);
|
||||
* @method lcd_draw_vline
|
||||
* 绘制一条垂直线。
|
||||
* @param {lcd_t*} lcd lcd对象。
|
||||
* @param {xy_t*} x x坐标。
|
||||
* @param {xy_t*} y y坐标。
|
||||
* @param {xy_t*} h 直线高度。
|
||||
* @param {xy_t} x x坐标。
|
||||
* @param {xy_t} y y坐标。
|
||||
* @param {xy_t} h 直线高度。
|
||||
*
|
||||
* @return {ret_t} 返回RET_OK表示成功,否则表示失败。
|
||||
*/
|
||||
@ -373,9 +374,9 @@ ret_t lcd_draw_vline(lcd_t* lcd, xy_t x, xy_t y, wh_t h);
|
||||
* @method lcd_draw_hline
|
||||
* 绘制一条水平线。
|
||||
* @param {lcd_t*} lcd lcd对象。
|
||||
* @param {xy_t*} x x坐标。
|
||||
* @param {xy_t*} y y坐标。
|
||||
* @param {xy_t*} w 直线宽度。
|
||||
* @param {xy_t} x x坐标。
|
||||
* @param {xy_t} y y坐标。
|
||||
* @param {xy_t} w 直线宽度。
|
||||
*
|
||||
* @return {ret_t} 返回RET_OK表示成功,否则表示失败。
|
||||
*/
|
||||
@ -393,13 +394,13 @@ ret_t lcd_draw_hline(lcd_t* lcd, xy_t x, xy_t y, wh_t w);
|
||||
ret_t lcd_draw_points(lcd_t* lcd, point_t* points, uint32_t nr);
|
||||
|
||||
/**
|
||||
* @method lcd_get_point_color_t
|
||||
* @method lcd_get_point_color
|
||||
* 获取指定点的颜色,对于基于非FrameBuffer的LCD,返回当前的fill_color。
|
||||
* @param {lcd_t*} lcd lcd对象。
|
||||
* @param {xy_t} x x坐标。
|
||||
* @param {xy_t} y y坐标。
|
||||
*
|
||||
* @return {ret_t} 返回RET_OK表示成功,否则表示失败。
|
||||
* @return {color_t} 返回RET_OK表示成功,否则表示失败。
|
||||
*/
|
||||
color_t lcd_get_point_color(lcd_t* lcd, xy_t x, xy_t y);
|
||||
|
||||
|
461
src/base/lcd_profile.c
Normal file
461
src/base/lcd_profile.c
Normal file
@ -0,0 +1,461 @@
|
||||
/**
|
||||
* File: lcd_profile.c
|
||||
* Author: AWTK Develop Team
|
||||
* Brief: wrap lcd for performance profile.
|
||||
*
|
||||
* Copyright (c) 2018 - 2019 Guangzhou ZHIYUAN Electronics Co.,Ltd.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* License file for more details.
|
||||
*
|
||||
*/
|
||||
|
||||
/**
|
||||
* History:
|
||||
* ================================================================
|
||||
* 2018-03-21 Li XianJing <xianjimli@hotmail.com> created
|
||||
*
|
||||
*/
|
||||
|
||||
#include "tkc/mem.h"
|
||||
#include "tkc/time_now.h"
|
||||
#include "base/lcd_profile.h"
|
||||
|
||||
#ifdef ENABLE_PERFORMANCE_PROFILE
|
||||
static ret_t lcd_profile_begin_frame(lcd_t* lcd, rect_t* dirty_rect) {
|
||||
ret_t ret = RET_OK;
|
||||
lcd_profile_t* profile = LCD_PROFILE(lcd);
|
||||
|
||||
profile->draw_image_times = 0;
|
||||
profile->draw_image_cost = 0;
|
||||
profile->draw_image_pixels = 0;
|
||||
profile->draw_text_times = 0;
|
||||
profile->draw_text_cost = 0;
|
||||
profile->draw_text_chars = 0;
|
||||
profile->fill_times = 0;
|
||||
profile->fill_cost = 0;
|
||||
profile->fill_pixels = 0;
|
||||
profile->stroke_times = 0;
|
||||
profile->stroke_cost = 0;
|
||||
profile->stroke_pixels = 0;
|
||||
|
||||
profile->begin_frame_time = time_now_ms();
|
||||
ret = lcd_begin_frame(profile->impl, dirty_rect, lcd->draw_mode);
|
||||
|
||||
return ret;
|
||||
}
|
||||
|
||||
static ret_t lcd_profile_set_clip_rect(lcd_t* lcd, rect_t* rect) {
|
||||
lcd_profile_t* profile = LCD_PROFILE(lcd);
|
||||
|
||||
return lcd_set_clip_rect(profile->impl, rect);
|
||||
}
|
||||
|
||||
static ret_t lcd_profile_get_clip_rect(lcd_t* lcd, rect_t* rect) {
|
||||
lcd_profile_t* profile = LCD_PROFILE(lcd);
|
||||
|
||||
return lcd_get_clip_rect(profile->impl, rect);
|
||||
}
|
||||
|
||||
static ret_t lcd_profile_resize(lcd_t* lcd, wh_t w, wh_t h, uint32_t line_length) {
|
||||
lcd_profile_t* profile = LCD_PROFILE(lcd);
|
||||
|
||||
return lcd_resize(profile->impl, w, h, line_length);
|
||||
}
|
||||
|
||||
static ret_t lcd_profile_set_global_alpha(lcd_t* lcd, uint8_t alpha) {
|
||||
lcd_profile_t* profile = LCD_PROFILE(lcd);
|
||||
|
||||
return lcd_set_global_alpha(profile->impl, alpha);
|
||||
}
|
||||
|
||||
static ret_t lcd_profile_set_text_color(lcd_t* lcd, color_t color) {
|
||||
lcd_profile_t* profile = LCD_PROFILE(lcd);
|
||||
|
||||
return lcd_set_text_color(profile->impl, color);
|
||||
}
|
||||
|
||||
static ret_t lcd_profile_set_stroke_color(lcd_t* lcd, color_t color) {
|
||||
lcd_profile_t* profile = LCD_PROFILE(lcd);
|
||||
|
||||
return lcd_set_stroke_color(profile->impl, color);
|
||||
}
|
||||
|
||||
static ret_t lcd_profile_set_fill_color(lcd_t* lcd, color_t color) {
|
||||
lcd_profile_t* profile = LCD_PROFILE(lcd);
|
||||
|
||||
return lcd_set_fill_color(profile->impl, color);
|
||||
}
|
||||
|
||||
static ret_t lcd_profile_set_font_name(lcd_t* lcd, const char* name) {
|
||||
lcd_profile_t* profile = LCD_PROFILE(lcd);
|
||||
|
||||
return lcd_set_font_name(profile->impl, name);
|
||||
}
|
||||
|
||||
static ret_t lcd_profile_set_font_size(lcd_t* lcd, uint32_t font_size) {
|
||||
lcd_profile_t* profile = LCD_PROFILE(lcd);
|
||||
|
||||
return lcd_set_font_size(profile->impl, font_size);
|
||||
}
|
||||
|
||||
static ret_t lcd_profile_draw_vline(lcd_t* lcd, xy_t x, xy_t y, xy_t h) {
|
||||
ret_t ret = RET_OK;
|
||||
|
||||
uint32_t cost = 0;
|
||||
uint32_t start = time_now_ms();
|
||||
lcd_profile_t* profile = LCD_PROFILE(lcd);
|
||||
ret = lcd_draw_vline(profile->impl, x, y, h);
|
||||
cost = time_now_ms() - start;
|
||||
|
||||
profile->stroke_times++;
|
||||
profile->stroke_cost += cost;
|
||||
profile->stroke_pixels += h;
|
||||
|
||||
return ret;
|
||||
}
|
||||
|
||||
static ret_t lcd_profile_draw_hline(lcd_t* lcd, xy_t x, xy_t y, xy_t w) {
|
||||
ret_t ret = RET_OK;
|
||||
|
||||
uint32_t cost = 0;
|
||||
uint32_t start = time_now_ms();
|
||||
lcd_profile_t* profile = LCD_PROFILE(lcd);
|
||||
ret = lcd_draw_hline(profile->impl, x, y, w);
|
||||
cost = time_now_ms() - start;
|
||||
|
||||
profile->stroke_times++;
|
||||
profile->stroke_cost += cost;
|
||||
profile->stroke_pixels += w;
|
||||
|
||||
return ret;
|
||||
}
|
||||
|
||||
static ret_t lcd_profile_draw_points(lcd_t* lcd, point_t* points, uint32_t nr) {
|
||||
ret_t ret = RET_OK;
|
||||
|
||||
uint32_t cost = 0;
|
||||
uint32_t start = time_now_ms();
|
||||
lcd_profile_t* profile = LCD_PROFILE(lcd);
|
||||
ret = lcd_draw_points(profile->impl, points, nr);
|
||||
cost = time_now_ms() - start;
|
||||
|
||||
profile->stroke_times++;
|
||||
profile->stroke_cost += cost;
|
||||
profile->stroke_pixels += nr;
|
||||
|
||||
return ret;
|
||||
}
|
||||
|
||||
static color_t lcd_profile_get_point_color(lcd_t* lcd, xy_t x, xy_t y) {
|
||||
lcd_profile_t* profile = LCD_PROFILE(lcd);
|
||||
|
||||
return lcd_get_point_color(profile->impl, x, y);
|
||||
}
|
||||
|
||||
static ret_t lcd_profile_fill_rect(lcd_t* lcd, xy_t x, xy_t y, wh_t w, wh_t h) {
|
||||
ret_t ret = RET_OK;
|
||||
|
||||
uint32_t cost = 0;
|
||||
uint32_t start = time_now_ms();
|
||||
lcd_profile_t* profile = LCD_PROFILE(lcd);
|
||||
ret = lcd_fill_rect(profile->impl, x, y, w, h);
|
||||
cost = time_now_ms() - start;
|
||||
|
||||
profile->fill_times++;
|
||||
profile->fill_cost += cost;
|
||||
profile->fill_pixels += w * h;
|
||||
|
||||
return ret;
|
||||
}
|
||||
|
||||
static ret_t lcd_profile_stroke_rect(lcd_t* lcd, xy_t x, xy_t y, wh_t w, wh_t h) {
|
||||
ret_t ret = RET_OK;
|
||||
|
||||
uint32_t cost = 0;
|
||||
uint32_t start = time_now_ms();
|
||||
lcd_profile_t* profile = LCD_PROFILE(lcd);
|
||||
ret = lcd_stroke_rect(profile->impl, x, y, w, h);
|
||||
cost = time_now_ms() - start;
|
||||
|
||||
profile->stroke_times++;
|
||||
profile->stroke_cost += cost;
|
||||
profile->stroke_pixels += w * h;
|
||||
|
||||
return ret;
|
||||
}
|
||||
|
||||
static ret_t lcd_profile_draw_glyph(lcd_t* lcd, glyph_t* glyph, rect_t* src, xy_t x, xy_t y) {
|
||||
ret_t ret = RET_OK;
|
||||
|
||||
uint32_t cost = 0;
|
||||
uint32_t start = time_now_ms();
|
||||
lcd_profile_t* profile = LCD_PROFILE(lcd);
|
||||
ret = lcd_draw_glyph(profile->impl, glyph, src, x, y);
|
||||
cost = time_now_ms() - start;
|
||||
|
||||
profile->draw_text_times++;
|
||||
profile->draw_text_cost += cost;
|
||||
profile->draw_text_chars++;
|
||||
|
||||
return ret;
|
||||
}
|
||||
|
||||
static float_t lcd_profile_measure_text(lcd_t* lcd, const wchar_t* str, uint32_t nr) {
|
||||
lcd_profile_t* profile = LCD_PROFILE(lcd);
|
||||
|
||||
return lcd_measure_text(profile->impl, str, nr);
|
||||
}
|
||||
|
||||
static ret_t lcd_profile_draw_text(lcd_t* lcd, const wchar_t* str, uint32_t nr, xy_t x, xy_t y) {
|
||||
ret_t ret = RET_OK;
|
||||
|
||||
uint32_t cost = 0;
|
||||
uint32_t start = time_now_ms();
|
||||
lcd_profile_t* profile = LCD_PROFILE(lcd);
|
||||
ret = lcd_draw_text(profile->impl, str, nr, x, y);
|
||||
cost = time_now_ms() - start;
|
||||
|
||||
profile->draw_text_times++;
|
||||
profile->draw_text_cost += cost;
|
||||
profile->draw_text_chars += nr;
|
||||
|
||||
return ret;
|
||||
}
|
||||
|
||||
static ret_t lcd_profile_draw_image(lcd_t* lcd, bitmap_t* img, rect_t* src, rect_t* dst) {
|
||||
ret_t ret = RET_OK;
|
||||
|
||||
uint32_t cost = 0;
|
||||
uint32_t start = time_now_ms();
|
||||
lcd_profile_t* profile = LCD_PROFILE(lcd);
|
||||
ret = lcd_draw_image(profile->impl, img, src, dst);
|
||||
cost = time_now_ms() - start;
|
||||
|
||||
profile->draw_image_times++;
|
||||
profile->draw_image_cost += cost;
|
||||
profile->draw_image_pixels += dst->w * dst->h;
|
||||
|
||||
return ret;
|
||||
}
|
||||
|
||||
static ret_t lcd_profile_draw_image_matrix(lcd_t* lcd, draw_image_info_t* info) {
|
||||
ret_t ret = RET_OK;
|
||||
|
||||
uint32_t cost = 0;
|
||||
uint32_t start = time_now_ms();
|
||||
lcd_profile_t* profile = LCD_PROFILE(lcd);
|
||||
ret = lcd_draw_image_matrix(profile->impl, info);
|
||||
cost = time_now_ms() - start;
|
||||
|
||||
profile->draw_image_times++;
|
||||
profile->draw_image_cost += cost;
|
||||
|
||||
return ret;
|
||||
}
|
||||
|
||||
static vgcanvas_t* lcd_profile_get_vgcanvas(lcd_t* lcd) {
|
||||
lcd_profile_t* profile = LCD_PROFILE(lcd);
|
||||
|
||||
return lcd_get_vgcanvas(profile->impl);
|
||||
}
|
||||
|
||||
static ret_t lcd_profile_take_snapshot(lcd_t* lcd, bitmap_t* img, bool_t auto_rotate) {
|
||||
ret_t ret = RET_OK;
|
||||
|
||||
uint32_t cost = 0;
|
||||
uint32_t start = time_now_ms();
|
||||
lcd_profile_t* profile = LCD_PROFILE(lcd);
|
||||
ret = lcd_take_snapshot(profile->impl, img, auto_rotate);
|
||||
cost = time_now_ms() - start;
|
||||
|
||||
return ret;
|
||||
}
|
||||
|
||||
static bitmap_format_t lcd_profile_get_desired_bitmap_format(lcd_t* lcd) {
|
||||
lcd_profile_t* profile = LCD_PROFILE(lcd);
|
||||
|
||||
return lcd_get_desired_bitmap_format(profile->impl);
|
||||
}
|
||||
|
||||
static ret_t lcd_profile_swap(lcd_t* lcd) {
|
||||
ret_t ret = RET_OK;
|
||||
|
||||
uint32_t cost = 0;
|
||||
uint32_t start = time_now_ms();
|
||||
lcd_profile_t* profile = LCD_PROFILE(lcd);
|
||||
ret = lcd_swap(profile->impl);
|
||||
cost = time_now_ms() - start;
|
||||
|
||||
profile->swap_cost = cost;
|
||||
|
||||
return ret;
|
||||
}
|
||||
|
||||
static ret_t lcd_profile_flush(lcd_t* lcd) {
|
||||
ret_t ret = RET_OK;
|
||||
|
||||
uint32_t cost = 0;
|
||||
uint32_t start = time_now_ms();
|
||||
lcd_profile_t* profile = LCD_PROFILE(lcd);
|
||||
ret = lcd_flush(profile->impl);
|
||||
cost = time_now_ms() - start;
|
||||
|
||||
profile->flush_cost = cost;
|
||||
|
||||
return ret;
|
||||
}
|
||||
|
||||
static ret_t lcd_profile_end_frame(lcd_t* lcd) {
|
||||
ret_t ret = RET_OK;
|
||||
|
||||
uint32_t cost = 0;
|
||||
uint32_t end = 0;
|
||||
uint32_t start = time_now_ms();
|
||||
lcd_profile_t* profile = LCD_PROFILE(lcd);
|
||||
ret = lcd_end_frame(profile->impl);
|
||||
end = time_now_ms();
|
||||
cost = end - start;
|
||||
|
||||
profile->total_cost = time_now_ms() - profile->begin_frame_time;
|
||||
|
||||
if (profile->total_cost > 25) {
|
||||
log_debug("#####################################\n");
|
||||
log_debug("%s:%d\n", __FILE__, __LINE__);
|
||||
log_debug("-------------------------------------\n");
|
||||
log_debug(" total_cost=%u \n", profile->total_cost);
|
||||
log_debug(" draw_image_cost=%u times=%u\n", profile->draw_image_cost,
|
||||
profile->draw_image_times);
|
||||
log_debug(" draw_text_cost=%u times=%u\n", profile->draw_text_cost, profile->draw_text_times);
|
||||
log_debug(" fill_cost=%u times=%u\n", profile->fill_cost, profile->fill_times);
|
||||
log_debug(" stroke_cost=%u times=%u\n", profile->stroke_cost, profile->stroke_times);
|
||||
|
||||
if (cost) {
|
||||
log_debug(" end_frame_cost=%u\n", cost);
|
||||
}
|
||||
if (profile->flush_cost) {
|
||||
log_debug(" flush_cost=%u\n", profile->flush_cost);
|
||||
}
|
||||
if (profile->swap_cost) {
|
||||
log_debug(" swap_cost=%u\n", profile->swap_cost);
|
||||
}
|
||||
log_debug("-------------------------------------\n");
|
||||
}
|
||||
|
||||
return ret;
|
||||
}
|
||||
|
||||
lcd_t* lcd_profile_create(lcd_t* impl) {
|
||||
lcd_t* lcd = NULL;
|
||||
|
||||
return_value_if_fail(impl != NULL, NULL);
|
||||
lcd = (lcd_t*)TKMEM_ZALLOC(lcd_profile_t);
|
||||
return_value_if_fail(lcd != NULL, NULL);
|
||||
|
||||
lcd->w = impl->w;
|
||||
lcd->h = impl->h;
|
||||
lcd->type = impl->type;
|
||||
lcd->ratio = impl->ratio;
|
||||
LCD_PROFILE(lcd)->impl = impl;
|
||||
lcd->support_dirty_rect = impl->support_dirty_rect;
|
||||
|
||||
lcd->begin_frame = lcd_profile_begin_frame;
|
||||
lcd->set_global_alpha = lcd_profile_set_global_alpha;
|
||||
lcd->set_text_color = lcd_profile_set_text_color;
|
||||
lcd->set_stroke_color = lcd_profile_set_stroke_color;
|
||||
lcd->set_fill_color = lcd_profile_set_fill_color;
|
||||
|
||||
if (impl->set_font_name != NULL) {
|
||||
lcd->set_font_name = lcd_profile_set_font_name;
|
||||
lcd->set_font_size = lcd_profile_set_font_size;
|
||||
}
|
||||
|
||||
if (impl->set_clip_rect != NULL) {
|
||||
lcd->set_clip_rect = lcd_profile_set_clip_rect;
|
||||
}
|
||||
|
||||
if (impl->get_clip_rect != NULL) {
|
||||
lcd->get_clip_rect = lcd_profile_get_clip_rect;
|
||||
}
|
||||
|
||||
if (impl->resize != NULL) {
|
||||
lcd->resize = lcd_profile_resize;
|
||||
}
|
||||
|
||||
if (impl->draw_vline != NULL) {
|
||||
lcd->draw_vline = lcd_profile_draw_vline;
|
||||
}
|
||||
|
||||
if (impl->draw_hline != NULL) {
|
||||
lcd->draw_hline = lcd_profile_draw_hline;
|
||||
}
|
||||
|
||||
if (impl->draw_points != NULL) {
|
||||
lcd->draw_points = lcd_profile_draw_points;
|
||||
}
|
||||
|
||||
if (impl->get_point_color != NULL) {
|
||||
lcd->get_point_color = lcd_profile_get_point_color;
|
||||
}
|
||||
|
||||
if (impl->fill_rect != NULL) {
|
||||
lcd->fill_rect = lcd_profile_fill_rect;
|
||||
}
|
||||
|
||||
if (impl->stroke_rect != NULL) {
|
||||
lcd->stroke_rect = lcd_profile_stroke_rect;
|
||||
}
|
||||
|
||||
if (impl->draw_glyph != NULL) {
|
||||
lcd->draw_glyph = lcd_profile_draw_glyph;
|
||||
}
|
||||
|
||||
if (impl->measure_text != NULL) {
|
||||
lcd->measure_text = lcd_profile_measure_text;
|
||||
}
|
||||
|
||||
if (impl->draw_text != NULL) {
|
||||
lcd->draw_text = lcd_profile_draw_text;
|
||||
}
|
||||
|
||||
if (impl->draw_image != NULL) {
|
||||
lcd->draw_image = lcd_profile_draw_image;
|
||||
}
|
||||
|
||||
if (impl->draw_image_matrix != NULL) {
|
||||
lcd->draw_image_matrix = lcd_profile_draw_image_matrix;
|
||||
}
|
||||
|
||||
if (impl->get_vgcanvas != NULL) {
|
||||
lcd->get_vgcanvas = lcd_profile_get_vgcanvas;
|
||||
}
|
||||
|
||||
if (impl->take_snapshot != NULL) {
|
||||
lcd->take_snapshot = lcd_profile_take_snapshot;
|
||||
}
|
||||
|
||||
if (impl->get_desired_bitmap_format != NULL) {
|
||||
lcd->get_desired_bitmap_format = lcd_profile_get_desired_bitmap_format;
|
||||
}
|
||||
|
||||
if (impl->swap != NULL) {
|
||||
lcd->swap = lcd_profile_swap;
|
||||
}
|
||||
|
||||
if (impl->flush != NULL) {
|
||||
lcd->flush = lcd_profile_flush;
|
||||
}
|
||||
|
||||
if (impl->end_frame != NULL) {
|
||||
lcd->end_frame = lcd_profile_end_frame;
|
||||
}
|
||||
|
||||
return lcd;
|
||||
}
|
||||
#else
|
||||
lcd_t* lcd_profile_create(lcd_t* impl) {
|
||||
return impl;
|
||||
}
|
||||
#endif /*ENABLE_PERFORMANCE_PROFILE*/
|
70
src/base/lcd_profile.h
Normal file
70
src/base/lcd_profile.h
Normal file
@ -0,0 +1,70 @@
|
||||
/**
|
||||
* File: lcd_profile.h
|
||||
* Author: AWTK Develop Team
|
||||
* Brief: wrap lcd for performance profile.
|
||||
*
|
||||
* Copyright (c) 2018 - 2019 Guangzhou ZHIYUAN Electronics Co.,Ltd.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* License file for more details.
|
||||
*
|
||||
*/
|
||||
|
||||
/**
|
||||
* History:
|
||||
* ================================================================
|
||||
* 2018-03-21 Li XianJing <xianjimli@hotmail.com> created
|
||||
*
|
||||
*/
|
||||
|
||||
#ifndef LCD_PROFILE_H
|
||||
#define LCD_PROFILE_H
|
||||
|
||||
#include "base/lcd.h"
|
||||
|
||||
BEGIN_C_DECLS
|
||||
|
||||
/**
|
||||
* @class lcd_profile_t
|
||||
* @parent lcd_t
|
||||
* 对现有LCD对象进行包装,实现对各个函数的时间统计,用于辅助定位性能瓶颈。
|
||||
*
|
||||
*/
|
||||
typedef struct _lcd_profile_t {
|
||||
lcd_t lcd;
|
||||
|
||||
/*private*/
|
||||
lcd_t* impl;
|
||||
|
||||
uint32_t begin_frame_time;
|
||||
|
||||
uint32_t total_cost;
|
||||
uint32_t swap_cost;
|
||||
uint32_t flush_cost;
|
||||
|
||||
uint32_t draw_image_cost;
|
||||
uint32_t draw_image_times;
|
||||
uint32_t draw_image_pixels;
|
||||
|
||||
uint32_t draw_text_cost;
|
||||
uint32_t draw_text_times;
|
||||
uint32_t draw_text_chars;
|
||||
|
||||
uint32_t fill_cost;
|
||||
uint32_t fill_times;
|
||||
uint32_t fill_pixels;
|
||||
|
||||
uint32_t stroke_cost;
|
||||
uint32_t stroke_times;
|
||||
uint32_t stroke_pixels;
|
||||
} lcd_profile_t;
|
||||
|
||||
lcd_t* lcd_profile_create(lcd_t* impl);
|
||||
|
||||
#define LCD_PROFILE(lcd) ((lcd_profile_t*)(lcd))
|
||||
|
||||
END_C_DECLS
|
||||
|
||||
#endif /*LCD_PROFILE_H*/
|
@ -824,7 +824,7 @@ ret_t widget_paint_helper(widget_t* widget, canvas_t* c, const char* icon, wstr_
|
||||
static ret_t widget_paint_impl(widget_t* widget, canvas_t* c) {
|
||||
int32_t ox = widget->x;
|
||||
int32_t oy = widget->y;
|
||||
uint8_t save_alpha = c->lcd->global_alpha;
|
||||
uint8_t save_alpha = c->global_alpha;
|
||||
|
||||
if (widget->opacity < TK_OPACITY_ALPHA) {
|
||||
canvas_set_global_alpha(c, (widget->opacity * save_alpha) / 0xff);
|
||||
|
File diff suppressed because it is too large
Load Diff
Loading…
Reference in New Issue
Block a user