def setup_default_item_mark_get_option_value(options, name, *args) value = options[name] if value and value.respond_to?(:call) value.call(*args) else value end end def setup_default_item_mark_type(type, item, canvas, x, y, w, h, color) type ||= "rectangle" normalized_type = type.to_s.downcase case normalized_type when "rectangle" canvas.draw_rectangle(true, x, y, w, h, color) when "circle" canvas.draw_circle(true, x, y, w, h, color) when "check", "dash" props = { "font-family" => @font_family, "weight" => "bold", "foreground" => canvas.make_color(color).to_gdk_format, }.merge(item.first.text_props) layout = make_layout(span(props, entity(normalized_type))) text_width, text_height = layout.pixel_size canvas.draw_layout(layout, x - text_width / 2.0, y - text_height / 3.0) else format = _("unknown item mark type: %s\n" \ "Rectangle type is used as fallback") canvas.logger.warn(format % type.inspect) setup_default_item_mark_type("rectangle") end end def setup_default_item_mark(items, name, width, height, space_ratio, color, options={}) option_value = Proc.new do |option_name, *args| setup_default_item_mark_get_option_value(options, option_name, *args) end mark_width = screen_x(width) mark_height = screen_y(height) mark_space = option_value.call("mark_space", mark_width) || mark_width indent_width = option_value.call("indent_width", mark_width, mark_space) indent_width ||= mark_width * 3 delete_pre_draw_proc_by_name(name) delete_post_draw_proc_by_name(name) args = [items, indent_width, mark_width, mark_height, name] draw_mark(*args) do |item, canvas, x, y, w, h| x -= mark_space if block_given? yield(item, canvas, x, y, w, h, color, options) else type = options["type"] setup_default_item_mark_type(type, item, canvas, x, y, w, h, color) end end space = @space * space_ratio margin_with(:bottom => space) end def setup_default_enum_item_mark_type(type, item) type ||= "numeric" normalized_type = type.to_s.downcase.gsub(/_/, '-') case normalized_type when "numeric" "#{item.order}. " when "lower-case", "upper-case" mark = normalized_type == "lower-case" ? "a" : "A" (item.order - 1).times do mark = mark.succ end "#{mark}. " else format = _("unknown enumeration item mark type: %s\n" \ "Numeric type is used as fallback") setup_default_enum_item_mark_type("numeric", item) end end def setup_default_enum_item_mark(items, name, indent, space_ratio, props, options={}) option_value = Proc.new do |option_name, *args| setup_default_item_mark_get_option_value(options, option_name, *args) end indent_width = screen_x(indent) indent_width = option_value.call("indent_width", indent_width) || indent_width default_props = { "font_family" => @font_family, }.merge(props) delete_pre_draw_proc_by_name(name) delete_post_draw_proc_by_name(name) draw_order(items, indent_width, name) do |item| props = default_props props = props.merge(item.first.text_props) unless item.empty? if block_given? enum_mark = yield(item) else type = option_value.call("type", item) enum_mark = setup_default_enum_item_mark_type(type, item) end span(props, enum_mark) end space = @space * space_ratio margin_with(:bottom => space) end