Multi-Threading in J2ME and LWUIT - java

I want to make dialog box to be shown while I load some data from the web service
I'm using the LWUIT,
The following is the code
public class LoaderAnimation extends Container implements Runnable {
private Thread t;
private boolean running = false;
public LoaderAnimation() {
}
public void start() {
running = true;
t = new Thread(this);
t.start();
}
public void run() {
while (running) {
// do something
t.sleep(150);
}
}
public void stop() {
running = false;
}
}
what happens now that it runs but the code of calling the web service has stop working
that is the calling of it
public static void showLoaderScreen ()
{
dialog = new Dialog();
dialog.setLayout(new BorderLayout());
canvas = new LoaderAnimation();
dialog.addComponent(BorderLayout.CENTER , canvas);
canvas.start();
dialog.show();
}
public static void dismissLoaderScreen ()
{
canvas.stop();
dialog.dispose();
}

try this piece of code.
private void startLoader() {
Dialog d = new Dialog();
d.getStyle().setBgColor(0xffffff);
d.getStyle().setBgTransparency(255);
d.show(100, 250, 90, 150, true, false);
d.setAutoDispose(true);
try {
Thread.sleep(30);
} catch (InterruptedException ex) {
ex.printStackTrace();
}
d.dispose();
new Timer().schedule(new TimerTask() {
public void run() {
new Loader().start();
}
}, 30);
}
Loader class we can write parsing stuff or web service handling etc.
class Loader extends Thread
{ public void run() {
try {
ServiceTypesScreen st = new ServiceTypesScreen();
st.init();
} catch (Exception e) {
e.printStackTrace();
}
}
}

Related

Java join doesn't wait for thread exit

