Exemple #1
0
def build_calibration_matrices(i, prev_sensor, K_matrices, filename1,
                               filename2):
    '''Extract exif metadata from image files, and use them to build the 2 calibration matrices.'''
    def get_sensor_sizes(i, prev_sensor, metadata1, metadata2):
        '''Looks up sensor width from the database based on the camera model.'''
        #focal length in pixels = (image width in pixels) * (focal length in mm) / (CCD width in mm)
        if i == 0:
            sensor_1 = cam_db.get_sensor_size(
                metadata1['Exif.Image.Model'].strip().upper())
            sensor_2 = cam_db.get_sensor_size(
                metadata2['Exif.Image.Model'].strip().upper())
        elif i >= 1:
            sensor_1 = prev_sensor
            sensor_2 = cam_db.get_sensor_size(metadata2['Exif.Image.Model'])

    metadata1 = GExiv2.Metadata(filename1)
    metadata2 = GExiv2.Metadata(filename2)

    # if False and metadata1.get_supports_exif() and metadata2.get_supports_exif():
    #         sensor_1, sensor_2 = get_sensor_sizes(i, prev_sensor, metadata1, metadata2)
    # else:
    #     if metadata1.get_supports_exif() == False:
    #             print "Exif data not available for ", filename1
    #     if metadata2.get_supports_exif() == False:
    #             print "Exif data not available for ", filename2
    #     sys.exit("Please try again.")

    # CDANCETTE : Fix sensor size at 30mm
    sensor_1, sensor_2 = 6.35, 6.35
    focal = 50  #3.8 # 50mm
    # CDANCETTE

    # Calibration matrix for camera 1 (K1)
    # f1_mm = metadata1.get_focal_length()
    f1_mm = focal
    w1 = metadata1.get_pixel_width()
    h1 = metadata1.get_pixel_height()
    f1_px = (w1 * f1_mm) / sensor_1
    K1 = np.array([[f1_px, 0, w1 / 2], [0, f1_px, h1 / 2], [0, 0, 1]])

    # Calibration matrix for camera 2 (K2)
    # f2_mm = metadata2.get_focal_length()
    f2_mm = focal
    w2 = metadata2.get_pixel_width()
    h2 = metadata2.get_pixel_height()
    f2_px = (w2 * f2_mm) / sensor_2
    K2 = np.array([[f2_px, 0, w2 / 2], [0, f2_px, h2 / 2], [0, 0, 1]])

    if i == 0:
        K_matrices.append(K1)
        K_matrices.append(K2)
    elif i >= 1:
        K_matrices.append(K2)

    return sensor_2, K_matrices
Exemple #2
0
    def resize(self, src, dst):
        src_meta = GExiv2.Metadata(src)
        src_p = QPixmap(src)
        dst_p = src_p.scaled(4500, 3000, Qt.KeepAspectRatio,
                             Qt.SmoothTransformation)

        dst_p.save(src)
        shutil.move(src, dst)

        # copy all the metadata
        dst_meta = GExiv2.Metadata(dst)
        for tag in src_meta.get_tags():
            dst_meta[tag] = src_meta[tag]
        dst_meta.save_file()
Exemple #3
0
def get_metadata(path):
    """
    get a gexiv2 metadata object or None for path
    :param path: path to an image that is supported by gexiv2
    :returns :py:class:`GExiv2.Metadata` or None
    """
    GExiv2.initialize()
    metadata = GExiv2.Metadata.new()
    try:
        metadata.open_path(path)
    except GLib.Error as e:
        print('{}: can not get metadata obj: {}'.format(path, e))
        return None
    else:
        return metadata
Exemple #4
0
 def comparePicturesByExifDate(self, curOrigFullFileName):
     try:
         src_exif = GExiv2.Metadata(self.absCopiesOrigDateiName)
         src_ExifDate = src_exif.get_date_time().strftime('%Y%m%d%H%M%S')
         #logging.DEBUG("src-exifTimeStamp for " + self.fileBaseName + " is " + src_ExifDate)
         tgt_exif = GExiv2.Metadata(curOrigFullFileName)
         tgt_ExifDate = tgt_exif.get_date_time().strftime('%Y%m%d%H%M%S')
         #logging.DEBUG("tgt-exifTimeStamp for " + os.path.basename(curOrigFullFileName) + " is " +tgt_ExifDate) )
         if src_ExifDate == tgt_ExifDate:
             return True
         else:
             return False
     except:
         logging.debug("Image does not have exiv date time")
         return False
