The HOOPS/Java integration consists of Java wrappers to HOOPS/3DGS, HOOPS/MVO, and HOOPS/Stream. This document describes how to use the HOOPS/Java integration to build a Java application that incorporates the HOOPS/3DF components. Some familiarity with Java, HOOPS/3DGS and HOOPS/MVO is assumed.
The HOOPS/Java integration is supported under the J2SE Development Kit 6.0 (JDK 6.0), on the Windows 32-bit and 64-bit platforms with Microsoft Visual Studio Version 2008(VC9) and Visual Studio 2010(VC10). It is also supported on the 32-bit platforms of Linux, Solaris Sparc, and Intel.
The following steps are required to compile and run a HOOPS/Java based application:
Compiling: You must place the HOOPS/3DF and HOOPS/Java .jar files in your classpath. This can either be done via the command line for both compiling and running, or it can be set in the manifest file for your project. The files are:
Executing: Ensure that the following files are in your application's directory.
The above files should all be located in your <hoops> /bin/nt_i386_<Visual Studio Version> directory on Windows, and your <hoops>/bin directory under Solaris and Linux.
For Unix and Linux platforms, prior to execution, you must execute two export commands. Below is a list based on the platform you are using:
For 32-bit linux (on a 32-bit machine ONLY):
$ cd bin/linux $ export LD_LIBRARY_PATH=./:../../Dev_Tools/hoops_3dgs/lib/linux/ $ export LD_PRELOAD=../../Dev_Tools/hoops_3dgs/lib/linux/libhoops1780.so:../../Dev_Tools/hoops_3dgs/lib/linux/libopengl1910hdi.so
For 64-bit linux (on a 64-bit machine ONLY):
$ cd bin/linux_x86_64 $ export LD_LIBRARY_PATH=./:../../Dev_Tools/hoops_3dgs/lib/linux_x86_64/ $ export LD_PRELOAD=../../Dev_Tools/hoops_3dgs/lib/linux_x86_64/libhoops1910.so:../../Dev_Tools/hoops_3dgs/lib/linux_x86_64/libopengl1910hdi.so
For 32-bit SPARC Solaris:
$ cd bin/solaris $ export LD_LIBRARY_PATH=./:../../Dev_Tools/hoops_3dgs/lib/solaris/ $ export LD_PRELOAD=/usr/lib/libXm.so:/usr/lib/libCrun.so.1:../../Dev_Tools/hoops_3dgs/lib/solaris/libhoops1910.so:../../Dev_Tools/hoops_3dgs/lib/solaris/libopengl1910hdi.so
For 32-bit Solaris Intel x86:
$ cd bin/solaris_i386 $ exportLD_LIBRARY_PATH=./:../../Dev_Tools/hoops_3dgs/lib/solaris_i386/:/usr/X11/lib $ export LD_PRELOAD=/usr/lib/libXm.so:../../Dev_Tools/hoops_3dgs/lib/solaris_i386/libhoops1910.so:../../Dev_Tools/hoops_3dgs/lib/solaris_i386/libopengl1910hdi.so
For 64-bit Solaris Intel x64:
$ cd bin/solaris_x64 $ exportLD_LIBRARY_PATH=./:../../Dev_Tools/hoops_3dgs/lib/solaris_x64/:/usr/X11/lib/64 $ export LD_PRELOAD=../../Dev_Tools/hoops_3dgs/lib/solaris_x64/libhoops1910.so:../../Dev_Tools/hoops_3dgs/lib/solaris_x64/libopengl1780hdi.so
Java/Swing by default uses DirectDraw to render its GUI elements, and does not mix well when HOOPS is being used to render to an OpenGL window. The "-Dsun.java2d.noddraw=True" flag disables DirectDraw. This can fix some rendering problems with the menus.
Windows run:
java -Dsun.java2d.noddraw=True -jar java_simple.jar
The routines and classes of the HOOPS/3DGS, HOOPS/MVO and HOOPS/Stream toolkits are all generally accessible via the Java wrappers, with a few exceptions and notes covered below. Developers should refer to the Reference Manual for each component, and can additionaly leverage the Intellisense capabilities of the NetBeans IDE to see listings of class members and function/method arguments.
Each HOOPS/3DGS routine name, such as Insert_Polyline in your HOOPS program must have a prefix before the name will actually be usable on your computer system. The prefix varies depending on which language you're calling from, and sometimes depending on the brand of the language you're calling from. When calling from Java, all calls to the HOOPS/3GS API are made through the HJ class, such as:
StringBuffer ex = new StringBuffer (""); HJ.Show_Alias("?picture", ex);
You must call Define_System_Options("multi-threading=full") as your first HOOPS call. This is because Java apps must be thought of as multi-threaded, since the garbage collector will run on a separate thread and may trigger HOOPS calls on a separate thread if it invokes certain destructors.
Most functions available under C are available in Java except for:
The largest difference between using HOOPS with Java and C is found when you have a write-back value, i.e. you pass a pointer to a function and it writes a value or values to that location. Because Java does not have pointers, we have to use other means of passing in by reference.
For example, the C HOOPS code that uses a char*:
char ex[1024]; HC_Show_Alias("?picture", ex); printf("?picture=%s\n",ex);
is replaced in Java by StringBuffer:
StringBuffer ex = new StringBuffer (1024); ; HJ.Show_Alias("?picture", ex); System.out.println("?picture="+ex);
NOTE: You must always pass a new or empty StringBuffer, as HJ uses append internally to return the string. Note that you must also call ensureCapacity to guarantee the buffer has a minimum size before anything can be written into it.
The C HOOPS code that uses &[float_value]:
float x,y,z; HC_Open_Segment("?picture"); HC_Show_Camera_Position(&x, &y, &z); HC_Close_Segment(); printf("x=%f y=%f z=%f\n", x, y, z);
is replaced in Java by single element float arrays:
float[] x = new float[1]; float[] y = new float[1]; float[] z = new float[1]; HJ.Open_Segment("?picture"); HJ.Show_Camera_Position(x, y, z); HJ.Close_Segment(); System.out.println("x=" + x[0] + "y=" + y[0] + "z=" + z[0]);
Arrays can be used in Java in a similar manner as they are used in C. Thus, the C HOOPS code:
float v1[3] = {1.0f,0.0f,0.0f}; float v2[3] = {0.0f,1.0f,0.0f}; float v3[3]; HC_Compute_Cross_Product(v1,v2,v3); printf("%f %f %f\n", v3[0], v3[1], v3[2]);
is replaced in Java by:
float[] v1 = {1.0f,0.0f,0.0f}; float[] v2 = {0.0f,1.0f,0.0f}; float[] v3 = new float[3]; HJ.Compute_Cross_Product(v1,v2,v3); System.out.println( v3[0]+" "+v3[1]+" "+ v3[2]);
It's important to allocate enough room in the array, lest HOOPS writes into unallocated memory and causes a segfault.
Another difference when using HOOPS with Java is found when dealing with HOOPS keys. In Java, you should use the Java 'long'.
long key = 0;
key = HJ.Open_Segment("?picture");
...
HJ.Open_Segment_By_Key(key);
The Java datatypes translate as follows:
HOOPS | HOOPS (HC) type | Java type |
'string' | const char * | String |
'writes string' | char * | StringBuffer |
'HC_KEY' | HC_KEY | long |
'int' | int | int |
'writes int' | &int | int[1] |
'float' | float | float |
'writes float' | &float | float[1] |
'point' | float[3] | float[3] |
'writes point' | &float | float[] |
'writes bytes' | unsigned char * | byte[] |
'writes ints' | &int | int[] |
The HOOPS Intermediate Mode library provides a means for an application to trap the HOOPS update cycle at certain points in the rendering pipeline through a set of callback classes. When you trap the update cycle at a callback point, you can decide what and how something is drawn, or even abort the process itself. The HOOPS I.M. library also provides a set of functions you can call from your callback class to draw to the display in an "immediate mode" style and to query the graphics database and the device characteristics. In the HOOPS/3dGS Programming Guide, you can learn more about HOOPS I.M. and how to implement and use the callback classes.
Any callback class, which has a virtual function with an array as a parameter, is not available in Java. This is because Java doesn't have any concept of a pointer so functions with array arguments cannot be mapped properly.
The capabilities/limitations of HOOPS/MVO for Java are largely analogous to those of C#. After reviewing this section, you can learn more by clicking here.
Member variables are accessed via helper set/get functions with member name appended to the end of set/get
Methods in the C++ classes which return arrays (as a return type) return the array through a parameter in Java
Example signature:
public GetWorldBounding(float[] values, int count);
Sample usage:
// tk is a valid BstreamFileToolkit float[] bounds = new float[6]; tk.GetWorldBounding(bounds, 6);
Array member variables return the array via a get_[variable name] method and are read-only
Example signature:
public get_point_list(HPoint[] values, int count);
Sample usage:
// shell is valid HShell // values is valid HPoint[] array shell.get_point_list(values, values.length);
You should use the enum HFileIOResult wherever HFileInputResult or HFileOutputResult are mentioned in our documentation. For example:
HFileIOResult result = myView.GetModel().Read("c:/datasets/bnc.hsf", myView); if (result != HFileIOResult.HIO_OK) { // ... error }
The HUtilityPMI classes have several caveats.
PMI_String[] datum_labels = new PMI_String[3]; datum_labels[0] = new PMI_String("A-B"); datum_labels[1] = new PMI_String("C"); datum_labels[2] = new PMI_String("D");
class PMI::FeatureControlFrameEntity<br /> void GetDiameterModifierType(DiameterModifier::Type & out_diameter_modifier_type, TextAttributes & out_text_attributes) const;
Java code:
FeatureControlFrameEntity fcf = new FeatureControlFrameEntity(HJ.Create_Segment("pmi/fcf")); int[] diameter_modifier_type = new int[1]; TextAttributes[] label_attributes; fcf.GetDiameterModifierType(diameter_modifier_type, text_attributes);
class PMI::FeatureControlFrameEntity void SetDatumReferences(unsigned int in_count, String const in_labels[], TextAttributes const in_label_attributes[],DatumModifier::Type const in_modifiers[], TextAttributes const in_modifier_attributes[]);
Java code:
int[] datum_modifiers = new int[3]; datum_modifiers[0] = com.techsoft.hoops.PMI.DatumModifier.Type.MaximumMaterialCondition.swigValue(); datum_modifiers[1] = com.techsoft.hoops.PMI.DatumModifier.Type.RegardlessOfFeatureSize.swigValue(); datum_modifiers[2] = com.techsoft.hoops.PMI.DatumModifier.Type.LeastMaterialCondition.swigValue(); // ... declare/populate other variables fcf.SetDatumReferences(3, datum_labels, datum_label_attributes, datum_modifiers, datum_modifier_attributes);
To convert a Java PMI enum to an int value, use [enum value].swigValue(). For example:
int v = com.techsoft.hoops.PMI.DatumModifier.Type.MaximumMaterialCondition.swigValue();
To convert from an int to an enum, use [enum].swigToEnum(). For example:
int[] tolerance_type = new int[1]; fcf.GetToleranceType(tolerance_type, text_attributes); com.techsoft.hoops.PMI.Tolerance.Type e = com.techsoft.hoops.PMI.Tolerance.Type.swigToEnum(tolerance_type[0])
Do not use BStreamFileToolkit::PrepareBuffer. Instead, do the following: