lib/prawn/document/text.rb in prawn-0.1.1 vs lib/prawn/document/text.rb in prawn-0.1.2
- old
+ new
@@ -35,30 +35,46 @@
#
# If your font contains kerning pairs data that Prawn can parse, the
# text will be kerned by default. You can disable this feature by passing
# <tt>:kerning => false</tt>.
#
+ # == Encoding
+ #
# Note that strings passed to this function should be encoded as UTF-8.
- # If you get unexpected characters appearing in your rendered
- # document, check this.
+ # If you get unexpected characters appearing in your rendered document,
+ # check this.
#
+ # If the current font is a built-in one, although the string must be
+ # encoded as UTF-8, only characters that are available in ISO-8859-1
+ # are allowed.
+ #
# If an empty box is rendered to your PDF instead of the character you
# wanted it usually means the current font doesn't include that character.
#
def text(text,options={})
+ # ensure a valid font is selected
+ font "Helvetica" unless fonts[@font]
+
+ # we'll be messing with the strings encoding, don't change the users
+ # original string
+ text = text.dup
+
# check the string is encoded sanely
- normalize_encoding(text)
+ # - UTF-8 for TTF fonts
+ # - ISO-8859-1 for Built-In fonts
+ if using_builtin_font?
+ normalize_builtin_encoding(text)
+ else
+ normalize_ttf_encoding(text)
+ end
if options.key?(:kerning)
options[:kerning] = false unless font_metrics.has_kerning_data?
else
options[:kerning] = true if font_metrics.has_kerning_data?
end
- # ensure a valid font is selected
- font "Helvetica" unless fonts[@font]
-
return wrapped_text(text,options) unless options[:at]
x,y = translate(options[:at])
font_size(options[:size] || current_font_size) do
font_name = font_registry[fonts[@font]]
@@ -149,11 +165,12 @@
end
alias_method :font_size=, :font_size!
private
-
+
+
# The current font_size being used in the document.
#
def current_font_size
@font_size || DEFAULT_FONT_SIZE
end
@@ -279,15 +296,29 @@
:Encoding => :"Identity-H",
:ToUnicode => to_unicode)
return basename
end
- def normalize_encoding(text)
+ # built-in fonts only work with latin encoding, so translate the string
+ def normalize_builtin_encoding(text)
+ if text.respond_to?(:encode!)
+ text.encode!("ISO-8859-1")
+ else
+ require 'iconv'
+ text.replace Iconv.conv('ISO-8859-1', 'utf-8', text)
+ end
+ rescue
+ raise Prawn::Errors::IncompatibleStringEncoding, "When using a " +
+ "builtin font, only characters that exist in " +
+ "WinAnsi/ISO-8859-1 are allowed."
+ end
+
+ def normalize_ttf_encoding(text)
# TODO: if the current font is a built in one, we can't use the utf-8
# string provided by the user. We should convert it to WinAnsi or
# MacRoman or some such.
- if text.respond_to?(:"encode!")
+ if text.respond_to?(:encode!)
# if we're running under a M17n aware VM, ensure the string provided is
# UTF-8 (by converting it if necessary)
begin
text.encode!("UTF-8")
rescue
@@ -314,11 +345,11 @@
raise Prawn::Errors::UnknownFont, "#{name} is not a known font."
end
fonts[name] ||= ref(:Type => :Font,
:Subtype => :Type1,
:BaseFont => name.to_sym,
- :Encoding => :MacRomanEncoding)
+ :Encoding => :WinAnsiEncoding)
return name
end
def set_current_font #:nodoc:
return if @font.nil?
@@ -339,8 +370,11 @@
def fonts #:nodoc:
@fonts ||= {}
end
+ def using_builtin_font?
+ fonts[@font].data[:Subtype] == :Type1
+ end
end
end
end