Exemple #5
0
 def merge_sc(self, other):
     # merge sidecar data into image file data, ignoring thumbnails
     raw_sc = GExiv2.Metadata()
     raw_sc.open_path(other._path)
     # allow exiv2 to infer Exif tags from XMP
     for tag in raw_sc.get_exif_tags():
         if tag.startswith('Exif.Thumbnail'):
             continue
         # ignore inferred datetime values the exiv2 gets wrong
         # (I think it's adding the local timezone offset)
         if tag in ('Exif.Image.DateTime', 'Exif.Photo.DateTimeOriginal',
                    'Exif.Photo.DateTimeDigitized'):
             self.clear_tag(tag)
         else:
             value = raw_sc.get_tag_string(tag)
             if value:
                 self.set_tag_string(tag, value)
     # copy all XMP tags except inferred Exif tags
     for tag in raw_sc.get_xmp_tags():
         if tag.startswith('Xmp.xmp.Thumbnails'):
             continue
         ns = tag.split('.')[1]
         if ns in ('exif', 'exifEX', 'tiff', 'aux'):
             # exiv2 will already have supplied the equivalent Exif tag
             pass
         elif self.get_tag_type(tag) == 'XmpText':
             value = raw_sc.get_tag_string(tag)
             if value:
                 self.set_tag_string(tag, value)
         else:
             value = raw_sc.get_tag_multiple(tag)
             if value:
                 self.set_tag_multiple(tag, value)
def UpdateFileMetadata(filename, datetime):
    exif = GExiv2.Metadata(filename)
    if exif is not None:
        fileDate = GetDateFromExif(exif)
        if fileDate is not None:
            fileDate = datetime.strptime(fileDate, DATE_FORMAT)
            # date within acceptable limit. don't update
            if abs((fileDate - datetime).days) <= FILE_METADATA_DATE_TOLERANCE:
                return

    log('Updating exif: %s to date: %s', \
        filename, datetime.strftime(DATE_FORMAT))

    if DRY_RUN == False:
        if exif is not None:
            exif['Exif.Photo.DateTimeOriginal'] = datetime.strftime(
                DATE_FORMAT)
            exif['Exif.Photo.DateTimeDigitized'] = datetime.strftime(
                DATE_FORMAT)
            exif['Exif.Image.DateTime'] = datetime.strftime(DATE_FORMAT)
            exif['Exif.Image.DateTimeOriginal'] = datetime.strftime(
                DATE_FORMAT)
            exif.save_file()

        xmpfile = XMPFiles(file_path=filename, open_forupdate=True)
        xmp = xmpfile.get_xmp()
        if xmp is not None:
            for xmpConst in XMP_CONSTANTS:
                for dateConst in DATE_CONSTANTS:
                    if xmp.does_property_exist(xmpConst, dateConst):
                        xmp.set_property( \
                            xmpConst, dateConst, datetime.strftime(DATE_FORMAT_XMP))
            if (xmpfile.can_put_xmp(xmp)):
                xmpfile.put_xmp(xmp)
                xmpfile.close_file()
Exemple #7
0
def remove_rotation(image_path):
    '''
    Fix a picture taken from an Apple device

    :param image: Image path
    '''

    # Get Metadata
    exif = GExiv2.Metadata(image_path)

    # Get current orientation
    orientation = exif.get_orientation()
    degrees = None
    if orientation == GExiv2.Orientation.ROT_90:
        degrees = 90
    elif orientation == GExiv2.Orientation.ROT_180:
        degrees = 180
    elif orientation == GExiv2.Orientation.ROT_270:
        degrees = 270

    if degrees is not None:
        # Remove orientation tag
        exif.set_orientation(GExiv2.Orientation.NORMAL)
        exif.save_file()

        # Rotate image
        image = Image.open(image_path)
        rotated_image = image.rotate(360 - degrees)
        rotated_image.save()
