Chrononaut-hirb 0.2.1

Sign up to get free protection for your applications and to get access to all the features.
data/CHANGELOG.rdoc ADDED
@@ -0,0 +1,19 @@
1
+ == 0.2.1
2
+ * Fixed typo in Hirb::Console.view
3
+
4
+ == 0.2.0
5
+ * Major refactoring with bug fixes and better tests.
6
+ * Improved table algorithm to ensure that tables don't wrap.
7
+ * Added a pager which detects if output should be paged, Hirb::Pager.
8
+ * Added a selection menu, Hirb::Menu
9
+ * Following API changes: Hirb::Helpers::Table.max_width removed and config files don't use
10
+ the :view key anymore.
11
+ == 0.1.2
12
+ * Added tree views.
13
+ * Added output_method option to Hirb::View.render_output.
14
+
15
+ == 0.1.1
16
+ * Fixed bug when rendering table with many fields.
17
+
18
+ == 0.1.0
19
+ * Initial release
data/LICENSE.txt ADDED
@@ -0,0 +1,22 @@
1
+ The MIT LICENSE
2
+
3
+ Copyright (c) 2009 Gabriel Horner
4
+
5
+ Permission is hereby granted, free of charge, to any person obtaining
6
+ a copy of this software and associated documentation files (the
7
+ "Software"), to deal in the Software without restriction, including
8
+ without limitation the rights to use, copy, modify, merge, publish,
9
+ distribute, sublicense, and/or sell copies of the Software, and to
10
+ permit persons to whom the Software is furnished to do so, subject to
11
+ the following conditions:
12
+
13
+ The above copyright notice and this permission notice shall be
14
+ included in all copies or substantial portions of the Software.
15
+
16
+ THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
17
+ EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
18
+ MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
19
+ NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
20
+ LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
21
+ OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
22
+ WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
data/README.rdoc ADDED
@@ -0,0 +1,164 @@
1
+ == Description
2
+
3
+ Hirb currently provides a mini view framework for console applications, designed to improve irb's default output.
4
+ Hirb improves console output by providing a smart pager and auto-formatting output. The smart pager detects when an output exceeds
5
+ a screenful and thus only pages output as needed. Auto-formatting adds a view to an output's class. This is helpful in separating
6
+ views from content (MVC anyone?). The framework encourages reusing views by letting you
7
+ package them in classes and associate them with any number of output classes. Hirb comes with tree views (see
8
+ Hirb::Helpers::Tree) and table views (see Hirb::Helpers::Table). By default Hirb displays Rails'
9
+ model classes as tables. Hirb also sports a nice selection menu, Hirb::Menu.
10
+
11
+ == Install
12
+
13
+ Install the gem with:
14
+
15
+ sudo gem install cldwalker-hirb --source http://gems.github.com
16
+
17
+ == Pager
18
+
19
+ Hirb has both pager and formatter functionality enabled by default.
20
+ If you want to turn off the functionality of either you can pass that in at startup:
21
+
22
+ Hirb.enable :pager=>false
23
+ Hirb.enable :formatter=>false
24
+
25
+ or toggle their state at runtime:
26
+
27
+ Hirb::View.toggle_pager
28
+ Hirb::View.toggle_formatter
29
+
30
+ == Create and Configure Views
31
+
32
+ If you'd like to learn how to create and configure views, {read the docs}[http://tagaholic.me/hirb/doc/classes/Hirb/Formatter.html].
33
+
34
+ == Rails Formatter Example
35
+
36
+ Let's load and enable the view framework:
37
+ bash> script/console
38
+ Loading local environment (Rails 2.2.2)
39
+ irb>> require 'hirb'
40
+ => true
41
+ irb>> Hirb.enable
42
+ => nil
43
+
44
+ The default configuration provides table views for ActiveRecord::Base descendants.
45
+ If a class isn't configured, Hirb reverts to irb's default echo mode.
46
+ irb>> Hirb::View.formatter_config
47
+ => {"ActiveRecord::Base"=>{:class=>"Hirb::Views::ActiveRecord_Base", :ancestor=>true}}
48
+
49
+ # Tag is a model class and descendant of ActiveRecord::Base
50
+ irb>> Tag.last
51
+ +-----+-------------------------+-------------+---------------+-----------+-----------+-------+
52
+ | id | created_at | description | name | namespace | predicate | value |
53
+ +-----+-------------------------+-------------+---------------+-----------+-----------+-------+
54
+ | 907 | 2009-03-06 21:10:41 UTC | | gem:tags=yaml | gem | tags | yaml |
55
+ +-----+-------------------------+-------------+---------------+-----------+-----------+-------+
56
+ 1 row in set
57
+
58
+ irb>> 'plain ol irb'
59
+ => 'plain ol irb'
60
+ irb>> :blah
61
+ => :blah
62
+
63
+ From above you can see there were no views configured for a String or a Symbol so Hirb defaulted to
64
+ irb's echo mode. Also note that Tag was able to inherit its view from the ActiveRecord::Base config
65
+ because it had an :ancestor option.
66
+
67
+ Now that you understand that Hirb displays views based on an output object's class,
68
+ you may appreciate it also detects configured output objects in an array:
69
+
70
+ irb>> Tag.all :limit=>3, :order=>"id DESC"
71
+ +-----+-------------------------+-------------+-------------------+-----------+-----------+----------+
72
+ | id | created_at | description | name | namespace | predicate | value |
73
+ +-----+-------------------------+-------------+-------------------+-----------+-----------+----------+
74
+ | 907 | 2009-03-06 21:10:41 UTC | | gem:tags=yaml | gem | tags | yaml |
75
+ | 906 | 2009-03-06 08:47:04 UTC | | gem:tags=nomonkey | gem | tags | nomonkey |
76
+ | 905 | 2009-03-04 00:30:10 UTC | | article:tags=ruby | article | tags | ruby |
77
+ +-----+-------------------------+-------------+-------------------+-----------+-----------+----------+
78
+ 3 rows in set
79
+
80
+ At any time you can disable Hirb if you really like irb's lovely echo mode:
81
+ irb>> Hirb.disable
82
+ => nil
83
+ irb>> Tag.all :limit=>3, :order=>"id DESC"
84
+ => [#<Tag id: 907, name: "gem:tags=yaml", description: nil, created_at: "2009-03-06 21:10:41",
85
+ namespace: "gem", predicate: "tags", value: "yaml">, #<Tag id: 906, name: "gem:tags=nomonkey",
86
+ description: nil, created_at: "2009-03-06 08:47:04", namespace: "gem", predicate: "tags", value:
87
+ "nomonkey">, #<Tag id: 905, name: "article:tags=ruby", description: nil, created_at: "2009-03-04
88
+ 00:30:10", namespace: "article", predicate: "tags", value: "ruby">]
89
+
90
+ == Views: Anytime, Anywhere
91
+ While preconfigured tables are great for database records, sometimes you just want to create
92
+ tables/views for any output object:
93
+
94
+ #These examples don't need to have Hirb::View enabled.
95
+ irb>>Hirb.disable
96
+ =>nil
97
+
98
+ # Imports table() and view()
99
+ irb>>extend Hirb::Console
100
+ =>main
101
+
102
+ # Create a table of Dates comparing them with different formats.
103
+ irb>> table [Date.today, Date.today.next_month], :fields=>[:to_s, :ld, :ajd, :amjd, :asctime]
104
+ +------------+--------+-----------+-------+--------------------------+
105
+ | to_s | ld | ajd | amjd | asctime |
106
+ +------------+--------+-----------+-------+--------------------------+
107
+ | 2009-03-11 | 155742 | 4909803/2 | 54901 | Wed Mar 11 00:00:00 2009 |
108
+ | 2009-04-11 | 155773 | 4909865/2 | 54932 | Sat Apr 11 00:00:00 2009 |
109
+ +------------+--------+-----------+-------+--------------------------+
110
+ 2 rows in set
111
+
112
+ # Same table as the previous method. However view() will be able to call any helper.
113
+ irb>> view [Date.today, Date.today.next_month], :class=>:object_table,
114
+ :fields=>[:to_s, :ld, :ajd, :amjd, :asctime]
115
+
116
+ If these console methods weren't convenient enough, try:
117
+
118
+ # Imports view() to all objects.
119
+ irb>> require 'hirb/import_object'
120
+ =>true
121
+ # Yields same table as above examples.
122
+ irb>> [Date.today, Date.today.next_month].view :class=>:object_table,
123
+ :fields=>[:to_s, :ld, :ajd, :amjd, :asctime]
124
+
125
+ Although views by default are printed to STDOUT, they can be easily modified to write anywhere:
126
+ # Setup views to write to file 'console.log'.
127
+ irb>> Hirb::View.render_method = lambda {|output| File.open("console.log", 'w') {|f| f.write(output) } }
128
+
129
+ # Writes to file with same table output as above example.
130
+ irb>> view [Date.today, Date.today.next_month], :class=>:object_table,
131
+ :fields=>[:to_s, :ld, :ajd, :amjd, :asctime]
132
+
133
+ # Doesn't write to file because Symbol isn't configured to use Hirb::View and thus defaults to irb's echo mode.
134
+ irb>> :blah
135
+ =>:blah
136
+
137
+ # Go back to printing Hirb views to STDOUT.
138
+ irb>> Hirb::View.reset_render_method
139
+
140
+ == Sharing Views
141
+ If you have tested views you'd like to share, fork Hirb and put your views under
142
+ the lib/hirb/views/ and/or helpers files under lib/hirb/helpers/. If not tested, feel free to share
143
+ them on the wiki.
144
+
145
+ == Limitations
146
+ If using Wirble, you should call Hirb after it since they both override irb's default output.
147
+
148
+ == Motivation
149
+ Table code from http://gist.github.com/72234 and {my console
150
+ app's needs}[http://github.com/cldwalker/tag-tree].
151
+
152
+ == Bugs/Issues
153
+ Please report them {on github}[http://github.com/cldwalker/hirb/issues].
154
+
155
+ == Links
156
+ * http://tagaholic.me/2009/03/13/hirb-irb-on-the-good-stuff.html
157
+ * http://tagaholic.me/2009/03/18/ruby-class-trees-rails-plugin-trees-with-hirb.html
158
+ * http://tagaholic.me/2009/06/19/page-irb-output-and-improve-ri-with-hirb.html
159
+
160
+ == Todo
161
+ * Consider applying multiple views/filters to output.
162
+ * Consider mapping a class' methods to their own views.
163
+ * Provides helper methods to all view classes.
164
+ * Consider adding a template system as needed.
data/Rakefile ADDED
@@ -0,0 +1,50 @@
1
+ require 'rake'
2
+ require 'rake/testtask'
3
+ require 'rake/rdoctask'
4
+ begin
5
+ require 'rcov/rcovtask'
6
+
7
+ Rcov::RcovTask.new do |t|
8
+ t.libs << 'test'
9
+ t.test_files = FileList['test/**/*_test.rb']
10
+ t.rcov_opts = ["-T -x '/Library/Ruby/*'"]
11
+ t.verbose = true
12
+ end
13
+ rescue LoadError
14
+ puts "Rcov not available. Install it for rcov-related tasks with: sudo gem install rcov"
15
+ end
16
+
17
+ begin
18
+ require 'jeweler'
19
+ Jeweler::Tasks.new do |s|
20
+ s.name = "hirb"
21
+ s.summary = "A mini view framework for console/irb that's easy to use, even while under its influence."
22
+ s.description = "Hirb currently provides a mini view framework for console applications, designed to improve irb's default output. Hirb improves console output by providing a smart pager and auto-formatting output. The smart pager detects when an output exceeds a screenful and thus only pages output as needed. Auto-formatting adds a view to an output's class. This is helpful in separating views from content (MVC anyone?). The framework encourages reusing views by letting you package them in classes and associate them with any number of output classes."
23
+ s.email = "gabriel.horner@gmail.com"
24
+ s.homepage = "http://github.com/cldwalker/hirb"
25
+ s.authors = ["Gabriel Horner"]
26
+ s.rubyforge_project = 'tagaholic'
27
+ s.has_rdoc = true
28
+ s.extra_rdoc_files = ["README.rdoc", "LICENSE.txt"]
29
+ s.files = FileList["[A-Z]*", "{bin,lib,test}/**/*"]
30
+ end
31
+
32
+ rescue LoadError
33
+ puts "Jeweler not available. Install it for jeweler-related tasks with: sudo gem install technicalpickles-jeweler -s http://gems.github.com"
34
+ end
35
+
36
+ Rake::TestTask.new do |t|
37
+ t.libs << 'lib'
38
+ t.pattern = 'test/**/*_test.rb'
39
+ t.verbose = false
40
+ end
41
+
42
+ Rake::RDocTask.new do |rdoc|
43
+ rdoc.rdoc_dir = 'rdoc'
44
+ rdoc.title = 'test'
45
+ rdoc.options << '--line-numbers' << '--inline-source'
46
+ rdoc.rdoc_files.include('README*')
47
+ rdoc.rdoc_files.include('lib/**/*.rb')
48
+ end
49
+
50
+ task :default => :test
data/VERSION.yml ADDED
@@ -0,0 +1,4 @@
1
+ ---
2
+ :patch: 2
3
+ :major: 0
4
+ :minor: 2
data/lib/hirb.rb ADDED
@@ -0,0 +1,56 @@
1
+ current_dir = File.dirname(__FILE__)
2
+ $:.unshift(current_dir) unless $:.include?(current_dir) || $:.include?(File.expand_path(current_dir))
3
+ require 'hirb/util'
4
+ require 'hirb/hash_struct'
5
+ require 'hirb/helpers'
6
+ require 'hirb/view'
7
+ require 'hirb/views/activerecord_base'
8
+ require 'hirb/console'
9
+ require 'hirb/formatter'
10
+ require 'hirb/pager'
11
+ require 'hirb/menu'
12
+
13
+ # Most of Hirb's functionality currently resides in Hirb::View.
14
+ # For an in-depth tutorial on creating and configuring views see Hirb::Formatter.
15
+ # Hirb has an optional yaml config file defined by config_file(). This config file
16
+ # has the following top level keys:
17
+ # [:output] This hash is used by the formatter object. See Hirb::Formatter.config for its format.
18
+ # [:width] Width of the terminal/console. Defaults to DEFAULT_WIDTH or possibly autodetected when Hirb is enabled.
19
+ # [:height] Height of the terminal/console. Defaults to DEFAULT_HEIGHT or possibly autodetected when Hirb is enabled.
20
+ # [:formatter] Boolean which determines if the formatter is enabled. Defaults to true.
21
+ # [:pager] Boolean which determines if the pager is enabled. Defaults to true.
22
+ # [:pager_command] Command to be used for paging. Command can have options after it i.e. 'less -r'.
23
+ # Defaults to common pagers i.e. less and more if detected.
24
+ #
25
+
26
+ module Hirb
27
+ class <<self
28
+ # Enables view functionality. See Hirb::View.enable for details.
29
+ def enable(options={}, &block)
30
+ View.enable(options, &block)
31
+ end
32
+
33
+ # Disables view functionality. See Hirb::View.disable for details.
34
+ def disable
35
+ View.disable
36
+ end
37
+ # Default is config/hirb.yml or ~/hirb.yml in that order.
38
+ def config_file
39
+ @config_file ||= File.exists?('config/hirb.yml') ? 'config/hirb.yml' : File.expand_path(File.join(ENV["HOME"],".hirb.yml"))
40
+ end
41
+
42
+ #:stopdoc:
43
+ def config_file=(value)
44
+ @config_file = value
45
+ end
46
+
47
+ def read_config_file(file=config_file)
48
+ File.exists?(file) ? YAML::load_file(file) : {}
49
+ end
50
+
51
+ def config(reload=false)
52
+ @config = (@config.nil? || reload) ? read_config_file : @config
53
+ end
54
+ #:startdoc:
55
+ end
56
+ end
@@ -0,0 +1,43 @@
1
+ module Hirb
2
+ # This module is meant to be extended to provide methods for use in a console/irb shell.
3
+ # For example:
4
+ # irb>> extend Hirb::Console
5
+ # irb>> view 'some string', :class=>Some::String::Formatter
6
+ # irb>> table [[:row1], [:row2]]
7
+ module Console
8
+ class<<self
9
+ # A console version of render_output() which takes its same options but allows for shorthand. All options are passed to
10
+ # the helper except for the formatter options. Formatter options are :class, :method and :output_method.
11
+ # Examples:
12
+ # render_output output, :class=>:tree :type=>:directory
13
+ # # is the same as:
14
+ # render_output output, :class=>:tree, :options=> {:type=>:directory}
15
+ #
16
+ def render_output(output, options={})
17
+ View.load_config unless View.config_loaded?
18
+ View.render_output(output, options.merge(:console=>true))
19
+ end
20
+
21
+ # Takes same arguments and options as render_output() but returns formatted output instead of rendering it.
22
+ def format_output(output, options={}, &block)
23
+ View.load_config unless View.config_loaded?
24
+ View.formatter.format_output(output, options.merge(:console=>true), &block)
25
+ end
26
+ end
27
+
28
+ # Renders a table for the given object. Takes same options as Hirb::Helpers::Table.render.
29
+ def table(output, options={})
30
+ Console.render_output(output, options.merge(:class=>"Hirb::Helpers::AutoTable"))
31
+ end
32
+
33
+ # Renders any specified view for the given object. Takes same options as Hirb::View.render_output.
34
+ def view(output, options={})
35
+ Console.render_output(output, options)
36
+ end
37
+
38
+ # Renders a menu given an array using Hirb::Menu.render.
39
+ def menu(output, options={}, &block)
40
+ Console.format_output(output, options.merge(:class=>"Hirb::Menu"), &block)
41
+ end
42
+ end
43
+ end
@@ -0,0 +1,199 @@
1
+ module Hirb
2
+ =begin rdoc
3
+ This class is format an output into a string using Hirb::Helpers::*, Hirb::Views::* or any user-created views.
4
+ The formatter object looks for an output's class config in Hirb::Formatter.config and if found applies a helper to the output.
5
+
6
+ == Create and Configure Views
7
+ Let's create a simple view and configure it in different ways to be Hash's default view:
8
+
9
+ === Setup
10
+ irb>> require 'hirb'
11
+ =>true
12
+ irb>> Hirb.enable
13
+ =>nil
14
+ irb>> require 'yaml'
15
+ =>true
16
+
17
+ === Configure As View Method
18
+ A view method is the smallest reuseable view.
19
+ # Create yaml view method
20
+ irb>> def yaml(output); output.to_yaml; end
21
+ =>nil
22
+
23
+ # Configure view
24
+ irb>>Hirb::View.format_class Hash, :method=>:yaml
25
+ =>true
26
+
27
+ # Hashes now appear as yaml
28
+ irb>>{:a=>1, :b=>{:c=>3}}
29
+ ---
30
+ :a : 1
31
+ :b :
32
+ :c : 3
33
+ => true
34
+
35
+ === Configure As View Class
36
+ A view class is suited for more complex views. View classes can be under any namespace
37
+ and are expected to provide a render method. However, if a class is under the Hirb::Views namespace,
38
+ it will be automatically loaded with no configuration. Something to think about when
39
+ sharing views with others.
40
+
41
+ # Create yaml view class
42
+ irb>> class Hirb::Views::Hash; def self.render(output, options={}); output.to_yaml; end ;end
43
+ =>nil
44
+ # Just reload since no configuration is necessary
45
+ irb>>Hirb::View.formatter.reload
46
+
47
+ # Hashes now appear as yaml ...
48
+
49
+ Although the Hirb::Views namespace is great for quick classes that just plug and play, you
50
+ often want view classes that can be reused with multiple outputs. For this case, it's recommended to
51
+ use the Hirb::Helpers namespace.
52
+
53
+ # Create yaml view class
54
+ irb>> class Hirb::Helpers::Yaml; def self.render(output, options={}); output.to_yaml; end ;end
55
+ =>nil
56
+
57
+ # Configure view and reload it
58
+ irb>>Hirb::View.format_class Hash, :class=>"Hirb::Helpers::Yaml"
59
+ =>true
60
+
61
+ # Hashes now appear as yaml ...
62
+
63
+ == Configure At Startup
64
+ Once you know what views are associated with what output classes, you can configure
65
+ them at startup by passing Hirb.enable an options hash:
66
+ # In .irbrc
67
+ require 'hirb'
68
+ # View class needs to come before enable()
69
+ class Hirb::Helpers::Yaml; def self.render(output, options={}); output.to_yaml; end ;end
70
+ Hirb.enable :output=>{"Hash"=>{:class=>"Hirb::Helpers::Yaml"}}
71
+
72
+ Or by creating a config file at config/hirb.yml or ~/.hirb.yml:
73
+ # The config file for the yaml example would look like:
74
+ # ---
75
+ # :output :
76
+ # Hash :
77
+ # :class : Hirb::Helpers::Yaml
78
+
79
+ # In .irbrc
80
+ require 'hirb'
81
+ # View class needs to come before enable()
82
+ class Hirb::Helpers::Yaml; def self.render(output, options={}); output.to_yaml; end ;end
83
+ Hirb.enable
84
+ =end
85
+
86
+ class Formatter
87
+ def initialize(additional_config={})
88
+ @klass_config = {}
89
+ @config = Util.recursive_hash_merge default_config, additional_config || {}
90
+ end
91
+
92
+ # A hash of Ruby class strings mapped to helper config hashes. A helper config hash must have at least a :method, :output_method
93
+ # or :class option for a helper to be applied to an output. A helper config hash has the following keys:
94
+ # [:method] Specifies a global (Kernel) method to do the formatting.
95
+ # [:class] Specifies a class to do the formatting, using its render() class method. If a symbol it's converted to a corresponding
96
+ # Hirb::Helpers::* class if it exists.
97
+ # [:output_method] Specifies a method or proc to call on output before passing it to a helper. If the output is an array, it's applied
98
+ # to every element in the array.
99
+ # [:options] Options to pass the helper method or class.
100
+ # [:ancestor] Boolean which when true causes subclasses of the output class to inherit its config. This doesn't effect the current
101
+ # output class. Defaults to false. This is used by ActiveRecord classes.
102
+ #
103
+ # Examples:
104
+ # {'WWW::Delicious::Element'=>{:class=>'Hirb::Helpers::ObjectTable', :ancestor=>true, :options=>{:max_width=>180}}}
105
+ # {'Date'=>{:class=>:auto_table, :ancestor=>true}}
106
+ def config
107
+ @config
108
+ end
109
+
110
+ # Sets the helper config for the given output class.
111
+ def format_class(klass, helper_config)
112
+ @klass_config.delete(klass)
113
+ @config[klass.to_s] = helper_config
114
+ true
115
+ end
116
+
117
+ # Reloads autodetected Hirb::Views
118
+ def reload
119
+ @config = Util.recursive_hash_merge default_config, @config
120
+ end
121
+
122
+ # This is the main method of this class. The formatter looks for the first helper in its config for the given output class.
123
+ # If a helper is found, the output is converted by the helper into a string and returned. If not, nil is returned. The options
124
+ # this class takes are a helper config hash as described in config. These options will be merged with any existing helper config hash
125
+ # an output class has in config. Any block given is passed along to a helper class.
126
+ def format_output(output, options={}, &block)
127
+ output_class = determine_output_class(output)
128
+ options = parse_console_options(options) if options.delete(:console)
129
+ options = Util.recursive_hash_merge(klass_config(output_class), options)
130
+ output = options[:output_method] ? (output.is_a?(Array) ? output.map {|e| call_output_method(options[:output_method], e) } :
131
+ call_output_method(options[:output_method], output) ) : output
132
+ args = [output]
133
+ args << options[:options] if options[:options] && !options[:options].empty?
134
+ if options[:method]
135
+ new_output = send(options[:method],*args)
136
+ elsif options[:class] && (helper_class = determine_helper_class(options[:class]))
137
+ new_output = helper_class.render(*args, &block)
138
+ elsif options[:output_method]
139
+ new_output = output
140
+ end
141
+ new_output
142
+ end
143
+
144
+ #:stopdoc:
145
+ def parse_console_options(options) #:nodoc:
146
+ real_options = [:method, :class, :output_method].inject({}) do |h, e|
147
+ h[e] = options.delete(e) if options[e]; h
148
+ end
149
+ real_options.merge! :options=>options
150
+ real_options
151
+ end
152
+
153
+ def determine_helper_class(klass)
154
+ if klass.is_a?(Symbol) && (helper_class = Helpers.constants.find {|e| e == Util.camelize(klass.to_s)})
155
+ klass = "Hirb::Helpers::#{helper_class}"
156
+ end
157
+ Util.any_const_get(klass)
158
+ end
159
+
160
+ def determine_output_class(output)
161
+ if output.is_a?(Array)
162
+ output[0].class
163
+ else
164
+ output.class
165
+ end
166
+ end
167
+
168
+ def call_output_method(output_method, output)
169
+ output_method.is_a?(Proc) ? output_method.call(output) : output.send(output_method)
170
+ end
171
+
172
+ # Internal view options built from user-defined ones. Options are built by recursively merging options from oldest
173
+ # ancestors to the most recent ones.
174
+ def klass_config(output_class)
175
+ @klass_config[output_class] ||= begin
176
+ output_ancestors_with_config = output_class.ancestors.map {|e| e.to_s}.select {|e| @config.has_key?(e)}
177
+ @klass_config[output_class] = output_ancestors_with_config.reverse.inject({}) {|h, klass|
178
+ (klass == output_class.to_s || @config[klass][:ancestor]) ? h.update(@config[klass]) : h
179
+ }
180
+ end
181
+ end
182
+
183
+ def reset_klass_config
184
+ @klass_config = {}
185
+ end
186
+
187
+ def default_config
188
+ Views.constants.inject({}) {|h,e|
189
+ output_class = e.to_s.gsub("_", "::")
190
+ if (views_class = Views.const_get(e)) && views_class.respond_to?(:render)
191
+ default_options = views_class.respond_to?(:default_options) ? views_class.default_options : {}
192
+ h[output_class] = default_options.merge({:class=>"Hirb::Views::#{e}"})
193
+ end
194
+ h
195
+ }
196
+ end
197
+ #:startdoc:
198
+ end
199
+ end