Як перейменувати кілька фотографій та відеозаписів на основі даних EXIF?


11

Я часто імпортую фотографії та відео (в основному з розширеннями JPG та MOV) з цифрових фотоапаратів та планшетів на свій ПК, і в ідеалі я б хотів, щоб вони були відсортовані за датами та часом, коли вони були прийняті у своїх даних EXIF. Отже, я бажаю перейменувати їх, бажано, використовуючи простий скрипт Nautilus , бажано вставляючи позначки дати та часу перед кожним іменем файлу.

Поки що мені вдалося зібрати лише наступний сценарій Наутілуса, який, на мою думку, далеко не ідеальний:

for i in *.*
do
mv -i "$i" "$(exiftool -CreateDate "$i" | awk -F ': ' '{print $2}')_"$i"" 
done

Що мені не подобається в цьому методі перейменування - це колонки, що використовуються в марках EXIF ​​дати та часу (наприклад, "2013: 09: 03 20: 55: 09_IMG_0108.JPG"), які можуть створювати проблеми при перенесенні цих файлів пізніше в інші середовища ( наприклад Windows).

Ця команда (використовуючи exiv2 замість exiftool ) зручно дозволяє маніпулювати марками дати та часу, але її недолік полягає в тому, що вона не працює на відео (наприклад, MOV) файли :

exiv2 -k -r '%Y-%m-%d_%H-%M-%S_:basename:' rename "$i"

Тож я сподіваюся, що хтось може придумати краще рішення. І було б магічно, якби навіть вдалося перетворити оригінальні назви файлів і розширень у малі!


Окрім чудових відповідей нижче, слід також перевірити pyRenamer . Я не маю досвіду його використання з відеофайлами (чи мають вони дані EXIF?), Але можу сказати, що він відмінний для фотографій. Він також може змінювати розширення файлів на малі регістри.
Том Броссман

Відповіді:


6

Що мені не подобається в цьому методі перейменування - це колонки, що використовуються в марках EXIF ​​дати та часу (наприклад, "2013: 09: 03 20: 55: 09_IMG_0108.JPG"), які можуть створювати проблеми при перенесенні цих файлів пізніше в інші середовища ( наприклад Windows).

Ви можете запустити схему іменування наскрізь sed, замінивши двокрапки та пробіли на підкреслення, наприклад:

mv -i "$i" "$(exiftool -CreateDate "$i" | awk -F ': ' '{print $2}' | sed -e 's/:/-/g' -e 's/ /_/g')_$i"

Що стосується того, щоб зробити всю річ маленькою, ви можете використовувати rename:

rename 's/(.*)/\L$1/' file.JPG
##  or
rename 's/(.*)/\L$1/' *.*

Або ви могли це зробити у своєму сценарії, використовуючи sed, як у:

j=$(echo "$i" | sed -e 's/\(.*\)/\L\1/')

... і потім використовувати $jзмінну замість фіналі $iвашої mvлінії. Цей спосіб sed є трохи більш портативним (якщо це важливо для вас), оскільки різні дистрибутиви Linux мають різні команди перейменування, тоді як sed є універсальним.

Або, альтернативно, скрипт можна змінити наступним чином, щоб виконати перетворення назви файлів у малі регістри на початку, використовуючи trзамість цього:

for arg 
do
  tmp="$(echo "$arg" | tr '[A-Z]' '[a-z]')"
  mv -i "$arg" "$(exiftool -CreateDate "$arg" | awk -F ': ' '{print $2}' | sed -e 's/:/-/g' -e 's/ /_/g')_$tmp"
done

Для виконання дещо різних команд для різних типів файлів у цьому сценарії може використовуватися оператор bash. Наприклад:

