M primary goal is to take in a series of .eps files and convert them to .jpg using ImageMagick and GhostScript. I have both ImageMagick and GhostScript installed in a Windows environment. I am referencing ImageMagick's convert command using Process in java with no luck. Using Window's cmd tool, I successfully converted an EPS to JPEG by navigating to C:\Program Files\ImageMagick-6.8.9-Q16 and using the following command:
convert Raw\R_GiftcardSizeNew3x5.eps Converted\R_GiftcardSizeNew3x5.jpg
In Java, I use almost the exact same command in the following code:
public void convertEPStoJPG()
{ //commands
ArrayList<String> cmds = new ArrayList<String>();
//absolute file paths of eps files retrieved using a helper method
ArrayList<String> filePaths = this.getFilePaths();
//beginning cmd line calls
cmds.add("cmd.exe");
cmds.add("/c");
cmds.add("cd C:\\Program Files\\ImageMagick-6.8.9-Q16\\");
for (int i = 0; i < filePaths.size(); i++)
{
//conversion calls
String tempPath = filePaths.get(i);
//shortening path name
tempPath = tempPath.substring(tempPath.lastIndexOf("\\") + 1, tempPath.length());
//adding command of "convert Raw\\image.eps Converted\\image.jpg"
cmds.add("convert \\Naked Wines\\Raw\\" + tempPath + " \\Naked Wines\\Converted\\" +
tempPath.substring(0,tempPath.length() - 3) + "jpg");
}
//building process with commands
ProcessBuilder pb = new ProcessBuilder(cmds);
Process process;
try {
pb.redirectErrorStream(true);
//executing commands
process = pb.start();
BufferedReader r = new BufferedReader(new InputStreamReader(process.getInputStream()));
String line;
while (true) {
line = r.readLine();
if (line == null) { break; }
//print output from command execution
System.out.println(line);
}
} catch (Exception e) {
e.printStackTrace();
}
}
where my files im trying to grab are C:\Program Files\ImageMagick-6.8.9-Q16\Naked Wines\Raw
and the destination I am converting to is C:\Program Files\ImageMagick-6.8.9-Q16\Naked Wines\Converted.
I get an error stating "The system cannot find the path specified". Looking at previously answered questions such as How to override Windows' convert command by ImageMagick's one?, people suggest you have to override Windows convert command. Would this be the cause of error, or is there something I am missing? I'm fairly new to ImageMagick and might have missed or misunderstood something.
I ended up approaching this problem in a different way using Im4Java, a pure-java interface to the ImageMagick commandline. I installed the libraries via http://im4java.sourceforge.net/#download. Here is my code for converting eps to jpg:
public void convertESPtoJPG()
{
//initialize ImageMagick operation
IMOperation op = new IMOperation();
//setting my path allows us to use ImageMagicks "convert" vs. Windows "convert"
String myPath="C:\\Program Files\\ImageMagick-6.8.9-Q16";
ProcessStarter.setGlobalSearchPath(myPath);
op.addImage(); //in
op.addImage(); //out
ConvertCmd cmd = new ConvertCmd();
//filter out files for eps files, and load the files using included FilenameLoader
ExtensionFilter filter = new ExtensionFilter("eps");
FilenameLoader loader = new FilenameLoader(filter);
List<String> files = loader.loadFilenames("C:\\Program Files\\ImageMagick-6.8.9-
Q16\\NakedWines\\Raw\\");
//what we plan on converting our eps files to
FilenamePatternResolver resolver = new FilenamePatternResolver("%P/%f.jpg");
//iterate through loaded files
for (String img: files)
{
try {
//execute our convert commands
cmd.run(op,img,resolver.createName(img));
} catch (Exception e) {
e.printStackTrace();
}
}
}
I found this method to be much easier to understand and more forward as well.
Related
I'm trying to make a loop that pass through a folder for files, then the script only takes the files with the extension .wav, so I call an exe with two parameters and converts the audio. Without a loop works, because the command is a String[] variable and I just have to put my parameters in parentheses, but when I tried to make it all dynamic nothing happens, even I tried the normal static version, but the parameters in two separated strings, then I've added those strings to the String[] that contains the command to execute the application and it just doesnt' work. This is the code (With loop):
File dir = new File("moved");
File[] dirlist = dir.listFiles();
for(File f3 : dirlist)
{
if(f3.getName().endsWith(".wav"))
{
String firstnam = f3.getName();
String secondnam = firstnam.replaceFirst(".wav", "_converted.wav")
String[] command = {"cmd", "/c", "AdpcmEncode.exe", firstnam, secondnam};
Runtime rt = Runtime.getRuntime();
Process process = rt.exec(command, null, dir);
}
}
What I need most is to know how to pass these dynamic parameters into the command, if it's posible also know how to change names through audio conversions (the input and output can't be the same).
Well after a research about this, I have finally put my code in a separate class from the main JFrame (That fixed the dynamic parameters, for some reason I don't understand, I have to say that code I had it into another JFrame Class), now because the code is into an IOException, the thing was a little bit complicated, but I realize that it was simple like this:
try{
ConvertAllClass.converter(null);
}catch(IOException e){
//e.printStackTrace();
}
Maybe the null is not necessary, but all works. This is the "test" function (I just wanted to know if converts one audio at least):
public class ConvertAllClass {
public static void converter(String args[]) throws IOException {
File f = new File("C:\\convertion_kit\\bin");
String firstnam = "mx_game_over.wav";
String secondnam = "mx_done.wav";
ProcessBuilder pb = new ProcessBuilder("cmd", "/c","start","AdpcmEncode.exe", firstnam, secondnam );
pb.directory(f);
Process process = pb.start();
}
}
I ran an Octave script through Java's ProcessBuilder and Process classes. I used Netbeans and the Script file is in resources folder of the Project I am doing.
When run from bash directly the script is working fine. When run from Java, I'm pretty sure the script is working fine.
In the below program,
#!/usr/bin/octave -qf
function ret = manipulateCell(x)
x = x/max(x(:));
x = x.*255;
x = int32(x);
a1 = mean(x(:));
ret = a1<70;
end
img = imread('aaa.png');
imgInd = rgb2ind(img);
imgGray = ind2gray(imgInd,colormap());
sizeVector = 100*ones(1,20);
Cells = mat2cell(imgGray,sizeVector,sizeVector);
ManipCells = cellfun(#manipulateCell,Cells);
file2D = fopen('data.txt','rw+');
dlmwrite(file2D,ManipCells);
Last two lines seem not to run from Netbeans; there is no output (i.e., no output file is created).
Java Code which is used to run this script.
ProcessBuilder pb = new ProcessBuilder("src/resources/ProcessImg.m");
try{
Process p = pb.start();
}
catch(IOException ex){
ex.printStackTrace();
}
--
Edit:
I have just tried imshow(img) in between the above code. It didn't work either.
Edit:
How I verified that ProcessBuilder and Process work fine? and How do I know which directory I am in.
String command = "pwd";
ProcessBuilder pb = new ProcessBuilder(command);
//pb.directory(new File("./"));
try{
Process p = pb.start();
//Debug Code
pb.redirectErrorStream(true);
BufferedReader bf = new BufferedReader(new InputStreamReader(p.getInputStream()));
String s;
while((s=bf.readLine())!=null){
System.out.println(s);
}
p.getInputStream().close();
p.getOutputStream().close();
p.getErrorStream().close();
}
catch(IOException ex){
ex.printStackTrace();
}
If the command string is pwd, the output is
/home/user/NetBeansProjects/Project
If the command string is ls, the output is
build
build.xml
manifest.mf
nbproject
src
test
I want to say that commands are being executed.
Also, process builder is identifying shebang notation.
The problem is NetBeans is not allowing ProcessImg.m to create files in it's directory by an external process probably.
#!/usr/bin/octave -qf
function ret = manipulateCell(x)
x = x/max(x(:));
x = x.*255;
x = int32(x);
a1 = mean(x(:));
ret = a1<70;
end
img = imread('~/Desktop/aaa.png');
imgInd = rgb2ind(img);
imgGray = ind2gray(imgInd,colormap());
sizeVector = 100*ones(1,20);
Cells = mat2cell(imgGray,sizeVector,sizeVector);
ManipCells = cellfun(#manipulateCell,Cells);
file2D = fopen('~/Desktop/data.txt','rw+');
dlmwrite(file2D,ManipCells);
I have put absolute path (from home) as suggested and it didn't work. Not only in NetBeans did the file hasn't been created but also on desktop.
I'm pretty sure that "ProcessBuilder" doesn't understand the Shebang in your script (or you haven't set it executable) and you have to call it like
ProcessBuilder pb = new ProcessBuilder("/usr/bin/octave",
"src/resources/ProcessImg.m");
But this looks like a common problem so I suggest searching for "ProcessBuilder execute bash script" (or perl script) which gives many hits.
Also try an absolute path to your script and explicitely close your file on exit.
I am trying to read 2 files after i read the files i want to get their contents and manipulate the contents of the two files then update a new file which is the output. The files are in the same folder as the program but the program always throws a FileNotFoundException.
Below is my code:-
import java.io.*;
import java.util.Scanner;
public class UpdateMaster {
public static void main(String[] args)
{
String master = "Customer.dat";
String trans = "Transactns.dat";
String newMaster = "Temp.txt";
Scanner inputStreamMaster = null;
Scanner inputStreamTrans = null;
PrintWriter inputStreamNewMaster = null;
try
{
inputStreamMaster = new Scanner(new File(master));
inputStreamTrans = new Scanner(new File(trans));
inputStreamNewMaster = new PrintWriter(newMaster);
}
catch(FileNotFoundException e)
{
System.out.println("Error: you opend a file that does not exist.");
System.exit(0);
}
catch(IOException e)
{
System.out.println("Error.");
System.exit(0);
}
do
{
String transLine = inputStreamTrans.nextLine();
String masterLine = inputStreamMaster.nextLine();
String[] transLineArr = transLine.split(",");
String[] masterLineArr = masterLine.split(",");
int trAccNo = Integer.parseInt(transLineArr[0]);
int sales = Integer.parseInt(transLineArr[1]);
int masterAccNo = Integer.parseInt(masterLineArr[0]);
int balance = Integer.parseInt(masterLineArr[1]);
while(masterAccNo== trAccNo){
inputStreamNewMaster.println(trAccNo+ " , "+masterAccNo);
masterLine = inputStreamMaster.nextLine();
masterLineArr = masterLine.split(",");
masterAccNo = Integer.parseInt(masterLineArr[0]);
balance = Integer.parseInt(masterLineArr[1]);
}
balance = balance + sales;
inputStreamNewMaster.println(masterAccNo+ " , "+balance);
}while(inputStreamTrans.hasNextLine());
inputStreamMaster.close();
inputStreamTrans.close();
inputStreamNewMaster.close();
//System.out.println(" the line were written to "+ newMaster);
}
}
Like #Ankit Rustagi said in the comments, you need the full path of the files if you want to keep the current implementation.
However, there is a solution where you only need the file names: use BufferedReader / BufferedWriter. See here an example on how to use these classes (in the example it uses the full path but it works without it too).
Use absolute path
String master = "C:/Data/Customer.dat";
String trans = "C:/Data/Transactns.dat";
String newMaster = "C:/Data/Temp.txt";
The code works for me, i guess you misspelled some filename(s) or your files are in the wrong folder. I created your files on the same level as the src or the project. Also this is the folder where the files are exspected.
There's nothing wrong with using relative paths like tihis. What's happening is that your program is looking for the files in the directory where you execute the program, which doesn't have to be the folder of the program. You can confirm this by logging the absolute path of the files before you try to read them. For example:
File masterFile = new File(master);
System.out.printf("Using master file '%s'%n", masterFile.getAbsolutePath());
inputStreamMaster = new Scanner(masterFile);
In general you should not hardcode file paths but allow the user to specify them in someway, for example using command line arguments, a configuration file with a well known path, or an interactive user interface.
There is a way to locate the program's class file but it's a little tricky because Java allows classes to be loaded from compressed archives that may be located in remote systems. It's better to solve this problem in some other manner.
Try this:
String current = new java.io.File( "." ).getCanonicalPath();
System.out.println("I look for files in:"+current);
To see what directory your program expects to find its input files. If it shows the correct directory, check spelling of filenames. Otherwise, you have a clue as to what's gone wrong.
I am loading a library into my java code.
I have put the library in the sytem 32 folder and I have also set the -Djava.library.path.
Earlier this code was running
try{
System.loadLibrary("resources/TecJNI");
System.out.println("JNI library loaded \n");
}
catch(UnsatisfiedLinkError e){
System.out.println("Did not load library");
e.printStackTrace();
}
but since last week it is showing
java.lang.UnsatisfiedLinkError: no resources/TecJNI in java.library.path.
Is this some file permission issue for the dll that I am loading in the java code OR dll are using by some other application.
Also all other my running applications that were using & loading the same dll in different workspace are not running now.
Could anyone suggest me?
EDIT: I am using -
Djava.library.path="${workspace_loc}/org.syntec.ivb.application/resources;${env_var:PATH}"
in my eclipse vm arguments. I think it is using this.
when comes to load libs in jvm, I like to copy the libs to a temp directory, then load them from the temp directory. here is the code:
private synchronized static void loadLib(String dllPath,String libName) throws IOException {
String osArch = System.getProperty("os.arch").contains("64")?"_X64":"_X86";
String systemType = System.getProperty("os.name");
String libExtension = (systemType.toLowerCase().indexOf("win") != -1) ? ".dll"
: ".so";
String libFullName = libName+osArch+ libExtension;
String nativeTempDir = System.getProperty("java.io.tmpdir");
InputStream in = null;
BufferedInputStream reader = null;
FileOutputStream writer = null;
File extractedLibFile = new File(nativeTempDir + File.separator
+ libFullName);
if (!extractedLibFile.exists()) {
try {
in = new FileInputStream(dllPath+ File.separator+
libFullName);
reader = new BufferedInputStream(in);
writer = new FileOutputStream(extractedLibFile);
byte[] buffer = new byte[1024];
while (reader.read(buffer) > 0) {
writer.write(buffer);
buffer = new byte[1024];
}
} catch (IOException e) {
e.printStackTrace();
} finally {
if (in != null)
in.close();
if (writer != null)
writer.close();
}
}
System.load(extractedLibFile.toString());
}
System.loadLibrary expects library name, not a path. The path to the directory containg the library should be set in PATH (Windows) env variable or in -Djava.library.path
Why do you need the additional "resources"?
When using System.loadLibrary("resources/TecJNI"); you are looking for TecJNI.dll in a subfolder "resources" of the java.library.path. So if you put C:\windows\system32 on the library-path (which you wouldn't need since it's on the search-path by default) your library should be C:\windows\system32\resources\TecJNI.dll
I'm trying to make the program to read QR codes, however when my code runs I am getting an exception javax.imageio.IIOException: Can't read input file. The image is in the src directory. Could someone please help me to find the problem in my code...
public class BarcodeSample {
public static void main(String[] args) {
Reader reader = new MultiFormatReader();
try {
BufferedImage image = ImageIO.read(new File("src/img.png"));
LuminanceSource source = new BufferedImageLuminanceSource(image);
BinaryBitmap bitmap = new BinaryBitmap(new HybridBinarizer(source));
Result result = reader.decode(bitmap);
BarcodeFormat format = result.getBarcodeFormat();
String text = result.getText();
ResultPoint[] points = result.getResultPoints();
for (int i=0; i < points.length; i++) {
System.out.println(" Point[" + i + "] = " + points[i]);
}
} catch (Exception ex) {
ex.printStackTrace();
}
}
}
First, use File.separator instead of '/' as it places the right separator according to the OS it is running on.
Now the problem is with src/img.png. I suggest you put your images outside the src directory as this directory is used for code (not a must).
I do not know on which IDE you run it but make sure your workspace current directory is set to your project root directory so src/img.png will be found (assuming src is under you root current directory), otherwise you will get the file not found exception