tasn pushed a commit to branch evas-1.7.

commit 78dafd57276b577aef0cd5a74fdf182f56e39f88
Author: Tom Hacohen <[email protected]>
Date:   Tue Aug 13 15:20:18 2013 +0100

    Evas textblock: Added proper size adjustments for "high" shaped texts.
    
    This adjusts the starting coords of the textblock to fit the shaped char of
    the first line.
---
 ChangeLog                                |  6 ++-
 NEWS                                     |  1 +
 src/lib/canvas/evas_object_textblock.c   | 70 +++++++++++++++++++++++++-------
 src/lib/engines/common/evas_font.h       |  1 +
 src/lib/engines/common/evas_font_query.c | 40 ++++++++++++++++++
 5 files changed, 103 insertions(+), 15 deletions(-)

diff --git a/ChangeLog b/ChangeLog
index b3c6e74..a141fbc 100644
--- a/ChangeLog
+++ b/ChangeLog
@@ -1340,7 +1340,11 @@
 
         * 1.7.8 release
 
-2013-07-08  Tom Hacohen
+2013-08-08  Tom Hacohen
 
         * Evas textblock: Make the ellipsis format the same as the surrounding.
 
+2013-08-13  Tom Hacohen
+
+        * Evas textblock: Added proper size adjustments for "high" shaped 
texts.
+
diff --git a/NEWS b/NEWS
index 2e068e0..2f0ae6c 100644
--- a/NEWS
+++ b/NEWS
@@ -6,6 +6,7 @@ Changes since Evas 1.7.8:
 Fixes:
    * Evas textblock: Fixed issue when parsing formats with quotes.
    * Evas textblock: Make the ellipsis format the same as the surrounding.
+   * Evas textblock: Added proper size adjustments for "high" shaped texts.
 
 Evas 1.7.8
 
diff --git a/src/lib/canvas/evas_object_textblock.c 
b/src/lib/canvas/evas_object_textblock.c
index dfde5aa..6019b5e 100644
--- a/src/lib/canvas/evas_object_textblock.c
+++ b/src/lib/canvas/evas_object_textblock.c
@@ -2450,6 +2450,13 @@ _format_dup(Evas_Object *obj, const 
Evas_Object_Textblock_Format *fmt)
 
 
 
+typedef enum
+{
+   TEXTBLOCK_POSITION_START,
+   TEXTBLOCK_POSITION_END,
+   TEXTBLOCK_POSITION_ELSE
+} Textblock_Position;
+
 /**
  * @internal
  * @typedef Ctxt
@@ -2481,6 +2488,7 @@ struct _Ctxt
    int underline_extend;
    int have_underline, have_underline2;
    double align, valign;
+   Textblock_Position position;
    Eina_Bool align_auto : 1;
    Eina_Bool width_changed : 1;
 };
@@ -2542,6 +2550,36 @@ _layout_format_ascent_descent_adjust(const Evas_Object 
*obj,
 
 /**
  * @internal
+ * Adjust the ascent/descent of the item and context.
+ *
+ * @param maxascent The ascent to update - Not NUL.
+ * @param maxdescent The descent to update - Not NUL.
+ * @param it The format to adjust - NOT NULL.
+ * @param position The position inside the textblock
+ */
+static void
+_layout_item_ascent_descent_adjust(const Evas_Object *eo_obj,
+      Evas_Coord *maxascent, Evas_Coord *maxdescent,
+      Evas_Object_Textblock_Item *it, Textblock_Position position)
+{
+   _layout_format_ascent_descent_adjust(eo_obj, maxascent, maxdescent, 
it->format);
+
+   if ((it->type == EVAS_TEXTBLOCK_ITEM_TEXT) &&
+         (position == TEXTBLOCK_POSITION_START))
+     {
+        int asc = 0, desc = 0;
+        evas_common_font_ascent_descent_get((void *) it->format->font.font,
+              &_ITEM_TEXT(it)->text_props, &asc, &desc);
+
+        if (maxascent && (asc > *maxascent))
+           *maxascent = asc;
+        if (maxdescent && (desc < *maxdescent))
+           *maxdescent = desc;
+     }
+}
+
+/**
+ * @internal
  * Create a new line using the info from the format and update the format
  * and context.
  *
@@ -3259,6 +3297,7 @@ loop_advance:
 static void
 _layout_line_advance(Ctxt *c, Evas_Object_Textblock_Format *fmt)
 {
+   c->position = TEXTBLOCK_POSITION_ELSE;
    _layout_line_finalize(c, fmt);
    _layout_line_new(c, fmt);
 }
@@ -4348,9 +4387,8 @@ _layout_par(Ctxt *c)
 
         if (it->type == EVAS_TEXTBLOCK_ITEM_TEXT)
           {
-             Evas_Object_Textblock_Text_Item *ti = _ITEM_TEXT(it);
-             _layout_format_ascent_descent_adjust(c->obj, &c->maxascent,
-                   &c->maxdescent, ti->parent.format);
+             _layout_item_ascent_descent_adjust(c->obj, &c->maxascent,
+                   &c->maxdescent, it, c->position);
           }
         else
           {
@@ -4362,8 +4400,8 @@ _layout_par(Ctxt *c)
                   /* If there are no text items yet, calc ascent/descent
                    * according to the current format. */
                   if (c->maxascent + c->maxdescent == 0)
