class HexaPDF::Stream
Forward declaration of Stream to circumvent circular require problem
:nodoc:
def after_data_change
def after_data_change super data.stream ||= ''.b unless data.stream.kind_of?(StreamData) || data.stream.kind_of?(String) raise ArgumentError, "Object of class #{data.stream.class} cannot be used as stream value" end end
def filter_for_name(filter_name)
Returns the filter object that corresponds to the given filter name.
def filter_for_name(filter_name) config.constantize('filter.map', filter_name) do raise HexaPDF::Error, "Unknown stream filter '#{filter_name}' encountered" end end
def must_be_indirect?
def must_be_indirect? true end
def perform_validation
def perform_validation super if value[:Filter].kind_of?(Symbol) && FILTER_MAP.key?(value[:Filter]) yield("A stream's /Filter entry may only use long-form filter names", true) value[:Filter] = FILTER_MAP[value[:Filter]] elsif value[:Filter].kind_of?(Array) value[:Filter].map! do |filter| next filter unless FILTER_MAP.key?(filter) yield("A stream's /Filter entry may only use long-form filter names", true) FILTER_MAP[filter] end end end
def raw_stream
The returned value can be of many different types (see #stream=). For working with the
Returns the raw stream object.
def raw_stream data.stream end
def set_filter(filter, decode_parms = nil)
be [:A85, :Fl], the stream would first be encoded with the Flate and then with the ASCII85
The filters have to be specified in the *decoding order*! For example, if the filters would
The arguments +filter+ as well as +decode_parms+ can either be a single items or arrays.
Sets the filters that should be used for encoding the stream.
def set_filter(filter, decode_parms = nil) if filter.nil? || (filter.kind_of?(Array) && filter.empty?) delete(:Filter) else self[:Filter] = filter end if decode_parms.nil? || (decode_parms.kind_of?(Array) && decode_parms.empty?) || !key?(:Filter) delete(:DecodeParms) else self[:DecodeParms] = decode_parms end end
def stream
Note that modifications done to the returned string are not reflected in the Stream object
Returns the (possibly decoded) stream data as string.
def stream if data.stream.kind_of?(String) data.stream.dup else HexaPDF::Filter.string_from_source(stream_decoder) end end
def stream=(stream)
The +stream+ argument can be a HexaPDF::StreamData object, a String object or +nil+.
Assigns a new stream data object.
def stream=(stream) data.stream = stream after_data_change end
def stream_decoder
Returns the decoder Fiber for the stream data.
def stream_decoder source = stream_source if data.stream.kind_of?(StreamData) data.stream.filter.zip(data.stream.decode_parms) do |filter, decode_parms| source = filter_for_name(filter).decoder(source, decode_parms) end end source end
def stream_encoder(source = stream_source)
Returns the encoder Fiber for the stream data.
stream.stream_encoder
:call-seq:
def stream_encoder(source = stream_source) encoder_data = [document.unwrap(self[:Filter])].flatten. zip([document.unwrap(self[:DecodeParms])].flatten). delete_if {|f, _| f.nil? } if data.stream.kind_of?(StreamData) decoder_data = data.stream.filter.zip(data.stream.decode_parms) while !decoder_data.empty? && !encoder_data.empty? && decoder_data.last == encoder_data.last decoder_data.pop encoder_data.pop end decoder_data.each do |filter, decode_parms| source = filter_for_name(filter).decoder(source, decode_parms) end end encoder_data.reverse!.each do |filter, decode_parms| source = filter_for_name(filter).encoder(source, decode_parms) end source end
def stream_source
def stream_source if data.stream.kind_of?(String) HexaPDF::Filter.source_from_string(data.stream) else data.stream.fiber(config['io.chunk_size']) end end