ImageMagick v6 Examples --
Montage, Arrays of Images

Index
ImageMagick Examples Preface and Index
Montage, Introduction and General
Montage Settings
Indexes of Image Directories
Special Usage and Notes

The original use of "montage" is to generate tables of image thumbnails, that is, to reference thumbnails of large collections of images, especially photos. And while it still can be used for that purpose, it can also do a lot more. This page examines what you can do with montage, and how you can use it on your own images.


Montage, Introduction

The default "montage" with no options is very plain, with quite large containment squares, no frame, labels, or shadows.

  montage balloon.gif medical.gif present.gif shading.gif  montage.jpg
[IM Output]

By default it is set to a size of about 128 pixels, with the special resize flag '>' defined so that only larger images being resized. As you can see above the smaller images were not resized.

You can remove the huge amount of surrounding space was added by montage by default by adding a "-geometry" position option. The position part of the option is interpreted as the amount of border space to leave around the image.

  montage balloon.gif medical.gif present.gif shading.gif \
          -geometry +2+2   montage_geom.jpg
[IM Output]

As no 'size' was specified in the above "-geometry" setting, the final 'cell' or 'tile' size allocated to ALL the montaged images is determined by the largest dimensions over all the images.

If a "-geometry" size setting is used to resize images, the final 'cell' size will not be set smaller than this size, though the default resize options will generally ensure images fit within that given size.

See Resize Examples for details of the special resize option flags. Especially note that the special option flag '>' can be used to ensure images are never enlarged, just as the default setting does.

Tile Controls

The next most important option in "montage" is the "-tile" setting. This tells montage what limits you want on how the tiled images are to be laid out on the final result.

In ImageMagick version 6 "montage" will make a educated guess as to how best to tile a given number of images, when you provide no "-tile" hints. It does however assume that the images being tiled are roughly squarish in nature, as it does not look at the images aspect ratios.

  montage font_1.gif      -geometry 16x16+1+1  tile_1.gif
  montage font_[12].gif   -geometry 16x16+1+1  tile_2.gif
  montage font_[123].gif  -geometry 16x16+1+1  tile_3.gif
  montage font_[1-4].gif  -geometry 16x16+1+1  tile_4.gif
  montage font_[1-5].gif  -geometry 16x16+1+1  tile_5.gif
  montage font_[1-6].gif  -geometry 16x16+1+1  tile_6.gif
  montage font_[1-7].gif  -geometry 16x16+1+1  tile_7.gif
  montage font_[1-8].gif  -geometry 16x16+1+1  tile_8.gif
  montage font_[1-9].gif  -geometry 16x16+1+1  tile_9.gif
  montage font_[0-9].gif  -geometry 16x16+1+1  tile_0.gif
[IM Output] [IM Output] [IM Output] [IM Output] [IM Output] [IM Output] [IM Output] [IM Output] [IM Output] [IM Output]

The strange "[1-5]" syntax is a UNIX shell shorthand, which is expanded into a list of filenames. The "montage" command itself does not see these characters, just the resulting list of files.

However if you specify a specific "-tile" setting, montage will always create a image big enough to hold that many images.

  montage font_[1-7].gif  -tile 9x1  -geometry 16x16+1+1  tile_9x1.gif
  montage font_[1-7].gif  -tile 4x3  -geometry 16x16+1+1  tile_4x3.gif
  montage font_[1-7].gif  -tile 3x3  -geometry 16x16+1+1  tile_3x3.gif
  montage font_1.gif      -tile 2x3  -geometry 16x16+1+1  tile_2x3.gif
[IM Output] [IM Output] [IM Output] [IM Output]

As you can see montage created an image that is large enough to hold the number of tiles specified, regardless of how many images are available to fill the tile space requested, be it 7 images, or just 1 image.

It will also only fill the space row by row, no option is currently provided to do a column by column fill of the tile space.

Before IM v6.1 montage would automatically truncate the extra space if the number of images did not use that space. As such a setting such as the first "9x1" image would have been truncated to produce a "7x1" tile image.

Because of this, past users of montage often used large numbers such as "999x1" to generate a single row of images. Now such a argument will produce a very long image, and could take a long time for IM to complete. As such...

Avoid the use of very large tile numbers in IM montage!

If you have more input images than montage can tile into the space given by a "-tile" setting, then multiple images can be generated by montage, either resulting in image sequence numbers being added to the filename, or some sort of GIF animation, being created. See Writing Multiple Image for details.

For example, here I have asked montage to save separate images for each page generated, by supplying a '%d' for the frame/scene/page number of each image filename.

  montage  font_*.gif  -tile 4x1  -geometry +2+2  multi_%d.gif
[IM Output] [IM Output] [IM Output]