#! /usr/bin/env bash
for filename in ./*
do
  tmp="$(echo "$filename" | tr '[A-Z]' '[a-z]')"
  case "$filename" in
    *.MOV|*.mov) 
      mv -i "$filename" "$(exiftool -a -s -CreateDate-tur "$filename" | awk -F ': ' '{print $2}' | sed -e 's/\-[0-9][0-9]\:00//g' -e 's/\+[0-9][0-9]\:00//g' -e 's/:/-/g' -e 's/ /_/g')_$tmp"
      ;;
    *.JPG|*.jpg)
      mv -i "$filename" "$(exiftool -a -s -CreateDate "$filename" | awk -F ': ' '{print $2}' | sed -e 's/:/-/g' -e 's/ /_/g')_"$tmp""
      ;;
    *)
      echo 'Not a *.jpg or a *.mov!'
      ;;
  esac
done

У цьому прикладі перейменування файлів MOV, у яких є часові позначки CreateDate, БУДЬ-ЯКІЙ РОКУ ПІСЛЯ АБО ПЕРЕД ПІД JPG-файли коригується за допомогою іншого (-tur) EXIF-даних та видалення цього суфікса різниці в часі, і можливо, буде потрібно змінити -tur частину відповідно до місця розташування, встановленого в системі.


На жаль , я не міг зрозуміти, як перетворити імена файлів в нижній регістр , як ви пропонуєте (вставивши цей рядок вище і зміни останнього , $iщоб $jнічого не робити). Натомість я на початку вставив перетворення іменних файлів у малі регістри і сміливо додав це як інший варіант (який працював принаймні для мене) до кінця вашої відповіді, щоб я міг прийняти вашу відповідь. Звичайно, ви можете редагувати свою відповідь далі за своїм бажанням.
Саді

@sadi, дивлячись на це свіжими очима, я бачу, що я робив неправильно з командою sed. Остання версія буде працювати, хоча, звичайно, якщо метод tr працює для вас, це нормально (у мене є підозріла думка, що рішення tr може бути трохи ефективнішим насправді, хоча sed буде краще обробляти неанглійські символи)
evilsoup

Дякую. Цікаво, чи можете ви допомогти мені ще більше вдосконалити цей скрипт, використовуючи одну команду для файлів MOV та іншу для інших по рядках: якщо [розширення MOV] бла-бла; ще бла-бла. Причина в тому, що я щойно зрозумів, що марка "CreateDate" у моїх файлах MOV (з iPad) дивно має +4 години, і мені потрібно використовувати інший варіант (CreateDate-tur) для них, щоб досягти точного порядку фотографій та відео .
Саді

Найкращий спосіб для цього (на мою думку) - використовувати випадок справи; ось щось для початку. Ви також можете використовувати оператор if, але висловлювання справ можна легше розширити для додаткових розширень файлів. Шукайте в Інтернеті "bash case statement" для отримання додаткової інформації.
злий

Завдяки мільйонів!!! Я також додаю цей варіант у відповідь, якщо ви не заперечуєте.
Саді

13

Мені потрібно було перейменувати свої фотографії, і тут я знайшов це запитання - я просто з’ясував, що exiftoolвін справляється з цим власним чином:

Від http://www.sno.phy.queensu.ca/~phil/exiftool/filename.html

exiftool -d %Y-%m-%d_%H-%M-%S%%-c.%%e "-filename<CreateDate" DIR 

Якщо ви хочете відслідковувати оригінальне ім’я файлу та записувати розширення в нижній регістр:

exiftool -d %Y%m%d_%H%M%S%%-c-%%f.%%le "-filename<DateTimeOriginal" [.|DIR]

Те ж саме працює і з усім ім'ям файлів у малому регістрі:

exiftool -d %Y%m%d_%H%M%S%%-c-%%lf.%%le "-filename<DateTimeOriginal" [.|DIR]

DIR повинен бути папкою, де виділяються фотографії. Якщо ми вже відкрили термінал у папці, де ми хочемо виконати команду, ми повинні замінити DIR на. І якщо ви хочете додати префікс, до імені файлу (тобто IMG_) це потрібно вставити перед ланцюжком дат без жодних лапок. Ось приклад: exiftool -d IMG_% Y% m% d_% H% M% S %% - c. %% e "-namename <CreateDate".
Нотор

2

Я знаю, ви сказали, що ви віддаєте перевагу сценарію, однак, якщо ви відкриті для безкоштовної програми Java, ви можете скористатися AmoK Exif Sorter

введіть тут опис зображення


1

Я б krenameдля цього скористався. Це

  • показує попередній попередній перегляд
  • дозволяє скасувати
  • може рекурсивно переходити в реж
  • дозволяє кілька моделей перейменування
  • дозволяє глобуси та регулярні вирівнювання в шаблонах
  • пам'ятає історію

0

Піренамер не працюватиме на моєму новому встановленому Ubuntu 16.04, тому мені доведеться знайти інший спосіб вирішити цю проблему.

У мене є файли, такі як IMG_0001.JPG, IMG_0002.JPG, ... в одній папці. Перевірте цей сайт, /programming/917260/can-var-parameter-expansion-expressions-be-nested-in-bash

Спершу встановіть "exiv2", і я написав такий командний рядок:

для img в $ (ls *. [Jj] [Pp] [Gg] 2> / dev / null); зробити exiv2 -r '% Y% m% d_% H% M% S _' "$ (tmp = $ {img %%. *}; echo $ {tmp ## * _})" перейменувати "$ img"; зроблено

Вихідні імена файлів - YYYYMMDD_HHMMSS_0001.JPG, YYYYMMDD_HHMMSS_0002.JPG, ... тощо. Навіть фотографії, зроблені в одну і ту ж секунду, оригінальний серійний номер фотографії зміниться.

Використовуючи наш веб-сайт, ви визнаєте, що прочитали та зрозуміли наші Політику щодо файлів cookie та Політику конфіденційності.
Licensed under cc by-sa 3.0 with attribution required.