MATLAB Spoken Here

Calling Java from MATLAB 60

Posted by Michael Katz,

So far no one has taken me up on the extra credit from the Interactive Web Pages post. I thought the problem of displaying a figure without an image file was too interesting to pass up, so I figured out the solution myself and put it up on the file exchange. The second challenge involving ActiveX will remain open until I get chance to write up its solution. Or, if you don't have the time to do that, you can still win a t-shirt by sending us your desktop.

My solution to the image challenge involves encoding binary information from an image file as text through the base64 scheme. At first I thought to implement the base64 algorithm myself in MATLAB, but I learned my lesson the hard way a few years ago writing my own md5 hash-computing program (don't ask). This time I wanted to use a readily-available solution. Since there is no toolbox function for this, I decided to take advantage of a Java library since (a) I could use the same library on every platform (instead of needing a different pre-compiled binary) and (b) I am pretty comfortable with Java. My solution takes advantage of the freely available Apache Commons Codec package.

Using Java from a MATLAB program is as simple as using a MATLAB function, particularly if you are used to using MATLAB package functions. You can use any public method in the Java SE API from the command line. The running version of the JRE depends on your version of MATLAB and operating system and determines what API functionality is available from MATLAB. To determine the Java version use the command version('-java'). To change the Java version (not recommended) you can follow these instructions.

For instance instead of MATLAB's str2num you could use: Double's parseDouble.

str2num('2.3')
java.lang.Double.parseDouble('2.3')
ans =

    2.3000


ans =

    2.3000

Of course, this is a trivial example. Many of our functions such as xmlread make use of more complicated series of calls to java objects. The payoff in the sendmail function comes at the end using the Transport object to send a pre-constructed MimeMessage.

javax.mail.Transport.send(msg)

My base64 program does not use a class from the standard JRE (in fact, neither does sendmail) but instead uses a third party library (Apache Commons Codec) that I happen to know ships with MATLAB and is already available on the classpath.

encoder = org.apache.commons.codec.binary.Base64;
base64string = char(encoder.encode(bytes))';

These examples has three things about using Java that I want to address so you can use other Java libraries in MATLAB: (1) the class path, (2) calling syntax, and (3) data types.

Java Class Path
MATLAB maintains a path for Java classes separate from the search path. That means even if you have a .class or .jar file on the MATLAB path, unless you use javaaddpath you will not be able to use it. To see what is currently on the path use javaclasspath. Running this command you will show you a long list of files that ship with matlab called the Static Class Path and then you'll see the Dynamic Class Path. The dynamic class path is where classes added to the path with javaaddpath will be placed. They can be removed with javarmpath and have to actively reloaded each session of matlab. The static class path comes from $matlabroot\toolbox\local\classpath.txt and are only added to the class path at MATLAB startup. The ones listed here by default are all the Java classes we write (everything in the com.mathworks package). Calling any of these classes directly is not supported and likely to break on a release-to-release basis, but there are resources on the web that make use of these effectively.

Calling Java Functions
Once you add a class to the classpath and it shows up in the javaclasspath, you can use it from the Command Line or from a MATLAB-file. To do that you can use the fully-qualified name (e.g. javax.swing.JTable) or like with MATLAB packages, you can use the import statement to just call the class name (e.g. import('javax.swing.*'),JTable ).

Data Types
Looking at my string to double example you'll see that I passed a MATLAB char array to the java function and got back a MATLAB double, even though methodsview('java.lang.Double') shows that parseDouble takes a java.lang.String as its input. MATLAB will automatically convert primitive types when calling Java methods, as well as convert char arrays to java.lang.String objects when used as inputs. As you can see in my base64 example, I have to explicitly convert the java.lang.String returned by encoder.encode() to a MATLAB char array.

Those are the basics of calling Java. In future posts I hope to discuss memory management with Java (a topic of some recent technical support queries) as well as threading issues, as related to GUIs.

60 CommentsOldest to Newest

I think calling java from matlab is one of the most useful capabilities of the whole system. Adding support for all swing components to guide would be simply awesome.

We’re certainly working on a nice, easy way to do this. However there are a several not so nice ways, maybe a future article here…

With the COM external interface one can register a matlab listener for COM events. Is the equivalent possible for Java? I can’t seem to find anything in the help files.

Dora,

It depends on what events you want to listen for. For instance, you can set MATLAB functions as AWT listeners:

f = javax.swing.JFrame;
set(f,'ComponentResizedCallback', @(handle,evt) disp(evt.getSource.getSize));
f.setSize(200,200);
f.show;

I think I will cover this stuff in a future post.

Hi Ken and Mike,

I received a simulation program written by someone and he asked my help to connect his simulation into matlab. SO he can use matlab function to start and stop the simulation.

Since you both are expert, I would like to ask you something about this.

To run the simulation there is a file “main” which is written in Windows NT command script (that’s what written in the file property), and to change the parameters of the simulation, he can write a java-script file and call it via “main” file.

I am not familiar with java, nor with the NT command script, and I can not see what is inside the “main” file. Therefore, do you have any suggestion how to put the “main” file I described above into m-file?
So the “main” file can be run under matlab functions.

sorry if I misaddress this question.
Any response will be appreciated,

best,
-bree

I have a problem in that the Java “JMSL” classes I’m trying to call from MATLAB are commercial and license protected. We have a filebased license and it works from normal java by passing the path to the JVM via the “-D” option.
So I tried to tell the MATLAB JVM where the license file was via the setProperty java method This is how I tried to tell JVM about the file:

javaMethod(‘setProperty’, ‘com.imsl.license.path’, ‘D:\dir1\dir2\license.dat’);
I put this at the top of the m file hoping that
the javaMethod, javaObject and javaArray calls I made
after that would then be satisfied by finding the license.
I get an error that the license server could not be found
Mark

Hi
First of all, thanks for the post, it is really useful. I am trying to develop a Java GUI within Matlab and I want to include the log4j API to control logging or tracing of the application.

I followed the steps how this post says. I put the log4j.jar into classpath.txt and it appeared on the list of .jar files when I executed javaclasspath. After that I called (e.g. javax.log4j.Logger) or (e.g. import(‘javax.log4j.*’), Logger ) but it didn’t work.

So if you could help me I’d appreciate it. If I manage to develop an interesting application including log4j API, I don’t mind to share with everyone.

Kind Regards,
Jose Miguel

Jose,

You need to make sure you are using the right class names and method signatures. Unlike MATLAB, Java is not forgiving when it comes to using the right inputs since it is statically typed.

You can create a log4j object with the following code:

javaaddpath log4j-1.2.15.jar
logger = org.apache.log4j.Logger.getLogger(java.lang.String.class)

See the log4j documentation for more information. We won’t be able to help you use these classes. For help you should post questions in the Apache forums or on the MATLAB newsgroup.

Hi Mike,
I have a problem. I wrote .m file that calls Java classes that are provided to control a hardware. The program is working. But, I would like compile the program so that I can deploy in a different computer. But, the compiled program is not able to execute the commands. The target system has the java classes installed, I updated ‘classpath.txt’ and ‘librarypath.txt’ in the /…/local folder. I tried to find more information on Java code in the .m file and problems with compilation. I appreciate your input.

Sincerely,
Ravi.

@Pavwell,

Your question does not make sense. This article is about using Java classes from MATLAB programs. There are blocks in Simulink that allow you to run MATLAB commands, which you can use these techniques from there, although I doubt the model would compile to C-code.

My problem is : I have mdl simulink scheme with real system. And my task is to use Java to run simulation of this simulink scheme. And because of it and want to do this from m-file because i want to use this m-file by Java Builder to create jar file for web based java application.

Pavwell,
It’s been awhile since I last handled stuff related to the MATLAB Compiler and Java Builder, but I don’t think you can compile and deploy a MATLAB application that runs a Simulink model: See http://www.mathworks.com/products/compiler/compiler_support.html and http://www.mathworks.com/access/helpdesk/help/toolbox/compiler/br2cqa0-20.html.

If you have real-time workshop, you can compile a Simulink model to C code. Then you can package it in a libray and call it through JNI. It’s a bit complicated to do that, though.

What if i would like to call a matlab function from a jar executable outside MATLAB?
Would the same methodology as described in matlab help work?

@Amin,

com.mathworks.* represent Java classes that we’ve built here. These mostly represent the libraries and widgets used by the Desktop and toolboxes, and as such are not considered part of the MATLAB language and are largely documented. Occasionally we mention some of these in technical support solutions as workarounds to bug fixes. Some of the classes are documented for use for xml, web, and database I/O, and a whole bunch are meant for use in with the MATLAB Builder JA product for deploying MATLAB code to work with Java programs.

Im tying to use the Restlet API inside my matlab application.

I have added all the required jar files necessary for my application.(using javaaddpath)(My application is the client which will interact with server).

org.restlet.ext.json-1.1.7.jar
org.json_2.0.0.jar
org.restlet-1.1.7.jar
com.noelios.restlet-1.1.7.jar

I can see all the jar files listed by executing Javaclasspath.

But when i execute my matlab script i get the following error:

??? Java exception occurred:
java.lang.RuntimeException: Unable to fully initialize the Restlet. No Restlet engine available.

But i have written a stand alone client with eclipse with above mentioned jar files. The eclipse standalone application work fine.

Can u pls help why im getting an runtime error with matlab.

Regards
Rashik.T

@Rashik,
It’s hard to say what the issue. The point at where you enter this Java code may require that some additional classes be on the classpath, resources available on the system path, or sockets set up in a certain way.

You might have to start a “Restlet engine” separately and connect to it manually. I don’t think I’ll be able to help you debug this, you may want to try our newsgroup or any forums associated with Restlet.

hi mike

I added above mentioned jar files statically(edited the classpath.txt) instead of doing it dynamically (javaaddpath).
Now im not getting the above error when im executing my script.

Thanks.

Regards
Rashik.T

@Rashik,

Thanks for the update. There is a bit of semantic difference between the static and dynamic path, and I guess the restlet code has some requirements on how its classes are loaded. I am not sure we make any guarantees about this behavior and it’s a bit out of scope for the blog, but it’s a good thing for me to keep in mind. I do have ideas for covering more of MATLAB’s java interface.

@Mike – actually, the problem with the dynamic javaclasspath is not limited to Restlet. Over the years there have been many posted examples of Java classes that fail on the dynamic path and work on the static path (I can send you some links if you wish). As far as I could tell, the problem stems from Matlab’s classloader.

An old MathWorks solutions page (http://www.mathworks.com/support/solutions/en/data/1-1YFUFB/) even said that this is supposed to be the expected behavior – a response I found very odd indeed. Anyway, that webpage has been removed from the public website some months ago, but you can probably access issue #1-1YFUFB using your internal system.

- Yair

@Yair,

I was not involved with that particular solution, but it was removed because it was flagged for having obsolete information. I looked at the internal notes and original customer case attached to it, and I don’t think it’s same issue, and certainly the information in it isn’t any more helpful to @Rashik, than using the static path.

However yes the static and dynamic classpaths do have different behaviors and part of that is because of our classloader. I want to check with my team to see how much of our class loader I can discuss on the blog and may make an advanced Java/MATLAB post.

I have one common problem with JMI ( I have seen this probelm in so many blogs but still not replied to solve the solution). In fact , from the replies, I could make out that persons( who replied) done in same way but they get succed calling java class from MATLAB. Anyway the problem is I made ImgPr public lass, compiled it with Ecllipse and generated class file, ImgPr.class, I placed in c:MATLAB7\Java\javaclass
Then added this path in classpath.txt
Also run the command javaaddpath c:MATLAB7\Java\javaclass
then run instance=ImgPr
but its erroring -> undefined function or variable ‘ImgPr’

Can I get the solution of this eorror..
or its very machine dependent that it works with some sytems and dosent with other PC’s?????

This post is very helpful, yet I still cannot get it to work. I added my java package to Matlab with

javaaddpath C:\….\PACKAGE_NAME\

and it appears on the dynamic java class path. I am not sure what is the “fully-qualified name”, so I typed,

import(‘PACKAGE_NAME.*’).

When I try to instantiate an object with javaObject(‘CLASSNAME’) I get an “Undefined function or variable ‘CLASSNAME'” error.

What am I missing? How do I find the “fully-qualified name”?

Thank you in advance,
Bar

@Bar – Fully-Qualified-Class-Name (or FQCN) is the full classname, including the package and sub-package names. For example, java.util.Hashtable is the FQCN for the Hashtable class.

The class’s FQCN is determined by the package instruction at the very top of your Java file. For example, in Hashtable’s case, the Java file includes something like a “package java.util” instruction. If you omit the package instruction from your Java file, the class is automatically added to the default package, and FQCN=YourClassName.

When you use the import function, you should use the FQCN.

Note that you must have a public constructor in your class, otherwise Matlab will not be able to instantiate an object from your class, even if it does recognize the class itself.

I hope this is my last query. I can now instantiate and run my main method, however I cannot access the fields or methods of any of the classes. For example,

x = TT.State;
x.code;

produces the error “??? No appropriate method, property, or field code for class TT.State.”
In other cases I get an “Not enough input arguments.” when trying to access a field, which make no sense.

Do you have any idea what could be the problem?

Thank you in advance.

@Bar,

You can use methodsview(TT) and fields(TT) to see what the public methods & fields are on the object, and what the input arguments are.

Hi @Mike,

You mentioned in comment #4 way above:

Dora,

It depends on what events you want to listen for. For instance, you can set MATLAB functions as AWT listeners:

f = javax.swing.JFrame;
set(f,‘ComponentResizedCallback’, @(handle,evt) disp(evt.getSource.getSize));
f.setSize(200,200);
f.show;
I think I will cover this stuff in a future post.

I’m using this technique to register listeners in a Java gui that call back into Matlab. It works like a charm, except one nagging issue that I can’t find a solution to. Once I’ve attached the listener and called it, I can no longer do a “clear java” call to remove links to the .class files. I need to do this while developing, to recompile the Java .class files. It seems like there is a dangling handle that is keeping a reference to the Java gui and won’t let it go. Any hints on how to solve that?

Thanks,
Mason

@Mason,

It was a bit tricky to figure out what was going on, and I had enlist some help in the matter. What’s going on is a circular reference problem because I used an anonymous function in my example. Because f contains a reference to the anonymous function in Java and that anonymous function contains a reference to f in MATLAB, neither memory management system can discover the circularity.

Try removing the inlined anonymous function. For example, create a sub-function to create the anon function in a clean workspace:

function fh = make_dispevt
fh = @(handle,evt) disp(evt.getSource.getSize);

and then in the example, replace the second line with:

set(f,‘ComponentResizedCallback’, make_dispevt);

@Mason & @Mike -
I suggest not to use

set(f,‘ComponentResizedCallback’, make_dispevt);

but rather:

hf = handle(f, 'CallbackProperties');
set(hf,'ComponentResizedCallback', make_dispevt);

Using the Matlab handle() has several benefits over the “naked” Java reference:
1. It solves a memory leak problem
2. It does not evoke a warning in R2010b (and an error in some future version)
3. It always works, whereas trying to set a callback property on a “naked” Java reference fails under some specific conditions. Actually, to be exact, setting a callback property on a handle() also fails sometimes, but this happens in extremely limited circumstances – a very small subset of cases where using the naked reference fails.

More details on this issue: http://UndocumentedMatlab.com/blog/uicontrol-callbacks/#memory_leak

-Yair

I have this code …..

public class ConCat {

public String concat(String s1, String s2) {
   String C;
   C = s1 + s2;
   return C;
}
}

I have added its path using “javaaddpath”.
Then I created its object …

>> O = ConCat;
>> plus = O.concat(‘Animesh ‘, ‘Pandey’);
??? No appropriate method or public field concat for class ConCat.

I am getting errors in invoking the method ‘concat’ !
What should I do ?
:)

@Animesh,

Assuming you’re using javaaddpath correctly, this should work. See if methods(O) lists “concat” as one of the methods. If it is and you’re still having trouble, contact technical support.

Hi,

Can you please provide me an example program and steps on how to call matlab from java? My intention is to establish an interaction between Java and Matlab for one of my projects.

Regards

Hi Mike,

I am working on image processing project. I have implemented my code in matlab. But I want to make Gui of my software in java. Which will be more suitable if I call matlab functions from java Gui. Or implement java Gui within matlab.
Can you give me few tips how to resolve my problem.
Thanks

@Naresh,

The supported way to access Java classes is described in our external interfaces documentation: http://www.mathworks.com/help/techdoc/matlab_external/f44062.html;jsessionid=vQGYTcGZtgQJ9LYQL0zLpD8tkzSQsGpq1vpJjclF03W1ySwTnSSB!-986364634. There is no supported, general way to access MATLAB from Java. You can compile MATLAB files for use in stand-alone Java programs with MATLAB Builder JA.

@Sarah,
This depends a lot on the end environment of your project. If you or your end-users will have MATLAB available to them, the easiest is to make a Java GUI that is launched from MATLAB and hook up MATLAB functions functions to its callbacks. As mentioned above, you can also use MATLAB Builder JA to include MATLAB functions in a Java project.

@Naresh and @Sarah –

There are several different ways you can call Matlab from Java, but none of them are supported or documented, so you should be very careful if you plan to use it in Production code:

1. Use JNI to directly call the Matlab DLLs. For example: http://jmatlink.sourceforge.net , http://www.jstatcom.com/jmatlab.html or https://jna.dev.java.net . JNA in particular is quite easy to use, once you get over the initial setup.

2. Use RMI/JMI to directly access the Java engine: http://UndocumentedMatlab.com/blog/jmi-java-to-matlab-interface/ and the follow-up articles in that series

3. Use a Java-COM bridge (for example, JACOB or JCOM)

4. Use DDE. An example for a .Net client that you can adapt: http://www.codeproject.com/KB/dotnet/matlabeng.aspx

5. There are several other alternatives, but I suggest you stick to the above. #1 and #2 are your best bets.

- Yair

Hello, thanks for taking the time to answer all those questions, they are very helpful.

I am still having some trouble with a very simple example of something I want to expand on.

I have two different classes I want to import, neither of which is packaged. First one is called simpleclass.class, has a constructor, has to methods that simple add a few numbers and that’s it. In Matlab I import it, create an instance of it, and use its methods, no problems. I can list the methods available with methodsview, it shows with the inmem command, everything.

Then I have a second class. It’s in another directory, but I have added this one to the javaclasspath as well. The other major difference is this class extends another class from a program’s API. When I try the same code that works for simpleclass with this one, I get “Arguments to IMPORT must either end with “.*”
or else specify a fully qualified class name: “AOTWrapper” fails this test.” If I add the “.*”, I get the following message: “No class AOTWrapper can be located or no methods for class”.

I have added the path to the jar file from the API to the javaclasspath, but it doesn’t work either.

Do I need to import that jar file into the matlab code before the other one?

Thanks very much in advance for your time.

Kind regards
Maria

Hello Michael,

Thanks for immediate Response!

Michael, I am trying to execute equivalent line of code “AssemblyFactory assemblyFactory = Lookup.getDefault().lookup(AssemblyFactory.class);” in Matlab. I mean I am trying to get reference of the “AssemblyFactory” class using Lookup class but it’s not working.

My matlab code is

import org.openide.util.*;
%creating string varaible
CurrentDevice = ‘dsPIC33FJ256GP710′;
%Creating object from the MCAssemblyFactory
assemblyFactory = com.microchip.mplab.mdbcore.assemblies.assemblyfactory.MCAssemblyFactory;

% Creating Lookup object
loookup_object = Lookup.getDefault();

%AssemblyFactory assemblyFactory = Lookup.getDefault().lookup(AssemblyFactory.class);
assemblyFactory = Lookup.getDefault().lookup.(assemblyFactory);

%%%%%%%%%%%% end of code %%%%%%%%%%%%%%%

%% Note I have added all related jar files to matlab jave path.

I am getting error as
“Static method or constructor invocations cannot be indexed.
Do not follow the call to the static method or constructor with
any additional indexing or dot references.”

Can you help me how to use Lookup class in Matlab with some examples.

Thanks in Advance.

@Ullas,

I’m not familiar with that particular class, but what MATLAB is complaining about is that the static methods can’t be followed on the same line with a method invocation. You’ll need to “Law of Demeter” on this call. Try something like:

assemblyFacory = lookup_object.lookup(assemblyFactory)

Hello Michael,

We have developed a simple class in the Netbeans IDE. This class is having a method which internally calls the “Lookup” for getting a reference of the Assembly Factory class.

Observations:
1.The compiled classes works properly when started from the dos command prompt (thus starting a new JVM with java cmd).
2.Instantiating the class within MATLAB (which has a standard JVM already started) does not work(returning null) due to the Lookup class used in the assembly class (other “standard” classes works fine without Lookup).

Please can you give any idea why “Lookup” class is not working in MATLAB or do we require any dependencies?
Also provide us some examples with Lookup class how it is used in the MATLAB.

Note – Included all dependent jars which are used by the Project in the MATLAB java search path.

Thanks,
Ullas

Hi

I am facing this problem while using a third party jar (stanford-parser.jar) function from matlab. Code snippet is as following

grammarResPath = java.lang.String(‘C:\stanford-parser-2011-09-14\grammar\englishPCFG.ser.gz’);
lp = javaObject(‘edu.stanford.nlp.parser.lexparser.LexicalizedParser’, grammarResPath);
tf = PTBTokenizer.factory(false, WordTokenFactory());
tp = TreePrint(‘penn,dependencies,wordsAndTags’);

All three lines call for some class constructors of jar. Second line of this code throws “java.lang.IllegalArgumentException: name”. To verify if it is java version conflict or some other configuration issue, I commented second line….rest of the lines work fine. What could be the issue? Kindly help.

PLEASE help me sir .I want to run the below java code in matlab .It ran successfully in JAVA environment .I have added the path of class and apache jar file in static path using classpath.txt.I went through the MATLAB External API reference guide but I am not able to get it.

import java.io.IOException;
import org.apache.commons.net.TimeTCPClient;
public final class TimeClient
{

public static final void timeTCP(String host) throws IOException
{
TimeTCPClient client = new TimeTCPClient();
try {
// We want to timeout if a response takes longer than 4 seconds
client.setDefaultTimeout(4000);
client.connect(host);
System.out.println(client.getDate());
}
finally {
client.disconnect();
}
}

public static final void main(String[] args)
{
{
try
{
timeTCP(args[0]);
}
catch (IOException e)
{
e.printStackTrace();
System.exit(1);
}
}

}

}

@saurabh,
You’ll want to make sure that the class is actually on the java class path, and that you are calling the right constructor. If you contact technical support they can help you debug any issues.

It is easier then that. Directly inside MATLAB:

client = org.apache.commons.net.time.TimeTCPClient;
client.connect(‘hist1-ny.ustiming.org’)
t = client.getDate()

sir please help me.currently for mu undergraduate project i am doing a File authentication project using hand gestures.i.e I’m using a 4 digit passcode in the form of hand gestures to allow access to a file.But I don’t know how to capture the images of the gestures in real time.2)how do I link a Javascript containing the File operation to Matlab.Please help me sir

These postings are the author's and don't necessarily represent the opinions of MathWorks.