В простейшем случае, слить несколько изображений можно вот так:
1 2 3 4 | convert -page +0+0 img0.png \ -page +256+0 img1.png \ -page +512+0 img3.png \ -background none -layers merge +repage merged.png |
где с помощью аргумента -page
передаётся смещение сливаемого изображения относительно границ получаемого изображения (merged.png).
Подробнее о слиянии изображений и вообще использовании команд пакета ImageMagick
написано здесь.
У меня же возникла необходимость выполнить слияние большого количества тайлов (более 1500) в одно большое изображение, в связи с чем был написан скрипт, который бодро-пакетно это всё выполняет. Подобный скрипт мне понадобился, чтобы склеить множество тайлов, выдранных с частного гуглмапса в полноценную карту высокого разрешения.
Первоначальное решение «в лоб» (подать на вход команды один большой список файлов с аргументами) оказалось работоспособным на сравнительно небольшом количестве файлов — 400 тайлов общим объёмом 5,5MB обработались примерно за 2 минуты. Но на 1500 файлах (~20MB) происходил затык, и скрипт, отъев 90% CPU, безрезультатно провисел полчаса.
Таким образом, пришлось подвергнуть скрипт небольшой оптимизации — сначала во временные файлы сливаются ряды, а затем через заданное количество итераций эти ряды сливаются между собой, до тех пор, пока не будет получено требуемое изображение.
Можно было пойти дальше, и создавать/сливать ряды рекурсивно — т.е. у нас, например, 50 картинок, нужно их слить в изображение шириной в 5 картинок, получаем 10 временных рядов, сливаем каждые 2, вновь получаем 5 рядов, сливаем каждые 2, получаем 2 ряда (один из них увеличенный), наконец, их этих двух получаем требуемое изображение. Но мне было лень, алгоритм сработал и так. Мои полтора с гаком тысячи тайлов собрались в изображение 10240×10240 px за ~5 минут (на последних минутах, когда скрипт оперировал большими кусками изображений, наблюдались ощутимые тормоза).
Как правильно подать параметры на вход скрипта:
1 2 3 4 5 6 7 8 | ./im-merger.sh \ --input-directory /home/user/graph/tiles_dir \ --output-file /home/user/graph/tiles_merged.png \ --background none \ --tile-width 100 \ --tile-height 200 \ --max-col 3 \ --merge-each-row 5 |
Файлы будут сливаться в указанном порядке. Получая список файлов из указанной директории, скрипт сортирует их по возрастанию (от img_0.png к img_3.png и так далее).
Скрипт имеет встроенную справку (./im-merger.sh --help
). Имеет смысл просмотреть исходный код: строки, помеченные [EDIT ON NECESSITY]
— влияют на логику скрипта.
Исходник лежит на гитхабе.