A Choice is a collection of data objects of which only one is active at any particular time. Method calls will be delegated to the active choice.
require 'bindata' type1 = [:string, {value: "Type1"}] type2 = [:string, {value: "Type2"}] choices = {5 => type1, 17 => type2} a = BinData::Choice.new(choices: choices, selection: 5) a # => "Type1" choices = [ type1, type2 ] a = BinData::Choice.new(choices: choices, selection: 1) a # => "Type2" choices = [ nil, nil, nil, type1, nil, type2 ] a = BinData::Choice.new(choices: choices, selection: 3) a # => "Type1" Chooser = Struct.new(:choice) mychoice = Chooser.new mychoice.choice = 'big' choices = {'big' => :uint16be, 'little' => :uint16le} a = BinData::Choice.new(choices: choices, copy_on_change: true, selection: -> { mychoice.choice }) a.assign(256) a.to_binary_s #=> "\001\000" mychoice.choice = 'little' a.to_binary_s #=> "\000\001"
Parameters may be provided at initialisation to control the behaviour of an object. These params are:
:choices
Either an array or a hash specifying the possible data objects. The format of the array/hash.values is a list of symbols representing the data object type. If a choice is to have params passed to it, then it should be provided as [type_symbol, hash_params]. An implementation constraint is that the hash may not contain symbols as keys, with the exception of :default. :default is to be used when then :selection does not exist in the :choices hash.
:selection
An index/key into the :choices array/hash which specifies the currently active choice.
:copy_on_change
If set to true, copy the value of the previous selection to the current selection whenever the selection changes. Default is false.
# File lib/bindata/trace.rb, line 78 def turn_off_tracing alias_method :do_read, :do_read_without_hook end
# File lib/bindata/trace.rb, line 73 def turn_on_tracing alias_method :do_read_without_hook, :do_read alias_method :do_read, :do_read_with_hook end
# File lib/bindata/trace.rb, line 83 def do_read_with_hook(io) trace_selection do_read_without_hook(io) end
# File lib/bindata/choice.rb, line 74 def initialize_instance @choices = {} @last_selection = nil end
Returns the current selection.
# File lib/bindata/choice.rb, line 80 def selection selection = eval_parameter(:selection) if selection.nil? raise IndexError, ":selection returned nil for #{debug_name}" end selection end
# File lib/bindata/trace.rb, line 88 def trace_selection BinData.trace_message do |tracer| selection_string = eval_parameter(:selection).inspect tracer.trace_obj("#{debug_name}-selection-", selection_string) end end
# File lib/bindata/choice.rb, line 107 def current_choice current_selection = selection @choices[current_selection] ||= instantiate_choice(current_selection) end
# File lib/bindata/choice.rb, line 112 def instantiate_choice(selection) prototype = get_parameter(:choices)[selection] if prototype.nil? raise IndexError, "selection '#{selection}' does not exist in :choices for #{debug_name}" end prototype.instantiate(nil, self) end