Monthly Archives: October 2009

ImageMagick “convert: Non-conforming drawing primitive definition `image” problem

ImageMagick is the great set of image processing utilities. But there are some problems to interact with it from your programs (java program in my case). About one of them I would like to talk. In one of our latest projects we used ImageMagick to resize images and put a watermark on them. Everything was fine on developers machines with OS Windows, but when we put project on Unix server… Agrrr. WTF?! We got this error: “convert: Non-conforming drawing primitive definition `image”. Magic… ImageMagick! Here is the best article that I have founded about this problem. It doesn’t help me ’cause it describes a little different problem, but it may be helpful for you) Ok, let us see the code that throws the error (in this example I removed resize parameter ’cause it works fine and the problem only in draw):

public void convertImage() {
    // List of commands that we want to execute
    List commands = new ArrayList();
 
    // Executable file
    commands.add("convert");
 
    // Executable file parameters
    commands.add("-gravity");
    commands.add("South-East");
    commands.add("-draw");
    commands.add(""image Over 0,0 0,0 'im-watermark.png'"");
    commands.add("im-image.png");
    commands.add("im-new.png");
 
    try {
        // I also tried to use Runtime.getRuntime().exec(...), but got the same result and it doesn't wonder
        // 'cause it use ProcessBuilder
        ProcessBuilder processBuilder = new ProcessBuilder();
        processBuilder.command(commands);
        Process process = processBuilder.start();
 
        BufferedReader error = new BufferedReader(new InputStreamReader(process.getErrorStream()));
 
        // Check if we have an error...
        if (error.ready()) {
            // ...then print them
            String line;
 
            while ((line = error.readLine()) != null) {
                System.out.println("error: " + line);
            }
        }
    } catch (IOException e) {
        e.printStackTrace();
    }
}

The process builder that we use in our code example must generate such command:

convert -gravity South-East -draw "image Over 0,0 0,0 'im-watermark.png'" im-image.png im-new.jpeg

Looks correct, but doesn’t work. Ok, let’s try to run this command from Unix shell. I can’t belive it! It works! In shell, but not from our program( I think that something happens with convert command parameters when JVM run it or may be it is some kind of Unix feature. I don’t know. So, I did this trick:

  1. create shell script “im-convert-proxy.sh” (don’t forget to execute “chmod +x im-convert-proxy.sh” command. It allows you to execute this script) with code:

    eval 'convert '$@

    How you can see it just runs convert command with all parmeters that we passed to script from our java program.

  2. replace executable file from “convert” to “im-convert-proxy.sh”:

    commands.add("im-convert-proxy.sh"); // was commands.add("convert");

That’s all! Everything works, everyone is happy)

P.S.: if you have found a better solution, please write me.

Backup мобильника

После знакомство со статьёй “Это сделает вас мобильнее” моё внимание привлёк сервис “Mobical“, который судя по описанию, позволял сохранить информацию с мобильного телефона. Заманчиво, подумал я, и полез смотреть: чего же там есть? Перво-наперво заглянул в раздел “Certified devices”, где без труда нашёл свой телефон. Уже неплохо, можно двигаться дальше. Смотрим раздел “What you need” и видим, что для того, чтобы успешно воспользоваться сервисом необходимо:

  1. мобильный с клиентом SyncML (первый раз узнал, что такой вообще есть, но раз телефон сертифицирован, значит, эта штука в нём есть);
  2. чтобы в телефоне было настроено Интернет подключение (благо у меня это уже было сделано).

Идём в регистрацию и заполняем несложную форму. Однако, так как я честно указал в качестве города Москву (ибо ничего ближе не было), после отправки формы получил сообщение, что мол, извините, но мы с такими странами не сотрудничаем) Не сотрудничаете, так и фиг с вами. Выбираем “US” и всё идёт как по маслу.

Настраиваем свой телефон для синхронизации с помощью простого мастера и вуаля — все данные с телефона (разумеется, которые телефон в состоянии отдать) доступны on-line, и их всегда можно синхронизировать. Имхо, весьма удобно.

mobical-1 mobical-2