diff --git a/OTFbuild/calligra_font_tests.odt b/OTFbuild/calligra_font_tests.odt index 6e7f6ba..c73d934 100644 Binary files a/OTFbuild/calligra_font_tests.odt and b/OTFbuild/calligra_font_tests.odt differ diff --git a/OTFbuild/font_builder.py b/OTFbuild/font_builder.py index 83c0d26..96ba4b5 100644 --- a/OTFbuild/font_builder.py +++ b/OTFbuild/font_builder.py @@ -371,6 +371,9 @@ def build_font(assets_dir, output_path, no_bitmap=False, no_features=False): try: fea_stream = io.StringIO(fea_code) addOpenTypeFeatures(font, fea_stream) + # Obtain raw .fea text for debugging + # with open("debugout_features.fea", "w") as text_file: + # text_file.write(fea_code) print(" Features compiled successfully") except Exception as e: print(f" [WARNING] Feature compilation failed: {e}") diff --git a/OTFbuild/opentype_features.py b/OTFbuild/opentype_features.py index 9a69bf0..988db62 100644 --- a/OTFbuild/opentype_features.py +++ b/OTFbuild/opentype_features.py @@ -856,6 +856,38 @@ def _generate_devanagari(glyphs, has, replacewith_subs=None): feat.append("} psts;") features.append('\n'.join(all_lookups + [''] + feat)) + # --- calt: contextual Visarga --- + # When Visarga (U+0903) is followed by a Devanagari character (mid-word), + # substitute with interword variant (uF010A). calt is applied globally + # across syllable boundaries, unlike psts which is per-syllable. + INTERWORD_VISARGA = 0xF010A + visarga = 0x0903 + if has(visarga) and has(INTERWORD_VISARGA): + # Build class of Devanagari characters that can follow Visarga mid-word: + # PUA consonants (full, half, RA-appended, RA-appended half) + independent vowels + deva_following_cps = ( + list(SC.DEVANAGARI_PRESENTATION_CONSONANTS) + + list(range(0xF0230, 0xF0320)) + # half forms + list(SC.DEVANAGARI_PRESENTATION_CONSONANTS_WITH_RA) + + list(range(0xF0410, 0xF0500)) + # RA-appended half forms + list(range(0x0904, 0x0915)) + # independent vowels + list(range(0x0915, 0x093A)) + # Unicode consonants (before ccmp) + list(range(0x0958, 0x0962)) # nukta consonants + ) + deva_following = [glyph_name(cp) for cp in sorted(set(deva_following_cps)) if has(cp)] + if deva_following: + calt_lines = [] + calt_lines.append(f"lookup InterwordVisarga {{") + calt_lines.append(f" sub {glyph_name(visarga)} by {glyph_name(INTERWORD_VISARGA)};") + calt_lines.append(f"}} InterwordVisarga;") + calt_lines.append("") + calt_lines.append("feature calt {") + calt_lines.append(" script dev2;") + calt_lines.append(f" @devaFollowing = [{' '.join(deva_following)}];") + calt_lines.append(f" sub {glyph_name(visarga)}' lookup InterwordVisarga @devaFollowing;") + calt_lines.append("} calt;") + features.append('\n'.join(calt_lines)) + if not features: return "" return '\n\n'.join(features) diff --git a/src/assets/devanagari_variable.tga b/src/assets/devanagari_variable.tga index 6262823..400d298 100644 --- a/src/assets/devanagari_variable.tga +++ b/src/assets/devanagari_variable.tga @@ -1,3 +1,3 @@ version https://git-lfs.github.com/spec/v1 -oid sha256:d0e62cb837710cb1838824703a77cbb92134486d41b159a91e532d499856d05f +oid sha256:d5f248770ad01d237c5c64a1a6ea03f872d5f93e5b0c2d78a3904a9a4652ad08 size 1474578 diff --git a/src/net/torvald/terrarumsansbitmap/gdx/TerrarumSansBitmap.kt b/src/net/torvald/terrarumsansbitmap/gdx/TerrarumSansBitmap.kt index 440684c..05c13b9 100755 --- a/src/net/torvald/terrarumsansbitmap/gdx/TerrarumSansBitmap.kt +++ b/src/net/torvald/terrarumsansbitmap/gdx/TerrarumSansBitmap.kt @@ -1401,6 +1401,10 @@ class TerrarumSansBitmap( else { seq0.add(c.toDevaInternal()) } + // Contextual Visarga: use interword variant when followed by a Devanagari character + else if (c == 0x0903 && (cNext in 0x0904..0x0939 || cNext in 0x0958..0x097F)) { + seq0.add(DEVANAGARI_INTERWORD_VISARGA) + } // re-order Sundanese diacritics else if ((c == 0x1BA1 || c == 0x1BA2) && cNext == 0x1BA5) { seq0.add(cNext); seq0.add(c); i += 1 @@ -2744,6 +2748,8 @@ class TerrarumSansBitmap( private const val DEVANAGARI_EYELASH_RA = 0xF010B private const val DEVANAGARI_RA_SUPER = 0xF010C private const val DEVANAGARI_RA_SUPER_COMPLEX = 0xF010D + private const val DEVANAGARI_INTERWORD_VISARGA = 0xF010A + private const val MARWARI_DD = 0x978 diff --git a/work_files/devanagari_variable.psd b/work_files/devanagari_variable.psd index d19aa46..784bd57 100644 --- a/work_files/devanagari_variable.psd +++ b/work_files/devanagari_variable.psd @@ -1,3 +1,3 @@ version https://git-lfs.github.com/spec/v1 -oid sha256:b3d0fbfb962df918b2316e2077d90cb0c1e34eace4dace9922370b174fc1d422 -size 1453551 +oid sha256:4201b49f4f4ef1195d295abf0d13297f305625aab867e2624e268bae6760aca4 +size 1453583