menu_helper 0.0.1 → 0.0.4
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- data/CHANGELOG +31 -0
- data/MIT-LICENSE +2 -2
- data/README +30 -33
- data/Rakefile +9 -8
- data/lib/menu_helper/html_element.rb +45 -47
- data/lib/menu_helper/menu.rb +98 -93
- data/lib/menu_helper/menu_bar.rb +141 -141
- data/lib/menu_helper.rb +72 -73
- data/test/app_root/log/in_memory.log +1 -0
- data/test/test_helper.rb +1 -3
- data/test/unit/html_element_test.rb +73 -49
- data/test/unit/menu_bar_test.rb +31 -19
- data/test/unit/menu_helper_test.rb +5 -5
- data/test/unit/menu_test.rb +28 -23
- metadata +57 -47
data/CHANGELOG
ADDED
@@ -0,0 +1,31 @@
|
|
1
|
+
*SVN*
|
2
|
+
|
3
|
+
*0.0.4* (June 1st, 2008)
|
4
|
+
|
5
|
+
* Remove dependency on set_or_append
|
6
|
+
|
7
|
+
*0.0.3* (May 5th, 2008)
|
8
|
+
|
9
|
+
* Updated documentation
|
10
|
+
|
11
|
+
*0.0.2* (September 26th, 2007)
|
12
|
+
|
13
|
+
* Add gem dependency on set_or_append
|
14
|
+
|
15
|
+
* Convert dos newlines to unix newlines
|
16
|
+
|
17
|
+
* Fix too many :nodoc: tags so that rdocs are generated properly
|
18
|
+
|
19
|
+
*0.0.1* (August 16th, 2007)
|
20
|
+
|
21
|
+
* Add README documentation
|
22
|
+
|
23
|
+
* Add api documentation
|
24
|
+
|
25
|
+
* Add dependency on plugin_test_helper in order to simplify the test setup code
|
26
|
+
|
27
|
+
* Remove MainMenuBar in favor of providing a default id for MenuBar
|
28
|
+
|
29
|
+
* Refactor helper classes into individual files
|
30
|
+
|
31
|
+
* Add unit tests
|
data/MIT-LICENSE
CHANGED
@@ -1,4 +1,4 @@
|
|
1
|
-
Copyright (c) 2006-
|
1
|
+
Copyright (c) 2006-2008 Aaron Pfeifer
|
2
2
|
|
3
3
|
Permission is hereby granted, free of charge, to any person obtaining
|
4
4
|
a copy of this software and associated documentation files (the
|
@@ -17,4 +17,4 @@ MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
|
|
17
17
|
NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
|
18
18
|
LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
|
19
19
|
OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
|
20
|
-
WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
|
20
|
+
WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
|
data/README
CHANGED
@@ -1,29 +1,25 @@
|
|
1
1
|
= menu_helper
|
2
2
|
|
3
|
-
menu_helper adds a helper method for generating a menubar.
|
3
|
+
+menu_helper+ adds a helper method for generating a menubar.
|
4
4
|
|
5
5
|
== Resources
|
6
6
|
|
7
|
-
API
|
8
|
-
|
9
|
-
* http://api.pluginaweek.org/menu_helper
|
10
|
-
|
11
7
|
Wiki
|
12
8
|
|
13
9
|
* http://wiki.pluginaweek.org/Menu_helper
|
14
10
|
|
15
|
-
|
16
|
-
|
17
|
-
* http://www.pluginaweek.org/
|
18
|
-
|
19
|
-
Source
|
11
|
+
API
|
20
12
|
|
21
|
-
* http://
|
13
|
+
* http://api.pluginaweek.org/menu_helper
|
22
14
|
|
23
15
|
Development
|
24
16
|
|
25
17
|
* http://dev.pluginaweek.org/browser/trunk/plugins/action_pack/menu_helper
|
26
18
|
|
19
|
+
Source
|
20
|
+
|
21
|
+
* http://svn.pluginaweek.org/trunk/plugins/action_pack/menu_helper
|
22
|
+
|
27
23
|
== Description
|
28
24
|
|
29
25
|
The generation of a menubar's structure can often be a repetitive and unDRY
|
@@ -32,7 +28,7 @@ a menubar. menu_helper attempts to following this standard in addition to
|
|
32
28
|
automatically adding ids, classes for selected menus, and default urls each
|
33
29
|
menu is linked to (base on various information, such as the name of the menu).
|
34
30
|
|
35
|
-
==
|
31
|
+
== Usage
|
36
32
|
|
37
33
|
routes.rb:
|
38
34
|
ActionController::Routing::Routes.draw do |map|
|
@@ -55,19 +51,19 @@ routes.rb:
|
|
55
51
|
end
|
56
52
|
end
|
57
53
|
|
58
|
-
_menubar.rhtml:
|
59
|
-
<%=
|
60
|
-
menu_bar do |main|
|
61
|
-
main.menu :home
|
62
|
-
main.menu :products
|
63
|
-
main.menu :services
|
64
|
-
main.menu :about_us do |about_us|
|
65
|
-
about_us.menu :overview, 'Overview', about_us_url
|
66
|
-
about_us.menu :who_we_are
|
67
|
-
about_us.menu :contact, 'Contact Us'
|
54
|
+
_menubar.rhtml:
|
55
|
+
<%=
|
56
|
+
menu_bar do |main|
|
57
|
+
main.menu :home
|
58
|
+
main.menu :products
|
59
|
+
main.menu :services
|
60
|
+
main.menu :about_us do |about_us|
|
61
|
+
about_us.menu :overview, 'Overview', about_us_url
|
62
|
+
about_us.menu :who_we_are
|
63
|
+
about_us.menu :contact, 'Contact Us'
|
68
64
|
end
|
69
|
-
main.menu :search, 'Search!', 'http://www.google.com', :class => 'ir'
|
70
|
-
end
|
65
|
+
main.menu :search, 'Search!', 'http://www.google.com', :class => 'ir'
|
66
|
+
end
|
71
67
|
%>
|
72
68
|
|
73
69
|
Output (formatted for sanity):
|
@@ -84,25 +80,26 @@ Output (formatted for sanity):
|
|
84
80
|
<li class="search ir" id="search"><a href="http://www.google.com">Search!</a></li>
|
85
81
|
</ul>
|
86
82
|
|
87
|
-
|
83
|
+
=== Caveat Emptor
|
88
84
|
|
89
85
|
Remember one of the basic principles of programming: KISS. There's no need to
|
90
86
|
use this plugin if you're writing a very, very simple menubar. The advantages
|
91
87
|
of this helper are consistency, DRYness, and decreased complexity if you have
|
92
88
|
lots of submenus.
|
93
89
|
|
94
|
-
I wrote this plugin
|
95
|
-
|
96
|
-
fits the needs of your application before committing to using it.
|
90
|
+
I wrote this plugin mostly as an educational/experimental piece, so I don't using
|
91
|
+
this in a production application, but rather a prototype.
|
97
92
|
|
98
93
|
== Testing
|
99
94
|
|
100
|
-
|
101
|
-
|
95
|
+
To test this plugin, the following gems must be installed:
|
96
|
+
* plugin_test_helper[http://wiki.pluginaweek.org/Plugin_test_helper]
|
97
|
+
|
98
|
+
To run against a specific version of Rails:
|
102
99
|
|
103
|
-
|
100
|
+
rake test RAILS_FRAMEWORK_ROOT=/path/to/rails
|
104
101
|
|
105
102
|
== Dependencies
|
106
103
|
|
107
|
-
|
108
|
-
|
104
|
+
* Rails 2.0 or later
|
105
|
+
* set_or_append[http://wiki.pluginaweek.org/Set_or_append]
|
data/Rakefile
CHANGED
@@ -4,7 +4,7 @@ require 'rake/gempackagetask'
|
|
4
4
|
require 'rake/contrib/sshpublisher'
|
5
5
|
|
6
6
|
PKG_NAME = 'menu_helper'
|
7
|
-
PKG_VERSION = '0.0.
|
7
|
+
PKG_VERSION = '0.0.4'
|
8
8
|
PKG_FILE_NAME = "#{PKG_NAME}-#{PKG_VERSION}"
|
9
9
|
RUBY_FORGE_PROJECT = 'pluginaweek'
|
10
10
|
|
@@ -22,6 +22,7 @@ desc 'Generate documentation for the menu_helper plugin.'
|
|
22
22
|
Rake::RDocTask.new(:rdoc) do |rdoc|
|
23
23
|
rdoc.rdoc_dir = 'rdoc'
|
24
24
|
rdoc.title = 'MenuHelper'
|
25
|
+
rdoc.template = '../rdoc_template.rb'
|
25
26
|
rdoc.options << '--line-numbers' << '--inline-source'
|
26
27
|
rdoc.rdoc_files.include('README')
|
27
28
|
rdoc.rdoc_files.include('lib/**/*.rb')
|
@@ -33,14 +34,14 @@ spec = Gem::Specification.new do |s|
|
|
33
34
|
s.platform = Gem::Platform::RUBY
|
34
35
|
s.summary = 'Adds a helper method for generating a menubar'
|
35
36
|
|
36
|
-
s.files = FileList['{lib,
|
37
|
+
s.files = FileList['{lib,test}/**/*'].to_a + %w(CHANGELOG init.rb MIT-LICENSE Rakefile README)
|
37
38
|
s.require_path = 'lib'
|
38
39
|
s.autorequire = 'menu_helper'
|
39
40
|
s.has_rdoc = true
|
40
41
|
s.test_files = Dir['test/**/*_test.rb']
|
41
42
|
|
42
|
-
s.author = 'Aaron Pfeifer
|
43
|
-
s.email = '
|
43
|
+
s.author = 'Aaron Pfeifer'
|
44
|
+
s.email = 'aaron@pluginaweek.org'
|
44
45
|
s.homepage = 'http://www.pluginaweek.org'
|
45
46
|
end
|
46
47
|
|
@@ -52,22 +53,22 @@ end
|
|
52
53
|
|
53
54
|
desc 'Publish the beta gem'
|
54
55
|
task :pgem => [:package] do
|
55
|
-
Rake::SshFilePublisher.new('
|
56
|
+
Rake::SshFilePublisher.new('aaron@pluginaweek.org', '/home/aaron/gems.pluginaweek.org/public/gems', 'pkg', "#{PKG_FILE_NAME}.gem").upload
|
56
57
|
end
|
57
58
|
|
58
59
|
desc 'Publish the API documentation'
|
59
60
|
task :pdoc => [:rdoc] do
|
60
|
-
Rake::SshDirPublisher.new('
|
61
|
+
Rake::SshDirPublisher.new('aaron@pluginaweek.org', "/home/aaron/api.pluginaweek.org/public/#{PKG_NAME}", 'rdoc').upload
|
61
62
|
end
|
62
63
|
|
63
64
|
desc 'Publish the API docs and gem'
|
64
|
-
task :publish => [:pdoc, :release]
|
65
|
+
task :publish => [:pgem, :pdoc, :release]
|
65
66
|
|
66
67
|
desc 'Publish the release files to RubyForge.'
|
67
68
|
task :release => [:gem, :package] do
|
68
69
|
require 'rubyforge'
|
69
70
|
|
70
|
-
ruby_forge = RubyForge.new
|
71
|
+
ruby_forge = RubyForge.new.configure
|
71
72
|
ruby_forge.login
|
72
73
|
|
73
74
|
%w( gem tgz zip ).each do |ext|
|
@@ -1,48 +1,46 @@
|
|
1
|
-
module PluginAWeek #:nodoc:
|
2
|
-
module
|
3
|
-
|
4
|
-
|
5
|
-
|
6
|
-
|
7
|
-
|
8
|
-
|
9
|
-
|
10
|
-
|
11
|
-
|
12
|
-
|
13
|
-
|
14
|
-
|
15
|
-
|
16
|
-
|
17
|
-
|
18
|
-
|
19
|
-
|
20
|
-
|
21
|
-
|
22
|
-
|
23
|
-
|
24
|
-
|
25
|
-
|
26
|
-
|
27
|
-
|
28
|
-
|
29
|
-
|
30
|
-
|
31
|
-
|
32
|
-
|
33
|
-
|
34
|
-
|
35
|
-
|
36
|
-
|
37
|
-
|
38
|
-
|
39
|
-
|
40
|
-
|
41
|
-
|
42
|
-
|
43
|
-
|
44
|
-
|
45
|
-
|
46
|
-
end
|
47
|
-
end
|
1
|
+
module PluginAWeek #:nodoc:
|
2
|
+
module MenuHelper
|
3
|
+
# Represents an HTML element
|
4
|
+
#
|
5
|
+
# == Modifying HTML options
|
6
|
+
#
|
7
|
+
# HTML options can normally be specified when creating the element.
|
8
|
+
# However, if they need to be modified after the element has been created,
|
9
|
+
# you can access the properties like so:
|
10
|
+
#
|
11
|
+
# m = Menu.new
|
12
|
+
# m[:style] = 'display: none;'
|
13
|
+
#
|
14
|
+
# or for a menu bar:
|
15
|
+
#
|
16
|
+
# b = MenuBar.new
|
17
|
+
# b[:style] = 'display: none;'
|
18
|
+
class HtmlElement
|
19
|
+
include ActionView::Helpers::TagHelper
|
20
|
+
|
21
|
+
delegate :[],
|
22
|
+
:[]=,
|
23
|
+
:to => '@html_options'
|
24
|
+
|
25
|
+
def initialize(html_options = {}) #:nodoc:
|
26
|
+
@html_options = html_options.symbolize_keys
|
27
|
+
end
|
28
|
+
|
29
|
+
# Generates the html representing this element
|
30
|
+
def html
|
31
|
+
content_tag(tag_name, content, @html_options)
|
32
|
+
end
|
33
|
+
|
34
|
+
private
|
35
|
+
# The name of the element tag to use (e.g. td, th, tr, etc.)
|
36
|
+
def tag_name
|
37
|
+
''
|
38
|
+
end
|
39
|
+
|
40
|
+
# The content that will be displayed inside of the tag
|
41
|
+
def content
|
42
|
+
''
|
43
|
+
end
|
44
|
+
end
|
45
|
+
end
|
48
46
|
end
|
data/lib/menu_helper/menu.rb
CHANGED
@@ -1,101 +1,106 @@
|
|
1
|
-
|
2
|
-
|
3
|
-
|
4
|
-
|
5
|
-
|
6
|
-
|
7
|
-
|
8
|
-
|
9
|
-
|
10
|
-
|
11
|
-
|
12
|
-
|
13
|
-
|
14
|
-
|
1
|
+
module PluginAWeek #:nodoc:
|
2
|
+
module MenuHelper
|
3
|
+
# Represents a single menu within a menu bar
|
4
|
+
class Menu < HtmlElement
|
5
|
+
include ActionView::Helpers::UrlHelper
|
6
|
+
|
7
|
+
# The url where this menu is linked to
|
8
|
+
attr_reader :url_options
|
9
|
+
|
10
|
+
# If there are submenus under this menu, they are stored in here
|
11
|
+
attr_reader :menu_bar
|
12
|
+
|
13
|
+
# Allow submenus to be created
|
14
|
+
delegate :menu,
|
15
|
+
:to => :menu_bar
|
16
|
+
|
17
|
+
def initialize(id, request_controller, parent = nil, *args) #:nodoc
|
18
|
+
id = id.to_s
|
19
|
+
@controller = @request_controller = request_controller
|
20
|
+
@parent = parent
|
21
|
+
@content = args.first.is_a?(String) ? args.shift : id.underscore.titleize
|
22
|
+
@url_options = args.shift || {}
|
23
|
+
super(args.shift || {})
|
24
|
+
|
25
|
+
# Set the default html options
|
26
|
+
@html_options[:id] ||= id
|
27
|
+
|
28
|
+
@menu_bar = MenuBar.new(@request_controller, {}, {:id => "#{self[:id]}_menubar"}, self)
|
29
|
+
|
30
|
+
# Build the url for the menu
|
31
|
+
url, @url_options = build_url(@url_options)
|
32
|
+
@content = link_to(@content, url) if auto_link?
|
33
|
+
|
34
|
+
yield self if block_given?
|
35
|
+
end
|
36
|
+
|
37
|
+
# Should we try to automatically generate the link?
|
38
|
+
def auto_link?
|
39
|
+
!@url_options.is_a?(Hash) || !@url_options.include?(:auto_link) || @url_options[:auto_link]
|
40
|
+
end
|
41
|
+
|
42
|
+
# Is this menu selected? A menu is considered selected if it or any of
|
43
|
+
# its submenus are selected
|
44
|
+
def selected?
|
45
|
+
current_page?(@url_options) || @menu_bar.menus.any? {|menu| menu.selected?}
|
46
|
+
end
|
47
|
+
|
48
|
+
# Builds the actual html of the menu
|
49
|
+
def html(last = false)
|
50
|
+
html_options = @html_options.dup
|
51
|
+
html_options[:class] = (html_options[:class].to_s + ' selected').strip if selected?
|
52
|
+
html_options[:class] = (html_options[:class].to_s + ' last').strip if last
|
53
|
+
|
54
|
+
content_tag(tag_name, content, html_options)
|
55
|
+
end
|
56
|
+
|
57
|
+
private
|
58
|
+
def tag_name
|
59
|
+
'li'
|
60
|
+
end
|
61
|
+
|
62
|
+
def content
|
63
|
+
content = @content
|
64
|
+
content << @menu_bar.html if @menu_bar.menus.any?
|
65
|
+
content
|
66
|
+
end
|
15
67
|
|
16
|
-
# Allow submenus to be created
|
17
|
-
delegate :menu,
|
18
|
-
:to => :menu_bar
|
19
|
-
|
20
|
-
def initialize(id, request_controller, parent = nil, *args) #:nodoc
|
21
|
-
id = id.to_s
|
22
|
-
@controller = @request_controller = request_controller
|
23
|
-
@parent = parent
|
24
|
-
@content = args.first.is_a?(String) ? args.shift : id.underscore.titleize
|
25
|
-
@url_options = args.shift || {}
|
26
|
-
super(args.shift || {})
|
27
|
-
|
28
|
-
# Set the default html options
|
29
|
-
@html_options[:id] ||= id
|
30
|
-
|
31
|
-
@menu_bar = MenuBar.new(@request_controller, {}, {:id => "#{self[:id]}_menubar"}, self)
|
32
|
-
|
33
|
-
# Build the url for the menu
|
34
|
-
url, @url_options = build_url(@url_options)
|
35
|
-
@content = link_to(@content, url) if auto_link?
|
36
|
-
|
37
|
-
yield self if block_given?
|
38
|
-
end
|
39
|
-
|
40
|
-
# Should we try to automatically generate the link?
|
41
|
-
def auto_link?
|
42
|
-
!@url_options.is_a?(Hash) || !@url_options.include?(:auto_link)
|
43
|
-
end
|
44
|
-
|
45
|
-
# Is this menu selected? A menu is considered selected if it or any of
|
46
|
-
# its submenus are selected
|
47
|
-
def selected?
|
48
|
-
current_page?(@url_options) || @menu_bar.menus.any? {|menu| menu.selected?}
|
49
|
-
end
|
50
|
-
|
51
|
-
# Builds the actual html of the menu
|
52
|
-
def build(last = false)
|
53
|
-
html = @content + @menu_bar.build
|
54
|
-
html_options = @html_options.dup
|
55
|
-
html_options.set_or_prepend(:class, 'selected') if selected?
|
56
|
-
html_options.set_or_prepend(:class, 'last') if last
|
57
|
-
|
58
|
-
content_tag('li', html, html_options)
|
59
|
-
end
|
60
|
-
|
61
|
-
private
|
62
68
|
# Builds the url based on the options provided in the construction of
|
63
|
-
# the menu
|
64
|
-
def build_url(options = {})
|
65
|
-
# Check if the name given for the menu is a named route
|
66
|
-
if options.blank? && route_options = (named_route(self[:id], @parent) || named_route(self[:id]))
|
67
|
-
options = route_options
|
69
|
+
# the menu
|
70
|
+
def build_url(options = {})
|
71
|
+
# Check if the name given for the menu is a named route
|
72
|
+
if options.blank? && route_options = (named_route(self[:id], @parent) || named_route(self[:id]))
|
73
|
+
options = route_options
|
68
74
|
elsif options.is_a?(Hash)
|
69
|
-
options[:controller] ||= find_controller(options)
|
75
|
+
options[:controller] ||= find_controller(options)
|
70
76
|
options[:action] ||= self[:id] unless options[:controller] == self[:id]
|
71
77
|
options[:only_path] ||= false
|
72
78
|
end
|
73
79
|
|
74
|
-
url = options.is_a?(Hash) ? url_for(options) : options
|
75
|
-
return url, options
|
76
|
-
end
|
77
|
-
|
78
|
-
# Finds the most likely controller that this menu should link to, in
|
79
|
-
# order of:
|
80
|
-
# 1. The specified controller in the menu link options
|
81
|
-
# 2. The name of the menu (e.g. products = ProductsController)
|
82
|
-
# 3. The parent's controller
|
83
|
-
# 4. The request controller
|
84
|
-
def find_controller(options)
|
85
|
-
options[:controller] ||
|
86
|
-
(begin; "#{self[:id].camelize}Controller".constantize.controller_path; rescue; nil; end) ||
|
87
|
-
@parent && @parent.url_options[:controller] ||
|
88
|
-
@request_controller.params[:controller]
|
89
|
-
end
|
90
|
-
|
91
|
-
# Finds the named route that is being linked to (if that route exists)
|
92
|
-
def named_route(name, parent = nil)
|
93
|
-
name = "#{parent[:id]}_#{name}" if parent
|
94
|
-
method_name = "hash_for_#{name}_url"
|
95
|
-
|
96
|
-
@request_controller.send(method_name) if @request_controller.respond_to?(method_name)
|
97
|
-
end
|
98
|
-
|
99
|
-
|
100
|
-
end
|
80
|
+
url = options.is_a?(Hash) ? url_for(options) : options
|
81
|
+
return url, options
|
82
|
+
end
|
83
|
+
|
84
|
+
# Finds the most likely controller that this menu should link to, in
|
85
|
+
# order of:
|
86
|
+
# 1. The specified controller in the menu link options
|
87
|
+
# 2. The name of the menu (e.g. products = ProductsController)
|
88
|
+
# 3. The parent's controller
|
89
|
+
# 4. The request controller
|
90
|
+
def find_controller(options)
|
91
|
+
options[:controller] ||
|
92
|
+
(begin; "#{self[:id].camelize}Controller".constantize.controller_path; rescue; nil; end) ||
|
93
|
+
@parent && @parent.url_options[:controller] ||
|
94
|
+
@request_controller.params[:controller]
|
95
|
+
end
|
96
|
+
|
97
|
+
# Finds the named route that is being linked to (if that route exists)
|
98
|
+
def named_route(name, parent = nil)
|
99
|
+
name = "#{parent[:id]}_#{name}" if parent
|
100
|
+
method_name = "hash_for_#{name}_url"
|
101
|
+
|
102
|
+
@request_controller.send(method_name) if @request_controller.respond_to?(method_name)
|
103
|
+
end
|
104
|
+
end
|
105
|
+
end
|
101
106
|
end
|