Theppitak's blog

My personal blog.

21 ตุลาคม 2561

Reproducible Fonts-TLWG

ความเปลี่ยนแปลงล่าสุดใน Fonts-TLWG คือเรื่อง reproducibility คือการ build ที่ให้ผลลัพธ์เป็น binary file ที่เป็นข้อมูลเดิมทุกบิตทุกครั้งที่ build โดยไม่ขึ้นกับสภาวะที่ใช้ในการ build

สำหรับฟอนต์จากโครงการ Fonts-TLWG มีปัญหา reproducibility ตามที่รายงานโดย Debian คือ modification timestamp ที่เกิดจาก Fontforge script ที่ใช้ build โดยมีการเปลี่ยนแปลงข้อมูลของฟอนต์ระหว่างทาง ทำให้ timestamp ของการเปลี่ยนแปลงถูกปรับเป็นเวลาขณะ script ทำงานนั้น และทำให้ข้อมูลฟอนต์ผลลัพธ์แปรเปลี่ยนไปตามเวลาที่ build

Modification กลางอากาศ

script ที่ใช้ generate ฟอนต์ชนิดต่าง ๆ จะมีการเปลี่ยนแปลงข้อมูลฟอนต์กลางอากาศขณะ build ดังนี้

  • OTF และ WOFF จะมีการตัด PUA glyphs สำหรับสระบน-ล่างและวรรณยุกต์ที่เลื่อนหลบหางพยัญชนะ
  • TTF มีการแปลง cubic spline เป็น quadratic ก่อน apply AutoInstr
  • LaTeX fonts (Postscript + TeX virtual fonts) จะไม่มี modification ใด ๆ

PUA Glyphs

PUA (Unicode Private Use Area) glyphs สำหรับสระบน-ล่างและวรรณยุกต์ที่เลื่อนหลบหางพยัญชนะ เป็นสิ่งจำเป็นสำหรับการ render ข้อความในสภาวะที่ไม่มีเทคโนโลยี OpenType เช่น บน Windows XP และการใช้ virtual font ใน TeX engine เก่า (เช่น pdfTeX) ซึ่งเราได้ตัดสินใจยกเลิกการรองรับ TTF แบบเก่าไปนานแล้ว แต่ยังไม่สามารถตัดการรองรับ TeX engine เก่าได้ จึงยังคง PUA glyphs ไว้ใน source ของฟอนต์ แต่ใช้วิธีลบกลางอากาศขณะ gen OTF และ TTF เอา

แต่การลบ glyph กลางอากาศนี่เองที่เป็นสาเหตุหนึ่งที่ทำให้ modification timestamp ของฟอนต์เปลี่ยน และทำให้ได้ไฟล์ฟอนต์ที่ไม่ reproducible

วิธีแก้ปัญหาก็เป็นไปได้สองทาง:

  1. ไม่ต้องตัด PUA glyphs เลย ใส่เกินไว้ในฟอนต์อย่างนั้นแหละ การมีอยู่ของ OpenType tables ต่าง ๆ จะทำให้ shaping engine อย่าง Harfbuzz ไม่ fallback มาใช้ PUA shaping เมื่อเจอ PUA glyphs ในฟอนต์
  2. ตัด PUA glyphs ออกจาก source ไปเลย ซึ่งจะหมายถึงการตัดการรองรับ shaping ผ่าน TeX virtual font ด้วย ผลคือ ตัดการรองรับ pdfTeX ไปเลย และหยุดอัปเดตแพกเกจ fonts-tlwg บน CTAN ไปเสีย

ทางเลือก 2 ดูจะเป็นเรื่องใหญ่ ผมคิดว่าควรชะลอไปก่อน และเลือกทางเลือก 1 ไว้ก่อน และได้ commit ไปตามนี้

TrueType Instructions

เพื่อเพิ่ม hint ให้กับฟอนต์ TrueType ในขณะที่ source ของเราอยู่ในรูป cubic spline ตัว script จึงใช้วิธีแปลง spline ให้เป็น quadratic ก่อน แล้ว apply AutoInstr กลางอากาศก่อน generate TTF

ซึ่งการแปลงและสั่ง AutoInstr ทำให้ modification timestamp ของฟอนต์เปลี่ยน ทำให้ได้ไฟล์ฟอนต์ที่ไม่ reproducible อีกเช่นกัน

ผมค้นคิดวิธีที่จะแก้ปัญหานี้ไปเรื่อย ๆ จนในที่สุดก็ได้ไอเดียการทำ mixed layers โดยมีหลักการคือ:

  • เพิ่ม layer ที่สี่ในไฟล์ SFD เป็นชนิด quadratic แล้ว copy spline ทั้งหมดจาก Front Layer ซึ่งเป็น cubic มายัง qudratic layer นี้ ซึ่ง Fontforge จะแปลง spline ให้ขณะ copy
  • เราสามารถแก้ไข quadratic spline ใน layer ใหม่นี้ได้ หรือหากต้องการ fine-tune TrueType instructions ก็ทำได้ แต่ในเบื้องต้นนี้ยังไม่ edit ใด ๆ และใช้ AutoInstr ไปก่อน
  • ในการ generate TTF ใน dialog box จะสามารถเลือกให้ generate จาก quadratic layer แทน Front Layer ได้ และใน script อัตโนมัติก็สามารถกำหนด layer ที่จะใช้ได้เช่นกัน เพียงแต่การเลือก layer ยังไม่รองรับใน Fontforge native script ด้วยข้อจำกัดเรื่อง syntax แต่ใน Python script สามารถทำได้

เมื่อได้หลักการเช่นนี้แล้ว ก็ได้แตก branch mixed-layer-ttf เพื่อดำเนินการ โดยตั้งชื่อ quadratic layer ให้เหมือนกันทุกฟอนต์ว่า Quad เพื่อจะได้ใช้ชื่อนี้ใน script ให้ทำงานได้ทุกฟอนต์ และเปลี่ยนมาใช้ Python script สำหรับ TTF แทน native script เดิม

ด้วยหลักการเช่นนี้ source สำหรับ TTF ก็จะเตรียมพร้อมอยู่ใน source สำหรับ generate ได้โดยไม่ต้องแก้ไขกลางอากาศอีก

ทำเสร็จหมดแล้ว ก็ merge เข้า master เสีย เป็นอันเสร็จพิธี

ส่วน LaTeX fonts ไม่มีประเด็นอะไรต้องแก้ ผลคือ ขณะนี้ fonts-tlwg สามารถ build แบบ reproducible ได้ทั้งหมดแล้ว

อนาคต

ประเด็นที่น่าจะทำในอนาคต:

  • ตัดสินใจว่าจะทำอย่างไรกับ PUA glyphs เช่น
    • หาวิธี ข้าม PUA glyphs ขณะ generate โดยไม่ต้องลบ glyph เพื่อจะได้หลีกเลี่ยง modification timestamp
    • ตัด PUA glyphs ออกจาก source เลยไหม? ซึ่งจะหมายถึงการตัดการรองรับ shaping ผ่าน TeX virtual font สำหรับ engine เก่าอย่าง pdfTeX ด้วย
  • Quad layer ที่เกิดขึ้นได้ให้อิสระในการปรับแต่ง TrueType spline และ instruction แล้ว สามารถ fine-tune ต่อไปในอนาคตได้

ป้ายกำกับ: , ,

0 ความเห็น:

แสดงความเห็น (มีการกลั่นกรองสำหรับ blog ที่เก่ากว่า 14 วัน)

<< กลับหน้าแรก

hacker emblem