Creating a threaded applet
I have two classes that I want to run in separate threads in the same applet:
ScrollingBanner.java
Code Java:
public class ScrollingBanner implements Runnable
{
private String msg = "This is scrolling text!";
private BannerCalcApplet bca;
ScrollingBanner(BannerCalcApplet bca)
{
this.bca = bca;
}
public void run()
{
char ch;
for( ; ; )
{
try
{
Thread.sleep(250);
ch = msg.charAt(0);
msg = msg.substring(1, msg.length());
msg += ch;
}
catch (InterruptedException ie)
{
}
}
}
}
CalculatorApplet.java
Code Java:
import java.applet.*;
import java.awt.*;
import java.awt.event.*;
/*
<applet code = "CalculatorApplet" width = 225 height = 300>
</applet>
*/
public class CalculatorApplet extends Applet {
private TextField fArgTxt;
private TextField sArgTxt;
private TextField ansTxt;
private BannerCalcApplet bca;
CalculatorApplet(BannerCalcApplet bca)
{
this.bca = bca;
}
public void init () {
// Construct the TextFields
this.fArgTxt = new TextField(25);
this.sArgTxt = new TextField(25);
this.ansTxt = new TextField(25);
this.ansTxt.setEditable(false);
Button adds = new Button("+");
Button subs = new Button("-");
Button mults = new Button("*");
Button divs = new Button("/");
// add the button to the layout
this.add(fArgTxt);
this.add(sArgTxt);
this.add(ansTxt);
this.add(adds);
this.add(subs);
this.add(mults);
this.add(divs);
AdditionAction aa = new AdditionAction(fArgTxt, sArgTxt, ansTxt);
adds.addActionListener(aa);
this.fArgTxt.addActionListener(aa);
this.sArgTxt.addActionListener(aa);
SubtractionAction sa = new SubtractionAction(fArgTxt, sArgTxt, ansTxt);
subs.addActionListener(sa);
this.fArgTxt.addActionListener(sa);
this.sArgTxt.addActionListener(sa);
MultiplicationAction ma = new MultiplicationAction(fArgTxt, sArgTxt, ansTxt);
mults.addActionListener(ma);
this.fArgTxt.addActionListener(ma);
this.sArgTxt.addActionListener(ma);
DivisionAction da = new DivisionAction(fArgTxt, sArgTxt, ansTxt);
divs.addActionListener(da);
this.fArgTxt.addActionListener(da);
this.sArgTxt.addActionListener(da);
// notice that ActionEvents produced by ansTxt are ignored.
}
}
class AdditionAction implements ActionListener {
private TextField arg1Txt;
private TextField arg2Txt;
private TextField answTxt;
public AdditionAction(TextField arg1Txt, TextField arg2Txt, TextField answTxt) {
this.arg1Txt = arg1Txt;
this.arg2Txt = arg2Txt;
this.answTxt = answTxt;
}
public void actionPerformed(ActionEvent ae) {
double arg1Val = Double.parseDouble(arg1Txt.getText());
double arg2Val = Double.parseDouble(arg2Txt.getText());
double sumVal = arg1Val + arg2Val;
answTxt.setText("" + sumVal);
}
}
class SubtractionAction implements ActionListener {
private TextField arg1Txt;
private TextField arg2Txt;
private TextField answTxt;
public SubtractionAction(TextField arg1Txt, TextField arg2Txt, TextField answTxt) {
this.arg1Txt = arg1Txt;
this.arg2Txt = arg2Txt;
this.answTxt = answTxt;
}
public void actionPerformed(ActionEvent ae) {
double arg1Val = Double.parseDouble(arg1Txt.getText());
double arg2Val = Double.parseDouble(arg2Txt.getText());
double difVal = arg1Val - arg2Val;
answTxt.setText("" + difVal);
}
}
class MultiplicationAction implements ActionListener {
private TextField arg1Txt;
private TextField arg2Txt;
private TextField answTxt;
public MultiplicationAction(TextField arg1Txt, TextField arg2Txt, TextField answTxt) {
this.arg1Txt = arg1Txt;
this.arg2Txt = arg2Txt;
this.answTxt = answTxt;
}
public void actionPerformed(ActionEvent ae) {
double arg1Val = Double.parseDouble(arg1Txt.getText());
double arg2Val = Double.parseDouble(arg2Txt.getText());
double prodVal = arg1Val * arg2Val;
answTxt.setText("" + prodVal);
}
}
class DivisionAction implements ActionListener {
private TextField arg1Txt;
private TextField arg2Txt;
private TextField answTxt;
public DivisionAction(TextField arg1Txt, TextField arg2Txt, TextField answTxt) {
this.arg1Txt = arg1Txt;
this.arg2Txt = arg2Txt;
this.answTxt = answTxt;
}
public void actionPerformed(ActionEvent ae) {
double arg1Val = Double.parseDouble(arg1Txt.getText());
double arg2Val = Double.parseDouble(arg2Txt.getText());
double quotVal = arg1Val / arg2Val;
answTxt.setText("" + quotVal);
}
}
BannerCalcApplet.java
I tried this:
Code Java:
import java.applet.*;
import java.awt.*;
/*
<applet code = "BannerCalcApplet" width = 225 height = 300
</applet>
*/
class BannerCalcApplet extends Applet
{
ScrollingBanner sb;
CalculatorApplet ca;
Thread sbt;
Thread cat;
BannerCalcApplet bca = this;
public void init()
{
sb = new ScrollingBanner(this);
sbt = new Thread(sb);
ca = new CalculatorApplet(this);
cat = new Thread (ca);
sbt.start();
cat.start();
}
}
But I am unsure how to actually create a window into which I can layout the banner and calculator. Also, the code doesn't compile, because the compiler doesn't recognize the form of the Thread constructor that takes the CalculatorApplet object as an argument but there is no compiler error for the corresponding Thread constructor that takes the ScrollingBanner object as an argument.
I'm probably missing something very basic, but I would appreciate it if someone pointed it out to me.
Re: Creating a threaded applet
You can't create a thread from a non-Runnable object. You can have your applet implement runnable, but then it won't have all of the initialization stuff done correctly.
What you should do is move the CalculatorApp code into your main BannerCalcApp class (it makes no sense to have two applet objects running in the same applet).
Re: Creating a threaded applet
Quote:
Originally Posted by
helloworld922
You can't create a thread from a non-Runnable object. You can have your applet implement runnable, but then it won't have all of the initialization stuff done correctly.
What you should do is move the CalculatorApp code into your main BannerCalcApp class (it makes no sense to have two applet objects running in the same applet).
How would I go about running the banner in one thread and the calculator in another?
Re: Creating a threaded applet
Can you explain what the calculator class is supposed to do?
The banner class I guess should have a panel where it can change the contents like a scrolling banner.
But why put the calculator on its own thread? what will it be doing.
If the calculator class is for user input while the banner is scrolling, put the banner on a thread and let it scroll its text.
Have the calculator class display its buttons etc and wait for the user to tell it what to do. When the user presses a button, Swing's Event Dispatch Thread starts a listener and the calculator code is executed.
Re: Creating a threaded applet
Quote:
Originally Posted by
Norm
Can you explain what the calculator class is supposed to do?
The banner class I guess should have a panel where it can change the contents like a scrolling banner.
But why put the calculator on its own thread? what will it be doing.
If the calculator class is for user input while the banner is scrolling, put the banner on a thread and let it scroll its text.
Have the calculator class display its buttons etc and wait for the user to tell it what to do. When the user presses a button, Swing's Event Dispatch Thread starts a listener and the calculator code is executed.
I guess I was a little confused as to what I need to put into a thread and what I didn't. I just want the applet to display a scrolling banner and allow the user to perform basic arithmetic calculations (addition subtraction, multiplication, and division). The calculator part works as I want it to, except that I can't get it to print "NaN" to the third text field when I divide by zero. (Any suggestions on how to get it to do that?) I am just having trouble understanding how to get the banner and calculator to fit together into a single integrated environment.
It is clear to me that I do need to have the banner in a thread because it needs to update and redisplay itself. However I am not so sure about the calculator's being in another thread, because it does not need to be updated continuously.
Do you have any pointers on when to thread an object and when not to?
Re: Creating a threaded applet
Put the banner on a thread. Leave the calculator as you normally would.
For NaN, how do you detect divide by 0? try{}catch(){}
Compute the result and put it in a String. If you detect div by 0, set the String to "NaN"
Use threads when you want to do something in the background while the GUI is waiting for user input.
Re: Creating a threaded applet
Quote:
Originally Posted by
Norm
For NaN, how do you detect divide by 0? try{}catch(){}
Compute the result and put it in a String. If you detect div by 0, set the String to "NaN"
Here is the code snippet for the division operation:
Code Java:
public DivisionAction(TextField arg1Txt, TextField arg2Txt, TextField answTxt)
{
this.arg1Txt = arg1Txt;
this.arg2Txt = arg2Txt;
this.answTxt = answTxt;
}
public void actionPerformed(ActionEvent ae)
{
double arg1Val = Double.parseDouble(arg1Txt.getText());
double arg2Val = Double.parseDouble(arg2Txt.getText());
double quotVal;
try
{
quotVal = arg1Val / arg2Val;
answTxt.setText("" + quotVal);
}
catch (Exception e)
{
answTxt.setText("NaN");
}
}
}
It does not work no matter what exception I tell it to catch. If you compile the entire .java file, it will print "Infinity" to the answer text field when you divide by zero.
Re: Creating a threaded applet
Look at the Double class and see if there are any methods or values you can use to test the results against.
Re: Creating a threaded applet
OK, now I am having trouble integrating the calculator with the banner.
I have a version of the code that compiles with out error:
Code Java:
import java.applet.*;
import java.awt.*;
import java.awt.event.*;
/*
<applet code = "BannerCalcApplet" width = 225 height = 300
</applet>
*/
class BannerCalcApplet extends Applet
{
private ScrollingBanner sb;
private Thread sbt;
private CalculatorApplet ca;
public void init()
{
sb = new ScrollingBanner(this);
sbt = new Thread(sb);
sbt.start();
ca = new CalculatorApplet(this);
}
}
The source code that defines ScrollingBanner and CalculatorApplet are the same as posted before, but when the applet is viewed no windows open, not even the applet window. This is really puzzling to me since it has never happened before. Usually, when an applet fails to initialize, the applet window at least opens and tells me that the applet failed to initialize and the run-time exceptions are printed to the console.
Re: Creating a threaded applet
Why do you have two classes that extend Applet? Only one of them is used by the browser as an applet. The CalculatorApplet class's methods (init and start) are NOT going to be called by the browser.
I'd recommend only one Applet class. Have that class start a thread for the banner and present the GUI for the calculator.
Re: Creating a threaded applet
I'm not sure how to being placing the elements in the GUI. I have tried several things and my latest attempt is:
Code Java:
public class CalculatorGUI
{
/*priavte*/ BannerCalcApplet bca;
CalculatorGUI(BannerCalcApplet bca)
{
this.bca = bca;
}
// Construct the TextFields
Container GUICont = getContentPane();
TextField fArgTxt = new TextField(25);
TextField sArgTxt = new TextField(25);
TextField ansTxt = new TextField(25);
Button adds = new Button("+");
Button subs = new Button("-");
Button mults = new Button("*");
Button divs = new Button("/");
// add the button to the layout
GUICont.add(fArgTxt);
GUICont.add(sArgTxt);
GUICont.add(ansTxt);
GUICont.add(adds);
GUICont.add(subs);
GUICont.add(mults);
GUICont.add(divs);
//code for button and text field actions
}
This won't compile, because it says that there are identifiers missing. For instance, for the line GUICont.add(fArgTxt);, the compiler returns an error:
Code :
CalculatorGUI.java:32: <identifier> expected
GIUCont.add(fArgTxt);
^
I'm not sure why it's not recognizing my identifiers, as I have declared my variables and created object for the to refer to.
Re: Creating a threaded applet
You must put the method calls(the add()s) inside of a method. They appear to be outside with the variable defs.
Re: Creating a threaded applet
I am still really lost on how exactly I am to achieve my desired results.
Do you have any references to tutorials that might tell me how to create applets that contain multiple classes of my own creation?
Re: Creating a threaded applet
Take a two step approach.
First create the Calculator applet with a place that shows the banner.
Then add a thread to move the contents of the place holding the banner.
Re: Creating a threaded applet
Quote:
Originally Posted by
Norm
First create the Calculator applet with a place that shows the banner.
Then add a thread to move the contents of the place holding the banner.
This is what I am unsure on how to do. I wrote a stand-alone calculator applet that works just fine. I am, however unsure on how to create a place for the banner within calculator applet and then add the banner thread to the applet.
I am really unfamiliar with most of the AWT classes, so I may be missing something really basic.
Re: Creating a threaded applet
Quote:
unsure on how to create a place for the banner
The place I'm talking about is GUI. Something like a JLabel in the applets GUI area.
In the applet you create a Thread object and start it. Say in the init() or start() method.
Re: Creating a threaded applet
Quote:
Originally Posted by
Norm
The place I'm talking about is GUI. Something like a JLabel in the applets GUI area.
In the applet you create a Thread object and start it. Say in the init() or start() method.
OK, here's what I have done.
Code Java:
import java.applet.*;
import java.awt.*;
import java.awt.event.*;
/*
<applet code = "BannerCalcApplet" width = 225 height = 300
</applet>
*/
class BannerCalcApplet extends Applet
{
Label banner = new Label();
private ScrollingBanner sb;
private Thread sbt;
private CalculatorGUI ca;
public void init()
{
sb = new ScrollingBanner(this);
sbt = new Thread(sb);
sbt.start();
ca.buildGUI (fArgTxt, sArgTxt, ansTxt, adds, subs, mults, divs);
}
}
Can I add the Thread to the Label? If so, how do I?
Re: Creating a threaded applet
Quick and dirty applet tutorial:
1. There is no main method.
2. You do not have a constructor (well, you do but generally you don't provide anything other than the default constructor). All applet initialization should go in the init() method.
3. When you applet is running, it should be inside the run() method. Once the run method finishes, the applet is "done"
4. If your applet gets closed pre-maturely (say, the user moves to a different webpage), you can provide cleanup inside the "stop" method.
5. Everything else about applet programming is basically the same as regular Java programming. There are a few access rules restrictions and extra features applets get for integrating into a web browser, but you don't need to worry about any of these for your project.
So, you just need two classes, the main applet class and a secondary banner thread to update the banner.
As a last note, you will want to start your banner thread inside the start() method (or at the beginning of the run() method) and also make sure it is running as a daemon thread to make cleanup much easier.
Code Java:
// setting a thread as a daemon thread
aThread.setDaemon(true);
Re: Creating a threaded applet
Quote:
add the Thread to the Label?
Not sure what that means.
The thread will started with a reference to the Label which is shown in the Applet's GUI. It can change the contents of the label and tell the applet to repaint its GUI to show the new contents of the label.
Re: Creating a threaded applet
Quote:
Originally Posted by
Norm
The thread will started with a reference to the Label which is shown in the Applet's GUI.
This is what I meant to say. I was wondering how to do this.
Re: Creating a threaded applet
How to pass a reference to a class?
A couple of ways:
In the constructor.
In a settor method.
Another approach would be to have your banner class extend the label class and have the Applet treat the banner class like any label and add it to a panel somewhere in its GUI. Then the banner class could use super() to get to the real label code.
Re: Creating a threaded applet
Quote:
Originally Posted by
Norm
How to pass a reference to a class?
Sorry, I've been trying to get this to work for a while, and my brain is fried. I understand what you were saying now that you phrased it.[/QUOTE]
Quote:
Originally Posted by
Norm
In the constructor.
The Label class does not have a constructor that takes a Thread object as a parameter, so I don't understand how I would run the Thread in the Label by passing the Thread to the Label's constructor.
Quote:
Originally Posted by
Norm
In a settor method.
Can you elaborate?
Re: Creating a threaded applet
Code :
class TheBannerRunner extends Runnable {
Label theLabel;
public TheBannerRunner(Label theLabel) {
this.theLabel = theLabel; // Save the reference to the label we're to update
}
public void run() {
... code here to move contents of label and repaint it