middleman/middleman-core/lib/middleman-core/core_extensions/default_helpers.rb

248 lines
8.0 KiB
Ruby
Raw Normal View History

2014-04-04 19:22:34 +02:00
require 'padrino-helpers'
2014-02-19 03:30:29 +01:00
2014-04-04 19:22:34 +02:00
# Don't fail on invalid locale, that's not what our current
# users expect.
::I18n.enforce_available_locales = false
class Padrino::Helpers::OutputHelpers::ErbHandler
# Force Erb capture not to use safebuffer
def capture_from_template(*args, &block)
2015-09-17 18:41:17 +02:00
self.output_buffer = ''
buf_was = output_buffer
2014-02-19 03:30:29 +01:00
raw = block.call(*args)
captured = template.instance_variable_get(:@_out_buf)
self.output_buffer = buf_was
engine_matches?(block) && !captured.empty? ? captured : raw
end
end
2013-04-20 23:36:38 +02:00
class Middleman::CoreExtensions::DefaultHelpers < ::Middleman::Extension
def initialize(app, options_hash={}, &block)
super
2013-04-20 23:36:38 +02:00
require 'active_support/core_ext/object/to_query'
2013-06-04 18:48:01 +02:00
2014-01-02 06:19:05 +01:00
::Middleman::TemplateContext.send :include, ::Padrino::Helpers::OutputHelpers
::Middleman::TemplateContext.send :include, ::Padrino::Helpers::TagHelpers
::Middleman::TemplateContext.send :include, ::Padrino::Helpers::AssetTagHelpers
::Middleman::TemplateContext.send :include, ::Padrino::Helpers::FormHelpers
::Middleman::TemplateContext.send :include, ::Padrino::Helpers::FormatHelpers
::Middleman::TemplateContext.send :include, ::Padrino::Helpers::RenderHelpers
::Middleman::TemplateContext.send :include, ::Padrino::Helpers::NumberHelpers
# ::Middleman::TemplateContext.send :include, ::Padrino::Helpers::TranslationHelpers
2013-04-20 23:36:38 +02:00
app.config.define_setting :relative_links, false, 'Whether to generate relative links instead of absolute ones'
end
2013-04-20 23:36:38 +02:00
# The helpers
helpers do
# Make all block content html_safe
2014-04-29 19:50:21 +02:00
def content_tag(name, content=nil, options=nil, &block)
2014-01-02 06:19:05 +01:00
# safe_content_tag(name, content, options, &block)
2013-06-18 20:06:43 +02:00
if block_given?
options = content if content.is_a?(Hash)
content = capture_html(&block)
end
options = parse_data_options(name, options)
attributes = tag_attributes(options)
output = ActiveSupport::SafeBuffer.new
output.safe_concat "<#{name}#{attributes}>"
2014-02-19 03:30:29 +01:00
2013-06-18 20:06:43 +02:00
if content.respond_to?(:each) && !content.is_a?(String)
content.each do |c|
output.safe_concat c
output.safe_concat ::Padrino::Helpers::TagHelpers::NEWLINE
end
2013-06-18 20:06:43 +02:00
else
output.safe_concat "#{content}"
end
output.safe_concat "</#{name}>"
block_is_template?(block) ? concat_content(output) : output
end
def capture_html(*args, &block)
2014-04-04 19:22:34 +02:00
result = if handler = auto_find_proper_handler(&block)
2014-02-19 03:30:29 +01:00
handler.capture_from_template(*args, &block)
else
block.call(*args)
end
2014-01-02 06:19:05 +01:00
2015-02-24 20:06:28 +01:00
::ActiveSupport::SafeBuffer.new.safe_concat(result)
end
def auto_find_proper_handler(&block)
2014-01-02 06:19:05 +01:00
if block_given?
engine = File.extname(block.source_location[0])[1..-1].to_sym
::Padrino::Helpers::OutputHelpers.handlers.select { |e, _| e == engine }.values.map { |h| h.new(self) }.find { |h| h.engine_matches?(block) }
2014-01-02 06:19:05 +01:00
else
find_proper_handler
end
end
2013-04-20 23:36:38 +02:00
# Disable Padrino cache buster
def asset_stamp
false
end
2013-04-20 23:36:38 +02:00
# Output a stylesheet link tag based on the current path
#
# @return [String]
def auto_stylesheet_link_tag
auto_tag(:css) do |path|
stylesheet_link_tag path
end
end
2013-04-20 23:36:38 +02:00
# Output a javascript tag based on the current path
#
# @return [String]
def auto_javascript_include_tag
auto_tag(:js) do |path|
javascript_include_tag path
end
end
2013-04-20 23:36:38 +02:00
# Output a stylesheet link tag based on the current path
#
# @param [Symbol] asset_ext The type of asset
# @param [String] asset_dir Where to look for assets
# @return [void]
def auto_tag(asset_ext, asset_dir=nil)
if asset_dir.nil?
asset_dir = case asset_ext
2014-04-29 01:02:18 +02:00
when :js
2014-04-29 20:43:05 +02:00
config[:js_dir]
2014-04-29 01:02:18 +02:00
when :css
2014-04-29 20:43:05 +02:00
config[:css_dir]
end
2013-04-20 23:36:38 +02:00
end
2013-04-20 23:36:38 +02:00
# If the basename of the request as no extension, assume we are serving a
# directory and join index_file to the path.
path = File.join(asset_dir, current_resource.path)
path = path.sub(/#{Regexp.escape(File.extname(path))}$/, ".#{asset_ext}")
2013-04-20 23:36:38 +02:00
yield path if sitemap.find_resource_by_path(path)
end
2013-04-10 05:21:21 +02:00
2013-04-20 23:36:38 +02:00
# Generate body css classes based on the current path
#
# @return [String]
2014-04-29 19:50:21 +02:00
def page_classes(path=current_path.dup, options={})
if path.is_a? Hash
options = path
path = current_path.dup
2013-12-13 17:30:19 +01:00
end
2013-04-20 23:36:38 +02:00
path << index_file if path.end_with?('/')
path = ::Middleman::Util.strip_leading_slash(path)
2013-02-09 07:22:33 +01:00
2014-07-10 21:35:47 +02:00
classes = Set.new
2013-04-20 23:36:38 +02:00
parts = path.split('.').first.split('/')
2014-04-29 19:50:21 +02:00
parts.each_with_index { |_, i| classes << parts.first(i + 1).join('_') }
2013-02-09 07:22:33 +01:00
prefix = options[:numeric_prefix] || 'x'
classes.map do |c|
# Replace weird class name characters
c = c.gsub(/[^a-zA-Z0-9\-_]/, '-')
# Class names can't start with a digit
2013-10-29 17:33:27 +01:00
c = "#{prefix}#{c}" if c =~ /\A\d/
c
end.join(' ')
2013-04-20 23:36:38 +02:00
end
2013-04-10 05:21:21 +02:00
2013-04-20 23:36:38 +02:00
# Get the path of a file of a given type
#
# @param [Symbol] kind The type of file
# @param [String] source The path to the file
# @param [Hash] options Data to pass through.
2013-04-20 23:36:38 +02:00
# @return [String]
def asset_path(kind, source, options={})
::Middleman::Util.asset_path(app, kind, source, options)
2013-04-20 23:36:38 +02:00
end
2013-04-10 05:21:21 +02:00
2013-04-20 23:36:38 +02:00
# Get the URL of an asset given a type/prefix
#
# @param [String] path The path (such as "photo.jpg")
# @param [String] prefix The type prefix (such as "images")
# @return [String] The fully qualified asset url
2014-06-16 18:05:24 +02:00
def asset_url(_path, prefix='', options={})
::Middleman::Util.asset_url(app, prefix, options)
2013-04-20 23:36:38 +02:00
end
2013-02-09 07:22:33 +01:00
2013-04-20 23:36:38 +02:00
# Given a source path (referenced either absolutely or relatively)
# or a Resource, this will produce the nice URL configured for that
# path, respecting :relative_links, directory indexes, etc.
def url_for(path_or_resource, options={})
2014-01-04 21:44:20 +01:00
options_with_resource = options.merge(current_resource: current_resource)
2014-01-02 06:19:05 +01:00
::Middleman::Util.url_for(app, path_or_resource, options_with_resource)
2013-04-20 23:36:38 +02:00
end
# Overload the regular link_to to be sitemap-aware - if you
# reference a source path, either absolutely or relatively,
# you'll get that resource's nice URL. Also, there is a
# :relative option which, if set to true, will produce
# relative URLs instead of absolute URLs. You can also add
#
# config[:relative_links] = true
#
# to config.rb to have all links default to relative.
#
# There is also a :query option that can be used to append a
# query string, which can be expressed as either a String,
# or a Hash which will be turned into URL parameters.
def link_to(*args, &block)
url_arg_index = block_given? ? 0 : 1
options_index = block_given? ? 1 : 2
if block_given? && args.size > 2
2014-04-29 01:02:18 +02:00
raise ArgumentError, 'Too many arguments to link_to(url, options={}, &block)'
end
2013-04-20 23:36:38 +02:00
if url = args[url_arg_index]
options = args[options_index] || {}
2014-04-29 01:02:18 +02:00
raise ArgumentError, 'Options must be a hash' unless options.is_a?(Hash)
2013-04-20 23:36:38 +02:00
# Transform the url through our magic url_for method
args[url_arg_index] = url_for(url, options)
# Cleanup before passing to Padrino
2014-01-04 21:44:20 +01:00
options.except!(:relative, :current_resource, :find_resource, :query, :anchor, :fragment)
2013-04-20 23:36:38 +02:00
end
super(*args, &block)
end
# Modified Padrino form_for that uses Middleman's url_for
# to transform the URL.
def form_tag(url, options={}, &block)
url = url_for(url, options)
super
end
2015-04-26 22:01:19 +02:00
# Modified Padrino image_tag so that it finds the paths for srcset
# using asset_path for the images listed in the srcset param
def image_tag(path, params={})
params.symbolize_keys!
2015-04-26 22:01:19 +02:00
if params.key?(:srcset)
2015-04-26 18:41:50 +02:00
images_sources = params[:srcset].split(',').map do |src_def|
if src_def.include?('//')
src_def
else
image_def, size_def = src_def.strip.split(/\s+/)
asset_path(:images, image_def) + ' ' + size_def
end
end
params[:srcset] = images_sources.join(', ')
end
super(path, params)
end
end
end