diff --git a/src/lv_draw/lv_draw_label.c b/src/lv_draw/lv_draw_label.c index ae6470ab8..4990d3e13 100644 --- a/src/lv_draw/lv_draw_label.c +++ b/src/lv_draw/lv_draw_label.c @@ -56,8 +56,8 @@ static uint8_t hex_char_to_num(char hex); * @param sel_end end index of selected area (`LV_LABEL_TXT_SEL_OFF` if none) */ void lv_draw_label(const lv_area_t * coords, const lv_area_t * mask, const lv_style_t * style, lv_opa_t opa_scale, - const char * txt, lv_txt_flag_t flag, lv_point_t * offset, uint16_t sel_start, uint16_t sel_end, - lv_draw_label_hint_t * hint, lv_bidi_dir_t bidi_dir) + const char * txt, lv_txt_flag_t flag, lv_point_t * offset, uint16_t sel_start, uint16_t sel_end, + lv_draw_label_hint_t * hint, lv_bidi_dir_t bidi_dir) { const lv_font_t * font = style->text.font; lv_coord_t w; @@ -75,7 +75,7 @@ void lv_draw_label(const lv_area_t * coords, const lv_area_t * mask, const lv_st /*If EXAPND is enabled then not limit the text's width to the object's width*/ lv_point_t p; lv_txt_get_size(&p, txt, style->text.font, style->text.letter_space, style->text.line_space, LV_COORD_MAX, - flag); + flag); w = p.x; } @@ -113,23 +113,6 @@ void lv_draw_label(const lv_area_t * coords, const lv_area_t * mask, const lv_st pos.y += hint->y; } - if(sel_start != 0xFFFF) { - sel_start = lv_bidi_get_visual_pos(txt, NULL, strlen(txt), bidi_dir, sel_start, NULL); - sel_start = lv_txt_encoded_get_byte_id(txt, sel_start); - } - - if(sel_end != 0xFFFF) { - sel_end = lv_bidi_get_visual_pos(txt, NULL, strlen(txt), bidi_dir, sel_end, NULL); - sel_end = lv_txt_encoded_get_byte_id(txt, sel_end); - } - - if(sel_start > sel_end) { - uint16_t tmp = sel_start; - sel_start = sel_end; - sel_end = tmp; - } - - uint32_t line_end = line_start + lv_txt_get_next_line(&txt[line_start], font, style->text.letter_space, w, flag); @@ -165,6 +148,12 @@ void lv_draw_label(const lv_area_t * coords, const lv_area_t * mask, const lv_st lv_opa_t opa = opa_scale == LV_OPA_COVER ? style->text.opa : (uint16_t)((uint16_t)style->text.opa * opa_scale) >> 8; + if(sel_start > sel_end) { + uint16_t tmp = sel_start; + sel_start = sel_end; + sel_end = tmp; + } + cmd_state_t cmd_state = CMD_STATE_WAIT; uint32_t i; uint16_t par_start = 0; @@ -185,16 +174,24 @@ void lv_draw_label(const lv_area_t * coords, const lv_area_t * mask, const lv_st uint32_t letter; uint32_t letter_next; #if LV_USE_BIDI - char *bidi_txt = lv_draw_get_buf(line_end - line_start + 1); - lv_bidi_process_paragraph(txt + line_start, bidi_txt, line_end - line_start, bidi_dir, NULL, 0); + char *bidi_txt = lv_draw_get_buf(line_end - line_start + 1); + lv_bidi_process_paragraph(txt + line_start, bidi_txt, line_end - line_start, bidi_dir, NULL, 0); #else - const char *bidi_txt = txt + line_start; + const char *bidi_txt = txt + line_start; #endif + while(i < line_end - line_start) { + uint16_t logical_char_pos = 0; + if(sel_start != 0xFFFF && sel_end != 0xFFFF) { + logical_char_pos = lv_txt_encoded_get_char_id(txt, line_start); + uint16_t t = lv_txt_encoded_get_char_id(bidi_txt, i); + logical_char_pos += lv_bidi_get_logical_pos(bidi_txt, NULL, line_end - line_start, bidi_dir, t, NULL); + } letter = lv_txt_encoded_next(bidi_txt, &i); letter_next = lv_txt_encoded_next(&bidi_txt[i], NULL); + /*Handle the re-color command*/ if((flag & LV_TXT_FLAG_RECOLOR) != 0) { if(letter == (uint32_t)LV_TXT_COLOR_CMD[0]) { @@ -240,7 +237,7 @@ void lv_draw_label(const lv_area_t * coords, const lv_area_t * mask, const lv_st if(sel_start != 0xFFFF && sel_end != 0xFFFF) { /*Do not draw the rectangle on the character at `sel_start`.*/ - if(i + line_start > sel_start && i + line_start <= sel_end) { + if(logical_char_pos > sel_start && logical_char_pos <= sel_end) { lv_area_t sel_coords; sel_coords.x1 = pos.x; sel_coords.y1 = pos.y; @@ -263,7 +260,7 @@ void lv_draw_label(const lv_area_t * coords, const lv_area_t * mask, const lv_st /*Align to middle*/ if(flag & LV_TXT_FLAG_CENTER) { line_width = - lv_txt_get_width(&txt[line_start], line_end - line_start, font, style->text.letter_space, flag); + lv_txt_get_width(&txt[line_start], line_end - line_start, font, style->text.letter_space, flag); pos.x += (lv_area_get_width(coords) - line_width) / 2; @@ -271,7 +268,7 @@ void lv_draw_label(const lv_area_t * coords, const lv_area_t * mask, const lv_st /*Align to the right*/ else if(flag & LV_TXT_FLAG_RIGHT) { line_width = - lv_txt_get_width(&txt[line_start], line_end - line_start, font, style->text.letter_space, flag); + lv_txt_get_width(&txt[line_start], line_end - line_start, font, style->text.letter_space, flag); pos.x += lv_area_get_width(coords) - line_width; } @@ -301,13 +298,13 @@ static uint8_t hex_char_to_num(char hex) if(hex >= 'a') hex -= 'a' - 'A'; /*Convert to upper case*/ switch(hex) { - case 'A': result = 10; break; - case 'B': result = 11; break; - case 'C': result = 12; break; - case 'D': result = 13; break; - case 'E': result = 14; break; - case 'F': result = 15; break; - default: result = 0; break; + case 'A': result = 10; break; + case 'B': result = 11; break; + case 'C': result = 12; break; + case 'D': result = 13; break; + case 'E': result = 14; break; + case 'F': result = 15; break; + default: result = 0; break; } }