lib/bindata/base.rb in bindata-1.1.0 vs lib/bindata/base.rb in bindata-1.2.0

- old
+ new

@@ -11,11 +11,11 @@ # This is the abstract base class for all data objects. # # == Parameters # # Parameters may be provided at initialisation to control the behaviour of - # an object. These params are: + # an object. These parameters are: # # [<tt>:check_offset</tt>] Raise an error if the current IO offset doesn't # meet this criteria. A boolean return indicates # success or failure. Any other return is compared # to the current offset. The variable +offset+ @@ -25,89 +25,66 @@ # [<tt>:adjust_offset</tt>] Ensures that the current IO offset is at this # position before reading. This is like # <tt>:check_offset</tt>, except that it will # adjust the IO offset instead of raising an error. class Base + include AcceptedParametersMixin + optional_parameters :check_offset, :adjust_offset + optional_parameter :onlyif # Used by Struct + mutually_exclusive_parameters :check_offset, :adjust_offset + class << self # Instantiates this class and reads from +io+, returning the newly # created data object. def read(io) data = self.new data.read(io) data end - def mandatory_parameters(*args) - accepted_parameters.mandatory(*args) + # Registers this class for use. + def register_self + register_class(self) end - def optional_parameters(*args) - accepted_parameters.optional(*args) - end - - def default_parameters(*args) - accepted_parameters.default(*args) - end - - def mutually_exclusive_parameters(*args) - accepted_parameters.mutually_exclusive(*args) - end - - alias_method :mandatory_parameter, :mandatory_parameters - alias_method :optional_parameter, :optional_parameters - alias_method :default_parameter, :default_parameters - - def accepted_parameters - unless defined? @accepted_parameters - ancestor = ancestors[1..-1].find { |cls| - cls.respond_to?(:accepted_parameters) - } - ancestor_params = ancestor.nil? ? nil : ancestor.accepted_parameters - @accepted_parameters = AcceptedParameters.new(ancestor_params) + # Registers all subclasses of this class for use + def register_subclasses + class << self + define_method(:inherited) do |subclass| + register_class(subclass) + end end - @accepted_parameters end - def sanitize_parameters!(params, sanitizer) #:nodoc: + def register_class(class_to_register) #:nodoc: + RegisteredClasses.register(class_to_register.name, class_to_register) end - #------------- - private - - def warn_replacement_parameter(params, bad_key, suggested_key) - if params.has_parameter?(bad_key) - warn ":#{bad_key} is not used with #{self}. " + - "You probably want to change this to :#{suggested_key}" - end - end - - def register(name, class_to_register) - RegisteredClasses.register(name, class_to_register) - end + private :register_self, :register_subclasses, :register_class end - optional_parameters :check_offset, :adjust_offset - mutually_exclusive_parameters :check_offset, :adjust_offset - # Creates a new data object. # - # +params+ is a hash containing symbol keys. Some params may - # reference callable objects (methods or procs). +parent+ is the - # parent data object (e.g. struct, array, choice) this object resides - # under. - def initialize(params = {}, parent = nil) - @params = Sanitizer.sanitize(params, self.class) + # +parameters+ is a hash containing symbol keys. Some parameters may + # reference callable objects (methods or procs). + # + # +parent+ is the parent data object (e.g. struct, array, choice) this + # object resides under. + def initialize(parameters = {}, parent = nil) + @params = Sanitizer.sanitize(parameters, self.class) @parent = parent end attr_reader :parent # Returns the result of evaluating the parameter identified by +key+. + # # +overrides+ is an optional +parameters+ like hash that allow the # parameters given at object construction to be overridden. + # # Returns nil if +key+ does not refer to any parameter. def eval_parameter(key, overrides = {}) LazyEvaluator.eval(self, get_parameter(key), overrides) end @@ -141,11 +118,11 @@ def done_read #:nodoc: _done_read end protected :do_read, :done_read - # Writes the value for this data to +io+. + # Writes the value for this data object to +io+. def write(io) io = BinData::IO.new(io) unless BinData::IO === io do_write(io) io.flush @@ -155,11 +132,11 @@ def do_write(io) #:nodoc: _do_write(io) end protected :do_write - # Returns the number of bytes it will take to write this data. + # Returns the number of bytes it will take to write this data object. def num_bytes do_num_bytes.ceil end def do_num_bytes #:nodoc: @@ -201,30 +178,30 @@ pp.pp(snapshot) end # Returns a user friendly name of this object for debugging purposes. def debug_name - if parent - parent.debug_name_of(self) + if @parent + @parent.debug_name_of(self) else "obj" end end # Returns the offset of this object wrt to its most distant ancestor. def offset - if parent - parent.offset + parent.offset_of(self) + if @parent + @parent.offset + @parent.offset_of(self) else 0 end end # Returns the offset of this object wrt to its parent. def rel_offset - if parent - parent.offset_of(self) + if @parent + @parent.offset_of(self) else 0 end end @@ -273,9 +250,14 @@ end end ########################################################################### # To be implemented by subclasses + + # Performs sanity checks on the given parameters. This method converts + # the parameters to the form expected by this data object. + def self.sanitize_parameters!(parameters, sanitizer) #:nodoc: + end # Resets the internal state to that of a newly created object. def clear raise NotImplementedError end