You can avoid the problems of extra space, and multiple images, especially for an unknown number of input images, by removing either a row, or the column number, from the "-tile" setting. The missing number will be taken by montage as being variable and montage will only create enough tile space to hold ALL the input images, producing only one image, never multiple images.

  montage font_[1-7].gif  -tile x1  -geometry 16x16+1+1  tile_x1.gif
  montage font_[1-7].gif  -tile x2  -geometry 16x16+1+1  tile_x2.gif
  montage font_[1-7].gif  -tile x4  -geometry 16x16+1+1  tile_x4.gif
  montage font_[1-7].gif  -tile 4x  -geometry 16x16+1+1  tile_4x.gif
  montage font_[1-7].gif  -tile 5x  -geometry 16x16+1+1  tile_5x.gif
  montage font_[1-7].gif  -tile 9x  -geometry 16x16+1+1  tile_9x.gif
[IM Output] [IM Output] [IM Output] [IM Output] [IM Output] [IM Output]

This is the more typical use of the "-tile" setting, as it ensures the montage is sized correctly, while still allowing it some control in determining the final array size.

Note the last image, in the above where we requested 9 columns of images. IM still generated the requested 9 columns, even though less than 9 images were given. On the other hand the first image (one row requested), is exactly the right length to hold all the images.

Frame and Shadow Montaged Images

The best part of using montage to arrange images, is that it provides a lot of extra controls to add extra 'fluff' around each image.

For example, you can better define the images being displayed by adding a "-frame" around each image.

  montage balloon.gif medical.gif present.gif shading.gif \
          -tile x1  -frame 5  -geometry +5+5   frame.jpg
[IM Output]

Unlike the same option in "convert" (See Adding a 3D frame example). The montage frame option will automatically figure out default values for the internal and external bevel of the frame. As such only a single argument number is needed.

Adding a shadow with the frame is also quite good.

  montage balloon.gif medical.gif present.gif shading.gif \
          -tile x1  -frame 5  -shadow  -geometry +5+5   frame_shadow.jpg
[IM Output]

Of course you don't actually need a frame to generate image shadows

  montage balloon.gif medical.gif present.gif shading.gif \
          -tile x1  -shadow  -geometry +5+5  -background lightblue \
          shadow_noframe.jpg
[IM Output]

As of IM v6.3.1 when 'soft shadows' were implemented, the shadows will now be shaped according to the transparency of the images being displayed!

  montage font_1.gif  font_7.gif  font_2.gif  font_0.gif \
          -tile x1  -shadow  -geometry +3+5 -background none \
          shadow_shaped.png
[IM Output]

As you can see the shadow used by montage is actually a semi-transparent color, allowing the background to affect its final color. This means if you create a montage with textured background, or use a transparent background and overlay it, the shadow will do the right thing.

Of course you need to use an image format that can handle semi-transparent colors, like PNG. GIF will not work well for the above example)

Note that shadows do not care about the "-geometry" spacing between the images. As such if the images are too close together, the shadow of previous images can be obscured by later images, and can also be clipped by the montage canvas size. For example...

  montage balloon.gif medical.gif present.gif shading.gif \
          -tile x1  -shadow  -geometry +1+1  -background none \
          shadow_spacing.png
[IM Output]

It is thus recommended at a reasonable amount of "-geometry" spacing be provided when using shadow.

Montage currently also provides no controls for the offset, color or the 'softness' of the generated shadow (at least not yet), but then, you didn't have such control with hard rectangular shadow that older versions of montage provided.

Labeling Montage Images

You can also tell montage to label the image with their source filenames, though you probably need to resize the image frames, or the labels may not fit, truncating the text label.

In this case we added a "60x60>" to the geometry string, which tells IM to shrink larger images to fit into this space, but not to enlarge images if they are smaller.

This is probably the most typical use of montage.

  montage -label '%f'  balloon.gif medical.gif rose: present.gif shading.gif \
          -tile x1  -frame 5  -geometry '60x60+4+4>'  label_fname.jpg
[IM Output]
The '%f' is a special format character, which can pull out various details about the images in memory. See Image Property Escapes for details of other information you can extract from images.

TO BE REVISED... Note that as "logo:" is a built in image, does not have a filename, it also does not have a label. That is because its filename is empty resulting in the empty 'do not label' label. If this is not wanted you could add a extra space to the "-format" string, so it will never be empty, even when no filename is present.

You don't have to use a "-frame" when labeling thumbnails. The labels are not shadowed, so that they remain clearly readable.

  montage -label '%f'  balloon.gif medical.gif logo: present.gif shading.gif \
          -tile x1 -shadow -geometry '60x60+2+2>'  label_shadow.jpg
[IM Output]

And as of IM v 6.2.1 you can now re-label images after they have been read in using the "-set" image attribute operator.

Lets use the "-set" operator add more information about the images. And also few more montage settings...

  montage balloon.gif medical.gif logo: present.gif shading.gif \
          -tile x1  -geometry '90x32+2+2>'  -pointsize 10 \
          -set label '%f\n%wx%h'   -background SkyBlue   label_fname3.jpg
[IM Output]