I'm trying to synchronize this code: what I want is that the class Gioca waits until the class Gioco calls the method fine (fine should stop the thread) but as the Gioca class invokes the run method it prints on the console the string "Fine" even thow the class Gioco hasn't called the method fine() yet.
public class Gioca implements Runnable
{
private int vite;
private int recuperi;
public Gioca()
{
vite=3;
recuperi=0;
}
public void gioca()
{
Thread t=new Thread(new Gioco(vite));
try
{
t.start();
t.join();
}
catch (Exception ex) {}
System.out.println("Fine");
}
#Override
public void run()
{
gioca();
}
}
public class Gioco extends Canvas implements ActionListener, KeyListener, Runnable
{
private int direzione;
private Timer timer;
private JFrame f;
private int vite;
private int velocità;
private int spazio;
private Personaggio p;
private int pos;
private LinkedList<Ostacolo> o;
private Random r;
private int po;
private Image imm1=new ImageIcon(this.getClass().getResource("images/sfondo.jpg")).getImage();
private Image imm2=new ImageIcon(this.getClass().getResource("images/cuore.png")).getImage();
public Gioco(int vite)
{
r=new Random();
try
{
File file=new File("images/punteggio.txt");
Scanner scanner=new Scanner(file);
spazio=scanner.nextInt();
}
catch (Exception e) {}
direzione=3;
this.vite=vite;
o=new LinkedList();
for(int i=0; i<20; i++)
o.add(new Ostacolo(Math.abs(400*i)+1000));
p=new Personaggio();
this.velocità=2;
timer=new Timer(10, this);
f=new JFrame("Gioco");
f.setSize(1000, 700);
f.setResizable(false);
f.setLocation(200,200);
f.add(this);
f.addKeyListener(this);
f.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
}
public void actionPerformed(ActionEvent ae)
{
if(direzione==2)
{
velocità-=2;
if(velocità<2)
velocità=2;
}
if(direzione==1)
p.setY(5);
if(direzione==0)
p.setY(-5);
spazio+=velocità;
if(spazio%1000<10)
velocità++;
pos=(pos+velocità)%4500;
po=-pos;
for(int i=0; i<20; i++)
{
o.get(i).muovi(velocità);
if(o.get(i).getX()<-100)
{
o.remove(i);
o.add(new Ostacolo(i*400));
}
}
verificaCollisioni();
repaint();
}
public void verificaCollisioni()
{
for(int i=0; i<20; i++)
{
if(o.get(i).getX()>300 && o.get(i).getX()<350)
{
int r[]=o.get(i).getDimensioni();
if(r[0]<p.getY() && r[1]>p.getY())
{
}
else
fine();
}
}
}
private void fine()
{
try
{
Thread.sleep(3000);
}
catch(Exception e){}
timer.stop();
try
{
File file=new File("images/punteggio.txt");
file.createNewFile();
FileOutputStream f=new FileOutputStream(file);
f.flush();
String sPunteggio=String.valueOf(spazio);
byte[] scrivi=sPunteggio.getBytes();
f.write(scrivi);
}
catch(Exception e){}
f.dispose();
}
#Override
public void keyPressed(KeyEvent ke)
{
int c=ke.getKeyCode();
if(c == 40)
direzione=1;
if(c == 38)
direzione=0;
if(c==32)
direzione=2;
}
public void paint(Graphics g)
{
Image workspace=createImage(getWidth(),getHeight());
Graphics2D buffer=(Graphics2D) workspace.getGraphics();
buffer.drawImage(imm1, po, 0, this);
buffer.setColor(new Color(242, 54, 33));
buffer.setFont(new Font(Font.SANS_SERIF, Font.BOLD, 20));
buffer.drawString(""+(spazio/100), 10, 20);
buffer.drawImage(imm2, 940, 4, this);
buffer.setColor(new Color(13, 226, 13));
buffer.drawString(""+vite, 920, 20);
buffer.drawImage(p.getImage(), 300, p.getY(), this);
for(int i=0; i<20; i++)
{
Ostacolo tmp=o.get(i);
buffer.drawImage(tmp.getImage(), tmp.getX(),tmp.getY(), this);
}
Graphics2D g2=(Graphics2D)g;
g2.drawImage(workspace, 0, 0, this);
buffer.dispose();
}
public void update(Graphics g)
{
paint(g);
}
public void keyReleased(KeyEvent ke) {direzione=3;}
public void keyTyped(KeyEvent ke) {}
#Override
public void run()
{
f.setVisible(true);
timer.start();
}
}
This code, using the same instructions, works well
public class Campana implements Runnable{
private String suono;
private int volte;
public Campana(String suono,int volte)
{
this.suono =suono;
this.volte=volte;
}
public void run()
{
for(int i=0;i<volte;i++) {
System.out.println((i+1)+" "+suono);
}
}
}
public class Suona {
public static void main(String args[]){
Thread campana1=new Thread(new Campana("din", 5));
Thread campana2=new Thread(new Campana("don", 5));
Thread campana3=new Thread(new Campana("dan", 5));
try {
campana1.start();
campana1.join();
campana2.start();
campana2.join();
campana3.start();
campana3.join();
} catch (InterruptedException ex) {
Logger.getLogger(Suona.class.getName()).log(Level.SEVERE, null, ex);
}
}
}
t.join(); in this case waits for run in Giocoto terminate. That method terminates after
f.setVisible(true);
timer.start();
have completed, which will be very fast since Timer will run actionPerformed a different thread from the one that timer.start(); is called in. It does not wait until the timer has been stopped. You can fix this by introducing some form of synchronization in your run method. I would not recommend a while loop since that will waste resources on running the loop. Instead consider using a CountDownLatch (javadoc link):
Add this to Gioco:
private final CountDownLatch doneSignal = new CountDownLatch(1);
At the end of fine() call doneSignal.countDown(). And finally change your run() method in Gioco to something like this:
#Override
public void run()
{
f.setVisible(true);
timer.start();
try {
doneSignal.await();
} catch (InterruptedException ex) {}//Logg this or something. Shouldn't really ever happen.
}

How to start and stop a threads in netbeans from a jButton click

