class Origami::FDF
Class representing an AcroForm Forms Data Format file.
def self.read(path, options = {})
def self.read(path, options = {}) path = File.expand_path(path) if path.is_a?(::String) FDF::Parser.new(options).parse(path) end
def <<(object)
def <<(object) object.set_indirect(true) object.set_document(self) if object.no.zero? maxno = 1 maxno = maxno.succ while get_object(maxno) object.generation = 0 object.no = maxno end @revisions.first.body[object.reference] = object object.reference end
def Catalog
def Catalog get_object(@revisions.first.trailer.Root) end
def cast_object(reference, type) #:nodoc:
def cast_object(reference, type) #:nodoc: @revisions.each do |rev| if rev.body.include?(reference) and type < rev.body[reference].class rev.body[reference] = rev.body[reference].cast_to(type, @parser) rev.body[reference] else nil end end end
def get_object(no, generation = 0) #:nodoc:
def get_object(no, generation = 0) #:nodoc: case no when Reference target = no when ::Integer target = Reference.new(no, generation) when Origami::Object return no end @revisions.first.body[target] end
def get_object_offset(no,generation) #:nodoc:
def get_object_offset(no,generation) #:nodoc: bodyoffset = @header.to_s.size objectoffset = bodyoffset @revisions.first.body.values.each { |object| if object.no == no and object.generation == generation then return objectoffset else objectoffset += object.to_s.size end } nil end
def indirect_objects
def indirect_objects @revisions.inject([]) do |set, rev| set.concat(rev.objects) end end
def init
def init catalog = Catalog.new(:FDF => FDF::Dictionary.new) @revisions.first.trailer.Root = self.insert(catalog) end
def initialize(parser = nil) #:nodoc:
def initialize(parser = nil) #:nodoc: @header = FDF::Header.new @revisions = [ Revision.new(self) ] @revisions.first.trailer = Trailer.new @parser = parser init if parser.nil? end
def save(path)
def save(path) bin = ::String.new.b bin << @header.to_s lastno, brange = 0, 0 xrefs = [ XRef.new(0, XRef::FIRSTFREE, XRef::FREE) ] xrefsection = XRef::Section.new @revisions.first.body.values.sort.each { |obj| if (obj.no - lastno).abs > 1 xrefsection << XRef::Subsection.new(brange, xrefs) brange = obj.no xrefs.clear end xrefs << XRef.new(bin.size, obj.generation, XRef::USED) lastno = obj.no obj.pre_build bin << obj.to_s obj.post_build } xrefsection << XRef::Subsection.new(brange, xrefs) @xreftable = xrefsection @trailer ||= Trailer.new @trailer.Size = @revisions.first.body.size + 1 @trailer.startxref = bin.size bin << @xreftable.to_s bin << @trailer.to_s if path.respond_to?(:write) io = path else path = File.expand_path(path) io = File.open(path, "wb", encoding: 'binary') close = true end begin io.write(bin) ensure io.close if close end self end