As we showed in the examples above you can use the "-label" setting to define the default label for an image, as they are read in, or you can re-label the image afterward using the "-set" operator.

Note that '%wx%h gives the current pixel width and height of the image as it is in memory. If the image size was modified, such as during input this may be different to the images on disk size. Use '%[width]x%[height]' instead if you want its on disk pixel size.

You can also label images differently by setting label of individual images. Either option can be used, though you will need to use of parenthesis to limit what images the "-set" operator will be applied to.

Here for example we use both forms of labeling. But lets also add a title to the montage, just because we can...

  montage -label Balloon   balloon.gif  \
          -label Medical   medical.gif  \
          \( present.gif  -set label Present  \) \
          \( shading.gif  -set label Shading  \) \
          -tile x1  -frame 5  -geometry '60x60+2+2>' \
          -title 'My Images'     titled.jpg
[IM Output]

You can turn off image labeling for the next image(s) by using a "-label '' " or "+label". However as you will see later these two settings are not quite the same. The same applies for a post reading, label "-set" operation.

  montage                    balloon.gif \
          -label 'My Image'  medical.gif \
          +label             present.gif \
          -label ' '         shading.gif \
          -tile x1  -frame 5  -geometry '60x60+2+2>'   labeling.jpg
[IM Output]

The last image shows how using a space for a image label, you can create a image label space, but leave it blank.

This presents a good rule of thumb when using montage...

Either label all your images, or none of them!

You don't have to label your images during the montage operation itself. Both the MIFF and PNG formats, can store a label as part of their image format.

Montage will automatically label any image read in that already contains a label. This is automatic and does not need to be specified, and I have used this technique to generate some very complex image montages. For example the montage array in Annotate Angle Examples was created using this technique.

If you do not want this automatic labeling, you must specifically tell montage to reset all the labels being read in or created to the empty string, using "-label ''" before reading or "-set label ''" after reading the images.

