# Latest Changes

### Upgrading from 3.0b4 to 3.0b5

1. In your NPP_GetJavaClass function, you'll need to declare all the classes that you're going to use in your plugin. The old way was to initialize your class with `init_ClassName(env)`. The new way is to declare `use_ClassName(env)`.

   >     jref
   >     NPP_GetJavaClass(void)
   >     {
   >         JRIEnv* env = NPN_GetJavaEnv();
   >         jref myClass = use_JavaTestPlugin(env);

   >         /* others that we're using: */
   >         use_netscape_plugin_Plugin(env);
   >         use_java_lang_Class(env);
   >         use_java_lang_String(env);

   >         return myClass;
   >     }

   You'll need to do this for every class whose methods you call. And if you need to call a method on a superclass (e.g. `netscape_plugin_Plugin_getPeer(env, p)`), you'll also have to declare that you're using that superclass (e.g. `use_netscape_plugin_Plugin(env)`).

2. We highly recommend that you build your test builds with the `DEBUG` symbol defined. This will give you much better error messages if you forget to "use" some class that you're actually using.

3. You'll need to include the `javah`-generated `.c` file (e.g. `ClassName.c`) in your project in order to get the `use_ClassName` functions. The `ClassName.c` also defines the stub functions that are needed to invoke your native methods, but are now placed in an `#ifdef IMPLEMENT_ClassName`. If you're including `ClassName.c` in the DLL that defines the native methods, you'll need to be sure to `#define IMPLEMENT_ClassName` before compiling this file. We often define a dummy `stub.c` file like this:

   >     #define IMPLEMENT_ClassName
   >     #include "_stubs/ClassName.c"

4. In your `NPP_Shutdown` function you'll want to declare that you're done using using these classes with `unuse_ClassName(env)`:

   >     void
   >     NPP_Shutdown(void)
   >     {
   >         JRIEnv* env = NPN_GetJavaEnv();
   >         unuse_JavaTestPlugin(env);
   >         unuse_netscape_plugin_Plugin(env);
   >         unuse_java_lang_Class(env);
   >         unuse_java_lang_String(env);
   >     }

5. Remove all the `JRIMethodThunk*` parameters from your native methods:

   >     /* public native foo(D)D */
   >     JRI_PUBLIC_API(jdouble)
   >     native_JavaTestPlugin_foo(JRIEnv* env,struct JavaTestPlugin* self,
   >     			  jdouble d)
   >     {
   >         return d + 1e10;
   >     }

6. Don't forget to declare your methods with `JRI_PUBLIC_API` macro or you'll get a link error on the PC.

7. If you use `JRI_CopyString` or `JRI_CopyStringUTF`, you'll need to change these to `JRI_GetStringChars` and `JRI_GetStringUTFChars`. These return pointers to garbage collected strings. You'll need to copy them yourself if you want to munge the string or keep it longer than you keep the local reference to the string object.

   We had to change these because they were `malloc`'ing the strings and you either needed a JRI free call to free the string, or you needed to be able to supply your own `malloc` procedure. This method avoids the `malloc` issue altogether.

8. If you access array element data using the `JRI_GetTypeArrayData` macros, you'll need to change the name to `JRI_GetTypeArrayElements`.

### Help! I'm experiencing problems!

#### I get an UnsatisfiedLinkError when I try to call one of my plug-in's operations from JavaScript.

This is most likely because you didn't define `IMPLEMENT__ClassName` before compiling the `ClassName.c` file (see above).

#### I get a "... has no properties" message from JavaScript when I try to call one of my plug-in's operations.

This is most likely because the class file for your plug-in wasn't found by the Navigator. JavaScript currently mis-reports this as missing properties rather than a missing class.

The `ClassName.class` file should go in a directory under the Navigator's plug-in directory. Typically this would be something like `MyCompanyName/MyPackageName/MyClass.class` where there are as many subdirectories as there are packages (with the same names). Other classes you define and ship should go in similar subdirectories.

Alternatively, you can package up all the classes into a zip file (uncompressed) and place this under your plug-in's directory: `MyCompanyName/MyProduct.zip`.

Your installer should do one of these two.

### Upgrading from 3.0b3 (Atlas) to 3.0b4

The following changes have been made since the Atlas Beta-3 release:

- Struct and class names are no longer prepended with an `H`. E.g. `struct Hjava_lang_String*` becomes `struct java_lang_String*`.

- You no longer need to declare `IMPORT_ClassName_methodName` for each method you intend to use. Now, you get all the methods without having to do anything.

  However, if you're concerned about the bit of global data used for each method (the "method thunk") then you can eliminate it by instead defining `UNUSED_ClassName_methodName` before compiling the `ClassName.c` file.

- If you're implementing the native methods of a particular class, you must define `IMPLEMENT_ClassName` to get at its private and protected fields and methods from C and C++. Do this before including the header file, "ClassName.h".

- The `netscape_plugin_Plugin_nativeInstance` field (and the corresponding `get_` and `set_` macros) has been replaced by the `netscape_plugin_Plugin_getPeer` method.

- Reasons for calling the class initializer (`init_ClassName`) has change -- now you only have to do it if you define native methods, not if you also want to access fields.

- The "npapi.h" function `NPN_GetJavaInstance` has been renamed to `NPN_GetJavaPeer`.

- The `getWindow` method was added to class `Plugin` and the corresponding C function `netscape_plugin_Plugin_getWindow` was added (in C++, `netscape_plugin_Plugin::getWindow`).

- All JRI calls have been renamed from `Java_whatever` to `JRI_Whatever`. This includes the calls for manipulating globals described in this document. Also the type `JavaGlobalRef` becomes `JRIGlobalRef` and the type `JavaEnv` becomes `JRIEnv`.