Ported text command over to the new args classes

* Involved a big rewrite of arg_loader to accomodate nil and false better. Sadly this meant dumping ||= for if-statements. Blech, but works.
  * Updates to regression tests are pretty trivial.
  * Removed graphics_text_spec because, even though it looks useful, with rake sanity it really isn't.
  * Exposed font on deck as well

Cleaned up graphics/text.rb too!
This commit is contained in:
Andy Meneely
2015-07-07 23:59:23 -04:00
parent 11f827cffa
commit e43f68d323
26 changed files with 441 additions and 456 deletions
+3 -3
View File
@@ -48,12 +48,12 @@ module Squib
# @return [Array] Returns an Array of hashes keyed by :width and :height that mark the ink extents of the text rendered.
# @api public
def text(opts = {})
opts = { stroke_width: 0, width: :auto, height: :auto }.merge(opts)
opts = { stroke_width: 0, width: :auto, height: :auto }.merge(opts)
range = Args::CardRange.new(opts[:range], deck_size: size)
para = Args::Paragraph.new.load!(opts, expand_by: size, layout: layout)
para = Args::Paragraph.new(font).load!(opts, expand_by: size, layout: layout)
box = Args::Box.new(self).load!(opts, expand_by: size, layout: layout, dpi: dpi)
trans = Args::Transform.new.load!(opts, expand_by: size, layout: layout, dpi: dpi)
draw = Args::Draw.new.load!(opts, expand_by: size, layout: layout, dpi: dpi)
draw = Args::Draw.new.load!(opts, expand_by: size, layout: layout, dpi: dpi)
embed = TextEmbed.new
yield(embed) if block_given? #store the opts for later use
extents = Array.new(@cards.size)
+34 -38
View File
@@ -13,38 +13,51 @@ module Squib
# Main class invoked by the client (i.e. api/ methods)
def load!(args, expand_by: 1, layout: {}, dpi: 300)
@dpi = dpi
set_attributes(args: args)
expand(by: expand_by)
layout_args = prep_layout_args(args[:layout], expand_by: expand_by)
defaultify(layout_args: layout_args || [], layout: layout)
args[:layout] = prep_layout_args(args[:layout], expand_by: expand_by)
expand_and_set_and_defaultify(args: args, by: expand_by, layout: layout)
validate
convert_units
self
end
# Iterate over the args hash and create instance-level attributes for
# each parameter
# Assumes we have a hash of parameters to their default keys in the class
def set_attributes(args: args)
def expand_and_set_and_defaultify(args: {}, by: 1, layout: {})
attributes = self.class.parameters.keys
attributes.each do |p|
instance_variable_set "@#{p}", args[p] # often nil, but ok
args[p] = defaultify(p, args, layout)
val = if expandable_singleton?(p, args[p])
[args[p]] * by
else
args[p] # not an expanding parameter
end
instance_variable_set "@#{p}", val
end
self.class.class_eval { attr_reader *(attributes) }
end
# Conduct singleton expansion
# If expanding-parameter is not already responding to
# :each then copy it into an array
#
# Assumes we have an self.expanding_parameters
def expand(by: 1)
exp_params = self.class.expanding_parameters
exp_params.each do |p|
attribute = "@#{p}"
arg = instance_variable_get(attribute)
unless arg.respond_to? :each
instance_variable_set attribute, [arg] * by #expand singleton
# Must be:
# (a) an expanding parameter, and
# (b) a singleton already (i.e. doesn't respond to :each)
def expandable_singleton?(p, arg)
self.class.expanding_parameters.include?(p) && !arg.respond_to?(:each)
end
# Incorporate defaults and layouts
# (1) Use whatever is specified if it is
# (2) Go over all layout specifications (if any) and look them up
# - Use layout when it's specified for that card
# - Use default if no layout was specified,
# or the layout itself did not specify
def defaultify(p, args, layout)
return args[p] if args.key? p # arg was specified, no defaults used
args[:layout].map do |layout_arg|
if layout_arg.nil?
self.class.parameters[p] # no layout specified, use default
else
if layout[layout_arg.to_s].key? p.to_s
layout[layout_arg.to_s][p.to_s] # param specified in layout
else
self.class.parameters[p] # layout specified, but not this param
end
end
end
end
@@ -58,23 +71,6 @@ module Squib
layout_args || []
end
# Go over each argument and fill it in with layout and defaults wherever nil
def defaultify(layout_args: [], layout: {})
self.class.parameters.each do |param, default|
attribute = "@#{param}"
val = instance_variable_get(attribute)
if val.respond_to? :each
new_val = val.map.with_index do |v, i|
v ||= layout[layout_args[i].to_s][param.to_s] unless layout_args[i].nil?
v ||= default
end
instance_variable_set(attribute, new_val)
else # a non-expanded singleton
# TODO handle this case
end
end
end
# For each parameter/attribute foo we try to invoke a validate_foo
def validate
self.class.parameters.each do |param, default|
+84 -9
View File
@@ -7,18 +7,19 @@ module Squib
class Paragraph
include ArgLoader
def self.parameters
{ align: :left,
str: 'Hello, World!',
font: :use_set,
{ align: :left,
str: 'Hello, World!',
font: :use_set,
font_size: nil,
markup: false,
justify: false,
wrap: true,
markup: false,
justify: false,
wrap: true,
ellipsize: :end,
spacing: 0,
valign: :top,
hint: :off
spacing: 0,
valign: :top,
hint: :off
}
end
@@ -30,10 +31,84 @@ module Squib
[] # none of them
end
def initialize(deck_font)
@deck_font = deck_font
end
def validate_str(arg, _i)
arg.to_s
end
def validate_font(arg, _i)
arg = @deck_font if arg == :use_set
arg = Squib::SYSTEM_DEFAULTS[:default_font] if arg == :default
arg
end
def validate_align(arg, _i)
case arg.to_s.downcase
when 'left'
Pango::ALIGN_LEFT
when 'right'
Pango::ALIGN_RIGHT
when 'center'
Pango::ALIGN_CENTER
else
raise ArgumentError, 'align must be one of: center, left, right'
end
end
def validate_wrap(arg, _i)
case arg.to_s.downcase
when 'word'
Pango::Layout::WRAP_WORD
when 'char', 'false'
Pango::Layout::WRAP_CHAR
when 'word_char', 'true'
Pango::Layout::WRAP_WORD_CHAR
else
raise ArgumentError, 'wrap must be one of: word, char, word_char, true, or false'
end
end
def validate_ellipsize(arg, _i)
case arg.to_s.downcase
when 'none', 'false'
Pango::Layout::ELLIPSIZE_NONE
when 'start'
Pango::Layout::ELLIPSIZE_START
when 'middle'
Pango::Layout::ELLIPSIZE_MIDDLE
when 'end', 'true'
Pango::Layout::ELLIPSIZE_END
else
raise ArgumentError, 'ellipsize must be one of: none, start, middle, end, true, or false'
end
end
def validate_justify(arg, _i)
case arg
when nil, true, false
arg
else
raise ArgumentError, 'justify must be one of: nil, true, or false'
end
end
def validate_spacing(arg, _i)
return nil if arg.nil?
raise ArgumentError, 'spacing must be a number or nil' unless arg.respond_to? :to_f
Pango::SCALE * arg.to_f
end
def validate_valign(arg, _i)
if %w(top middle bottom).include? arg.to_s.downcase
arg.to_s.downcase
else
raise ArgumentError, 'valign must be one of: top, middle, bottom'
end
end
end
end
+1 -1
View File
@@ -35,7 +35,7 @@ module Squib
:img_dir, :prefix, :text_hint, :typographer
# :nodoc:
# @api private
attr_reader :layout, :conf, :dpi
attr_reader :layout, :conf, :dpi, :font
#
# deck.size is really just @cards.size
+3 -44
View File
@@ -20,47 +20,6 @@ module Squib
cc.stroke
end
# :nodoc:
# @api private
def set_ellipsize!(layout, ellipsize)
case ellipsize.to_s.downcase
when 'none', 'false'
layout.ellipsize = Pango::Layout::ELLIPSIZE_NONE
when 'start'
layout.ellipsize = Pango::Layout::ELLIPSIZE_START
when 'middle'
layout.ellipsize = Pango::Layout::ELLIPSIZE_MIDDLE
when 'end', 'true'
layout.ellipsize = Pango::Layout::ELLIPSIZE_END
end
end
# :nodoc:
# @api private
def set_wrap!(layout, wrap)
case wrap.to_s.downcase
when 'word'
layout.wrap = Pango::Layout::WRAP_WORD
when 'char'
layout.wrap = Pango::Layout::WRAP_CHAR
when 'word_char', 'true'
layout.wrap = Pango::Layout::WRAP_WORD_CHAR
end
end
# :nodoc:
# @api private
def set_align!(layout, align)
case align.to_s.downcase
when 'left'
layout.alignment = Pango::ALIGN_LEFT
when 'right'
layout.alignment = Pango::ALIGN_RIGHT
when 'center'
layout.alignment = Pango::ALIGN_CENTER
end
end
# :nodoc:
# @api private
def compute_valign(layout, valign)
@@ -173,9 +132,9 @@ module Squib
set_font_rendering_opts!(layout)
set_wh!(layout, box.width, box.height)
set_wrap!(layout, para.wrap)
set_ellipsize!(layout, para.ellipsize)
set_align!(layout, para.align)
layout.wrap = para.wrap
layout.ellipsize = para.ellipsize
layout.alignment = para.align
layout.justify = para.justify unless para.justify.nil?
layout.spacing = para.spacing * Pango::SCALE unless para.spacing.nil?