I write Java desktop app to fetch and post some data from my online rails backend app. The App have to call a get request every 5 second to update the relay state(example Arduino). here is my code:
public class GUI extends javax.swing.JFrame {
private Serial serial = null;
private Service service = null;
private volatile boolean connected = false;
private Thread updateThread;
public GUI() {
initComponents();
init_serial();
service = new Service();
updateThread = new Thread() {
public void run() {
while (connected) {
updateJob();
}
}
};
updateThread.start();
}
private void init_serial() {
serial = new Serial();
serial.searchForPorts();
serial.connect();
serial.initIOStream();
serial.initListener();
}
private void updateJob() {
ActionListener actListner = new ActionListener() {
#Override
public void actionPerformed(ActionEvent event) {
updateState();
}
};
Timer timer = new Timer(5000, actListner);
timer.start();
}
private void updateState() {
String portState = service.get_port_state();
serial.write(portState);
System.out.println(portState);
}
private void jButton1ActionPerformed(java.awt.event.ActionEvent evt) {
connected = true;
logger.setText(null);
logger.setText("connected");
}
private void jButton2ActionPerformed(java.awt.event.ActionEvent evt) {
logger.setText(null);
logger.setText("disconnected");
}
public static void main(String args[]) {
java.awt.EventQueue.invokeLater(new Runnable() {
public void run() {
new GUI().setVisible(true);
}
});
}
}
but it didn't work as expected, my question is how can i fix my code and how to put the thread correctly?
You can use a Thread object in class's member and you can start and stop in button click action events. Here is the sample to start/stop thread.
public class GUI extends javax.swing.JFrame {
Thread updateThread = null;
public GUI() {
JButton btnStart = new JButton("Start");
JButton btnStop = new JButton("Stop");
JPanel jPanel = new JPanel();
jPanel.setBounds(0, 0, 100, 200);
jPanel.add(btnStart);
jPanel.add(btnStop);
add(jPanel);
btnStart.addActionListener(new ActionListener() {
#Override
public void actionPerformed(ActionEvent e) {
updateThread = new Thread(new Runnable() {
#Override
public void run() {
while (true) {
System.out.println("Work updated");
try {
Thread.sleep(1000);//Time to wait for next routine
} catch (InterruptedException e) {
e.printStackTrace();
}
}
}
});
updateThread.start();
}
});
btnStop.addActionListener(new ActionListener() {
#Override
public void actionPerformed(ActionEvent e) {
updateThread.stop();
}
});
setVisible(true);
setBounds(0, 0, 100, 200);
}
public static void main(String[] args) {
new GUI();
}
}
You can possibly use thread.join();

synchronize the jprogress bar

