Introduction
Calling
a Java Applet From JavaScript (for Navigator
4.0+)
Communicating
with a Plug-in From JavaScript
Calling
JavaScript from Java
Communicating
with a Plug-in from Java
Conclusion
Resources
LiveConnect is interesting to the developers because it is an invisible architecture that runs in the background. All the things that happens when you, for example, try to communicate with an applet from JavaScript, happen in the Navigator engine in the background. Therefore there is not much extra work to be done to use LiveConnect!
As a JavaScript programmer, you don't need to do anything special with your code to use LiveConnect. You use the same JavaScript statements and functions. However, for Java applets and plug-ins, you need to make sure that these objects are LiveConnect aware. We will explore what that means in detail later in this TechNote.
So what can you do with LiveConnect? Suppose you have a Java applet that animates text, and you wish to set that text using JavaScript. Using HTML, create a text box which takes text input from the user. With LiveConnect, you can transfer that text to the applet which will then display the new text. Or if you have an audio and video player plug-in installed, using LiveConnect, you can click a button to cue separate video and audio files to play simultaneously. In this scenario, the audio file can provide synched narration and score. Alternatively, clicking a button can bring up an audio-only introduction, which in turn can trigger a movie to run.
This powerful technique makes it possible to create live, multimedia savvy pages using core Netscape ONE technologies such as HTML, Java, JavaScript and Plug-ins. An article from Information Week stated:
"With LiveConnect, developers can finally do serious, interesting software
development on the client side of the Web as well. The potential applications
of LiveConnect are innumerable."
- Internet view: An
Application Infrastructure by Jason
Levitt
Information Week, June 3, 1996
LiveConnect (both client and server) makes it possible to design Web pages with a new and more dynamic level of interactivity by enabling:
The LiveConnect-enabled applet we will be talking about here takes text, URL, font size, font color and font type as its parameters and animates the text. Please take a look at the example before you look at the code below.
Here are the public methods which make it possible to control the applet from JavaScript:
(Note: there are two classes for this applet: fade.class and thoughts.class. When we compile the .java file these files are created with one class in each)
public void setBackgroundColor(int
R, int G, int B)
{
thoughts.SetBackground(R,G,B);
bgChange=true;
repaint();
}
public void setFontColor(int
R, int G, int B)
{
thoughts.SetTextColor(R,G,B);
}
public void setAnimateSpeed(int
speed)
{
thoughts.SetChangeFactor(speed);
}
public void setText(int
which,String text)
{
bgChange=true;
thoughts.theThoughts[which]=text;
thoughts.Reset();
}
public void setUrl(int
which,String url) throws MalformedURLException
{
thoughts.theUrls[which]=new URL(url);
}
public void setFont(int
which,Font font)
{
bgChange=true;
thoughts.theFonts[which]=font;
thoughts.Reset();
}
Each function is passed one or more parameters that manipulate the applet in a different way. For example, to display text that will be animated by the applet, we pass the text, such as, "Hello World", to the function setText() like this: setText('Hello World').
CREATING THE USER INTERFACE:
Now we create the HTML page in which
the applet is embedded. This page will also need some form elements
to communicate with the applet. Here is how we embed the applet:
<applet code="Fade.class"
name="fader" width=400 height=100>
<param name="text1"
value="Look at this text carefully">
<param name="url1"
value="http://www.netscape.com">
<param name="font1"
value="Helvetica,PLAIN,36">
</applet>
Notice that we name the applet (name="fader")
so that it is easier to
call the applet from JavaScript. You can however call unnamed applets
using array indexing (for example,. document.applets[0], document.applets[1]
etc.).
Now we create the following text boxes:
Text:
<input type="text"
size=50 value="Look at this text carefully" name="text_val"
onChange="fader.setText(0,myform.text_val.value)">
URL:
<input type="text"
size=50 value="http://www.netscape.com/" name="url"
onChange="fader.setUrl(0,myform.url.value)">
As you can see there are two text boxes which take the text to display and the URL address for handling mouse clicks on the applet's window area. To change the text that the applet displays, we use the OnChange event handler which calls the public Java applet's function setText(). Note how we pass the value of the text field to the event handler. What happens here is simple, we retrieve the form named myform, its property text_val, and then the property of text_val called value. To assign the new URL address we use the same process, but call the setURL() function.
To change the font type, the event handler sets variable fontName to the value from the text box, then calls the JavaScript function doFont(). Here we are using the onBlur event handler so that right after the text box loses cursor focus, the value is passed on to the fontName variable. We will talk about this variable and the doFont() function in a little bit. Here is the code:
<br>Name:
<input type="text"
size=50 value="Helvetica" name="font_Name"
onBlur="fontName=myform.font_Name.value;doFont()">
Lastly, we have some pull down menus so that you can set the the background color, font size, font style and animation speed.
For the size of the font, we use the onChange event handler, so that when you choose one of the options from the menu, the handler argument gets invoked. For the handler argument, we assign the selection value that is chosen to the variable fontSize. As before, we also call the doFont() function. You may have noticed that we take the selection value and multiply it by 1. Why? To make sure that JavaScript knows that the value for fontSize is actually an integer, not a string. Here is the code:
Size:
<select name="font"
onChange="fontSize=this.options[this.selectedIndex].value*1;doFont()"
>
<option value="12">
12
<option value="18">
18
<option value="24">
24
<option value="36"
selected> 36
</select>
When the user selects a font style
from the style pull down menu, the onChange event handler assigns
that selection value to the fontStyle variable and calls the doFont()
function. Here is the code:
Style:
<select name="style"
onChange="fontStyle=eval('Font.'+this.options[this.selectedIndex].value);
doFont()" >
<option value="PLAIN">Plain
<option value="BOLD">Bold
<option value="ITALIC">Italic
</select>
To set the animation speed using the pull down menu called speed, we again use the onChange event handler. When a selection is made, the event handler calls the applet's setAnimateSpeed() method and passes the selection value. Note that we multiply again by 1 to make sure that an integer is passed to the function, not a string. Take a look at the code:
Animation Speed:
<select name="speed"
onChange="fader.setAnimateSpeed(this[this.selectedIndex].value*1)"
>
<option value="1">
1
<option value="2">
2
<option value="3">
3
</select>
Similarly, to set the background color for the applet, the onChange event handler calls the Applet's public method setBackgroundColor(). The value of the selection is passed to this method which changes the applet's background color immediately. Here is the code:
Background:
<select name="bg"
onChange=
"eval('fader.setBackgroundColor('+this[this.selectedIndex].value+')')"
>
<option value="0,0,0">Black
<option value="255,0,0">Red
<option value="0,255,0">Green
<option value="0,0,255">Blue
<option value="255,255,255">White
</select>
WRITING THE BACKEND CODE:
Now let's look at some of the JavaScript code that works in the background:
<SCRIPT LANGAUGE="JavaScript1.2">
// Note that we are using
JavaScript 1.2 extension
// in the script tag
as the function doFont()
// uses JS 1.2 feature
(function constructor).
// Therefore this example
must be run in Navigator 4.0+.
var fader;
var Font=java.awt.Font;
var fontName='Helvetica';
var fontStyle=Font.PLAIN;
var fontSize=36;
function onload() { // wait for the applet reflection
fader=document.applets.fader
}
function doFont() {
fader.setFont(0,Font(fontName,fontStyle,fontSize))
// this construct is 1.2 specific
/*
Note that we already
defined font above.
You can also do "new
Font(...)" when constructing.
*/
}
</SCRIPT>
First we declare some global variables (remember that these are the same variables that we assigned values to from the HTML form) and a JavaScript object called Font. The Fontobject is created using the Java AWT (Abstract Window Toolkit) Font class. The onload() function assigns the applet to the global variable fader as soon as the the page is loaded.
The doFont() JavaScript function uses the setFont() method of the applet to set the font name, style and size. Note that we used a function constructor here to convert the font object into a number.
Note: The applet discussed
here was one that was originally written by Giuseppe Gennaro. Because
the applet did not exhibit public methods, the applet was modified by Sankalp
Acharya & Henri Torgemane of Netscape. Take a look at the initial
.java file and the modified .java
file to see how the LiveConnect-enabled Java file was effected.
First we embed the LiveAudio file
(a midi file) like this:
<EMBED
SRC="sound.mid"
HIDDEN=TRUE
NAME="Mysound"
MASTERSOUND
AUTOSTART=NO
LOOP=NO>
Note that we must use the <EMBED>
tag inside the <BODY> of the HTML file. We name the object just
like any other object in the HTML file so that it is easier to call it
from JavaScript. The attributes in the <EMBED> tag manipulate
the file and the plug-in just like a Java
applet. For example, if want to file to play in a loop you can set
LOOP=YES. Notice that we use the HIDDEN=TRUE so
the small sound player widow in the HTML page is hidden.
The LiveAudio plug-in has callable
public methods. The information about these methods can be found
at the LiveAudio homepage.
In our example we will only call the stop() and play()
methods. So we create two buttons:
<form>
<input type="button"
value="Play Sound" onClick="document.Mysound.play(false)">
<input type="button"
value="Stop Sound" onClick="document.Mysound.stop()">
</form>
When the buttons are clicked the
onClick event handlers call the play() and stop() methods
which plays and stops the file respectively.
To give you an example of Java communicating with JavaScript, let's assume that there are two applets: one verifies user name and password from a database and another display an animated greeting. You can now use JavaScript to capture the user name from the first applet after the user successfully logs on to a page. Later you can pass that value to the other applet which can then animate the string. It is also possible to pass the user name from the first applet to JavaScript which can set a cookie in the browser (for state maintenance).
To control JavaScript from Java, LiveConnect uses the netscape.javascript.JSObject class. All the interactions with JavaScript are accomplished through this class. Note that because all JavaScript objects must appear in a hierarchical manner in the browser window, the class must also appear in the hierarchy.
The class has the following methods:
public Object call(String methodName, Object args[])
To learn more about the netscape.javascript.JSObject class, see the JavaScript documentation.
To understand how JavaScript and Java can interact on an HTML page using
LiveConnect, please refer to the Java example: HitManApplet.
First we need to embed the plug-in file, just like we did before. Again we use the <EMBED> tag and name our embedded object as mySound.
Next we embedded the Java class file like this:
<applet MAYSCRIPT
code="CallPlugin2.class" width=200 height=40>
<param name="plugin"
value="Mysound">
</applet>
Here MAYSCRIPT opens the LiveConnect communication channel between the Java applet and the plug-in. Notice that we have assigned the value Mysound for the parameter named plugin.
Now, if you take a look at the .java file for this applet, you will notice that we have the following line of code in the file:
SoundPlayer plugin;
Button play =
new Button("Play Sound");
Button stop =
new Button("Stop Sound");
We first declared an object of class SoundPlayer. This class is not in the standard Java package. That is the reason we need to add the path of the plugin class into the class path before being able to compile it. The last two lines declare and instantiate our two buttons.
Next we create a function called init() which initiates the applet. In the function, we first declare two object of class netscape.javascript.JSObject. These objects are used as an interface between JavaScript and Java. We need javascript here to get the plugin object from the document. The first object, win refers to the JavaScript window object and second object, doc refers to the JavaScript document object. Take a look at the code:
JSObject win,doc;
win=JSObject.getWindow(this);
doc=(JSObject)win.getMember("document");
We have another object called plugin. Here we first look at what the parameter 'plugin' contains (defined with <param name="plugin" value="Mysound"> ), then we access the member Mysound. In JavaScript we would call the same code in HTML like this: plugin=doc.Mysound. Here is the code:
plugin=(SoundPlayer)doc.getMember(getParameter("plugin"));
Tip: You can also do:
plugin = (Plugin) win.eval("document.plugin") The limitation on using JSObject.eval() comes when you need to pass objects into JavaScript and preserve them as objects (i.e. not convert them to strings). There are two ways to do this: either put the object in a JavaScript variable using setProperty and then refer to that variable in the eval string, or pass the object as an argument through JSObject.call(). |
The last two lines in the function simply put the buttons in the applet:
this.add("left",play);
this.add("right",stop);
Now we create another function called handleEvent(). This function calls the play() plug-in method when the play button is clicked from the HTML page. At the end, the function returns true. On the other hand, when the stop button is clicked then the stop() method is called and the function returns true. If no button is clicked then the function returns false. Take a look at the code:
public boolean
handleEvent(Event e) {
if (e.id==Event.ACTION_EVENT)
{
if (e.target==play) {
plugin.play();
return
true;
}
if (e.target==stop)
{
plugin.stop();
return
true;
}
}
return
false;
}
That's it! We then compile the file and just embed the new complied
.class file in the HTML page as shown earlier.
Articles
Java
Articles
Java
News Articles
Intro-level
Java Articles
Java
FAQ
Member's Resource
Java
Newsgroup
Web Site
JavaScript Resources A
2 Z
Original Fade Applet
TN-JSCR-03-9707
For the latest technical information on Sun-Netscape Alliance products, go to: http://developer.iplanet.com
For more Internet development resources, try Netscape TechSearch.