Понравился контент? Нажми:
Зайдите на любой фото-форум и вы найдете тред о том, почему мыльница не настоящий фотоаппарат, в отличие от зеркалки. Я же расскажу вам о ситуации, когда мыльница не то, чтобы лучше, но, по крайней мере, интереснее. Когда фото- и видеокамеры научились подключаться к компьютеру, группа ведущих разработчиков фото и видео оборудования создала протокол PTP (Picture Transfer Protocol – протокол передачи изображений). Основная задача протокола PTP, как и следует из его названия, – передача изображений между камерой и компьютером, однако этим возможности PTP не исчерпываются. PTP позволяет не только перекачивать изображения из одного хранилища в другое, но и устанавливать настройки фокуса и экспозиции камеры, делать снимки и даже смотреть на мир «глазами камеры», используя механизм пред-просмотра изображений. Попросту говоря, если ваша камера поддерживает PTP, вы можете управлять ей со своего компьютера. Это были хорошие новости. Плохая новость заключается в том, что далеко не все фото и видео камеры умеют работать с PTP. Одна из причин сего неприятного явления заключается в том, что с самого начала у протокола PTP был серьезный конкурент – стандарт USB Mass Storage, который позволяет представить любое USB-устройство, обладающее хранилищем данных, как внешний USB-диск. Стандарт USB Mass Storage не поддерживает широких возможностей протокола PTP, зато он удобнее в области передачи данных с устройства в компьютер (а это, все же, основная функция, которую требуют владельцы цифровых камер). Неудивительно, что все производители цифровой фотоаппаратуры реализовали в своих изделиях USB Mass Storage, а вот про PTP многие «забыли». Как это ни странно, поддержку PTP чаще можно найти в недорогих мыльницах, нежели в дорогих зеркальных аппаратах, так что если хотите экспериментировать с PTP, имеет смысл приобрести мыльничку за пару сотен условных единиц (что я и сделал). Если вы уже решили бежать за новой мыльницей, дочитайте эту статью хотя бы до описания утилиты gphoto2.

