Appending to a GUI from a seperate class...
Basically, I am working on a program that runs a thread each time a user enters in a file name into the GUI. Every second it checks to see if the file exists, and when it is found the Thread is done. It appends a message every second to the JTextArea of the GUI until the file is found, at which point is prints the finishing message and then stops.
My problem is that I don't know how to get it to append the JTextArea in the GUI with the message that's supposed to append to the JTextArea every second until the file is found.
This is the code I have so far for the Thread class:
import java.io.*;
publicclass FileSearcher
{
public String fileName ="";
public String output ="";
publicvoid checkForFile(String fileName)
{
while(anotherThread ==true)
{
anotherThread =false;
this.fileName = fileName;
Thread fileThread =new Thread(new MyThread());
fileThread.setPriority(( (int) (Math.random() * 10)) + 1);
fileThread.start();
}
}
class MyThreadextends Thread
{
publicvoid run()
{
File file =null;
do
{
file =new File(fileName);
output = String.format(file.exists()?"Searching for file "+ fileName :"***File "+ fileName +" has been created.***\n");
try
{
this.wait(1);
}
catch(InterruptedException ie)
{
System.out.println(ie.getMessage());
}
}while (file.exists() ==false);
}
}
}
GUI class:
import java.awt.*;
import java.awt.event.*;
import javax.swing.*;
import java.util.*;
publicclass RunFileSearcher
{
/**
*Creates the JFrame
**/
JFrame frame =new JFrame();
/**
*Panels needed for the interface
**/
JPanel topPanel =new JPanel();
JPanel midPanel =new JPanel();
JPanel bottomPanel =new JPanel();
/**
*Text field, text area, and label
**/
JLabel enterFile =new JLabel("Enter a file name to search");
JTextField fileNameField =new JTextField(15);
JTextArea outputArea =new JTextArea(10, 20);
/**
*Buttons
**/
JButton searchButton =new JButton("Search");
JButton clearButton =new JButton("Clear");
JButton exitButton =new JButton("Exit");
/**
*Scroll pane
**/
JScrollPane scrollPane =new JScrollPane(outputArea);
/**
*Default constructor
**/
public RunFileSearcher()
{
frame.setTitle("File Searcher");
frame.setSize(500, 400);
frame.setLocation(200, 200);
/**
*Setting the Mnemonics
**/
searchButton.setMnemonic('S');
clearButton.setMnemonic('C');
exitButton.setMnemonic('x');
/**
*Adding listeners to the buttons
**/
ButtonListener buttonListener =new ButtonListener();
searchButton.addActionListener(buttonListener);
clearButton.addActionListener(buttonListener);
exitButton.addActionListener(buttonListener);
/**
*Setting up the top panel
**/
topPanel.add(enterFile);
topPanel.add(fileNameField);
/**
*Setting up the middle panel
**/
outputArea.setEditable(false);
scrollPane.setPreferredSize(new Dimension(500, 350));
midPanel.add(scrollPane);
/**
*Setting up the botton panel
**/
bottomPanel.add(searchButton);
bottomPanel.add(clearButton);
bottomPanel.add(exitButton);
/**
*Adding the panels to the frame
**/
frame.add(topPanel, BorderLayout.NORTH);
frame.add(midPanel, BorderLayout.CENTER);
frame.add(bottomPanel, BorderLayout.SOUTH);
/**
*Adding a window listener to handle window closing
**/
frame.addWindowListener(new WindowAdapter()
{
publicvoid windowClosing(WindowEvent we)
{
System.exit(0);
}
});
/**
*Making the frame visible
**/
frame.setVisible(true);
}
publicclass ButtonListenerimplements ActionListener
{
publicvoid actionPerformed(ActionEvent ae)
{
}
}
publicstaticvoid main(String[] args)
{
RunFileSearcher runFileSearcher =new RunFileSearcher();
}
}
[7834 byte] By [
Sekka] at [2007-11-26 15:14:39]

FileSearcher should have a reference to an interface which RunFileSearcher
implements. The interface should have a method named something like addLogRecord(String)
You do also have an error FileSearcher. You should use sleep instead of wait, and the argument is milliseconds and not seconds. It's also pretty pointless to recreate the File object in the loop.
Kaj
If that was the case, then wouldn't I also have to add the one-second sleep for appending the output in the addLogRecord method?
Sekka at 2007-7-8 9:06:10 >

> If that was the case, then wouldn't I also have to> add the one-second sleep for appending the output in> the addLogRecord method?No, why do you want to sleep there? You should check for a file, log the result, sleep, check for a file, log the result,
Ah, I got it now. Thank you for your help.
Sekka at 2007-7-8 9:06:10 >