public class frame11 extends javax.swing.JFrame implements ActionListener,
PropertyChangeListener {
public String[] columnNames = { "Path",
"File Name",
"Size"};
public Object[][] data ;
int isJPEG (String s) throws IOException
{ int c=0;//not jpeg
if ( (s.endsWith(".JPG")) || (s.endsWith(".JPEG"))||(s.endsWith(".jpeg"))||(s.endsWith(".jpg")))
{
c=1;//is jpeg
}
return c;
}
}
private void jButton1ActionPerformed(java.awt.event.ActionEvent evt) {//GEN-FIRST:event_jButton1ActionPerformed
setCursor(Cursor.getPredefinedCursor(Cursor.WAIT_CURSOR));
JFileChooser fch = new JFileChooser("C:\\");
jProgressBar1.setValue(0);
jProgressBar1.setStringPainted(true);
jTextField1.setText(null);
jTextField2.setText(null);
jTextField4.setText(null);
jLabel7.setText(null);
data = new Object[15][3];
jTable2.setModel(new DefaultTableModel(data, columnNames));
fch.setFileSelectionMode(JFileChooser.DIRECTORIES_ONLY);
int ret = fch.showOpenDialog(null);
int apr=0;
if (ret==JFileChooser.APPROVE_OPTION)
{ apr=1;
jTextField1.setText(fch.getSelectedFile().toString());
setCursor(Cursor.getPredefinedCursor(Cursor.WAIT_CURSOR));
}
else jTextField1.setText("Nothing clicked!!!");
if (apr==1) {
jLabel7.setText("Wait Please, While searching ...");
task = new Task();
task.addPropertyChangeListener(this);
task.execute();
EventQueue.invokeLater(new Runnable() { // Added
#Override
public void run() {
File f = fch.getSelectedFile();
String s= f.getAbsolutePath();
int cnt;
int st=0;
Path myfile = Paths.get(s);
if(f.isDirectory()&& Files.isReadable(myfile)){
try {
st=st+CheckFiles(f);
cnt=count(f);
String ss=Integer.toString(cnt);
jTextField2.setText(ss);
jTextField4.setText(Integer.toString(st));
} catch (IOException ex) {
Logger.getLogger(frame1.class.getName()).log(Level.SEVERE, null, ex);
}
}
jLabel7.setText("Scanning Finished. Thanks for waiting ");
}
});
}
}//GEN-LAST:event_jButton1ActionPerformed
private Task task;
#Override
public void propertyChange(PropertyChangeEvent evt) {
if ("progress".equals(evt.getPropertyName())) {
int progress = (Integer) evt.getNewValue();
jProgressBar1.setValue(progress);
System.out.println("Property changed");
}
}
//#Override
public void actionPerformed(ActionEvent e) {
}
class Task extends SwingWorker<Void, Void> {
#Override
public Void doInBackground() {
Random random = new Random();
int progress = 0;
setProgress(0);
while (progress < 100) {
try {
Thread.sleep(random.nextInt(100));
} catch (InterruptedException ignore) {}
progress += random.nextInt(10);
setProgress(Math.min(progress, 100));
}
return null;
}
/*
* Executed in event dispatching thread
*/
#Override
public void done() {
Toolkit.getDefaultToolkit().beep();
setCursor(null);
}
}
I would like your help, I'm trying to scan my pc for JPEG images to count them. I have two problems, the first is that I'm using a jtable, but the results is never added until the program ends, and the progress bar isn't synchronized sometimes it ends before the program and sometimes after. please help me resolve these two problems and thank you.
You're using a SwingWorker in order to create a background thread -- good -- but you're making Swing calls directly from that background thread -- bad:
jProgressBar1.setValue(n);
Instead call setProgress(...) from within your SwingWorker, and add a PropertyChangeListener to the worker that listens for changes to the worker's "progress" bound property.
For examples:
How do I make my SwingWorker example work properly?
Cant get JProgressBar to update from SwingWorker class
JProgressBar Tutorial
For an example of an mcve that shows an example of use of a JProgressBar with a SwingWorker:
import java.awt.event.ActionEvent;
import java.awt.event.KeyEvent;
import java.beans.PropertyChangeEvent;
import java.beans.PropertyChangeListener;
import java.util.Random;
import java.util.concurrent.ExecutionException;
import javax.swing.*;
#SuppressWarnings("serial")
public class TestProgress2 extends JPanel {
private JProgressBar progressBar = new JProgressBar(0, 100);
private Action startBackgroundTaskAction = new StartBackgroundTaskAction();
public TestProgress2() {
progressBar.setStringPainted(true);
add(progressBar);
add(new JButton(startBackgroundTaskAction));
}
public void setActionEnabled(boolean enabled) {
startBackgroundTaskAction.setEnabled(enabled);
}
private class StartBackgroundTaskAction extends AbstractAction {
public StartBackgroundTaskAction() {
super("Start Background Task");
putValue(MNEMONIC_KEY, KeyEvent.VK_S);
}
#Override
public void actionPerformed(ActionEvent e) {
progressBar.setString(null);
progressBar.setValue(0);
setActionEnabled(false);
MyTask myTask = new MyTask();
myTask.addPropertyChangeListener(new MyTaskListener());
myTask.execute();
}
}
private class MyTaskListener implements PropertyChangeListener {
#Override
public void propertyChange(PropertyChangeEvent pcEvt) {
MyTask myTask = (MyTask) pcEvt.getSource();
if ("progress".equals(pcEvt.getPropertyName())) {
int progress = myTask.getProgress();
progressBar.setValue(progress);
}
if (pcEvt.getNewValue() == SwingWorker.StateValue.DONE) {
setActionEnabled(true);
progressBar.setString("Done");
try {
myTask.get();
} catch (InterruptedException e) {
e.printStackTrace();
} catch (ExecutionException e) {
e.printStackTrace();
}
}
}
}
private class MyTask extends SwingWorker<Void, Void> {
#Override
protected Void doInBackground() throws Exception {
Random random = new Random();
int progress = 0;
setProgress(0);
while (progress < 100) {
try {
Thread.sleep(random.nextInt(1000));
} catch (InterruptedException ignore) {}
progress += random.nextInt(10);
setProgress(Math.min(progress, 100));
}
return null;
}
}
private static void createAndShowGui() {
TestProgress2 mainPanel = new TestProgress2();
JFrame frame = new JFrame("TestProgress2");
frame.setDefaultCloseOperation(JFrame.DISPOSE_ON_CLOSE);
frame.getContentPane().add(mainPanel);
frame.pack();
frame.setLocationByPlatform(true);
frame.setVisible(true);
}
public static void main(String[] args) {
SwingUtilities.invokeLater(new Runnable() {
public void run() {
createAndShowGui();
}
});
}
}