По умолчанию все фотокамеры работают в режиме Mass Storage, а в режим PTP их нужно специально переключать (рис. 1). Камера, которая поддерживает PTP, это только половина дела. Для того чтобы поразить мир изумительными снимками, созданными под управлением компьютера, нам понадобится специализированное программное обеспечение.
Операционная система Windows умеет работать с PTP, однако, «голая» винда предоставляет нам минимальные возможности, такие как установка режима фотовспышки и снимок нажатием кнопки на компьютере (как будто ее нельзя нажать на фотоаппарате). В Сети можно найти множество условно-бесплатных и просто бесплатных программ для Windows, которые более широко используют возможности PTP, но самое сильное желание, которое возникает при знакомстве с этими программами, – написать свою собственную, которая бы делала именно то, что надо мне. Не удержусь о того, чтобы не сказать несколько слов о том, как нынче пишутся Windows-программы. Большинство программистов-индивидуалов, работающих исключительно под Windows, - шараварщики, которые стремятся максимально нарастить «рыночную стоимость» своего продукта. В результате, вместо того чтобы сделать простую утилиту для управления фотокамерой с помощью PTP и продавать ее, скажем, за пять единиц (и не надо говорить мне, что она стоит дороже, я такую утилиту написал на C# примерно за 2 часа, начиная с изучения PTP Windows API и заканчивая украшением пользовательского интерфейса), они объединяют эту утилиту с каталогизатором фотографий и генератором Web-галерей и продают ее за 40 тех же единиц (это при том, что менеджер каталогов и генератор галерей и так есть практически в каждой графической утилите).
Переходя на платформу Linux, мы оказываемся в несравненно более дружественной среде. Рабочая лошадка Linux для камер, поддерживающих PTP – консольная программа gphoto2 (а точнее – библиотека libgphoto2). Установите программу gphoto2 (желательно – самую последнюю версию) и в окне консоли скомандуйте:
gphoto2 --list-cameras
Будет распечатан список фотокамер, которые поддерживает текущая версия gphoto2. Если собираетесь покупать мыльницу специально для экспериментов, прихватите с собой копию этого списка.
Убедитесь, что ваша камера находится в режиме PTP, подключите ее к компьютеру и скомандуйте:
gphoto2 -l
Эта команда выдаст список хранилищ данных для обнаруженного оборудования. Список может выглядеть, например, так:
There is 1 folder in folder '/'. - store_00010001 There are 2 folders in folder '/store_00010001'. - DCIM - MISC There is 1 folder in folder '/store_00010001/DCIM'. - 101NIKON There are 0 folders in folder '/store_00010001/DCIM/101NIKON'. There are 0 folders in folder '/store_00010001/MISC'.
Отлично, наша камера опознана.
Раскол продолжается
Из листинга вы можете понять, фотоаппаратом какой фирмы я пользуюсь. Поклонникам Кэнонов я могу напомнить анекдот про старообрядческого епископа, которому подарили фотоаппарат конкурирующей фирмы. Владыка растоптал его со словами: «никогда в моем доме ничего никонианского не было и не будет!»
Утилита gphoto2 таит в себе массу возможностей. Команда
gphoto2 --list-config
Распечатывает список настроек, которыми можно управлять с помощью утилиты. В моей системе этот список выглядит так:
/main/actions/autofocusdrive /main/actions/manualfocusdrive /main/settings/datetime /main/settings/fastfs /main/settings/capturetarget /main/imgsettings/imagequality /main/imgsettings/imagesize /main/capturesettings/autofocusmode /main/capturesettings/focallength /main/capturesettings/focusmode /main/capturesettings/flashmode /main/other/5001 /main/other/5003 /main/other/5004 /main/other/5008
Как видим, программа позволяет контролировать режимы автофокуса, вспышки, фокусного расстояния, размера и качества сохраняемого изображения, а так же поддерживает несколько неведомых настроек типа main/other/5008 (на самом деле эти настройки дублируют приведенные выше, но используют в описаниях названия на языке локали). Между прочим, программа gphoto2 старается переводить сообщения фотокамеры на язык системы, независимо от того, на каком языке «разговаривает» само устройство. Теперь командуем:
gphoto2 --get-config=/main/imgsettings/imagesize
в результате получаем:
Type: RADIO Current: 3072x2304 Choice: 0 1024x768 Choice: 1 2048x1536 Choice: 2 2592x1944 Choice: 3 3072x2304
Я думаю, вы уже поняли, что камера поддерживает 4 размера изображения, из которых в настоящий момент выбран максимальный - 3072x2304. Обратите внимание на то, что в первой строке выдачи команда указала тип настройки RADIO (что в данном случае означает «переключатель») – то есть возможность выбрать только одно из предложенных значений (этот параметр можно использовать при динамическом построении графической оболочки к утилите gphoto2). Уменьшим размер изображений:
gphoto2 --set-config=/main/imgsettings/imagesize=1024x768
Скомандовав еще раз
gphoto2 --get-config=/main/imgsettings/imagesize
Вы можете убедиться, что значение параметра imagesize изменилось. Отметим, что новая настройка сохранится и после выключения фотоаппарата. Ну и наконец, самое главное:
gphoto2 --capture-image
Эта команда заставляет камеру сделать снимок. После непродолжительной задержки «из камеры вылетит птичка», а результат будет сохранен на внутреннем диске (рис. 2).

Команда
gphoto2 --capture-image-and-download
делает снимок и автоматически загружает изображение в компьютер. Ну и конечно, программа gphoto2 не была бы самой собой, если бы не обладала целым набором команд для перемещения файлов между фотоаппаратом и компьютером. Например, команда
gphoto2 --get-all-files --folder=/store_00010001/DCIM/101NIKON
скопирует все файлы изображений из папки фотоаппарата /store_00010001/DCIM/101NIKON в текущую директорию вашего компьютера.

Программа gphoto2 в режиме оболочки.
Между прочим, у gphoto2 есть и режим оболочки (рис. 3), запускаемый ключом --shell, который позволяет перемещаться по внутреннему диску фотокамеры как по локальной файловой системе. Еще один вариант «графического интерфейса», позволяющего выбирать настройки камеры, запускается ключом --config.
Так в чем же заключается преимущество консольной утилиты gphoto2 перед красочным программами для Windows? Прежде всего, эта утилита делает именно то, что она должна делать, и ничего более. Ее компактность позволяет объединять ее с другими программами таким способом, который нужен пользователю. Консольную программу легко использовать в других программах, написанных на различных интерпретируемых (и не только интерпретируемых) языках программирования. Между прочим, у gphoto2 есть опция, позволяющая выводить полученные изображения в стандартный поток вывода. Тут уж возможности ограничены только вашей фантазией. Можно заставить камеру делать фотоснимки через определенные промежутки времени (первое, что приходит в голову). Стоит отметить, что выполнение фото-камерой снимков осуществляется с задержкой в несколько секунд (продолжительность которой зависит от модели камеры), так что делать слишком частые снимки в автоматическом режиме не удастся. Можно, конечно, заставить камеру снимать кино (если она поддерживает эту возможность). Объединив gphoto2 с другими программами можно запрограммировать камеру делать фотоснимки в ответ на определенные события системы, например, фотографировать каждого, кто входит в систему с местного терминала. А подключив фотоаппарат к нетбуку, вы сможете делать снимки не только там, куда никогда не ступала нога человека, но и там, куда его рука не дотянется.
Очень полезную возможность gphoto2 представляет ключ --hook-script, который позволяет привязать файл сценария оболочки к определенным событиям программы gphoto2. Допустим, что нам надо, чтобы фотокамера делала фотоснимки в определенные промежутки времени и загружала на указанный ей сервер FTP (попробуйте найти такую программу под Windows). Начнем по порядку. Команда вызова gphoto2 в этом случае должна выглядеть так:
gphoto2 --capture-image-and-download --hook-script test-hook.sh
Если вы хотите получать снимки через регулярные интервалы времени, эту команду можно вызывать с помощью cron. Сценарий test-hook.sh – учебный сценарий, который демонстрирует взаимодействие сценариев оболочки и команды gphoto2 (вы найдете его в директории /usr/share/doc/gphoto2/). Ниже приводится текст этого сценария, модифицированный для наших целей:
#!/bin/sh self=`basename $0` case "$ACTION" in init) echo "$self: INIT" ;; start) echo "$self: START" ;; download) echo "$self: uploading $ARGUMENT" ./ftp-upload.sh $ARGUMENT rm $ARGUMENT ;; stop) echo "$self: STOP" ;; *) echo "$self: Unknown action: $ACTION" ;; esac exit 0
Сценарий узнает о событиях gphoto2 при помощи переменной окружения $ACTION. Событие init соответствует инициализации камеры, событие start указывает на начало выполнения камерой команды, событие download свидетельствует о том, что камера готова к передаче файла (имя файла содержится в переменной $ARGUMENT). Событие stop указывает на завершение операции. В нашем сценарии в ответ на событие download мы вызываем сценарий ftp-upload.sh, который загружает файл на заданный FTP-сайт. Вот текст этого сценария:
#!/bin/bash HOST='ftp.foo.com' USER='user' PASSWD='password' ftp -i -n $HOST << EOF user ${USER} ${PASSWD} binary cd /home/somedir/photos put $1 quit EOF

Утилита gtkam распознает нашу фотокамеру

Программа gtkam – простейший браузер содержимого фотокамеры
Для утилиты gphoto2 существует несколько графических оболочек и вспомогательных утилит, но они предназначены, в основном, для управления сохраненными в фотокамере фотографиями и передачи их на компьютер. Программа gtkam использует gphoto2 для точного определения модели подключенной камеры (рис. 4) и управления сохраненными фото (рис. 5). Утилита gphotofs позволяет подмонтировать файловую систему камеры к локальной файловой системе. Например, команда
gphotofs /home/andrei/nikon/
монтирует файловую систему камеры в директории /home/andrei/nikon/, после чего содержимое диска камеры можно просматривать в любом файловом менеджере (рис. 6).

Файловая система камеры как часть локальной файловой системы
Как уже отмечалось выше, возможности протокола PTP в плане перемещения файлов не дают ничего принципиально нового по сравнению с USB Mass Storage, так что если вы заинтересовались PTP рассмотренные утилиты вряд ли вас удовлетворят. Вы можете добавить функциональность управления камерой в свои программы, используя возможности консольного режима gphoto2 и языки сценариев (и для большинства из вас этого будет вполне достаточно), но есть и другой путь. Утилита gphoto2 представляет собой, по сути говоря, оболочку вокруг библиотеки libgphoto2, которая экспортирует интерфейс управления PTP-устройствами на языке С. Для демонстрации возможностей этого интерфейса мы напишем небольшую графическую программу Libgphoto Tester, используя Qt library. Вы найдете ее на диске в архиве libgphototester.
Наша программа (рис. 7) умеет определять, подключена ли к системе PTP-камера, выводить подробную информацию о подключенном устройстве и делать фотоснимок по команде пользователя.

Программа libgphototester показывает возможности фотоаппарата Nikon Coolpix
После установки пакетов разработки libgphoto2 у вас появится весьма внушительный набор заголовочных файлов в директории /usr/include/gphoto2. Все элементы API, относящиеся к управлению камерой, собраны в файле gphoto2-camera.h. Начало и конец любой процедуры, работающей с PTP-устройством посредством libgphoto2, должны выглядеть примерно так:
GPContext * context; Camera * camera; int init_result; context = gp_context_new(); gp_camera_new(&camera); init_result = gp_camera_init(camera, context); //Командуем фотокамерой ... gp_camera_exit(camera, context); gp_camera_free(camera); gp_context_unref(context);
Структура GPContext – это контекст API, в котором содержится служебная информация о текущей сессии libgphoto2. Большинство функций API получает в качестве одного из параметров указатель на эту структуру. Структура Camera представляет в программе фотокамеру (между прочим, libgphoto может работать с несколькими фотокамерами одновременно). Функция gp_camera_new() создает экземпляр структуры Camera, а функция gp_camera_init() инициализирует фотокамеру (именно в этот момент происходит первое обращение к физическим устройствам). На самом деле эта функция делает гораздо больше, чем может показаться исходя из ее названия. В системе всегда присутствует несколько USB-портов, к которым может быть подключено несколько PTP-устройств. Функция gp_camera_init() сканирует порты в поисках PTP-устройств и инициализирует первое найденное устройство. Если вы хотите работать одновременно с несколькими устройствами, вам лучше всего посмотреть исходный текст функции gp_camera_init() в файле /trunk/libgphoto2/libgphoto2/gphoto2-camera.c из svn-репозитория libgphoto2. Дело в том, что интерфейс для работы с несколькими устройствами в libgphoto2 все еще не обрел стабильности, а документация в некоторых частях просто отсутствует. Самая лучшая документация в данном случае – исходный текст функции, которая гарантированно может обрабатывать несколько подключенных устройств.
Если фотокамера была инициализирована с помощью вызова gp_camera_init(), работу с ней следует завершить при помощи функции gp_camera_exit(). После этого структура Camera освобождается с помощью gp_camera_free(), а контекст – с помощью функции gp_context_unref().
Для того чтобы заставить фотокамеру сделать снимок, воспользуемся функцией gp_camera_capture(). Эта функция возвращает информацию о сделанном снимке в структуре CameraFilePath. Члены path и name этой структуры содержат, соответственно, путь и имя файла в файловом пространстве фотокамеры.
Для работы с файлами, сохраненными на внутреннем диске камеры, а также для передачи файлов в компьютер, существует свой набор функций, объявленных в файле gphoto2-file.h. Прежде всего, для работы с файлами нужно создать хотя бы один экземпляр структуры CameraFile, которая является аналогом дескриптора файла для файловых функций libgphoto2:
CameraFile * file; result = gp_file_new(&file); ... gp_file_free(file);
Функция gp_file_free() уничтожает соответствующий объект. Для работы с файлами вам так же доступны функции gp_file_open(), gp_file_save (), gp_file_copy() gp_file_detect_mime_type() (определение типа данных файла). Эта функция полезна, если вы пишете свой собственный файловый браузер для фотокамеры (напомню, что современный фотоаппарат может хранить в себе не только фотографии но и видеоролики и даже звуковые файлы сопровождения в различных форматах). Функция gp_file_append () осуществляет добавление данных в уже существующий файл, а функция gp_file_clean() (или, в зависимости от версии API - gp_file_delete()) очищают файлы.
Скачать файл из фотокамеры в компьютер можно, например, с помощью функции gp_file_get(), но при этом надо учитывать, что аргументом функции, представляющим фал-приемник для скачивания, должен быть указатель на структуру CameraFile. Функция gp_file_new_from_fd() позволяет связать структуру CameraFile и обычный идентификатор файла Linux (а если учесть, что идентификатор файла в Linux может представлять практически что угодно, начиная с устройства и заканчивая потоком ввода другой программы, возможности открываются необозримые). Теперь вы знаете достаточно для того, чтобы доработать программу libgphoto tester и научить ее не только делать снимки, но и показывать результаты в режиме реального времени. Оставляю вам это в качестве домашнего задания.
Разумеется, наличие мыльницы (как, впрочем, и дорогой зеркальной фотокамеры) не сделает из вас Картье-Брессона. С другой стороны, новые технические возможности в сочетании со старой человеческой способностью к творчеству позволят вам реализовать такие идеи, которые даже в голову не приходили великим фотографам пошлого.
Исходные тексты примера: gphototest.tar.gz
Понравился контент? Нажми: