lib/ttfunk/table/head.rb in ttfunk-1.7.0 vs lib/ttfunk/table/head.rb in ttfunk-1.8.0
- old
+ new
@@ -2,31 +2,95 @@
require_relative '../table'
module TTFunk
class Table
+ # Font Header (`head`) Table.
class Head < TTFunk::Table
+ # Table version.
+ # @return [Integer]
attr_reader :version
+
+ # Font revision.
+ # @return [Integer]
attr_reader :font_revision
+
+ # Checksum adjustment.
+ # @return [Integer]
attr_reader :checksum_adjustment
+
+ # Magic number.
+ # @return [Integer] must be `0x5F0F3CF5`
attr_reader :magic_number
+
+ # Flags.
+ # @return [Integer]
attr_reader :flags
+
+ # Units per Em.
+ # @return [Integer]
attr_reader :units_per_em
+
+ # Font creation time.
+ # @return [Integer] Long Date Time timestamp.
attr_reader :created
+
+ # Font modification time.
+ # @return [Integer] Long Date Time timestamp.
attr_reader :modified
+
+ # Minimum x coordinate across all glyph bounding boxes.
+ # @return [Integer]
attr_reader :x_min
+
+ # Minimum y coordinate across all glyph bounding boxes.
+ # @return [Integer]
attr_reader :y_min
+
+ # Maximum x coordinate across all glyph bounding boxes.
+ # @return [Integer]
attr_reader :x_max
+
+ # Maximum y coordinate across all glyph bounding boxes.
+ # @return [Integer]
attr_reader :y_max
+
+ # Mac font style.
+ # @return [Integer]
attr_reader :mac_style
+
+ # Smallest readable size in pixels.
+ # @return [Integer]
attr_reader :lowest_rec_ppem
+
+ # Font direction hint. Deprecated, set to 2.
+ # @return [Integer]
attr_reader :font_direction_hint
+
+ # Index to Location format.
+ # @return [Integer]
attr_reader :index_to_loc_format
+
+ # Glyph data format.
+ # @return [Integer]
attr_reader :glyph_data_format
class << self
- # mapping is new -> old glyph ids
+ # Long date time (used in TTF headers).
+ # January 1, 1904 00:00:00 UTC basis used by Long date time.
+ # @see https://developer.apple.com/fonts/TrueType-Reference-Manual/RM06/Chap6.html
+ # TrueType Font Tables
+ LONG_DATE_TIME_BASIS = Time.new(1904, 1, 1, 0, 0, 0, 0).to_i
+ private_constant :LONG_DATE_TIME_BASIS
+
+ # Encode table.
+ #
+ # @param head [TTFunk::Table::Head]
+ # @param loca [Hash] result of encoding Index to Location (`loca`) table
+ # @param mapping [Hash{Integer => Integer}] keys are new glyph IDs, values
+ # are old glyph IDs
+ # @return [EncodedString]
def encode(head, loca, mapping)
EncodedString.new do |table|
table <<
[head.version, head.font_revision].pack('N2') <<
Placeholder.new(:checksum, length: 4) <<
@@ -34,24 +98,38 @@
head.magic_number,
head.flags, head.units_per_em,
head.created, head.modified,
*min_max_values_for(head, mapping),
head.mac_style, head.lowest_rec_ppem, head.font_direction_hint,
- loca[:type] || 0, head.glyph_data_format
- ].pack('Nn2q2n*')
+ loca[:type] || 0, head.glyph_data_format,
+ ].pack('Nn2q>2n*')
end
end
+ # Convert Long Date Time timestamp to Time.
+ # @param ldt [Float, Integer]
+ # @return [Time]
+ def from_long_date_time(ldt)
+ Time.at(ldt + LONG_DATE_TIME_BASIS, in: 'UTC')
+ end
+
+ # Convert Time to Long Date Time timestamp
+ # @param time [Time]
+ # @return [Integer]
+ def to_long_date_time(time)
+ Integer(time) - LONG_DATE_TIME_BASIS
+ end
+
private
def min_max_values_for(head, mapping)
x_min = Min.new
x_max = Max.new
y_min = Min.new
y_max = Max.new
- mapping.each do |_, old_glyph_id|
+ mapping.each_value do |old_glyph_id|
glyph = head.file.find_glyph(old_glyph_id)
next unless glyph
x_min << glyph.x_min
x_max << glyph.x_max
@@ -59,19 +137,19 @@
y_max << glyph.y_max
end
[
x_min.value_or(0), y_min.value_or(0),
- x_max.value_or(0), y_max.value_or(0)
+ x_max.value_or(0), y_max.value_or(0),
]
end
end
private
def parse!
@version, @font_revision, @check_sum_adjustment, @magic_number,
- @flags, @units_per_em, @created, @modified = read(36, 'N4n2q2')
+ @flags, @units_per_em, @created, @modified = read(36, 'N4n2q>2')
@x_min, @y_min, @x_max, @y_max = read_signed(4)
@mac_style, @lowest_rec_ppem, @font_direction_hint,
@index_to_loc_format, @glyph_data_format = read(10, 'n*')