JProgressBar won't update

I'm trying the code I found on the voted answer from this question: Download file using java apache commons?
It's a download application, take a little look, (I'm not much familiar with JFrames and ActionEvents)
Download.java
package main;
public class Download extends JFrame implements Runnable{
public static int total;
public static int done;
private static class ProgressListener implements ActionListener{
#Override
public void actionPerformed(ActionEvent e) {
done = (int)((DownloadCountingOutputStream) e.getSource()).getByteCount();
jbar.repaint();
DownloadCountingOutputStream.parent.draw((int)((DownloadCountingOutputStream) e.getSource()).getByteCount());//redraw
DownloadCountingOutputStream.parent.repaint();
}
}
public static JProgressBar jbar = new JProgressBar();
public void draw(int downloaded){System.out.println("downloaded: "+downloaded+ " Total: "+total);
if (downloaded== 0){
Container cont = new Container();
setDefaultCloseOperation(3);
setSize(600, 450);
setResizable(false);
setVisible(true);
cont.add(jbar);
jbar.setBounds(40, 50, 500, 50);
jbar.setMaximum(total);//The total value of bytes to download
//jbar.setValue(50);
add(cont);
jbar.setVisible(true);
}
jbar.setValue(downloaded);
//This should update the value of the progress Bar
}
public void run() {
URL dl = null;
File fl = null;
OutputStream os = null;
InputStream is = null;
ProgressListener progressListener = new ProgressListener();
draw(done);
try {
fl = new File(System.getProperty("user.home").replace("\\", "/") + "/Desktop/afile.rar");
dl = new URL("https://dl.dropbox.com/u/48076798/afile.rar");
os = new FileOutputStream(fl);
is = dl.openStream();
total = Integer.parseInt(dl.openConnection().getHeaderField("Content-Length"));
String total = dl.openConnection().getHeaderField("Content-Length");
DownloadCountingOutputStream dcount = new DownloadCountingOutputStream(os);
dcount.setListener(progressListener);
dcount.setParent(this);
IOUtils.copy(is, dcount);
} catch (Exception e) {
System.out.println(e);
} finally {
if (os != null) {
try {
os.close();
} catch (IOException e) {
e.printStackTrace();
}
}
if (is != null) {
try {
is.close();
} catch (IOException e) {
e.printStackTrace();
}
}
}
}
}
DownloadCountingOutputStream.java
package main;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
import java.io.IOException;
import java.io.OutputStream;
import org.apache.commons.io.output.CountingOutputStream;
public class DownloadCountingOutputStream extends CountingOutputStream {
private ActionListener listener = null;
public static Download parent;
public DownloadCountingOutputStream(OutputStream out) {
super(out);
}
public void setListener(ActionListener listener) {
this.listener = listener;
}
public void setParent(Download o){
parent = o;
}
#Override
protected void afterWrite(int n) throws IOException {
super.afterWrite(n);
if (listener != null) {
listener.actionPerformed(new ActionEvent(this, 0, null));
}
}
}
It's difficult to tell from the code sample you've provide...
The main cause of this problem is trying to update the UI while blocking from the Event Dispatching Thread (EDT).
It's important to NEVER do any long running or blocking operations within the EDT as this will prevent repaint requests from been acted upon.
For more information have a read through Concurrency in Swing
The example below demonstrates the use of a SwingWorker that provides progress updates that are re-synced with the UI
public class TestProgress {
public static void main(String[] args) {
new TestProgress();
}
public TestProgress() {
EventQueue.invokeLater(new Runnable() {
#Override
public void run() {
try {
UIManager.setLookAndFeel(UIManager.getSystemLookAndFeelClassName());
} catch (ClassNotFoundException ex) {
} catch (InstantiationException ex) {
} catch (IllegalAccessException ex) {
} catch (UnsupportedLookAndFeelException ex) {
}
ProgressPane progressPane = new ProgressPane();
JFrame frame = new JFrame("Test");
frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
frame.setLayout(new BorderLayout());
frame.add(progressPane);
frame.setSize(200, 200);
frame.setLocationRelativeTo(null);
frame.setVisible(true);
progressPane.doWork();
}
});
}
public class ProgressPane extends JPanel {
private JProgressBar progressBar;
public ProgressPane() {
setLayout(new GridBagLayout());
progressBar = new JProgressBar();
add(progressBar);
}
public void doWork() {
Worker worker = new Worker();
worker.addPropertyChangeListener(new PropertyChangeListener() {
#Override
public void propertyChange(PropertyChangeEvent evt) {
if ("progress".equals(evt.getPropertyName())) {
progressBar.setValue((Integer) evt.getNewValue());
}
}
});
worker.execute();
}
}
public class Worker extends SwingWorker<Object, Object> {
#Override
protected Object doInBackground() throws Exception {
for (int index = 0; index < 1000; index++) {
int progress = Math.round(((float) index / 1000f) * 100f);
setProgress(progress);
Thread.sleep(10);
}
return null;
}
}
}