Exemple #8
0
    def resize_image_to_1024(parent_file_path, file_path):
        """Resizes the image to 1024 if it is larger in width.

        Parameters
        ==========
        parent_file_path : string
            The path to the original image file with all the metadata.
        file_path : string
            The path to the temporary image file that should be resized.

        Notes
        =====
        Do this before rotating the image because it is only based on width.

        """
        img = Image.open(file_path)
        width, height = img.size
        aspect_ratio = float(width) / float(height)
        max_width = 1024
        if width > max_width:

            reduced_size = max_width, int(max_width / aspect_ratio)
            img.thumbnail(reduced_size, Image.ANTIALIAS)
            img.save(file_path, img.format)

            # Copy all metadata from parent file to the resized file
            os.system('jhead -q -te {} {}'.format(parent_file_path, file_path))

            metadata = GExiv2.Metadata(file_path)
            if (metadata.get_pixel_width() != reduced_size[0]
                    or metadata.get_pixel_height() != reduced_size[1]):

                metadata.set_pixel_width(reduced_size[0])
                metadata.set_pixel_height(reduced_size[1])
                metadata.save_file()
    def add_meta_data(self, img_path, comment="", rotation="landscape"):
        # Comment tags used by various programs: http://redmine.yorba.org/projects/shotwell/wiki/PhotoTags
        # All the supported tags: http://www.exiv2.org/metadata.html
        metadata = GExiv2.Metadata(img_path)

        metadata['Iptc.Application2.DateCreated'] = self.developed.date(
        ).strftime('%Y-%m-%d')
        metadata[
            'Iptc.Application2.DigitizationDate'] = self.last_digitized.date(
            ).strftime('%Y-%m-%d')
        metadata[
            'Iptc.Application2.DigitizationTime'] = self.last_digitized.time(
            ).strftime('%H:%M:%S%z')
        metadata['Exif.Photo.DateTimeOriginal'] = self.developed.date(
        ).strftime('%Y-%m-%d')
        metadata[
            'Exif.Photo.DateTimeDigitized'] = self.last_digitized.strftime(
                '%Y-%m-%d %H:%M:%S')

        metadata['Iptc.Application2.Caption'] = comment
        metadata['Exif.Image.ImageDescription'] = comment

        # We already rotated correctly, so specify that there are no further
        # rotations.
        #See: http://sylvana.net/jpegcrop/exif_orientation.html
        metadata['Exif.Image.Orientation'] = '1'

        metadata.save_file()
Exemple #10
0
    def write_metadata(self, filepath, info):

        metadata = GExiv2.Metadata()
        metadata.open_path(filepath)

        compressor_name = "compressor v[{}]".format(info["version"])

        # Exif.Image.ProcessingSoftware is overwritten by Lightroom when the final export is done
        key = "Exif.Image.ProcessingSoftware";  metadata.set_tag_string(key, compressor_name)
        key = "Exif.Image.Software";            metadata.set_tag_string(key, compressor_name)

        try:
            key = "Exif.Image.ExposureTime";    metadata.set_exif_tag_rational(key, info["exposure_time"], 1)
        except Exception as e:
            key = "Exif.Image.ExposureTime";    metadata.set_exif_tag_rational(key, info["exposure_time"])
        key = "Exif.Image.ImageNumber";         metadata.set_tag_long(key, info["exposure_count"])
        key = "Exif.Image.DateTimeOriginal";    metadata.set_tag_string(key, info["capture_date"].strftime(self.EXIF_DATE_FORMAT))
        key = "Exif.Image.DateTime";            metadata.set_tag_string(key, info["compressing_date"].strftime(self.EXIF_DATE_FORMAT))

        if info["focal_length"] is not None:
            try:
                key = "Exif.Image.FocalLength"; metadata.set_exif_tag_rational(key, info["focal_length"])
            except Exception as e:
                key = "Exif.Image.FocalLength"; metadata.set_exif_tag_rational(key, info["focal_length"], 1)
        # TODO GPS Location

        metadata.save_file(filepath)
        self.log.debug("metadata written to {}".format(filepath))
Exemple #11
0
    def get_data(self, filename):
        tag_camera = ""
        tag_focal = ""
        tag_city = ""
        tag_country = ""

        # get EXIF metadata
        self.tags = GExiv2.Metadata(filename)

        # read tags from metadata
        if 'Exif.Image.Model' in self.tags:
            tag_camera = self.tags['Exif.Image.Model']
        if 'Exif.Photo.FocalLengthIn35mmFilm' in self.tags:
            tag_focal = self.tags['Exif.Photo.FocalLengthIn35mmFilm']
        if 'Xmp.photoshop.City' in self.tags:
            tag_city = self.tags['Xmp.photoshop.City']
        if 'Xmp.photoshop.Country' in self.tags:
            tag_country = self.tags['Xmp.photoshop.Country']

        # check if GPS info available
        posGPS = self.tags.get_gps_info()
        if posGPS[0] <> 0 or posGPS[1] <> 0: tag_gps = "yes"
        else: tag_gps = "no"

        return tag_camera, tag_focal, tag_gps, tag_city, tag_country
