I have this jFrame class:
public class Frame1 extends javax.swing.JFrame {
........
String name;
File file;
JFileChooser FileChooser = new JFileChooser();
if (FileChooser.getSelectedFile().isFile()) {
try {
file = FileChooser.getSelectedFile();
name = FileChooser.getSelectedFile().getName();
System.out.println( name );
} catch (FileNotFoundException ex) {
Logger.getLogger(Frame1.class.getName()).log(Level.SEVERE, null, ex);
}
}
........
private void Button1 (java.awt.event.ActionEvent evt) {
java.awt.EventQueue.invokeLater(new Runnable() {
#Override
public void run() {
Frame2 obj = new Frame2 ();
}
});
}
}
Then I created the class "Frame2":
public class Frame2 extends javax.swing.JFrame {
.......
}
As you can image, when my program starts I use a JFileChooser to choose a file;
after that I click a button that opens another jFrame; in this jFrame (Frame2)
What I would need is to use the file that I have chosen in the previous jFrame (Frame1).
So I need to use "file" variable from "Frame1" in "Frame2".
I tried to do this in Frame2:
Frame1 obj1 = new Frame1();
File file2 = obj1.file;
System.out.println( file2 );
So when I run the program and choose a file and then I click "Button1" to run "Frame2", it first prints the file name ("name") from "Frame1"
and after that it prints "null" so I can't get correct "file" value from "Frame1" and use it in "Frame2".
How can I do that?
Thanks
This won't work:
Frame1 obj1 = new Frame1();
File file2 = obj1.file;
System.out.println( file2 );
because it falls into a common newbie trap: thinking that a new instance of a class (here Frame1) holds the same information as another previously used instance of the class (the previous Frame1 instance that was displayed), and this simply isn't true unless you use static variables -- something I strongly urge you not to do.
Instead why not:
Change your first JFrame into a modal JDialog or JOptionPane
Give it a public method getSelectedFile() that returns the selected file. This is what your question is really about -- sharing the state of one object with another object -- and one way to do this is via your basic getter and setter methods.
Then show your dialog, and when it returns, call the above method on the above object.
Or why not instead simply show a JFileChooser dialog since it does all of this for you?
For example:
import java.io.File;
import javax.swing.*;
public class Foo {
private static void createAndShowGui() {
JFileChooser fileChooser = new JFileChooser();
int result = fileChooser.showOpenDialog(null);
if (result == JFileChooser.APPROVE_OPTION) {
File file = fileChooser.getSelectedFile();
JTextField field = new JTextField(file.getAbsolutePath(), 30);
JPanel panel = new JPanel();
panel.add(new JLabel("Selected File:"));
panel.add(field);
// create and open a new JFrame with the selected file's path
JFrame frame = new JFrame("Foo");
frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
frame.getContentPane().add(panel);
frame.pack();
frame.setLocationByPlatform(true);
frame.setVisible(true);
}
}
public static void main(String[] args) {
SwingUtilities.invokeLater(new Runnable() {
public void run() {
createAndShowGui();
}
});
}
}
Related
// Java Program to Launch the browser
// and open a specific URI
import java.awt.*;
import javax.swing.*;
import java.awt.event.*;
import java.net.*;
public class WOAH extends JFrame implements ActionListener{
//Creates a list of constants,,,, these are the names
private enum Actions {
Open,
Close
}
// frame
static JFrame f;
public static void main(String[] LOLZ){
desk d = new desk();
// create a frame
f = new JFrame("Nudes");
// create a panel
JPanel p = new JPanel();
// create a button
JButton b = new JButton("LUNCH");
JButton c = new JButton("CLOTHS");
//sets value for Command name
b.setActionCommand(Actions.Open.name());
c.setActionCommand(Actions.Close.name());
// add Action Listener
b.addActionListener(d);
c.addActionListener(d);
p.add(b);
p.add(c);
f.add(p);
f.setVisible(true);
f.setSize(200, 200);
}
// if button is pressed
public void actionPerformed(ActionEvent e)
{
try {
if (e.getActionCommand() == Actions.Open.name()) {
// create a URI
URI u = new URI("www.geeksforgeeks.org");
Desktop d = Desktop.getDesktop();
d.browse(u);
}
else if (e.getActionCommand() == Actions.Close.name()) {
System.exit(0);
}
}
catch (Exception evt) {
}
}
}
I have two sets of code in this set that I am trying to run, for simplicity sake I deleted the lines that ran which use a JOptionPane method.
My goal is to generate a JAR file but in this line of code I am not sure what the incompatibility is. Could it be the enum list or Action$ list that are saved to an external file? or is it the ActionListener? does anyone have any advice?
The code runs fine outside of the JAR configuration
I am trying to create a program where when the user clicks a JMenuItem (basic) in the frame in class2, it opens the frame in class1. However, when I try to run the code, I keep getting errors about how it can't find the "setVisible" method. I was wondering whether something could give me some pointers. Also, both classes are stored in different java files (but in the same folder).
CLASS 1:
public class CalculatorFrame {
private JFrame frame;
public String calc = "";
public CalculatorFrame() {
frame = new JFrame("Basic Calculator");
frame.setDefaultCloseOperation(JFrame.DISPOSE_ON_CLOSE);
CLASS 2:
public class CalculatorFrameA extends CalculatorFrame{
private JFrame frameA;
public CalculatorFrameA() {
frameA = new JFrame("Advanced Calculator");
frameA.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
ActionListener basicListener = new ActionListener(){ //basic is a JMenuItem
#Override
public void actionPerformed(ActionEvent e){
CalculatorFrame frame = new CalculatorFrame();
//frame.show();
frameA.dispose();
frame.setVisible(true);
}
};
I'm creating a parser that's why I use JFileChooser.
When I select a file with JFileChooser, I would like to have a JLabel that says : "parsing in progress" or smth like that.
And when it's done : "parsing done".
(My first aim was to use progress bars, but it's a bit complicated for me now)
The ReadFile class will take array of files and create Callable for each file. If 5 files : 5 threads will be called. I used Callable because I need to get back Strings of data for each Threads and write it in a same csv file.
Well, when I click on Cancel on JFileChooser, the JLabel displays correctly at the right moment but when I select files / file for the parsing function, the JLabel waits the entire execution of my Callables and then "processing" appears (but when it has already ended ^^).
I cannot manage to display processing at the beginning of the threads.
Note : I called CardLayout at this moment, but it is not used yet.
Here is my code :
public class Main {
private static final String CARD_MAIN = "Card Main";
private static final String CARD_FILE = "Card File";
public static void main(String[] args) throws IOException {
createGUI();
}
public static void createGUI(){
// the JFrame
final JFrame window = new JFrame();
window.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
window.setLocationRelativeTo(null);
window.setTitle("TMG Parser - Thales");
window.setSize(400, 100);
// the buttonPanel ( one to open JFileChooser & one to quit )
JPanel container = new JPanel();
JPanel buttonPanel = new JPanel();
final JButton fileButton = new JButton("Choose File");
fileButton.setBackground(Color.BLACK);
fileButton.setForeground(Color.WHITE);
final JButton quitButton = new JButton("Quit");
quitButton.setBackground(Color.RED);
quitButton.setForeground(Color.WHITE);
// adding buttons to panel
buttonPanel.add(fileButton);
buttonPanel.add(quitButton);
// the status label that says : processing or done
final JLabel status = new JLabel();
container.add(status);
fileButton.addActionListener(new ActionListener()
{
public void actionPerformed(ActionEvent ae)
{
JFileChooser dialogue = new JFileChooser(new File("."));
dialogue.setMultiSelectionEnabled(true) ;
if (dialogue.showOpenDialog(null)==
JFileChooser.APPROVE_OPTION) {
status.setText("Processing");
File[] fichiers=dialogue.getSelectedFiles();
for( int i = 1; i<fichiers.length; ++i){
fichiers[i].getName();
fichiers[i].getAbsolutePath();
}
// calling my execution function (threads)
ReadFile readProgram = new ReadFile(fichiers);
}
else{status.setText("Action cancelled");}
}
});
quitButton.addActionListener(new ActionListener()
{
public void actionPerformed(ActionEvent ae)
{
System.exit(0);
}
});
window.add(container, BorderLayout.CENTER);
window.add(buttonPanel, BorderLayout.PAGE_END);
window.setVisible(true);
}
}
Ok so #tobias_k was right ! Thank you man.
When I launched ReadFile, that was freezing my swing thread until ReadFile was done.
I changed ReadFile to a thread (and calling callables), and now it works perfectly.
Thanks !
I do not want to specify a directory. I just want it to automatically "know" and open in the directory the user is working in. How do I do this?
This examples defaults to the user.dir on first showing. It then retains the instance of the chooser to automatically track the last load or save location, as suggested by MadProgrammer.
import java.awt.*;
import java.awt.event.*;
import javax.swing.*;
import javax.swing.border.EmptyBorder;
import java.io.*;
public class ChooserInCurrentDir {
// the GUI as seen by the user (without frame)
JPanel gui = new JPanel(new BorderLayout());
JFileChooser fileChooser;
private JTextArea output = new JTextArea(10, 40);
ChooserInCurrentDir() {
initComponents();
}
public final void initComponents() {
gui.setBorder(new EmptyBorder(2, 3, 2, 3));
String userDirLocation = System.getProperty("user.dir");
File userDir = new File(userDirLocation);
// default to user directory
fileChooser = new JFileChooser(userDir);
Action open = new AbstractAction("Open") {
#Override
public void actionPerformed(ActionEvent e) {
int result = fileChooser.showOpenDialog(gui);
if (result == JFileChooser.APPROVE_OPTION) {
try {
File f = fileChooser.getSelectedFile();
FileReader fr = new FileReader(f);
output.read(fr, f);
fr.close();
} catch (Exception ex) {
ex.printStackTrace();
}
}
}
};
Action save = new AbstractAction("Save") {
#Override
public void actionPerformed(ActionEvent e) {
int result = fileChooser.showSaveDialog(gui);
throw new UnsupportedOperationException("Not supported yet.");
}
};
JToolBar tb = new JToolBar();
gui.add(tb, BorderLayout.PAGE_START);
tb.add(open);
tb.add(save);
output.setWrapStyleWord(true);
output.setLineWrap(true);
gui.add(new JScrollPane(
output,
JScrollPane.VERTICAL_SCROLLBAR_ALWAYS,
JScrollPane.HORIZONTAL_SCROLLBAR_NEVER));
}
public final JComponent getGui() {
return gui;
}
public static void main(String[] args) {
Runnable r = new Runnable() {
#Override
public void run() {
ChooserInCurrentDir cicd = new ChooserInCurrentDir();
JFrame f = new JFrame("Chooser In Current Dir");
f.add(cicd.getGui());
// Ensures JVM closes after frame(s) closed and
// all non-daemon threads are finished
f.setDefaultCloseOperation(JFrame.DISPOSE_ON_CLOSE);
// See http://stackoverflow.com/a/7143398/418556 for demo.
f.setLocationByPlatform(true);
// ensures the frame is the minimum size it needs to be
// in order display the components within it
f.pack();
// should be done last, to avoid flickering, moving,
// resizing artifacts.
f.setVisible(true);
}
};
// Swing GUIs should be created and updated on the EDT
// http://docs.oracle.com/javase/tutorial/uiswing/concurrency
SwingUtilities.invokeLater(r);
}
}
Basically, you can't. You need to tell it.
When constructed with a null currentDirectory (such as the default constructor), it will use FileSystemView#getDefaultDirectory.
You could create a single instance of JFileChooser for each base task (one for saving, one for opening for example) and simply maintain that instance, which will "remember" the last directory that it was using, you'd still need to seed it with a starting directory though
Another choice would be to construct some kind of library call that could load and save the last directory the user used based on some unique key. This means you could simply do something like...
File toFile = MyAwesomeLibrary.getSaveFile(APPLICATION_DOCUMENT_SAVE_KEY);
Which would load the last known directory for the supplied key and show the JFileChooser configured with that value and would be capable of returning the selected File or null if the user canceled the operation...for example...
If you want to set the directory they were in at the previous opening of the file chooser you need to set the current directory.
//This will set the directory to the directory they previously chose a file from.
fileChooser.setCurrentDirectory(fileChooser.getCurrentDirectory());
Im not sure if this is what you're looking for, But when they select a file then go to select another file, it will maintain the directory they were in from the previous selection.
If you want your application to look for the user's working directory, you can try this:
String curDir = System.getProperty("user.dir");
How do you display the contents of a text file in a TextArea when your using JFileChooser.
You have to read official Oracle's JTextArea tutorial
Especially method JTextArea.read(fileSelectedFromJFileChooser) , maybe right way in this case
Please have a look at Reading, Writing and Creating Files Tutorials
Here find one example program, for your help, though if the file to be read is long, then always take the help of SwingWorker :
import java.io.*;
import java.awt.*;
import java.awt.event.*;
import javax.swing.*;
public class ReadFileExample
{
private BufferedReader input;
private String line;
private JFileChooser fc;
public ReadFileExample()
{
line = new String();
fc = new JFileChooser();
}
private void displayGUI()
{
final JFrame frame = new JFrame("Read File Example");
frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
final JTextArea tarea = new JTextArea(10, 10);
JButton readButton = new JButton("OPEN FILE");
readButton.addActionListener(new ActionListener()
{
public void actionPerformed(ActionEvent ae)
{
int returnVal = fc.showOpenDialog(frame);
if (returnVal == JFileChooser.APPROVE_OPTION) {
File file = fc.getSelectedFile();
//This is where a real application would open the file.
try
{
input = new BufferedReader(
new InputStreamReader(
new FileInputStream(
file)));
tarea.read(input, "READING FILE :-)");
}
catch(Exception e)
{
e.printStackTrace();
}
} else {
System.out.println("Operation is CANCELLED :(");
}
}
});
frame.getContentPane().add(tarea, BorderLayout.CENTER);
frame.getContentPane().add(readButton, BorderLayout.PAGE_END);
frame.pack();
frame.setLocationByPlatform(true);
frame.setVisible(true);
}
public static void main(String... args)
{
SwingUtilities.invokeLater(new Runnable()
{
public void run()
{
new ReadFileExample().displayGUI();
}
});
}
}
Your question is unclear, but I am assuming you want to add the JTextArea to the JFileChooser so that it can act like a file preview panel.
You can add a JTextArea to the JFileChooser by using the setAccessory() method.
This tutorial on JFileChooser shows how to do something similar where the accessory displays an image from the file rather than text from the file.
You will need to be careful to deal properly with files that don't contain text, or which are too large, or which cannot be opened due to permission, etc. It will take a good bit of effort to get it right.