Load function in a thread

How can i use the callme(input); to get launched with a new thread?
/* We send username and password for register and load a heavy load */
public class button3 implements ActionListener
{
public void actionPerformed(ActionEvent e)
{
String input = output.getText();
if (input.length()<=0)
{
JOptionPane.showMessageDialog(null, "Empty....");
} else {
callme(input);
}
}
}
public static String callme() { //heavy loads... starts, which freezed the button
return "Did you called me?";
}
Try 1: but getting failed (output1 does not get the returned text results):
/* We send username and password for register and nat mapping */
public class button3 implements ActionListener
{
public void actionPerformed(ActionEvent e)
{
String input = output.getText();
if (input.length()<=0)
{
JOptionPane.showMessageDialog(null, "Empty....");
} else {
new Thread(new Runnable() {
public void run() {
try {
output1.setText( callme(output.getText()) );
} catch(Exception t) {
}
}
}).start();
}
}
}
Try 2: Also tried this, did not returns output1 = callme();
new Thread(new Runnable() {
public void run() {
final String result = callme(output.getText());
SwingUtilities.invokeLater(new Runnable() {
public void run() {
try {
output1.setText( result );
} catch(Exception t) {
}
}
});
}
}).start();
new Thread(new Runnable() {
public void run() {
try {
callme(input);
} catch(Exception t) {
// appropriate error reporting here
}
}
}).start();
Note that input must be declared as final.
Also, consider using invokeLater(Runnable) from Swing Utilities
Try this:
public class button3 implements ActionListener {
public void actionPerformed(ActionEvent e) {
final String input = output.getText();
if ( input.length() <= 0 ) {
JOptionPane.showMessageDialog(null, "Empty....");
}
else {
Thread t = new Thread(new Runnable() {
public void run() {
callme(input);
}
});
t.start();
}
}
public static String callme(String input) {}
}
If you modify swing controls inside your method you should use
new Thread(new Runnable() {
#Override
public void run() {
final String result = callme(input);
SwingUtilities.invokeLater(new Runnable() {
#Override
public void run() {
try {
output1.setText( result );
} catch(Exception t) {
}
}
});
}
}).start();
If you need the return value, you should really be using a Callable with an ExecutorService which will give you back a Future that you can use the retrieve the value later on.
See:
http://download.oracle.com/javase/6/docs/api/java/util/concurrent/Executors.html
http://download.oracle.com/javase/6/docs/api/java/util/concurrent/ExecutorService.html

Categories