This is where "+label" differs from using an empty label ("-label ''". The former will reset the default behavior back to automatically using any label meta-data that the image being read-in may have (this is also equivalent to a "-label '%l'"), while the later specifically turns off all labels (sets them to an empty string). Note that "-set" can not restore the original label of an image, once it has been removed.


  convert -label 'medical'  medical.gif  label_medical.png
  convert -label 'logo'     logo:        label_logo.png
  convert -label 'rose'     rose:        label_rose.png

  montage           label_medical.png \
          -label '' label_logo.png    \
          +label    label_rose.png    \
          -tile x1  -frame 5  -geometry '60x60+2+2>' label_files.jpg
[IM Output]

In the above you can see that the first image was labeled using the label supplied with the image itself. The second had the incoming label removed by a "-label '' " setting, while the third also used the images label because we turned-off the label setting with "+label".

While the MIFF and PNG format can store 'label' meta-data in their image file formats, other formats (such as JPG) allow you to save and use 'comment' meta-data. By specifying a '%c' argument to "-label" you can use this saved comment string instead of the default label string.

  convert -comment '- PNG -'  logo:      comment.png
  convert -comment '- GIF -'  rose:      comment.gif
  convert -comment '- JPG -'  netscape:  comment.jpg

  montage -label '%c' comment.png comment.gif comment.jpg \
          -tile x1  -frame 5  -geometry '60x60+2+2>' comment_files.jpg
[IM Output]

This is often more useful for pictures saved in the JPEG file format, though JPEG image comments generally are too large (often whole paragraphs describing the image), for use as montage labels, as they will not be word wrapped (see Montage of Polaroid Photos for an alternative method of labeling using image 'comment' meta-data).

Note also that many programs automatically add 'made-by' labels and comments to images they save (YUCK) so some caution is recommended.

Note that IM is generally not used to add comments to saved JPEG files, (due to JPEG Lossy Compression) unless processing them for other reasons. Instead they are usually added by some other method in order to avoid reading and re-writing the image data and thereby degrading the JPEG image files in which you are adding comments. See lossless JPEG Processing options, for some such methods.

It is also important to note that labeling (and image 'comments') is not specific to montage. Montage just makes automatic use of image labels if present. Labels and comments are attached to images, and the their specific file formats, and is not montage or even IM specific.

Leaving Gaps in a Montage

While you can leave extra space in a montage at the bottom by judicious use of the "-tile" setting and controlling the number of images given, leaving a empty tile space in the middle of a montage requires the use of a special image.

The "null:" generated image was defined specifically for this purpose. The position in which it appears will not receive any label (even if one is defined), nor will it have any frame or shadow 'fluff' added. The cell is just left completely empty except for the background color (or texture) of the montage drawing canvas itself.

  montage -label 'Image' medical.gif null: present.gif \
          -tile x1  -frame 5  -geometry +2+2   montage_null.jpg
[IM Output]

Note that to other IM commands the "null:" image is represented a single pixel transparent image. It is also used as a 'error image' for options like "-crop" or "-trim" which could produce a 'zero' or empty image as a result of the operation.

This special image can not be saved and then later used to leave gaps, currently it is only 'special' if given on the command line of "montage".

There is no method, at this time to allow montaged images to span multiple rows or columns, as you can in HTML tables. Nor can you generate variable sized rows and columns to best fit the array of images being generated.

If you really need this sort of ability you will need to develop your own montage type of application. If you do develop something, then please contribute, and we'll see about merging it into the existing montage application.

Some solutions for this includes labeling and framing the image thumbnails yourself and then using either Append Images or use a more free form Mosaic of Images with your own image positioning calculations.

For one such example see Layered Polaroid Photos


More Montage Settings

The "montage" settings I have shown above are only the basic controls for montage. Their are a lot of other settings you may like to consider for your own needs.

Montage Color Settings

-background The color outside the drawn frame. Often this is set to the 'none' or 'transparent', for use on web pages.
-bordercolor   The fill color inside the frame for images that do not fill that frame completely. It is also used around unframed transparent images.
-mattecolor The color used as the frame color. Note that the color is also made lighter and darker to give the frame a beveled 3D look. So this setting really defines 5 colors. (See also Framing Images)
-fill The color to use for text labels and titles within montage.
-stroke The border color around the outside of text labels.

Montage Control Settings

-tile {cols}x{rows}
The number of images across and down to fill a single montage image. If more images were read in or created than fits in a single montage image, then multiple images will be created. (See Tile Controls above)
-title {string}
Set a title over the whole montage, using the same font (but larger) as that used to label the individual images.
-frame {width}
Create a frame around the box containing the image, using the width provided (must be at least 2, but 5 or 6 is a good value)
-shadow
Generate a shadow of the frame. Note that no argument is required or expected, even though that is what is indicated in the manuals.
-texture {filename}
Use a texture for the background instead of a specific color. (See Background and Transparency below)
-geometry {W}x{H}+{X}+{Y}
Resize images after they have all been read in before montage overlays them onto its canvas. It also defines the size and the spacing between the tiles into which the images are drawn. If no size is specified the images will not be resized.
-compose
The alpha composition setting "-compose" defines how images are to be overlaid onto frame cells and shadows. It does not however effect how that result is then overlaid onto the background canvas of the montage. For more detail see Background and Transparency montage examples below
-gravity {direction}
if the image is smaller than the frame, where in the frame to place the image. By default it is centered.

Added to the above settings, is the settings that the "label:" image creation operator would understand (See Label Image Generator). These settings are used for the creation of labels added underneath the displayed image.

These include settings such as "-font", "-pointsize" (ignored for "-title"), "-fill", "-stroke", and "-strokewidth".

As long as any or all of the above setting are defined or reset, before the final 'output filename' argument, montage will use them as you have requested.

Re-Using Settings for Image Read/Creation

Note however that many of these options are also used for other purposes, in either the generation of images or during image processing. But thanks to the 'do things as you see them' command line handling on IM v6, this presents no problem to the "montage" command.

That means you are free to use any of these option settings to read, create, or modify the images being read in, then reset those settings after all the images have been read in or created. The final setting value will be what montage will use for its final processing.

This was not the case in versions of IM before version 6, in which it was generally impossible to separate image creation settings, from montage settings, without generating intermediate images (such as in the Image Labels example above).

Here is a practical example of setting reuse. I wanted to make a table of some of the fonts I have been using in these example pages, then reset the settings, to other values for the final processing of the images by montage.

  montage -pointsize 24  -background Lavender \
          -font Candice      -label Candice      label:Abc-123 \
          -font Corsiva      -label Corsiva      label:Abc-123 \
          -font SheerBeauty  -label SheerBeauty  label:Abc-123 \
          -font Ravie        -label Ravie        label:Abc-123 \
          -font Arial        -label Arial        label:Abc-123 \
          -font ArialI       -label ArialI       label:Abc-123 \
          -font ArialB       -label ArialB       label:Abc-123 \
          -font ArialBk      -label ArialBk      label:Abc-123 \
          -font CourierNew   -label CourierNew   label:Abc-123 \
          -font LokiCola     -label LokiCola     label:Abc-123 \
          -font Gecko        -label Gecko        label:Abc-123 \
          -font Wedgie       -label Wedgie       label:Abc-123 \
          -font WebDings     -label WebDings     label:Abc-123 \
          -font WingDings    -label WingDings    label:Abc-123 \
          -font WingDings2   -label WingDings2   label:Abc-123 \
          -font Zymbols      -label Zymbols      label:Abc-123 \
          \
          -frame 5  -geometry +2+2   -font Arial -pointsize 12 \
          -background none  -bordercolor SkyBlue  -mattecolor DodgerBlue \
          montage_fonts.gif
[IM Output]
Note the two stages to the "montage" command. Which I clearly marked using a extra almost empty line.

The first part is essentially exactly as you would define multiple images using the normal IM "convert" command, and is processed in the same, 'do it as you see it' order.

The second part, defines all the settings I wanted the "montage" command itself to use. That is the framing, image resizing, fonts and colors I wanted to use in the final montage image. I especially take care to reset the "-font" and "-pointsize" settings for the labeling underneath the montaged images.

While you can separate the options of "montage" like this, you can actually define the montage settings at any time on the command line. As long as those settings do not interfere with your image creating and processing options, and are still defined correctly when the end of the command line is reached, "montage" will use them.

ASIDE: You may like to look at the shell script I wrote to do something similar to the above (and which works with earlier versions of montage) to display a directory truetype (.ttf) fonts called "show_fonts". Another shell script example is "show_colors".

Montage vs Convert Option Differences

Now while "montage" generally allow you to use any "convert" settings and operators in reading and processing its input images, their are a few differences which need to be highlighted.

These "convert" operators and settings are different when used within "montage".

-tile
In "convert" the "-tile" setting defines a image to use as a texture instead of using the "-fill" color. In "montage" it defines how to layout the individual image cell 'tiles'.
-frame
In "convert" this is an operator used to add a 3D frame border around images, and requires 4 arguments to work correctly (See Convert Frame examples). In "montage" a single number is given defining the thickness of the frame around the image cell as defined by the "-geometry" resize setting.
-shadow
The "-shadow" option in "convert" takes an argument which is used to create a soft blurry shadow to which can be place under a second copy of the original image. However in "montage" this is only a Boolean setting that just turns the rectangular shadowing abilities, on and off.

If you really need to use the "convert" form of these options, then you will need to pre-process your images using "convert" before passing them to "montage".

One method using intermediate files was demonstrated in the Image Labels example above.

Another is to just do your processing in "convert" and just pipe the resulting multiple images into "montage". This separation is easy to do if you always do your image input handling first, then set the "montage" specific settings afterward, such as I have done in all these examples. Especially as shown in the last previous font example above.

For example lets frame our images using the "convert" frame, and then frame them again using the "montage" labeled frames.

  convert -label %f   balloon.gif medical.gif present.gif shading.gif \
          -mattecolor peru  -frame 10x5+3+0    miff:-  |\
     montage  -   -tile x1  -frame 5  -geometry '64x56+5+5>' double_frame.jpg
[IM Output]

You can also see the extra arguments required by the "convert" form of the "-frame" operator.


Indexes of Image Directories

HTML Thumbnail Image Maps

Montage is especially designed for generating thumbnail maps of images.

For example here I have created a photo index of the original source images (JPEG and PNG) used for digital photos processing throughout IM Examples. Click an image on the index page to view it.

  montage -label '%t\n%[width]x%[height]' \
          -size 512x512 '../photo_store/*_orig.*[120x90]' \
          -geometry +5+5 -tile 5x  -frame 5  -shadow  photo_index.html
[IM Output]
IM Examples
Photo Store

Note the use of '%[width]x%[height]' instead of just '%wx%h'. This is important as the image is being resized as it is read in. The former will label the images with their original pixel size as it is on disk, while the latter will use the current resized size of the image. This is something that is easilly overlooked by users.

The result of this command were three files...
photo_index.png The montage of all thumbnails of the images
photo_index_map.shtml An HTML 'image map' for the thumbnail image
photo_index.html The HTML thumbnail index page for the World Wide Web.
This also includes a copy of the previous image map.

Of course you don't have to generate an HTML index file if you only want an index image. In that case just replace "INDEX.html" in the command above with the image you want to generate.

Note the use of the Image Property Escape '%t' for the image "-label". This is the filename of the image without any 'path' components. Though the HTML link will still contain the appropriate 'path' components allowing you to build the index image in a different directory to the images themselves.

The source images "'*_orig.*'" in the above examples is quoted, so the "montage" command does the expansion of '*' itself, and not the command line shell. This avoids any command line length limits that you may have problems with. Also I do some initial resizing of images '[120x190]' as I read them (see Read Image Modifiers).

For JPEG images I also specified a smaller "-size" setting so the JPEG library can do some very rough initial scaling, and not read the whole image into memory. If this is not done, then very large JPEG images could use up an enormous amount of memory and CPU cycles when there is no real need. I also "-strip" any profiles that the images may have. For more info see Profiles, Stripping, and JPEG Handling and Reading JPEG Images.

Remember the montage "-geometry" option can also specify a final resize setting, though in this case it is isn't needed as I did it during the read process, so I don't set any 'size' in that setting.

Finally the "-tile" option of '5x' is used to ensure all images appear in a single image, otherwise "montage could generate a multi-page HTML files, which are not correctly linked together. This will hopefully change, though HTML generation is not a primary goal of ImageMagick.

For other ways of generating thumbnails and HTML index pages, read the Thumbnail Examples Page.

Smaller HTML Index Maps, using JPEG images

The above index image generated a PNG format index image. This was used because it is a non-lossy format, which can be important when the images being indexed are of wildly different colors. It also enables the use of the new 'soft shadows' features of montage if the background color is set to 'transparent' or 'none'.

Very very old IM's will have generated a GIF image for the above. However This has some heavy color reduction on the results as part of the formats limitations. It also did not allow the use of semi-transparent 'soft shadows' as PNG allows.

JPEG also does not allow semi-transparency, but that is not a problem if you do not use a transparent background for the image. It is however a lot smaller than PNG, whcih provides a way to drastically reduce the size of the index image, especially for web use, and still handle a large range of colors.

However HTML output above only generates PNG format images, so you will need to not only convert the PNG to JPEG, but also some extra processing to fix the HTML file.

  montage -label '%t\n%[width]x%[height]' \
          -size 512x512 '../photo_store/*_orig.*[120x90]' \
          -geometry +5+5 -tile 5x  -frame 5  -shadow  photo_jpeg.html
  convert photo_jpeg.png photo_jpeg.jpg
  perl -i -lpe 's/src="photo_jpeg.png"/src="photo_jpeg.jpg"/' photo_jpeg.html
  rm -f  photo_jpeg.png  photo_jpeg_map.shtml
[IM Output]
IM Examples
Photo Store

The above commands are rather tricky so here is what happens...

And hey presto, we have a Thumbnail index using a very small JPEG image for the thumbnail index image.

Here are a comparison the file sizes of the thumbnail index image...
[IM Text]

That is the image used for the index is only about 15% of the size of the original PNG image. A big saving for a downloadable web page of thumbnails!

You can make the JPEG image even smaller by using a smaller "-quality" setting, though the default setting produces a very reasonable result. Other possible options include using "-sampling-factor 2x1" to make it even smaller.

Visual Index Images (a non-montage solution)

An alternative to using montage, is to use a special "visual index" input format...

  convert  'vid:../photo_store/*_orig.*' vid_index.gif
[IM Output]
Visual Index of
Photo Store

And can also generate 'clickable' HTML index files.

  convert  'vid:../photo_store/*_orig.*' vid_index.html
[IM Output]
Visual HTML of
Photo Store

It is obvious that "VID:" uses montage internally to generate the index array. However you do not have the same controls as you do if you had used montage directly.

Note that a VID HTML index creates a PNG format thumbnail image.

A Montage of Polaroid Photos

With the advent of a Complex Polaroid Transform it is now possible to generate quite a different style of montage, and montage indexing.

  montage -size 256x256 '../photo_store/*_orig.*' -thumbnail 128x128 \
          -set caption '%t' -bordercolor AliceBlue -background grey20 \
          +polaroid \
          -set label ''  -background white  -geometry +1+1  -tile 4x \
          polaroid_index.html
[IM Output]
Polaroid
Montage

Note that as I used "+polaroid" to frame and label the images, I needed to resize the image (using "-thumbnail") myself, and make sure the "-background" and image "-label" has been reset before actually creating the "montage" index array.

The Polaroid Transform however tends to blur the text during the addition of the 'curl' to the thumbnail image. However you can improve the overall by generating the polaroid images at a larger size then shrinking the result by 50%. The only drawback is the reduced 'shadow' effect.

  montage -size 400x400  '../photo_store/*_orig.*'  -thumbnail 200x200 \
          -set caption '%t' -bordercolor Lavender -background grey40 \
          -pointsize 9  -density 144x144  +polaroid  -resize 50% \
          -set label ''  -background white  -geometry +1+1  -tile 5x \
          polaroid_index2.html
[IM Output]
Sharper
Polaroid
Montage

This fancy montage, as well as other techniques shown above was used to create a script "generate_index" to generate a montage thumbnail index in the actual "photo_store" directory.

See Photograph Store Index for the results of this script.


Special Notes and Usage of Montage

Overlapped Montage Tiles

In the IM User Forum, during a discussion between, Fred Weinhaus ('fmw42') and 'pooco', it was discovered that if you set the inter-tile space (set in the "-geometry" setting) to a negative number you can actually overlap the tiled areas into which the images are drawn.

For example, here we use a negative horizontal inter-tile spacing, for a single row of images.

  montage null:   font_*.gif   null: \
          -tile x1 -geometry -5+2  montage_overlap.jpg
[IM Output]

Rotating the images will make the overlapping series even more interesting...

  montage null: font_*.gif null: -background none -rotate 30 \
          -background white -tile x1 -geometry -8+2  montage_rot_overlap.jpg
[IM Output]

Note that I needed to add a special "null:", spacing image at the start and end of the row of images so the images do not overflow the canvas, "montage" calculates and generates.

This presents us with some interesting possibilities. For example you could generate a very interesting row of overlapping thumbnails, by making use of the randomly rotated Polaroid Transform.

  montage -size 400x400 null: '../photo_store/*_orig.jpg' null: \
          -thumbnail 200x200 -bordercolor Lavender -background black \
          +polaroid  -resize 30%  -background LightGray  \
          -geometry -10+2  -tile x1    polaroid_overlap.jpg
[IM Output]

This is a very interesting result, though it should actually be classed as a BUG, and this is not the intended purpose of "montage". I also would not expect any HTML image mapping to work correctly, without some fixing by the user.

However a more complex, and user controllable solution for overlapping images is demonstrated using a scripted form of Layer Merging, which is the recommended and more logical solution.

Zero Geometry, caution required

With only a "-geometry" spacing values (no image resizing specified), all montages image frames are set to the same size, so that both the widest and tallest image will fit, without being resized.

This is itself a useful behaviour...

  montage present.gif rose: shading.gif \
          -frame 5  -geometry +1+1   montage_geom_1.jpg
[IM Output]

However a 1 pixel gap was left around and between the image frames.

But if you try to remove those gaps with a "-append" position of "+0+0", you run into a very unusual problem...

  montage present.gif rose: shading.gif \
          -tile x1  -frame 5  -geometry +0+0  montage_geom_0.jpg
[IM Output]

The 'zero geometry' (EG: "-geometry 0x0+0+0" ), has the extra effect of putting montage in a 'concatenation' mode (see below), which is NOT what we were after in the above.

For single images it also does not matter if we use a zero "-append" (and thus concatenation mode). The desired result is what we want, no extra borders. As such a "-geometry +0+0" is fine if you are only using "montage" to add a label to an image.

The concatenation mode will however not be invoked if you specify a non-zero geometry 'size' for your images, even though you used a zero offset. This in turn gives us a tricky solution to our original problem.

What we do a set a geometry image size of "1x1" but also tell IM, never to shrink images (using a "<" character) to this size! In other words, never resize an image ever, just use a zero offset, in a non-zero geometry argument.

  montage present.gif rose: shading.gif \
          -frame 5  -geometry '1x1+0+0<'  montage_geom_1x1.jpg
[IM Output]

This brings up another good rule of thumb...

Always set a non-zero geometry when using montage

Even if it is only the 'fake' geometry such as I used above.

Montage Concatenation Mode

As you saw, montage has a special concatenation mode, which can be used to join images together without any extra spaces just like the "-append" option. I do however recommend you set the "-tile" option appropriately, so as to direct the appending either horizontally, vertically or in an array.

For example here we use a "-tile x1" to append images horizontally.

  montage balloon.gif medical.gif present.gif shading.gif \
          -mode Concatenate  -tile x1  montage_cat.jpg
[IM Output]

But you can also use it to just as easily create an array of images. Preferably images that are the same size, so they fit together properly.

  montage balloon.gif medical.gif present.gif shading.gif \
          -mode Concatenate  -tile 2x2  montage_array.jpg
[IM Output]

When concatenating images of different sizes, the images are concatenated with 'top' vertical alignment, then 'left' horizontal row alignment.

  montage medical.gif rose:       present.gif shading.gif \
          granite:    balloon.gif netscape:   recycle.gif \
          -mode Concatenate  -tile 4x  montage_cat2.jpg
[IM Output]

However vertical alignment goes weird when framing is also added.

  montage medical.gif rose:       present.gif shading.gif \
          granite:    balloon.gif netscape:   recycle.gif \
          -mode Concatenate  -tile 4x  -frame 5  montage_cat3.jpg
[IM Output]

Of course, framing is not really part concatenate mode, so if "-frame" is set before the "-mode" setting, it will be turned off. As such this quirk is not likely to be seen, except by mistake when you accidentally use a 'zero geometry' (see above).

Montage Concatenation to the 'HTML' image indexing format, produces incorrect image maps. basically the resulting image map will be as if the generated montage was a true equally divided 'array' of images, rather than a concatenation of the images in line. In other words it is wrong for lines of 'short' images.

Center Aligned Append of Images

Montage can use use for appending images with centering, without gaps between the images. In this case concatenation mode is not wanted.

For example horizontal appending, with center alignment of the images...

  montage netscape: rose: granite: \
          -background skyblue -geometry +0+0 -tile x1 append_horz.png
[IM Output]

However it only works if the first image has the largest height. It will go wrong if this is not the case.

It can also be used for vertical appending too.

There are other ways to do this type of operation without using "montage", which is detailed in Appending Images. This alternative method may be better suited to your task as you can do it as part of a larger "convert" image operation, all in one command.

FUTURE: Perhaps this should be defined as a special "-mode" for montage.
EG: -mode "Append"

Background and Transparency Handling

By default images are overlaid onto the montage canvas which is created using the "-background" color setting, as you can see here.

  montage font_9.gif  \( recycle.gif -set label recycle \)  medical.gif \
          -tile x1  -geometry +5+5  -background lightblue   bg_lightblue.gif
[IM Output]

Instead of a solid color, you can instead use "-texture" to define a tile image to use instead of the "-background" color.

  montage font_9.gif  \( recycle.gif -set label recycle \)  medical.gif \
          -tile x1  -geometry +5+5   -texture bg.gif      bg_texture.gif
[IM Output]

Adding frames (which add extra border space into the tiles) just adds more drawn 'fluff' on top of the background canvas.

  montage font_9.gif  \( recycle.gif -set label recycle \)  medical.gif \
          -tile x1  -frame 5  -geometry '40x40+5+5>' \
          -bordercolor lightblue  -texture bg.gif  bg_frame.gif
[IM Output]

Note that when framed, the "-bordercolor" setting will be used to fill in the inside the frame, effectively becoming the background color of the image. Also notice that any transparent areas of the image are also set to this color.

Before version 6.1.4 of IM, what was seen in the transparent areas of images was undefined. In some versions you would see through the framed image to the background color or texture. On others you might get black, or white. In still other versions you would be able to see though all the layers and the final image would be transparent where the original image was transparent. Upgrade NOW if this is a problem for you.

Also new to IM version 6.1.4 is the ability to use a special 1 pixel wide frame. This will basically remove the frame around the image cells completely, but retaining the internal "-bordercolor" padding around (and underneath) the image. For example compare a frame of '1' with the minimal frame width of '2'.

  montage font_1.gif  \( recycle.gif -set label recycle \)  medical.gif \
          -tile x1  -frame 1  -geometry '40x40+5+5>' \
          -bordercolor lightblue  -texture bg.gif  bg_frame_1.gif
[IM Output]

  montage font_2.gif  \( recycle.gif -set label recycle \)  medical.gif \
          -tile x1  -frame 2  -geometry '40x40+5+5>' \
          -bordercolor lightblue  -texture bg.gif  bg_frame_2.gif
[IM Output]

Also resolved at this time was the ability to use the various Alpha Composition methods to determine just how an image, (with or without transparent areas) is handled by montage, and a "-frame" is used with the image. As usual the last "-compose" setting defined in "montage", specifies how the image is overlaid onto the framing background of the image cell.

For example, lets use 'Copy" to preserve the images transparency when it is framed, allowing the montage canvas to show through.

  montage font_9.gif  recycle.gif  medical.gif   -matte \
          -tile x1 -frame 5 -geometry '40x40+5+5>' -bordercolor LimeGreen \
          -compose copy  -texture bg.gif   bg_compose_copy.gif
[IM Output]

Other interesting combinations include using 'DstOut'...

  montage font_9.gif  recycle.gif  medical.gif   -matte \
          -tile x1 -frame 5 -geometry '40x40+5+5>' -bordercolor LimeGreen \
          -compose DstOut  -texture bg.gif   bg_compose_dstout.gif
[IM Output]

Or its inverse 'DstIn'...

  montage font_9.gif  recycle.gif  medical.gif   -matte \
          -tile x1 -frame 5 -geometry '40x40+5+5>' -bordercolor LimeGreen \
          -compose DstIn  -texture bg.gif   bg_compose_dstin.gif
[IM Output]

For more examples of using the "-compose" setting with "-frame", see the Frame Compose examples.

But what if you want your montage to have a transparent background? Particularly if you plan to use it on a web page containing a texture mapping.

Simple, just use a "-background" color of 'None' or 'Transparent', without any "-texture" image to override that setting.

For example here we generated a transparent montage. Note that "-geometry" is still used to add space around and between the images.

  montage font_9.gif  recycle.gif  medical.gif \
          -tile x1  -geometry +2+2  -background none   bg_none.gif
[IM Output]

Of course if you also use "-frame", you need to make the "-bordercolor" transparent too.

  montage font_9.gif  recycle.gif  medical.gif \
          -tile x1 -frame 5 -geometry '40x40+5+5>' \
          -bordercolor none  -background none    bg_framed_trans.gif
[IM Output]

Note that the montage "-shadow" option is completely unaffected by all the above. it is applied according to the final transparent shape of the cells, before it is overlaid onto the background color or texture.

  montage font_9.gif  recycle.gif  medical.gif \
          -tile x1  -shadow  -geometry '40x40+5+5>' \
          -texture bg.gif  bg_shadow.gif
[IM Output]


  montage font_9.gif  recycle.gif  medical.gif \
          -tile x1 -frame 5 -shadow  -geometry '40x40+5+5>' \
          -bordercolor none   -texture bg.gif  bg_shadow_framed.gif
[IM Output]




Any suggestions, ideas, or other examples of using "montage" are of course always welcome. Just as it is for any part of these example pages.


Montage Image Output Size

The mathematics of montage is straight forward...

Basically the montage width should be....
   (geometry_size + 2*frame_size) * images_per_row
         +  geometry_offset * (images_per_row  + 1)

The height is similar but with extra spacing for labels and the
optional montage title, both of whcih are much more difficult to calculate.

Created: 3 January 2004
Updated: 6 December 2006
Author: Anthony Thyssen, <A.Thyssen@griffith.edu.au>
Examples Generated with: [version image]
URL: http://www.imagemagick.org/Usage/montage/

a