More information on using Contextual Substitutions.

Hello, I'm new here. I'm looking for some example of how to use contextual alternates substitution.

For example, i have a , a.alt1 and a.alt2, i know that after a space, it returns to a, but how can i change it to a.alt1 or a.alt2.

Please any help.

Comments

  • Sorry, i already check it but still need more help.
  • notdef
    notdef Posts: 168
    edited October 2018
    sub whateverTriggersYourContext space a' by a.alt;

    Make sure it is a straight quote, and not the ’

    (PS: I remember at one point having some trouble with contextual subs across the space in one of the major web browsers, but it’s been a while since I’ve tested it.)
  • Jess McCarty
    Jess McCarty Posts: 97
    edited October 2018
    You can do a direct substitution, in which @lowercase is whatever class or sequence triggers your contextual substitution:
    sub @lowercase a' space by a.alt;

    The straight quote immediately following the a indicates this is the glyph that should be affected by the substitution. Classes can also be marked in this way, so if you wanted to include all a diacritics in this substitution, make a class called @aaltdiacritics and include all of the relevant glyphs within it. In this example, your line might look something like this:

    sub @lowercase @adiacritics' space by @aaltdiacritics;

    Make sure any classes have exactly the same number of characters, and remember that the substitutions within the classes happen in the order you list. In other words, @adiacriticsa aring atilde and @aaltdiacriticsa.alt aring.alt atilde.alt will give you the results you want. @adiacriticsatilde a aring and @aaltdiacriticsa.alt aring.alt atilde.alt will not. (Note: these are not all of the a diacritics in a basic Latin font, I've just shortened the list in this example.)

    Better practice is to utilize the ignore sub. In this example, the @notspace class includes every glyph except the space:

    lookup LoweraSpace useExtension { # Substitutes a for a.alt when preceded by a lowercase letter and followed by a space
    	ignore sub @lowercase a' @notspace;
    	sub @lowercase a' by a.alt;
    } LoweraSpace;

    Don't forget that both of these methods only apply to the space character. If you want the swap to happen inside of punctuation and quotation marks, you'll need to include all of those glyphs within your @notspace class (or your @space class, if you go the simple substitution route).

    You can view more how/why examples here: https://www.adobe.com/devnet/opentype/afdko/topic_feature_file_syntax.html#1
  • Thank you very much. It works now.
  • Kent Lew
    Kent Lew Posts: 937
    edited October 2018
    Jess — I’m curious why you included the useExtension keyword in your last example.
    Is that just because the kind of script faces you develop usually end up with large contextual feature sets, and so you’ve gotten into the habit of specifying them as 32-bit Extension lookup types in order to pre-empt problems compiling?
    I’ve personally never had to invoke useExtension for contextual lookups, even with some fairly complicated fonts that I’ve developed for folks, so I’m curious about your experience.
    (Massive {kern} features is another story, however, and I have found value in invoking useExtension for those, but still rarely.)
  • Jess McCarty
    Jess McCarty Posts: 97
    edited October 2018
    Ah, good catch Kent! Yes -- I grabbed this snippet from a script typeface with a huge contextual feature set and forgot to remove that bit of code before posting here. It's not something I usually use, unless the script becomes the typographic equivalent of a Rubix cube. 

    Menshinhl, as Kent explained, you shouldn't need to incorporate the useExtension into your lookups unless you're building something very large and very strange. :)


  • John Hudson
    John Hudson Posts: 3,186
    Apparently almost everything I build is very large and very strange.
  • Kent Lew
    Kent Lew Posts: 937
    John — Given the kinds of projects you specialize in, that wouldn’t surprise me one bit. ;-)