How to use subshell to crop several coordinates in a single process

Questions and postings pertaining to the usage of ImageMagick regardless of the interface. This includes the command-line utilities, as well as the C and C++ APIs. Usage questions are like "How do I use ImageMagick to create drop shadows?".
Post Reply
cgkas
Posts: 42
Joined: 2018-10-10T23:36:52-07:00
Authentication code: 1152

How to use subshell to crop several coordinates in a single process

Post by cgkas »

Hello to all,

I have these coordinates and the input image below.

coords="110x16+255+175
178x59+29+65
178x59+223+65
178x59+417+65
178x59+611+65
240x151+462+176
240x151+87+257
240x151+366+355
240x151+77+448
240x151+468+542
240x151+140+624"

areas.png
Image

For the first 5 coordinates I apply this code (images 0 to 4):

Code: Select all

(
for coord in $coords; do
echo >&2 "$coord"
convert areas2.png +repage -crop $coord +repage -bordercolor black -border 2x2 miff:-
done
) | \
convert - -write mpr:img -delete 0--1 \( mpr:img[1,2] -smush -2 \) \( mpr:img[3,4] -smush -2 \) \
+smush -2 mpr:img[0] +swap -gravity center -background none -smush +3 ImgHeader.png
And for the rest of coordinates (5 to 10), I want to apply the convert command below in consecutive pairs, this is join coordinate 5 with 6, 7 with 8 and 9 with 10.
But it seems I cannot use the first subshell code where was stored the frames in miff memory for the rest of the coordinates.

So, when I run these 3 command failed.

Code: Select all

convert - -write mpr:img -delete 0--1 \( mpr:img[5,6]   +smush +6 \) \
+smush -2 LeftRight.png +swap -gravity center -background none -smush +3 ImgTop.png

convert - -write mpr:img -delete 0--1 \( mpr:img[7,8]   +smush +6 \)\
+smush -2 LeftRight.png +swap -gravity center -background none -smush +3 ImgMiddle.png

convert - -write mpr:img -delete 0--1 \( mpr:img[9,10]  +smush +6 \) \
+smush -2 LeftRight.png +swap -gravity center -background none -smush +3 ImgBottom.png
Do I need to do a subshell for each pair of coordinates or how to mix in a single process the operations for all the coordinates?

The outputs would be like this:

ImgHeader.png
Image

ImgTop.png
Image

ImgMiddle.png
Image

ImgBottom.png
Image

LeftRight.png (This is only a helper image to use it to put the header over each resulting image)
Image

Thanks in advance for any help.
User avatar
GeeMack
Posts: 718
Joined: 2015-12-01T22:09:46-07:00
Authentication code: 1151
Location: Central Illinois, USA

Re: How to use subshell to crop several coordinates in a single process

Post by GeeMack »

cgkas wrote: 2018-10-25T09:29:04-07:00Do I need to do a subshell for each pair of coordinates or how to mix in a single process the operations for all the coordinates?
You can do everything you have there in a single command by very careful use of nested sets of parentheses. Remember when you set the "-gravity" before your "-smush" operations you need to unset it again with "+gravity" before your crop operations, otherwise your crops won't come out the way you intend.

This command works for me with IM 6.8.9-9 in a bash shell inside the Windows 10 Ubuntu installation...

Code: Select all

convert areas2.png -write mpr:img -delete 0--1 \
   -background none -bordercolor black \
   \( mpr:img -crop 178x59+29+65 \) \( mpr:img -crop 178x59+223+65 \) \
   \( mpr:img -crop 178x59+417+65 \) \( mpr:img -crop 178x59+611+65 \) \
   -border 2 \( -clone 0,1 -smush -2 \) \( -clone 2,3 -smush -2 \) -delete 0-3 \
   -gravity center +smush -2 +gravity \
   \( mpr:img -crop 110x16+255+175 -border 2 \) \
   +swap -gravity center -smush +3 +gravity -write ImgHeader.png \
   \( \( mpr:img -crop 240x151+462+176 \) \( mpr:img -crop 240x151+87+257 \) \
      +smush +6 LeftRight.png +swap -gravity center -smush +3 +gravity \
      -write ImgTop.png \) -delete 0--1 \
   \( \( mpr:img -crop 240x151+366+355 \) \( mpr:img -crop 240x151+77+448 \) \
      +smush +6 LeftRight.png +swap -gravity center -smush +3 +gravity \
      -write ImgMiddle.png \) -delete 0--1 \
   \( \( mpr:img -crop 240x151+468+542 \) \( mpr:img -crop 240x151+140+624 \) \
      +smush +6 LeftRight.png +swap -gravity center -smush +3 +gravity \
      -write ImgBottom.png \) null:
cgkas
Posts: 42
Joined: 2018-10-10T23:36:52-07:00
Authentication code: 1152

Re: How to use subshell to crop several coordinates in a single process

Post by cgkas »

Hi GeeMack. Thanks for your answer.

Certainly works for me too in my ImageMagick 6.9.10-11 Q16 x86_64 on Cygwin/Windows7.

The thing here is I have stored the coordinates in a variable that comes from a previous process, then in this case there are 11 coordinates and the first 5 make the first output image, then the rest of coordinates will make taking them in pairs the rest of output images. The issue is that could be more that 11 coordinates, lets say 21 coordinates where the first 5 will be handled in the same way and the rest taking in consecutive pairs to produce the others output images. So I need to handle the process with variables and considering the number of coordinates not always be the same. Because of that in my post is included a loop in a subshell.

I hope make sense.

Regards
Post Reply