Chris@909: # The engines plugin makes it trivial to share public assets using plugins. Chris@909: # To do this, include an assets directory within your plugin, and put Chris@909: # your javascripts, stylesheets and images in subdirectories of that folder: Chris@909: # Chris@909: # my_plugin Chris@909: # |- init.rb Chris@909: # |- lib/ Chris@909: # |- assets/ Chris@909: # |- javascripts/ Chris@909: # | |- my_functions.js Chris@909: # | Chris@909: # |- stylesheets/ Chris@909: # | |- my_styles.css Chris@909: # | Chris@909: # |- images/ Chris@909: # |- my_face.jpg Chris@909: # Chris@909: # Files within the asset structure are automatically mirrored into Chris@909: # a publicly-accessible folder each time your application starts (see Chris@909: # Engines::Assets#mirror_assets). Chris@909: # Chris@909: # Chris@909: # == Using plugin assets in views Chris@909: # Chris@909: # It's also simple to use Rails' helpers in your views to use plugin assets. Chris@909: # The default helper methods have been enhanced by the engines plugin to accept Chris@909: # a :plugin option, indicating the plugin containing the desired asset. Chris@909: # Chris@909: # For example, it's easy to use plugin assets in your layouts: Chris@909: # Chris@909: # <%= stylesheet_link_tag "my_styles", :plugin => "my_plugin", :media => "screen" %> Chris@909: # <%= javascript_include_tag "my_functions", :plugin => "my_plugin" %> Chris@909: # Chris@909: # ... and similarly in views and partials, it's easy to use plugin images: Chris@909: # Chris@909: # <%= image_tag "my_face", :plugin => "my_plugin" %> Chris@909: # Chris@909: # <%= image_path "my_face", :plugin => "my_plugin" %> Chris@909: # Chris@909: # Where the default helpers allow the specification of more than one file (i.e. the Chris@909: # javascript and stylesheet helpers), you can do similarly for multiple assets from Chris@909: # within a single plugin. Chris@909: # Chris@909: # --- Chris@909: # Chris@909: # This module enhances four of the methods from ActionView::Helpers::AssetTagHelper: Chris@909: # Chris@909: # * stylesheet_link_tag Chris@909: # * javascript_include_tag Chris@909: # * image_path Chris@909: # * image_tag Chris@909: # Chris@909: # Each one of these methods now accepts the key/value pair :plugin => "plugin_name", Chris@909: # which can be used to specify the originating plugin for any assets. Chris@909: # Chris@909: module Engines::RailsExtensions::AssetHelpers Chris@909: def self.included(base) #:nodoc: Chris@909: base.class_eval do Chris@909: [:stylesheet_link_tag, :javascript_include_tag, :image_path, :image_tag].each do |m| Chris@909: alias_method_chain m, :engine_additions Chris@909: end Chris@909: end Chris@909: end Chris@909: Chris@909: # Adds plugin functionality to Rails' default stylesheet_link_tag method. Chris@909: def stylesheet_link_tag_with_engine_additions(*sources) Chris@909: stylesheet_link_tag_without_engine_additions(*Engines::RailsExtensions::AssetHelpers.pluginify_sources("stylesheets", *sources)) Chris@909: end Chris@909: Chris@909: # Adds plugin functionality to Rails' default javascript_include_tag method. Chris@909: def javascript_include_tag_with_engine_additions(*sources) Chris@909: javascript_include_tag_without_engine_additions(*Engines::RailsExtensions::AssetHelpers.pluginify_sources("javascripts", *sources)) Chris@909: end Chris@909: Chris@909: #-- Chris@909: # Our modified image_path now takes a 'plugin' option, though it doesn't require it Chris@909: #++ Chris@909: Chris@909: # Adds plugin functionality to Rails' default image_path method. Chris@909: def image_path_with_engine_additions(source, options={}) Chris@909: options.stringify_keys! Chris@909: source = Engines::RailsExtensions::AssetHelpers.plugin_asset_path(options["plugin"], "images", source) if options["plugin"] Chris@909: image_path_without_engine_additions(source) Chris@909: end Chris@909: Chris@909: # Adds plugin functionality to Rails' default image_tag method. Chris@909: def image_tag_with_engine_additions(source, options={}) Chris@909: options.stringify_keys! Chris@909: if options["plugin"] Chris@909: source = Engines::RailsExtensions::AssetHelpers.plugin_asset_path(options["plugin"], "images", source) Chris@909: options.delete("plugin") Chris@909: end Chris@909: image_tag_without_engine_additions(source, options) Chris@909: end Chris@909: Chris@909: #-- Chris@909: # The following are methods on this module directly because of the weird-freaky way Chris@909: # Rails creates the helper instance that views actually get Chris@909: #++ Chris@909: Chris@909: # Convert sources to the paths for the given plugin, if any plugin option is given Chris@909: def self.pluginify_sources(type, *sources) Chris@909: options = sources.last.is_a?(Hash) ? sources.pop.stringify_keys : { } Chris@909: sources.map! { |s| plugin_asset_path(options["plugin"], type, s) } if options["plugin"] Chris@909: options.delete("plugin") # we don't want it appearing in the HTML Chris@909: sources << options # re-add options Chris@909: end Chris@909: Chris@909: # Returns the publicly-addressable relative URI for the given asset, type and plugin Chris@909: def self.plugin_asset_path(plugin_name, type, asset) Chris@909: raise "No plugin called '#{plugin_name}' - please use the full name of a loaded plugin." if Engines.plugins[plugin_name].nil? Chris@909: "#{ActionController::Base.relative_url_root}/#{Engines.plugins[plugin_name].public_asset_directory}/#{type}/#{asset}" Chris@909: end Chris@909: Chris@909: end Chris@909: Chris@909: module ::ActionView::Helpers::AssetTagHelper #:nodoc: Chris@909: include Engines::RailsExtensions::AssetHelpers Chris@909: end