|
如果直接使用im4java,在windows xp可能会出现问题,见使用im4java生成gif的缩略图。跟踪了一下im4java的源代码,未发现有针对linux的特殊设置。问题可能出在环境变量或者shell与windows命令行(cmd)之间的不同上。
直接测试了一下自己起进程运行imagemagick的convert命令:
public static void main(String[] args) {
ProcessBuilder processBuilder = new ProcessBuilder("convert", "1.gif",
"-resize", "64x64", "2.gif");
System.out.println(processBuilder.environment());
try {
Process process = processBuilder.start();
process.waitFor();
System.out.println(process.exitValue());
InputStream stream = process.getErrorStream();
BufferedReader reader = new BufferedReader(new InputStreamReader(stream));
for(String s=reader.readLine();s!=null;s=reader.readLine()){
System.out.println(s);
}
} catch (Exception e) {
e.printStackTrace();
出现的问题和调用im4java的一样:
无效参数 – -resize
应该是进程调用了windows的转换分区命令convert.exe。而不是imagemagick的convert命令。
如果这样调用,则问题解决:
ProcessBuilder processBuilder = new ProcessBuilder(“cmd.exe”, “/C”,”convert”, “1.gif”,
“-resize”, “64×64″, “2.gif”);
问题是怎么将这个代码增加到im4java中去,而又尽量做到:
不改变im4java的代码;
在windows下和linux下通用;
便于部署。
最终考虑的是通过反射来实现这个功能,获取到im4java的命令List,在List的头部增加两个字符串元素:cmd和/C。
然后封装成一个继承ConvertCmd的类,供程序调用:
import java.lang.reflect.Field;
import java.util.Arrays;
import java.util.List;
import org.im4java.core.ConvertCmd;
public class ForWinConvertCmd extends ConvertCmd {
public ForWinConvertCmd() {
super();
this.initForWin();
}
public ForWinConvertCmd(boolean useGM) {
super(useGM);
this.initForWin();
}
@SuppressWarnings("unchecked")
protected void initForWin() {
if (System.getProperty("os.name").startsWith("Windows")) {
try {
Field field = this.getClass().getSuperclass().getSuperclass()
.getDeclaredField("iCommands");
field.setAccessible(true);
List<String> value = (List<String>) field.get(this);
value.addAll(0, Arrays.asList(new String[]{"cmd","/C"}));
} catch (Exception e) {
throw new RuntimeException(e);
}
}
}
}*注意 环境变量Path里面的imagemagic需要配置在系统环境变量前面 否则会调用windows的convert.exe |
|