How to know the Java interfaces an OpenOffice Calc UNO object supports (through queryInterface)

329 views Asked by At

I'm developing a "macro" for OpenOffice Calc. As the language, I chose Java, in order to get code assistance in Eclipse. I even wrote a small ant build script that compiles and embeds the "macro" in an *.ods file. In general, this works fine and surprisingly fast; I'm already using some simple stuff quite successfully.

BUT

So often I get stuck because with UNO, I need to "query" an interface for any given non-trivial object, to be able to access data / call methods of that object. I.e., I literally need to guess which interfaces a given object may provide. This is not at all obvious and not even visible during Java development (through some sort of meta-information, reflection or the like), and also sparsely documented (I downloaded tons of stuff, but I don't find the source or maybe JavaDoc for the interfaces I'm using, like XButton, XPropertySet, etc. - XButton has setLabel, but not getLabel - what??).

There is online documentation (for the most fundamental concepts, which is not bad at all!), but it lacks many details that I'm faced with. It always magically stops exactly at the point I need to solve.

I'm willing to look at the C++ code to get a clue what interfaces an object (e.g. the button / event I'm currently stuck with) may provide. Confusingly, the C++ class and file names don't exactly match the Java interfaces. It's almost what I'm looking for, but then in Java I don't really find the equivalent, or calling queryInterface on a given object returns null.. It's becoming a bit frustrating.

How are the UNO Java interfaces generated? Is there some kind of documentation in the code that serves as the origin for the generated (Java) code?

I think I really need to know what interfaces are available at which point, in order to become a bit more fluent during Java-UNO-macro development.

1

There are 1 answers

1
Jim K On BEST ANSWER

For any serious UNO project, use an introspection tool.

As an example, I created a button in Calc, then used the Java Object Inspector to browse to the button. Right-clicking and choosing "Add to Source Code" generated the following.

import com.sun.star.awt.XControlModel;
import com.sun.star.beans.XPropertySet;
import com.sun.star.container.XIndexAccess;
import com.sun.star.container.XNameAccess;
import com.sun.star.drawing.XControlShape;
import com.sun.star.drawing.XDrawPage;
import com.sun.star.drawing.XDrawPageSupplier;
import com.sun.star.sheet.XSpreadsheetDocument;
import com.sun.star.sheet.XSpreadsheets;
import com.sun.star.uno.AnyConverter;
import com.sun.star.uno.UnoRuntime;
import com.sun.star.uno.XInterface;

//...
public void codesnippet(XInterface _oUnoEntryObject){
try{
    XSpreadsheetDocument xSpreadsheetDocument =  (XSpreadsheetDocument) UnoRuntime.queryInterface(XSpreadsheetDocument.class, _oUnoEntryObject);
    XSpreadsheets xSpreadsheets = xSpreadsheetDocument.getSheets();
    XNameAccess xNameAccess =  (XNameAccess) UnoRuntime.queryInterface(XNameAccess.class, xSpreadsheets);
    Object oName = xNameAccess.getByName("Sheet1");
    XDrawPageSupplier xDrawPageSupplier =  (XDrawPageSupplier) UnoRuntime.queryInterface(XDrawPageSupplier.class, oName);
    XDrawPage xDrawPage = xDrawPageSupplier.getDrawPage();
    XIndexAccess xIndexAccess =  (XIndexAccess) UnoRuntime.queryInterface(XIndexAccess.class, xDrawPage);
    Object oIndex = xIndexAccess.getByIndex(0);
    XControlShape xControlShape =  (XControlShape) UnoRuntime.queryInterface(XControlShape.class, oIndex);
    XControlModel xControlModel = xControlShape.getControl();
    XPropertySet xPropertySet =  (XPropertySet) UnoRuntime.queryInterface(XPropertySet.class, xControlModel);
    String sLabel = AnyConverter.toString(xPropertySet.getPropertyValue("Label"));
}catch (com.sun.star.beans.UnknownPropertyException e){
    e.printStackTrace(System.out);
    //Enter your Code here...
}catch (com.sun.star.lang.WrappedTargetException e2){
    e2.printStackTrace(System.out);
    //Enter your Code here...
}catch (com.sun.star.lang.IllegalArgumentException e3){
    e3.printStackTrace(System.out);
    //Enter your Code here...
}
}
//...

Python-UNO may be better than Java because it does not require querying specific interfaces. Also XrayTool and MRI are easier to use than the Java Object Inspector.