Sha256: f4c23b835392b726adf66e9a962e28eaedbd2e3e7ad4abbfff25303c9a7f6e56

Contents?: true

Size: 1.6 KB

Versions: 6

Compression:

Stored size: 1.6 KB

Contents

require 'xmp/silencer'
XMP::Silencer.silently { require 'nokogiri' }
require 'xmp/namespace'

# = XMP XML parser
#
# == Example
#   xmp = XMP.new(File.read('xmp.xml'))
#   xmp.dc.title           # => "Amazing Photo"
#   xmp.photoshop.Category # => "summer"
#   xmp.photoshop.SupplementalCategories # => ["morning", "sea"]
class XMP
  # underlying XML content
  attr_reader :xml
  # available namespace names
  attr_reader :namespaces

  # accepts valid XMP XML
  def initialize(xml)
    doc = Nokogiri::XML(xml)
    @xml = doc.root

    available_namespaces = doc.collect_namespaces
    # let nokogiri know about all namespaces
    available_namespaces.each do |ns, url|
      @xml.add_namespace_definition ns, url
    end

    # collect namespace names
    @namespaces = available_namespaces.collect do |ns, _|
      ns =~ /^xmlns:(.+)/
      $1
    end
  end

  def inspect
    "#<XMP:@namespaces=#{@namespaces.inspect}>"
  end

  # returns Namespace object if namespace exists, otherwise tries to call a method
  def method_missing(namespace, *args)
    if has_namespace?(namespace)
      Namespace.new(self, namespace)
    else
      super
    end
  end

  def respond_to?(method)
    has_namespace?(method) or super
  end

  def self.parse(doc)
    case doc.class.to_s
    when 'EXIFR::JPEG'
      if xmp_chunk = doc.app1s.find { |a| a =~ %r|\Ahttp://ns.adobe.com/xap/1.0/| }
        xmp_data = xmp_chunk.split("\000")[1]
        XMP.new(xmp_data)
      end
    else
      raise "Document not supported:\n#{doc.inspect}"
    end
  end

  private

  def has_namespace?(namespace)
    namespaces.include?(namespace.to_s)
  end
end

Version data entries

6 entries across 6 versions & 3 rubygems

Version Path
xmpfixed-0.2.3 lib/xmp.rb
xmp-fixed_prefix-0.2.2 lib/xmp.rb
xmp-fixed_prefix-0.2.1 lib/xmp.rb
xmp-0.2.0 lib/xmp.rb
xmp-0.1.1 lib/xmp.rb
xmp-0.1.0 lib/xmp.rb