-                     _layout_format_ascent_descent_adjust(c->obj, 
&c->maxascent,
-                           &c->maxdescent, it->format);
+                     _layout_item_ascent_descent_adjust(c->obj, &c->maxascent,
+                           &c->maxdescent, it, c->position);
 
                   _layout_calculate_format_item_size(c->obj, fi, &c->maxascent,
                         &c->maxdescent, &fi->y, &fi->parent.w, &fi->parent.h);
@@ -4933,6 +4971,8 @@ _layout(const Evas_Object *obj, int w, int h, int *w_ret, 
int *h_ret)
       int par_count = 1; /* Force it to take the first one */
       int par_index_pos = 0;
 
+      c->position = TEXTBLOCK_POSITION_START;
+
       if (par_index_step == 0) par_index_step = 1;
 
       /* Clear all of the index */
@@ -9695,7 +9735,7 @@ evas_object_textblock_size_formatted_get(const 
Evas_Object *obj, Evas_Coord *w,
 
 static void
 _size_native_calc_line_finalize(const Evas_Object *obj, Eina_List *items,
-      Evas_Coord *ascent, Evas_Coord *descent, Evas_Coord *w)
+      Evas_Coord *ascent, Evas_Coord *descent, Evas_Coord *w, 
Textblock_Position position)
 {
    Evas_Object_Textblock_Item *it;
    Eina_List *i;
@@ -9708,8 +9748,8 @@ _size_native_calc_line_finalize(const Evas_Object *obj, 
Eina_List *items,
         Evas_Coord asc = 0, desc = 0;
         /* If there are no text items yet, calc ascent/descent
          * according to the current format. */
-        _layout_format_ascent_descent_adjust(obj, &asc, &desc,
-              it->format);
+        _layout_item_ascent_descent_adjust(obj, &asc, &desc,
+              it, position);
 
         if (asc > *ascent)
            *ascent = asc;
@@ -9752,6 +9792,7 @@ _size_native_calc_paragraph_size(const Evas_Object *obj,
    Evas_Object_Textblock_Item *it;
    Eina_List *line_items = NULL;
    Evas_Coord w = 0, y = 0, wmax = 0, h = 0, ascent = 0, descent = 0;
+   Textblock_Position position = TEXTBLOCK_POSITION_START;
 
    EINA_LIST_FOREACH(par->logical_items, i, it)
      {
@@ -9763,7 +9804,7 @@ _size_native_calc_paragraph_size(const Evas_Object *obj,
                       _IS_PARAGRAPH_SEPARATOR(o, fi->item)))
                {
                   _size_native_calc_line_finalize(obj, line_items, &ascent,
-                        &descent, &w);
+                        &descent, &w, position);
 
                   if (ascent + descent > h)
                      h = ascent + descent;
@@ -9773,6 +9814,7 @@ _size_native_calc_paragraph_size(const Evas_Object *obj,
                      wmax = w;
                   h = 0;
                   ascent = descent = 0;
+                  position = TEXTBLOCK_POSITION_ELSE;
                   line_items = eina_list_free(line_items);
                }
              else
@@ -9781,8 +9823,8 @@ _size_native_calc_paragraph_size(const Evas_Object *obj,
                   /* If there are no text items yet, calc ascent/descent
                    * according to the current format. */
                   if (it && (ascent + descent == 0))
-                     _layout_format_ascent_descent_adjust(obj, &ascent,
-                           &descent, it->format);
+                     _layout_item_ascent_descent_adjust(obj, &ascent,
+                           &descent, it, position);
 
                   _layout_calculate_format_item_size(obj, fi, &ascent,
                         &descent, &fy, &fw, &fh);
@@ -9790,12 +9832,12 @@ _size_native_calc_paragraph_size(const Evas_Object *obj,
           }
         else
           {
-             _layout_format_ascent_descent_adjust(obj, &ascent,
-                   &descent, it->format);
+             _layout_item_ascent_descent_adjust(obj, &ascent,
+                   &descent, it, position);
           }
      }
 
-   _size_native_calc_line_finalize(obj, line_items, &ascent, &descent, &w);
+   _size_native_calc_line_finalize(obj, line_items, &ascent, &descent, &w, 
position);
 
    line_items = eina_list_free(line_items);
 
diff --git a/src/lib/engines/common/evas_font.h 
b/src/lib/engines/common/evas_font.h
index b95c4f2..aa8621c 100644
--- a/src/lib/engines/common/evas_font.h
+++ b/src/lib/engines/common/evas_font.h
@@ -75,6 +75,7 @@ EAPI int               evas_common_font_query_pen_coords     
(RGBA_Font *fn, con
 EAPI int               evas_common_font_query_char_at_coords (RGBA_Font *fn, 
const Evas_Text_Props *intl_props, int x, int y, int *cx, int *cy, int *cw, int 
*ch);
 EAPI int               evas_common_font_query_last_up_to_pos (RGBA_Font *fn, 
const Evas_Text_Props *intl_props, int x, int y);
 EAPI int               evas_common_font_query_run_font_end_get(RGBA_Font *fn, 
RGBA_Font_Int **script_fi, RGBA_Font_Int **cur_fi, Evas_Script_Type script, 
const Eina_Unicode *text, int run_len);
+EAPI void              evas_common_font_ascent_descent_get(RGBA_Font *fn, 
const Evas_Text_Props *text_props, int *ascent, int *descent);
 
 void evas_common_font_load_init(void);
 void evas_common_font_load_shutdown(void);
diff --git a/src/lib/engines/common/evas_font_query.c 
b/src/lib/engines/common/evas_font_query.c
index 4c904d9..bb7697b 100644
--- a/src/lib/engines/common/evas_font_query.c
+++ b/src/lib/engines/common/evas_font_query.c
@@ -274,6 +274,46 @@ evas_common_font_query_right_inset(RGBA_Font *fn 
__UNUSED__, const Evas_Text_Pro
 
 /**
  * @internal
+ * Calculate the ascent/descent of a run. This is different from
+ * evas_common_font_[max]_ascent/descent_get because this one returns the
+ * actual sizee (i.e including accents), and not just what the font reports.
+ *
+ * @param fn the font set to use.
+ * @param text_props the string object.
+ * @param[out] ascent the calculated ascent
+ * @param[out] descent the calculated descent
+ */
+EAPI void
+evas_common_font_ascent_descent_get(RGBA_Font *fn, const Evas_Text_Props 
*text_props, int *ascent, int *descent)
+{
+   int asc = 0, desc = 0;
+   int max_asc, max_desc;
+
+   max_asc = evas_common_font_ascent_get(fn);
+   max_desc = evas_common_font_descent_get(fn);
+
+   /* FIXME: Not supported yet!!! */
+   desc = max_desc;
+
+   EVAS_FONT_WALK_TEXT_INIT();
+   EVAS_FONT_WALK_TEXT_START()
+     {
+        EVAS_FONT_WALK_TEXT_WORK();
+        if (!EVAS_FONT_WALK_IS_VISIBLE) continue;
+
+        if ((EVAS_FONT_WALK_PEN_Y + EVAS_FONT_WALK_Y_OFF + 
EVAS_FONT_WALK_Y_BEAR) > asc)
+          {
+             asc = EVAS_FONT_WALK_PEN_Y + EVAS_FONT_WALK_Y_OFF + 
EVAS_FONT_WALK_Y_BEAR;
+          }
+     }
+   EVAS_FONT_WALK_TEXT_END();
+
+   if (ascent) *ascent = (asc > max_asc) ? asc : max_asc;
+   if (descent) *descent = (desc < max_desc) ? desc : max_desc;
+}
+
+/**
+ * @internal
  * Calculate the size of the string (width and height).
  * The width is the disntance between the first pen position and the last pixel
  * drawn.

-- 

------------------------------------------------------------------------------
Get 100% visibility into Java/.NET code with AppDynamics Lite!
It's a free troubleshooting tool designed for production.
Get down to code-level detail for bottlenecks, with <2% overhead. 
Download for free and get started troubleshooting in minutes. 
http://pubads.g.doubleclick.net/gampad/clk?id=48897031&iu=/4140/ostg.clktrk

Reply via email to