--- title: 'Canvas2D Shaped Text Extensions' linkTitle: 'Canvas2D Text Extensions' --- [Shaped Text](/docs/dev/design/text_shaper) is a proposal for exposing the Browser's text shaping engine. It takes in a block of (annoated) text, and returns the low-level information needed to correctly measure, hit-test, and draw the text as positioned glyphs. This processing step is needed whenever text is measured or drawn in the browser, and this processing can be complex and time consuming. The output of this processing is, however, simple and can be rendered quite efficiently. It is runs (tied to a specific Typeface and size) of glyph IDs and x,y postions. This proposal extends Canvas2D to allow it to draw those glyphs directly, and also includes utilities for querying attributes of the glyphs (not needed for drawing, but useful for other operations). ### Principles * Drawing postioned glyphs should be at least as flexible as the existing fillText() method. * It is expected that drawing glyphs can be faster than fillText() -- no shaping/processing is needed. * With the additional utilities, new effects should be easy and efficient. ## Drawing glyphs At the heart of the proposal is a parallel to fillText/strokeText... ```js context.fillGlyphs(glyphs, positions, Font); context.strokeGlyphs(glyphs, positions, Font); ``` These respect all of the same settings as their 'Text' equivalents (e.g. current transform, clip, style) with the exception of the actual text attributes: - font - textAlign - textBaseline - direction These are ignored, because they have already been 'computed' by the Shape Text processing, and their results are represented in the glyphs, positions, and [Font](/docs/dev/design/text_shaper) parameters. [Font](/docs/dev/design/text_shaper) is far more specific in this extension that the existing context.font attribute. In today's canvas2d, "font" holds a high-level description of the typeface(s): It is a string with the font's name, which has to be resolved to find the actual (set of) resources. For Shaped Text, this resolution has already occured. The glyph IDs are specific to exactly 1 resource (i.e. file/blob) and so the Font interface contains not the name, but a handle to the actual resource. The upside to this specificity is performance: with all "fallback" and shaping having already occured, the draw calls can execute faster. ## Font utilities [Shaped Text](/docs/dev/design/text_shaper) introduced the Font interface, but for shaping, it only needed to specify the resource (Typeface object) sizing information, and (on input) optional font-features. After shaping, clients may want to query information about specific glyphs within that Font. Those extended methods are presented here. ```WebIDL interface Font { // return array of advance widths for the specified glyphs. // sequence getGlyphAdvances(sequene glyphs); // return array of [left, top, right, bottom] coordinates for the specified glyphs, // // If positions are provided, then the rectangles are relative to each glyph's postion. // If no positions are provided, then the rectangles are all relateive to (0,0). // Note: positions are stored as (x,y) pairs // sequence getGlyphBounds(sequene glyphs, sequence positions?); // return array of Path2D objects for the specified glyphs, // // If positions are provided, then the paths are relative to each glyph's postion. // If no positions are provided, then the paths are all relateive to (0,0). // Note: positions are stored as (x,y) pairs // // If a glyph has no visual representation (e.g. a SPACE) then its path will be null. // If a glyph has an image for its representation, then its path will be undefined. // sequence getGlyphPaths(sequene glyphs, sequence positions?); // A glyph may be represented with an image (e.g. emoji). getGlyphImage() for these glyphs // will return a GlyphImage object. If the glyph does not have an Image, null is returned. // GlyphImage getGlyphImage(unsigned short glyphID); }; interface GlyphImage { readonly attribute ImageBitmap image; readonly attribute DOMMatrix transform; }; ``` [Overview document](/docs/dev/design/text_overview) ## Contributors: [mikerreed](https://github.com/mikerreed),