> Oh, no, the output has to be actively updated to the
> JTextArea every second, not just print all at once
> when the Thread is finished.
>
> Edited: typo
What? What is described was a loop that updates the text area each second. Who said anything about updating only once?
Kaj
Ah, thought I had it, but I hit another roadblock. I referenced the file in FileSearcher and logged the results, but when defining the addLogRecord method in RunFileSearcher, where would the String argument come from?
This is the code I have so far:
FileSearcher
import java.io.*;
public class FileSearcher
{
boolean anotherThread = false;
public String fileName = "";
public String output = "";
public void checkForFile(String fileName)
{
while(anotherThread == true)
{
anotherThread = false;
this.fileName = fileName;
Thread fileThread = new Thread(new MyThread());
fileThread.setPriority(( (int) (Math.random() * 10)) + 1);
fileThread.start();
}
}
class MyThread extends Thread
{
public FileSearcherInterface fsi = new RunFileSearcher();
public void run()
{
File file = new File(fileName);
do
{
fsi.addLogRecord(String.format(file.exists()? "Searching for file "+ fileName : "***File "+ fileName +" has been created.***\n"));
try
{
this.sleep(1000);
}
catch(InterruptedException ie)
{
System.out.println(ie.getMessage());
}
} while (file.exists() == false);
}
}
}
RunFileSearcher
import java.awt.*;
import java.awt.event.*;
import javax.swing.*;
import java.util.*;
public class RunFileSearcher implements FileSearcherInterface
{
/**
*Creates the JFrame
**/
JFrame frame = new JFrame();
/**
*Panels needed for the interface
**/
JPanel topPanel = new JPanel();
JPanel midPanel = new JPanel();
JPanel bottomPanel = new JPanel();
/**
*Text field, text area, and label
**/
JLabel enterFile = new JLabel("Enter a file name to search");
JTextField fileNameField = new JTextField(15);
JTextArea outputArea = new JTextArea(10, 20);
/**
*Buttons
**/
JButton searchButton = new JButton("Search");
JButton clearButton = new JButton("Clear");
JButton exitButton = new JButton("Exit");
/**
*Scroll pane
**/
JScrollPane scrollPane = new JScrollPane(outputArea);
/**
*Default constructor
**/
public RunFileSearcher()
{
frame.setTitle("File Searcher");
frame.setSize(500, 400);
frame.setLocation(200, 200);
/**
*Setting the Mnemonics
**/
searchButton.setMnemonic('S');
clearButton.setMnemonic('C');
exitButton.setMnemonic('x');
/**
*Adding listeners to the buttons
**/
ButtonListener buttonListener = new ButtonListener();
searchButton.addActionListener(buttonListener);
clearButton.addActionListener(buttonListener);
exitButton.addActionListener(buttonListener);
/**
*Setting up the top panel
**/
topPanel.add(enterFile);
topPanel.add(fileNameField);
/**
*Setting up the middle panel
**/
outputArea.setEditable(false);
scrollPane.setPreferredSize(new Dimension(500, 350));
midPanel.add(scrollPane);
/**
*Setting up the botton panel
**/
bottomPanel.add(searchButton);
bottomPanel.add(clearButton);
bottomPanel.add(exitButton);
/**
*Adding the panels to the frame
**/
frame.add(topPanel, BorderLayout.NORTH);
frame.add(midPanel, BorderLayout.CENTER);
frame.add(bottomPanel, BorderLayout.SOUTH);
/**
*Adding a window listener to handle window closing
**/
frame.addWindowListener(new WindowAdapter()
{
public void windowClosing(WindowEvent we)
{
System.exit(0);
}
});
/**
*Making the frame visible
**/
frame.setVisible(true);
}
public class ButtonListener implements ActionListener
{
public void addLogRecord(String theOutput)
{
outputArea.append(output);
}
public void actionPerformed(ActionEvent ae)
{
JButton buttonSource = (JButton)ae.getSource();
if(buttonSource == searchButton)
{
FileSearcher fileSearcher = new FileSearcher();
addLogRecord(output);
}
else
{
if(buttonSource == clearButton)
{
outputArea.setText("");
fileNameField.requestFocusInWindow();
}
else
{
System.exit(0);
}
}
}
}
public static void main(String[] args)
{
RunFileSearcher runFileSearcher = new RunFileSearcher();
}
}
Sekka at 2007-7-8 9:06:10 >

addLogRecord in RunFileSearcher should look something like this:public void addLogRecord(String text) {outputArea.append(text);}
Your code is very odd..
MyThread should implement Runnable and not extend thread. The constructor to MyThread should take an argument which is of type FileSearcherInterface. You should not create a new instance of RunFileSearcher in that class.
RunFileSearcher should pass a reference to itself (using this) when creating a FileSearcher instance. (FileSearcher constructor should also take FileSearcherInterface as argument)
Kaj
Now I'm getting confused. What would I do with the FileSearcherInterface argument in the MyThread constructor if I'm not to make a reference of it in the run method that I can use to set the output to each time the thread loops?
Sekka at 2007-7-8 9:06:10 >

> Now I'm getting confused. What would I do with the
> FileSearcherInterface argument in the MyThread
> constructor if I'm not to make a reference of it in
> the run method that I can use to set the output to
> each time the thread loops?
I hope this explains what I mean. It's just a small sample which looks like what you have written
class FileSearcher {
private Logger logger;
FileSearcher(Logger logger) {
this.logger = logger;
}
public void checkForFile(String filename) {
new Thread(new MyThread(logger, filename)).start();
}
static class MyThread implements Runnable {
private String filename;
private Logger logger;
MyThread(Logger logger, String filename) {
this.logger = logger;
this.filename = filename;
}
public void run() {
while (true) {
logger.addRecord("Checking for " + filename);
try {
Thread.sleep(1000);
} catch (InterruptedException e) {
e.printStackTrace();
}
}
}
}
}
class RunFileSearcher implements Logger {
RunFileSearcher() {
new FileSearcher(this).checkForFile("blah.txt");
}
public static void main(String[] args) {
new RunFileSearcher();
}
public void addRecord(String text) {
System.out.println(text);
}
}
interface Logger {
void addRecord(String text);
}
Ah, yes, that clears it up. I really appreciate the help!
Sekka at 2007-7-8 9:06:10 >
