wpf - Get Displayed Text from TextBlock -


i have simple textblock defined this

<stackpanel>     <border width="106"             height="25"             margin="6"             borderbrush="black"             borderthickness="1"             horizontalalignment="left">         <textblock name="mytextblock"                    texttrimming="characterellipsis"                    text="textblock: displayed text"/>     </border> </stackpanel> 

which outputs this

alt text

this me "textblock: displayed text"

string text = mytextblock.text; 

but there way text that's displayed on screen?
meaning "textblock: display..."

thanks

you can first retrieving drawing object represents appearance of textblock in visual tree, , walk looking glyphrundrawing items - contain actual rendered text on screen. here's rough , ready implementation:

private void button1_click(object sender, routedeventargs e) {     drawing textblockdrawing = visualtreehelper.getdrawing(mytextblock);     var sb = new stringbuilder();     walkdrawingfortext(sb, textblockdrawing);      debug.writeline(sb.tostring()); }  private static void walkdrawingfortext(stringbuilder sb, drawing d) {     var glyphs = d glyphrundrawing;     if (glyphs != null)     {         sb.append(glyphs.glyphrun.characters.toarray());     }     else     {         var g = d drawinggroup;         if (g != null)         {             foreach (drawing child in g.children)             {                 walkdrawingfortext(sb, child);             }         }     } } 

this direct excerpt little test harness wrote - first method's button click handler ease of experimentation.

it uses visualtreehelper rendered drawing textblock - that'll work if thing has been rendered way. , walkdrawingfortext method actual work - traverses drawing tree looking text.

this isn't terribly smart - assumes glyphrundrawing objects appear in order you'll want them. particular example - 1 glyphrundrawing containing truncated text, followed second 1 containing ellipsis character. (and way, it's 1 unicode character - codepoint 2026, , if editor lets me paste in unicode characters, it's "…". it's not 3 separate periods.)

if wanted make more robust, need work out positions of glyphrundrawing objects, , sort them, in order process them in order in appear, rather merely hoping wpf happens produce them in order.

updated add:

here's sketch of how position-aware example might look. although parochial - assumes left-to-right reading text. you'd need more complex internationalized solution.

private string gettextfromvisual(visual v) {     drawing textblockdrawing = visualtreehelper.getdrawing(v);     var glyphs = new list<positionedglyphs>();      walkdrawingforglyphruns(glyphs, transform.identity, textblockdrawing);      // round vertical position, provide tolerance rounding errors     // in position calculation. not totally robust - better     // identify lines, complicate example...     var glyphsorderedbyposition = glyph in glyphs                                     let roundedbaseliney = math.round(glyph.position.y, 1)                                     orderby roundedbaseliney ascending, glyph.position.x ascending                                     select new string(glyph.glyphs.glyphrun.characters.toarray());      return string.concat(glyphsorderedbyposition); }  [debuggerdisplay("{position}")] public struct positionedglyphs {     public positionedglyphs(point position, glyphrundrawing grd)     {         this.position = position;         this.glyphs = grd;     }     public readonly point position;     public readonly glyphrundrawing glyphs; }  private static void walkdrawingforglyphruns(list<positionedglyphs> glyphlist, transform tx, drawing d) {     var glyphs = d glyphrundrawing;     if (glyphs != null)     {         var textorigin = glyphs.glyphrun.baselineorigin;         point glyphposition = tx.transform(textorigin);         glyphlist.add(new positionedglyphs(glyphposition, glyphs));     }     else     {         var g = d drawinggroup;         if (g != null)         {             // drawing groups allowed transform children, need             // keep running accumulated transform in tree.             matrix current = tx.value;             if (g.transform != null)             {                 // note, matrix struct, modifies our local copy without                 // affecting 1 in 'tx' transforms.                 current.append(g.transform.value);             }             var accumulatedtransform = new matrixtransform(current);             foreach (drawing child in g.children)             {                 walkdrawingforglyphruns(glyphlist, accumulatedtransform, child);             }         }     } } 

Comments

Popular posts from this blog

asp.net - repeatedly call AddImageUrl(url) to assemble pdf document -

java - Android recognize cell phone with keyboard or not? -

iphone - How would you achieve a LED Scrolling effect? -