Exemple #12
0
def read_photo_metadata(filepath):
    '''Parses image metadata using GExiv2.'''
    metadata = GExiv2.Metadata(filepath)
    if not metadata.get_tags():
        return None
    else:
        return metadata
Exemple #13
0
def save_pixbuf(pixbuf, filename, update_orientation_tag=False):
    """Save the image with all the exif keys that exist if we have exif support.

    NOTE: This is used to override edited images, not to save images to new
        paths. The filename must exist as it is used to retrieve the image
        format and exif data.

    Args:
        pixbuf: GdkPixbuf.Pixbuf image to act on.
        filename: Name of the image to save.
        update_orientation_tag: If True, set orientation tag to NORMAL.
    """
    if not os.path.isfile(filename):
        raise FileNotFoundError(
            "Original file to retrieve data from not found")
    # Get needed information
    info = GdkPixbuf.Pixbuf.get_file_info(filename)[0]
    extension = info.get_extensions()[0]
    if _has_exif:
        exif = GExiv2.Metadata(filename)
    # Save
    pixbuf.savev(filename, extension, [], [])
    if _has_exif and exif.get_supports_exif():
        if update_orientation_tag:
            exif.set_orientation(GExiv2.Orientation.NORMAL)
        exif.save_file()
Exemple #14
0
def fetch_thumbnail(filename, size=Gst.get_int('thumbnail-size'), orient=1):
    """Load a photo's thumbnail from disk

    >>> fetch_thumbnail('gg/widgets.py')
    Traceback (most recent call last):
    OSError: gg/widgets.py: No thumbnail found.
    >>> type(fetch_thumbnail('demo/IMG_2411.JPG'))
    <class 'gi.repository.GdkPixbuf.Pixbuf'>
    """
    try:
        exif = GExiv2.Metadata(filename)
    except GObject.GError:
        raise OSError('{}: No thumbnail found.'.format(filename))

    with ignored(KeyError, ValueError):
        orient = int(exif['Exif.Image.Orientation'])

    try:
        thumb = GdkPixbuf.Pixbuf.new_from_file_at_size(filename, size, size)
    except GObject.GError:
        try:
            preview = exif.get_preview_properties()
            data = exif.get_preview_image(preview[0]).get_data()
        except (IndexError, GObject.GError):
            raise OSError('{}: No thumbnail found.'.format(filename))

        return GdkPixbuf.Pixbuf.new_from_stream_at_scale(
            Gio.MemoryInputStream.new_from_data(data, None), size, size, True,
            None)

    return ROTATIONS.get(orient, lambda x: x)(thumb)
Exemple #15
0
    def run(self, task):
        # Save task id for logging.
        self.task_id = task.id

        # Read metadata from a temp file.
        try:
            self.metadata = GExiv2.Metadata()
            self.metadata.open_buf(bytes(task.get_file_data))
        except Exception as e:
            logger.warning(
                "[Task {0}]: Unable to read image metadata: {1}".format(
                    task.id, e))
            self.metadata = None

        # Run all analysis.
        if self.metadata:
            self._get_comment()
            self._get_dimensions()
            self._get_exif()
            self._get_iptc()
            self._get_xmp()
            self._get_previews()
            self._get_gps_data()

        return self.results
Exemple #16
0
    def read(self):
        if self.pixmap is None:
            self.pixmap = QPixmap(self.path)
            self.metadata = GExiv2.Metadata(self.path)

            # the view will need three parameters:
            # rotation
            # size
            # zoom
            # the first is needed to properly orient the view over the scene
            # the other two are needed for zoom, mostly
            # but the rotation defines the images size, so they're linked
            self.size = self.pixmap.size()

            try:
                # try directly to get the tag, because sometimes get_tags() returns
                # tags that don't actually are in the file

                # this implicitly loads the metadata
                rot = self.metadata['Exif.Image.Orientation']
            except KeyError:
                # guess :-/
                logger.info("rotation 'guessed'")
                rot = '1'

            self.rotation = self.rotation_to_degrees[rot]
            if self.rotation in (90, 270):
                self.size = QSize(self.size.height(), self.size.width())

            self.zoom
