Safe and consistent vector to raster conversion

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
hakunin
Posts: 13
Joined: 2013-05-15T12:05:55-07:00
Authentication code: 6789

Safe and consistent vector to raster conversion

Post by hakunin »

Imagine a use case where customers upload vector images (eps, pdf, svg, etc) and you need to automatically convert them to high quality raster images. Problem is — those uploaded images could have missing or bad width/height info. So if you simply convert foo.eps foo.png you may end up with a tiny resolution image that looks bad. So what I did was — for any uploaded vector image I added -density 300, which resulted in something like:

Code: Select all

convert -density 300 foo.eps -resize "10000x10000>" foo.png
The 10x10k is a safety limit, but we do want resulting images as big as reasonably possible for print.

Then one day somebody uploaded a 64kb .eps file that had resolution identified as 5000x7000. This crashed the server, because (if I understand correctly) it tried to blow up a 5x7k image 300 times in memory. This is what I mean by "safe" - this shouldn't happen. So adding -density 300 makes most vectors look good, but some could crash the server. Removing -density 300 makes most vectors look bad - they become tiny PNGs, but server doesn't die. Hence the question:

Could you recommend a safe, consistent way to do this? It's ok if some vectors can be identified "broken" - we can show error to the customer. As long as there is a way. It's also ok to guess things. After image is uploaded we first "identify" it, which means we can write code to react to whatever it discovered.

Appreciate any advice!
User avatar
fmw42
Posts: 25562
Joined: 2007-07-02T17:14:51-07:00
Authentication code: 1152
Location: Sunnyvale, California, USA

Re: Safe and consistent vector to raster conversion

Post by fmw42 »

Extract the width and height and x and y density before trying to process the image.

see string formats http://www.imagemagick.org/script/escape.php

identify -ping -format "%wx%h %xx%y" yourimage
hakunin
Posts: 13
Joined: 2013-05-15T12:05:55-07:00
Authentication code: 6789

Re: Safe and consistent vector to raster conversion

Post by hakunin »

Fred,

What do I do after I discover these values? As I mentioned, width, height, and density are not always set (correctly) in vector images, so I could end up getting default density of 72 and no WxH.
User avatar
fmw42
Posts: 25562
Joined: 2007-07-02T17:14:51-07:00
Authentication code: 1152
Location: Sunnyvale, California, USA

Re: Safe and consistent vector to raster conversion

Post by fmw42 »

hakunin wrote:Fred,

What do I do after I discover these values? As I mentioned, width, height, and density are not always set (correctly) in vector images, so I could end up getting default density of 72 and no WxH.
Best I can suggest is to test for known types of issue, such as the one you mentioned.
hakunin
Posts: 13
Joined: 2013-05-15T12:05:55-07:00
Authentication code: 6789

Re: Safe and consistent vector to raster conversion

Post by hakunin »

Best I can suggest is to test for known types of issue, such as the one you mentioned.
This is understood. However, I need to figure out the next step. Let's say I get 5000x7000 EPS file showing 72 (default) density. By which logic should I proceed making it a reasonable PNG file? Should I use -resample? Some combination of -density and -resize? Should I load it with certain density (based on its resolution?), and then convert to different density? I am confused about this interplay between density, resolution, and resampling, and was hoping for some pointers for handling different scenarios.
snibgo
Posts: 12159
Joined: 2010-01-23T23:01:33-07:00
Authentication code: 1151
Location: England, UK

Re: Safe and consistent vector to raster conversion

Post by snibgo »

Code: Select all

identify -density 300 -format "%w %h" x.eps
This seems to return whatever pixel dimensions convert would create at the given density. If this is too small, increase the density. If too large, decrease it.

If this trick fails on a file, please post that file, or at least the "identify -verbose".
snibgo's IM pages: im.snibgo.com
User avatar
fmw42
Posts: 25562
Joined: 2007-07-02T17:14:51-07:00
Authentication code: 1152
Location: Sunnyvale, California, USA

Re: Safe and consistent vector to raster conversion

Post by fmw42 »

Personally, I never use -resample. I like the flexibility to use -resize or -distort resize or -thumbnail (with the choices of filters) or just scale if appropriate and then I set the density and units afterwards. I have more control over the process. I guess I do not understand well enough how -resample works to trust it.
hakunin
Posts: 13
Joined: 2013-05-15T12:05:55-07:00
Authentication code: 6789

Re: Safe and consistent vector to raster conversion

Post by hakunin »

snibgo wrote:

Code: Select all

identify -density 300 -format "%w %h" x.eps
This seems to return whatever pixel dimensions convert would create at the given density. If this is too small, increase the density. If too large, decrease it.

If this trick fails on a file, please post that file, or at least the "identify -verbose".
Interesting, when running this on my problematic eps file, this causes the same thing to happen as when running actual convert — as in — takes up all the resources and renders machine unresponsive for indefinite time.

This gives me an idea though, I can easily tell what would the result be by running with as small density as possible, like

Code: Select all

identify -density 2 -format "%w %h" x.eps
and simply multiplying the result.
User avatar
fmw42
Posts: 25562
Joined: 2007-07-02T17:14:51-07:00
Authentication code: 1152
Location: Sunnyvale, California, USA

Re: Safe and consistent vector to raster conversion

Post by fmw42 »

try adding -ping. does that make it faster

Code: Select all

identify -ping -density 300 -format "%w %h" x.eps
hakunin
Posts: 13
Joined: 2013-05-15T12:05:55-07:00
Authentication code: 6789

Re: Safe and consistent vector to raster conversion

Post by hakunin »

fmw42 wrote:try adding -ping. does that make it faster

Code: Select all

identify -ping -density 300 -format "%w %h" x.eps
Just tried this and it didn't seem to help. Looks like identify actually creates the images according to arguments in order to extract the information.
User avatar
fmw42
Posts: 25562
Joined: 2007-07-02T17:14:51-07:00
Authentication code: 1152
Location: Sunnyvale, California, USA

Re: Safe and consistent vector to raster conversion

Post by fmw42 »

Yes, I guess that is because it is a vector file. With raster files, -ping would just read the header for size information. Sorry.
hakunin
Posts: 13
Joined: 2013-05-15T12:05:55-07:00
Authentication code: 6789

Re: Safe and consistent vector to raster conversion

Post by hakunin »

For those who might find this thread, here's my solution that's been working well so far.

Vector images don't have density, so trying to identify their density is useless, it will just waste time and return 72. What you do need, is to identify their width and height, and you can just assume it's at 72 density. All I ended up doing is as follows:

If uploaded image is found to be a vector image (based on content_type):
  1. Identify its width/height
  2. If either width or height doesn't exist, make them 500, because this should never happen, and vector is broken anyway, so who cares
  3. Take the bigger of source width/height from #2 and the bigger of destination width/height, lets call them bigger_src_dim, bigger_dst_dim
  4. density = (bigger_dst_dim / (bigger_src_dim / 72.0)) + 5
    (+5 is here because we want vector image to be slightly bigger in memory than our desired raster size, for better detail)
  5. Round down the result and use it to load vector image, e.g. convert -density 91 foo.eps -resize "600x600>" bar.png
Hope this helps someone.
Post Reply