1 # encoding: utf-8
2 require 'cldr'
3
4 module I18n
5 module Backend
6 module Cldr
7 include ::Cldr::Format
8
9 def localize(locale, object, format = :default, options = {})
10 options[:as] ||= detect_type(object, options)
11 send(:"format_#{options[:as]}", locale, object, format, options)
12 end
13
14 def format_decimal(locale, object, format = :default, options = {})
15 formatter(locale, :decimal, format).apply(object, options)
16 end
17
18 def format_integer(locale, object, format = :default, options = {})
19 format_object(number, options.merge(:precision => 0))
20 end
21
22 def format_currency(locale, object, format = :default, options = {})
23 options.merge!(:currency => lookup_currency(locale, options[:currency], object)) if options[:currency].is_a?(Symbol)
24 formatter(locale, :currency, format).apply(object, options)
25 end
26
27 def format_percent(locale, object, format = :default, options = {})
28 formatter(locale, :percent, format).apply(object, options)
29 end
30
31 def format_date(locale, object, format = :default, options = {})
32 formatter(locale, :date, format).apply(object, options)
33 end
34
35 def format_time(locale, object, format = :default, options = {})
36 formatter(locale, :time, format).apply(object, options)
37 end
38
39 def format_datetime(locale, object, format = :default, options = {})
40 key = :"calendars.gregorian.formats.datetime.#{format}.pattern"
41 date = I18n.l(object, :format => options[:date_format] || format, :locale => locale, :as => :date)
42 time = I18n.l(object, :format => options[:time_format] || format, :locale => locale, :as => :time)
43 I18n.t(key, :date => date, :time => time, :locale => locale, :raise => true)
44 end
45
46 protected
47
48 def detect_type(object, options)
49 options.has_key?(:currency) ? :currency : case object
50 when ::Numeric
51 :decimal
52 when ::Date, ::DateTime, ::Time
53 object.class.name.downcase.to_sym
54 else
55 raise_unspecified_format_type!
56 end
57 end
58
59 def formatter(locale, type, format)
60 (@formatters ||= {})[:"#{locale}.#{type}.#{format}"] ||= begin
61 format = lookup_format(locale, type, format)
62 data = lookup_format_data(locale, type)
63 ::Cldr::Format.const_get(type.to_s.camelize).new(format, data)
64 end
65 end
66
67 def lookup_format(locale, type, format)
68 key = case type
69 when :date, :time, :datetime
70 :"calendars.gregorian.formats.#{type}.#{format}.pattern"
71 else
72 :"numbers.formats.#{type}.patterns.#{format || :default}"
73 end
74 I18n.t(key, :locale => locale, :raise => true)
75 end
76
77 def lookup_format_data(locale, type)
78 key = case type
79 when :date, :time, :datetime
80 :'calendars.gregorian'
81 else
82 :'numbers.symbols'
83 end
84 I18n.t(key, :locale => locale, :raise => true)
85 end
86
87 def lookup_currency(locale, currency, count)
88 I18n.t(:"currencies.#{currency}", :locale => locale, :count => count)
89 end
90
91 def raise_unspecified_format_type!
92 raise ArgumentError.new("You have to specify a format type, e.g. :as => :number.")
93 end
94
95 def raise_unspecified_currency!
96 raise ArgumentError.new("You have to specify a currency, e.g. :currency => 'EUR'.")
97 end
98 end
99 end
100 en