Exemple #17
0
    def __init__(self, file_path):
        try:
            self.metadata = GExiv2.Metadata(file_path)
        except Exception as e:
            logger.warning("Unable to read image metadata: {0}".format(e))
            self.metadata = None

        self.results = AutoVivification()
Exemple #18
0
def gexiv2_version() -> str:
    """
    :return: version number of GExiv2
    """
    # GExiv2.get_version() returns an integer XXYYZZ, where XX is the
    # major version, YY is the minor version, and ZZ is the micro version
    v = "{0:06d}".format(GExiv2.get_version())
    return "{}.{}.{}".format(v[0:2], v[2:4], v[4:6]).replace("00", "0")
    def update_images_info(self, folder, output_folder):
        """
        1) Retrieves all the images available in the input folder
        2) For each image, retrieves the timestamp
        3) From the list of available locations, searches for the closest location in time.
        4) EXIF is modified and image is stored in the output folder.

        :param folder: Name of the input folder
        :param output_folder: Name of the output folder.
        :return: None
        """
        extensions = ["jpg"]

        if not os.path.exists(output_folder):
            mkpath(output_folder)

        files = []
        for extension in extensions:
            files += glob.glob('%s/*.%s' % (folder, extension.lower()))
            files += glob.glob('%s/*.%s' % (folder, extension.upper()))

        timestamps = sorted(self.locations.keys())

        take_closest = lambda num, collection: min(collection,
                                                   key=lambda x: abs(x - num))

        # http://coreygoldberg.blogspot.com.es/2014/01/python-fixing-my-photo-library-dates.html
        # https://git.gnome.org/browse/gexiv2/tree/GExiv2.py
        for filename in files:
            output_file = os.path.join(output_folder,
                                       os.path.basename(filename))
            print filename, "-->", output_file

            copyfile(filename, output_file)

            exif = GExiv2.Metadata(filename)

            curr_timestamp = datetime.strptime(exif['Exif.Image.DateTime'],
                                               "%Y:%m:%d %H:%M:%S")
            curr_timestamp = (curr_timestamp -
                              datetime(1970, 1, 1)).total_seconds()

            closest_timestamp = take_closest(curr_timestamp, timestamps)

            gps_coords = self.locations[closest_timestamp]

            exif.set_gps_info(gps_coords[1], gps_coords[0], 0.0)
            if gps_coords[0] >= 0.0:
                exif.set_tag_string("Exif.GPSInfo.GPSLatitudeRef", "N")
            else:
                exif.set_tag_string("Exif.GPSInfo.GPSLatitudeRef", "S")

            if gps_coords[1] >= 0.0:
                exif.set_tag_string("Exif.GPSInfo.GPSLongitudeRef", "E")
            else:
                exif.set_tag_string("Exif.GPSInfo.GPSLongitudeRef", "W")

            exif.save_file(output_file)
