1
0
Fork 0
mirror of https://github.com/ruby/ruby.git synced 2022-11-09 12:17:21 -05:00
ruby--ruby/lib/rdoc/any_method.rb
drbrain 6d1266a879 * lib/rdoc/*: Added --root option for building documentation outside
the source directory.
* test/rdoc/*:  ditto
* common.mk (rdoc):  Added --root to rdoc rule


git-svn-id: svn+ssh://ci.ruby-lang.org/ruby/trunk@37896 b2dd03c8-39d4-4d8f-98ff-823fe69b080e
2012-11-27 08:54:03 +00:00

262 lines
5.9 KiB
Ruby

##
# AnyMethod is the base class for objects representing methods
class RDoc::AnyMethod < RDoc::MethodAttr
##
# 2::
# RDoc 4
# Added calls_super
# Added parent name and class
# Added section title
MARSHAL_VERSION = 2 # :nodoc:
##
# Don't rename \#initialize to \::new
attr_accessor :dont_rename_initialize
##
# The C function that implements this method (if it was defined in a C file)
attr_accessor :c_function
##
# Different ways to call this method
attr_accessor :call_seq
##
# Parameters for this method
attr_accessor :params
##
# If true this method uses +super+ to call a superclass version
attr_accessor :calls_super
include RDoc::TokenStream
##
# Creates a new AnyMethod with a token stream +text+ and +name+
def initialize text, name
super
@c_function = nil
@dont_rename_initialize = false
@token_stream = nil
@calls_super = false
@superclass_method = nil
end
##
# Adds +an_alias+ as an alias for this method in +context+.
def add_alias an_alias, context = nil
method = self.class.new an_alias.text, an_alias.new_name
method.record_location an_alias.file
method.singleton = self.singleton
method.params = self.params
method.visibility = self.visibility
method.comment = an_alias.comment
method.is_alias_for = self
@aliases << method
context.add_method method if context
method
end
##
# Prefix for +aref+ is 'method'.
def aref_prefix
'method'
end
##
# The call_seq or the param_seq with method name, if there is no call_seq.
#
# Use this for displaying a method's argument lists.
def arglists
if @call_seq then
@call_seq
elsif @params then
"#{name}#{param_seq}"
end
end
##
# Dumps this AnyMethod for use by ri. See also #marshal_load
def marshal_dump
aliases = @aliases.map do |a|
[a.name, parse(a.comment)]
end
[ MARSHAL_VERSION,
@name,
full_name,
@singleton,
@visibility,
parse(@comment),
@call_seq,
@block_params,
aliases,
@params,
@file.relative_name,
@calls_super,
@parent.name,
@parent.class,
@section.title,
]
end
##
# Loads this AnyMethod from +array+. For a loaded AnyMethod the following
# methods will return cached values:
#
# * #full_name
# * #parent_name
def marshal_load array
@dont_rename_initialize = nil
@is_alias_for = nil
@token_stream = nil
@aliases = []
@parent = nil
@parent_name = nil
@parent_class = nil
@section = nil
@file = nil
version = array[0]
@name = array[1]
@full_name = array[2]
@singleton = array[3]
@visibility = array[4]
@comment = array[5]
@call_seq = array[6]
@block_params = array[7]
# 8 handled below
@params = array[9]
# 10 handled below
@calls_super = array[11]
@parent_name = array[12]
@parent_title = array[13]
@section_title = array[14]
array[8].each do |new_name, comment|
add_alias RDoc::Alias.new(nil, @name, new_name, comment, @singleton)
end
@parent_name ||= if @full_name =~ /#/ then
$`
else
name = @full_name.split('::')
name.pop
name.join '::'
end
@file = RDoc::TopLevel.new array[10] if version > 0
end
##
# Method name
#
# If the method has no assigned name, it extracts it from #call_seq.
def name
return @name if @name
@name = @call_seq[/^.*?\.(\w+)/, 1] || @call_seq if @call_seq
end
##
# A list of this method's method and yield parameters. +call-seq+ params
# are preferred over parsed method and block params.
def param_list
if @call_seq then
params = @call_seq.split("\n").last
params = params.sub(/.*?\((.*)\)/, '\1')
params = params.sub(/(\{|do)\s*\|([^|]*)\|.*/, ',\2')
elsif @params then
params = @params.sub(/\((.*)\)/, '\1')
params << ",#{@block_params}" if @block_params
elsif @block_params then
params = @block_params
else
return []
end
params = params.gsub(/\s+/, '').split ','
params.map { |param| param.sub(/=.*/, '') }
end
##
# Pretty parameter list for this method. If the method's parameters were
# given by +call-seq+ it is preferred over the parsed values.
def param_seq
if @call_seq then
params = @call_seq.split("\n").last
params = params.sub(/[^( ]+/, '')
params = params.sub(/(\|[^|]+\|)\s*\.\.\.\s*(end|\})/, '\1 \2')
elsif @params then
params = @params.gsub(/\s*\#.*/, '')
params = params.tr("\n", " ").squeeze(" ")
params = "(#{params})" unless params[0] == ?(
else
params = ''
end
if @block_params then
# If this method has explicit block parameters, remove any explicit
# &block
params.sub!(/,?\s*&\w+/, '')
block = @block_params.gsub(/\s*\#.*/, '')
block = block.tr("\n", " ").squeeze(" ")
if block[0] == ?(
block.sub!(/^\(/, '').sub!(/\)/, '')
end
params << " { |#{block}| ... }"
end
params
end
##
# Sets the store for this method and its referenced code objects.
def store= store
super
@file = @store.add_file @file.full_name if @file
end
##
# For methods that +super+, find the superclass method that would be called.
def superclass_method
return unless @calls_super
return @superclass_method if @superclass_method
parent.each_ancestor do |ancestor|
if method = ancestor.method_list.find { |m| m.name == @name } then
@superclass_method = method
break
end
end
@superclass_method
end
end