Exemple #20
0
def main(camera, date, film, iso, files):
    """Tag scanned images with film-specific EXIF metadata."""

    if date:
        exif_datetime = date.strftime('%Y:%m:%d %H:%M:%S')
        click.echo('Set dates to:  {}'.format(date))
    if camera:
        click.echo('Set camera to: {}'.format(camera))
    if film:
        click.echo('Set film to:   {}'.format(film))
    if iso:
        click.echo('Set ISO to:    {}'.format(iso))

    click.confirm('Does this look OK?', abort=True)

    workqueue = []
    for f in files:
        p = Path(f)
        if p.exists() and p.is_dir():
            workqueue.extend([x for x in p.glob("*.[jJ][pP][gG]")])
        elif p.exists() and p.is_file():
            workqueue.append(p)

    with click.progressbar(workqueue, label='Tagging images...',
                           show_pos=True) as bar:
        for image in bar:
            # Write new metadata to image.
            m = GExiv2.Metadata()
            m.register_xmp_namespace("http://analogexif.sourceforge.net/ns",
                                     "AnalogExif")
            m.open_path(str(image))
            if date:
                m.set_tag_string('Exif.Image.DateTime', exif_datetime)
                m.set_tag_string('Exif.Photo.DateTimeOriginal', exif_datetime)
                m.set_tag_string('Exif.Photo.DateTimeDigitized', exif_datetime)
            if camera:
                if not camera in m.get_tag_multiple('Xmp.dc.subject'):
                    m.set_tag_string('Xmp.dc.subject',
                                     camera)  # set a keyword!
                for k, v in cameras[camera].items():
                    if isinstance(v, int):
                        m.set_tag_long(k, v)
                    else:
                        m.set_tag_string(k, v)
            if film:
                if not film in m.get_tag_multiple('Xmp.dc.subject'):
                    m.set_tag_string('Xmp.dc.subject', film)  # set a keyword!
                m.set_tag_string('Xmp.AnalogExif.Film', film)
                for k, v in films[film].items():
                    if isinstance(v, int):
                        m.set_tag_long(k, v)
                    else:
                        m.set_tag_string(k, v)
            if iso:
                m.set_tag_long("Exif.Photo.ISOSpeedRatings", iso)
            m.save_file(str(image))
    click.echo("Done.")
    def test_rotate_image(self):

        tmp_image_path = 'tmp_rotation_test_image.jpg'
        shutil.copyfile('rotation_test_image.jpg', tmp_image_path)

        metadata_before = GExiv2.Metadata(tmp_image_path)

        self.uploader.rotate_image(tmp_image_path)

        metadata_after = GExiv2.Metadata(tmp_image_path)

        assert metadata_after['Exif.Image.Orientation'] == '1'
        assert metadata_after.get_pixel_height() == \
            metadata_before.get_pixel_width()
        assert metadata_after.get_pixel_width() == \
            metadata_before.get_pixel_height()

        os.remove('tmp_rotation_test_image.jpg')
Exemple #22
0
 def do_activate(self):
     if not self.window:
         self.window = psp_mw.MainWindow(self)
         GExiv2.initialize()
     self.window.present()
Exemple #23
0
    except ValueError:
        pass
from gi.repository import GObject, GExiv2
import six

from photini import __version__

logger = logging.getLogger(__name__)

gexiv2_version = '{} {}, GExiv2 {}, GObject {}'.format(
    ('PyGI', 'pgi')[using_pgi], gi.__version__,
    GExiv2._version, GObject._version)

# pydoc gi.repository.GExiv2.Metadata is useful to see methods available

GExiv2.log_set_level(GExiv2.LogLevel.MUTE)

def safe_fraction(value):
    # Avoid ZeroDivisionError when '0/0' used for zero values in Exif
    if isinstance(value, six.string_types):
        numerator, sep, denominator = value.partition('/')
        if denominator and int(denominator) == 0:
            return Fraction(0.0)
    return Fraction(value).limit_denominator(1000000)


class MetadataValue(object):
    # base for classes that store a metadata value, e.g. a string, int
    # or float
    def __init__(self, value):
        assert(value is not None)
Exemple #24
0
# didjvu is distributed in the hope that it will be useful, but WITHOUT
# ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
# FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
# for more details.

'''XMP support (GExiv2 backend)'''

import re

import gi
try:
    gi.require_version('GExiv2', '0.10')
except ValueError as exc:  # no coverage
    raise ImportError(exc)
from gi.repository import GExiv2
if GExiv2.get_version() < 1003:
    raise ImportError('GExiv2 >= 0.10.3 is required')  # no coverage

from .. import temporary
from .. import timestamp

from . import namespaces as ns

GExiv2.Metadata.register_xmp_namespace(ns.didjvu, 'didjvu')

class XmpError(RuntimeError):
    pass

class MetadataBase(object):

    _empty_xmp = (
Exemple #25
0
##  modify it under the terms of the GNU General Public License as
##  published by the Free Software Foundation, either version 3 of the
##  License, or (at your option) any later version.
##
##  This program is distributed in the hope that it will be useful,
##  but WITHOUT ANY WARRANTY; without even the implied warranty of
##  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
##  General Public License for more details.
##
##  You should have received a copy of the GNU General Public License
##  along with this program.  If not, see
##  <http://www.gnu.org/licenses/>.

from gi.repository import GObject, GExiv2

GExiv2.initialize()

class MetadataHandler(object):
    def __init__(self, path):
        self._path = path
        self._md = GExiv2.Metadata()
        self._md.open_path(path)

    def save(self):
        try:
            return self._md.save_file(self._path)
        except GObject.GError as ex:
            print str(ex)
            return False

    def copy(self, other, exif=True, iptc=True, xmp=True, comment=True):