Gui and binary files - java

I'm currently working on a project for a class I have, where we have to create a GUI that asks for a number, then read a binary files of 10,000 customers and return the other information on the one with the customer number entered. We also have to have an error that pops up as a JOptionPane when a number outside of 1-10,000 is entered. I'm having some problems with the error message, and my professor also said we need to have a method with this signature:
private Customer getCustomer(long custNumber) throws IOException
that searches the file and returns a customer object. I'm also not sure where exactly to do that. So I started with what I already know, and here's what I have:
import javax.swing.*;
import java.awt.event.*;
import java.io.*;
import java.util.logging.Level;
import java.util.logging.Logger;
import javax.swing.JOptionPane;
public class CustomerLocator extends JFrame
{
private JPanel panel;
private JLabel custNumLabel;
private JLabel custNameLabel;
private JLabel custDisLabel;
private JLabel custBalLabel;
private JLabel custPrefLabel;
private JTextField custNumField;
private JTextField custNameField;
private JTextField custDisField;
private JTextField custBalField;
private JTextField custPrefField;
private JButton findCustBut;
private final int WINDOW_WIDTH = 300;
private final int WINDOW_HEIGHT = 500;
public CustomerLocator()
{
setTitle("Customer Locator");
setSize(WINDOW_WIDTH, WINDOW_HEIGHT);
setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
buildPanel();
add(panel);
setVisible(true);
}
private void buildPanel()
{
custNumLabel = new JLabel("Enter a valid Customer Number: ");
custNumField = new JTextField(10);
custNameLabel = new JLabel("Customer Name: ");
custNameField = new JTextField(10);
custNameField.setEditable(false);
custDisLabel = new JLabel("Customer Discount: ");
custDisField = new JTextField(10);
custDisField.setEditable(false);
custBalLabel = new JLabel("Customer Balance: ");
custBalField = new JTextField(10);
custBalField.setEditable(false);
custPrefLabel = new JLabel("Preferred? ");
custPrefField = new JTextField(10);
custPrefField.setEditable(false);
findCustBut = new JButton("Find this Customer!");
panel = new JPanel();
findCustBut.addActionListener(new ListenerToFindCustomer());
panel.add(custNumLabel);
panel.add(custNumField);
panel.add(findCustBut);
panel.add(custNameLabel);
panel.add(custNameField);
panel.add(custDisLabel);
panel.add(custDisField);
panel.add(custBalLabel);
panel.add(custBalField);
panel.add(custPrefLabel);
panel.add(custPrefField);
}
private class ListenerToFindCustomer implements ActionListener
{
public void actionPerformed(ActionEvent e)
{
String numEnteredStr;
long custNumEntered;
String custName;
boolean preferred;
String preferredDisplay;
double acctBal;
String acctBalDisplay;
double discount;
String discountDisplay;
numEnteredStr = custNumField.getText();
custNumEntered = Long.parseLong(numEnteredStr);
int ct=0;
try
{
FileInputStream inStream =
new FileInputStream("c:\\cps\\CustomerObjects.dat");
// DataInputStream inputFile = new DataInputStream(inStream);
ObjectInputStream objectInputFile =
new ObjectInputStream(inStream);
while(true)
{
ct++;
Customer obj = (Customer)objectInputFile.readObject();
//System.out.println(obj.getCustName());
if (custNumEntered == obj.getCustNum())
{
custName = obj.getCustName();
acctBal = obj.getBalance();
acctBalDisplay = Double.toString(acctBal);
discount = obj.getDiscount();
discountDisplay = Double.toString(discount);
preferred = obj.getPreferred();
preferredDisplay = Boolean.toString(preferred);
custNameField.setText(custName);
custBalField.setText(acctBalDisplay);
custPrefField.setText(preferredDisplay);
custDisField.setText(discountDisplay);
if (custNameField == null)
{
JOptionPane.showMessageDialog(null, "Error");
}
}
}
}
catch (Exception ex)
{
System.out.println(ex.toString());
}
}
}
public static void main(String[] args)
{
new CustomerLocator();
}
}
So, with this, the JOptionPane doesn't show up, so my questions are
1. How do I get the error message to pop up?
2. How do I incorporate the method my professor requested?

Your code
if (custNameField == null)
{
JOptionPane.showMessageDialog(null, "Error");
}
should read
if (custName == null)
{
JOptionPane.showMessageDialog(null, "Error");
}
It should also be moved outside of the while loop.
You also need a way to break the loop once you reach the end of the file.
Everything inside and including your try { ... } catch (Exception ex) { ... } can be moved to the method that your instructor suggests.
You should also change the try-catch to have another catch (IOException ioEx) { throw ioEx; }

Related

How do I refresh the information from text fields in this loop?

I am trying to make a login GUI, which closes when a correct combination of username and password are entered. When I enter them correctly, it works fine, but if an incorrect combination is entered, the loop just keeps repeating with the same values of "u" and "pw", stopping me from typing anything else.
I tried adding a logB.setSelected(false); at the end of the while loop, but it still doesn't let me enter new values.
(BTW I know that the incorrect password label shows up from the beginning, but I'm just trying to solve this problem right now. Also the Login class started off as CLI, so there are some remnants of that left in the code, but I just want to get it working before I clean it up.)
GUI class:
import javax.swing.*;
import java.awt.event.*;
import java.io.*;
public class Login_GUI implements ActionListener {
private static JLabel userL;
private static JTextField userT;
private static JLabel pwL;
private static JPasswordField pwT;
private static JLabel respL;
private static JFrame f;
public static boolean authorized;
public static void GUIfunc(){
JPanel p = new JPanel();
f = new JFrame("RMT 1.0");
f.setSize(250, 225);
f.setLocation(1080,530);
f.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
f.setVisible(true);
f.add(p);
userL = new JLabel("Username:");
userL.setBounds(10,20,80,25);
p.add(userL);
userT = new JTextField(20);
userT.setBounds(100,20,165,25);
p.add(userT);
pwL = new JLabel("Password:");
pwL.setBounds(10,50,80,25);
p.add(pwL);
pwT = new JPasswordField(20);
pwT.setBounds(100,50,165,25);
p.add(pwT);
JButton logB = new JButton("Login");
logB.setBounds(10,80,80,25);
logB.addActionListener(new Login_GUI());
p.add(logB);
respL = new JLabel("Incorrect username or password.");
respL.setBounds(10,100,80,25);
respL.setEnabled(false);
p.add(respL);
}
#Override
public void actionPerformed(ActionEvent e){
while (authorized != true){
String u = userT.getText();
String pw = pwT.getText();
try {
authorized = Login2.loginfunc(u,pw);
}
catch(IOException exc){
exc.printStackTrace();
}
logB.setSelected(false);
}
f.dispatchEvent(new WindowEvent(f, WindowEvent.WINDOW_CLOSING));
}
}
Login class:
import java.util.*;
import java.io.*;
import java.nio.*;
class Login2{
public static boolean loginfunc(String u, String pw)throws IOException{
File users = new File("C:\\Users\\Marcell\\OneDrive\\Computer Science\\IA\\users.txt");
Scanner kb = new Scanner (System.in);
Scanner sc = new Scanner (users);
String token1 = "";
int numOfEmp = 3;
boolean authorized = false;
boolean repeat = true;
String temp[] = new String[numOfEmp];
for(int x=0;x<numOfEmp;x++){
token1 = sc.nextLine();
temp[x] = token1;
}
String full = u + "," + pw;
for (int x=0;x<numOfEmp;x++ ){
String pass = temp[x];
if (pass.equals(full)){
System.out.println("Login successful.");
authorized = true;
repeat = false;
}
}
if (repeat = false){
return(false);
}
return(authorized);
}
}
Thanks for the help in advance!
Replace actionPerformed as follows:
public void actionPerformed(ActionEvent e){
if (!authorized){
String u = userT.getText();
String pw = pwT.getText();
try {
authorized = Login2.loginfunc(u,pw);
if(authorized) {
f.dispatchEvent(new WindowEvent(f, WindowEvent.WINDOW_CLOSING));
}
}
catch(IOException exc){
exc.printStackTrace();
}
logB.setSelected(false);
}
}

Break a while(true) dependency from class A that depends on class B

Consider the following class that just gets an IP and port number :
package view;
import java.awt.*;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
import java.net.InetAddress;
import javax.swing.*;
import javax.swing.border.EmptyBorder;
/**
* Server side
* #author X
*
*/
class ServerConnector implements ActionListener
{
private JFrame m_frame = null;
private JTextField m_serverIP;
private JTextField m_serverPort; // you can use also JPasswordField
private JButton m_submitButton;
// location of the jframe
private final int m_centerX = 500;
private final int m_centerY = 300;
// dimensions of the jframe
private final int m_sizeX = 1650;
private final int m_sizeY = 150;
private String m_ip;
private String m_port;
private boolean ready = false;
/**
* Ctor
*/
ServerConnector()
{
m_frame = new JFrame("Sever Side Listener");
m_frame.setDefaultCloseOperation(JFrame.DISPOSE_ON_CLOSE);
m_serverIP = new JTextField(20);
m_serverPort = new JTextField(20);
JPanel gui = new JPanel(new BorderLayout(3,3));
gui.setBorder(new EmptyBorder(5,5,5,5));
gui.setSize(m_sizeX , m_sizeY);
m_frame.setContentPane(gui);
JPanel labels = new JPanel(new GridLayout(0,1));
JPanel controls = new JPanel(new GridLayout(0,1));
gui.add(labels, BorderLayout.WEST);
gui.add(controls, BorderLayout.CENTER);
labels.add(new JLabel("Server IP: "));
controls.add(m_serverIP);
labels.add(new JLabel("Server Port: "));
controls.add(m_serverPort);
m_submitButton = new JButton("Start Listening");
m_submitButton.addActionListener(this);
gui.add(m_submitButton, BorderLayout.SOUTH);
m_frame.setLocation(m_centerX , m_centerY);
m_frame.setSize(m_sizeX , m_sizeY);
m_frame.pack();
m_frame.setVisible(true);
}
public static void main(String[] args) {
new ServerConnector();
}
#Override
public void actionPerformed(ActionEvent event) {
Object object = event.getSource();
if (object == this.m_submitButton)
{
// grab all values from the connection box
// if one of them is missing then display an alert message
String ip = this.m_serverIP.getText().trim();
String port = this.m_serverPort.getText().trim();
if (ip.length() == 0)
{
JOptionPane.showMessageDialog(null, "Please enter IP address !");
return;
}
if (port.length() == 0)
{
JOptionPane.showMessageDialog(null, "Please enter Port number!");
return;
}
int s_port = 0;
try
{
// try parse the Port number
// throws exception when an incorrect IP address
// is entered , and caught in the catch block
s_port = Integer.parseInt(port);
}
catch(Exception exp)
{
JOptionPane.showMessageDialog(null, "Port number is incorrect!");
return;
}
try
{
// try parse the IP address
// throws exception when an incorrect IP address
// is entered , and caught in the catch block
InetAddress.getByName(ip);
}
catch(Exception exp)
{
JOptionPane.showMessageDialog(null, "IP address is incorrect!");
return;
}
m_frame.dispose();
this.m_ip = ip;
this.m_port = port;
ready = true;
// new ServerGUI(ip , s_port);
}
}
public boolean isReady()
{
return this.ready;
}
/**
*
* #return
*/
public String[] getIPandPort()
{
String[] ipPort = new String[2];
ipPort[0] = this.m_ip;
ipPort[1] = this.m_port;
return ipPort;
}
}
And the would be controller class
public class ServerController {
String m_ip;
int m_port;
public static void main(String args[])
{
ServerConnector sc = new ServerConnector();
while (!sc.isReady())
{
// run
}
// get IP and port
String[] ipPort = sc.getIPandPort();
System.out.println("IP is :" + ipPort[0] + " and port is :" + ipPort[1]);
}
}
For now ServerController is in a while(true) loop , until the user has entered the IP and Port.
How can I avoid this kind of dependency (avoid the while loop) ?
First of all, get rid of the while (true) loop as its only purpose will be to mess your code up.
A general solution is to get the information from the user in code that blocks program flow. A problem occurs, though if this is needed in a GUI that cannot have its event thread blocked.
One Swing solution is as we have discussed previously in your previous question: use a modal dialog to get the information. The modality of the dialog will halt the program flow in the calling code until the dialog is handled.
If you want to avoid use of modal dialogs, then another general event-driven solution is to use a observer design pattern -- have one object be notified by another when information or state has changed. This can be achieved easily with use of PropertyChangeSupport and PropertyChangeListeners, although there are other ways as well, including using the XxxxListeners available in the Swing library.
For example of listener use and MVC with Swing:
Modifying independent JPanels from the JFrame
Java keeps adding buttons! - JFrames
Edit
For example, changes marked with a // !! comment:
import java.awt.*;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
import java.beans.PropertyChangeEvent;
import java.beans.PropertyChangeListener;
import java.net.InetAddress;
import javax.swing.*;
import javax.swing.border.EmptyBorder;
import javax.swing.event.SwingPropertyChangeSupport;
public class ServerController {
String m_ip;
int m_port;
private static String[] ipPort;
public static void main(String args[]) {
final ServerConnector sc = new ServerConnector();
sc.addPropertyChangeListener(new PropertyChangeListener() {
#Override
public void propertyChange(PropertyChangeEvent evt) {
if (ServerConnector.READY.equals(evt.getPropertyName())) {
if (sc.isReady()) {
ipPort = sc.getIPandPort();
System.out.println("IP is :" + ipPort[0] + " and port is :" + ipPort[1]);
}
}
}
});
}
}
class ServerConnector implements ActionListener {
public static final String READY = "ready"; //!!
private SwingPropertyChangeSupport pcSupport = new SwingPropertyChangeSupport(this); //!!
private boolean ready = false;
private JFrame m_frame = null;
private JTextField m_serverIP;
private JTextField m_serverPort; // you can use also JPasswordField
private JButton m_submitButton;
// location of the jframe
private final int m_centerX = 500;
private final int m_centerY = 300;
// dimensions of the jframe
private final int m_sizeX = 1650;
private final int m_sizeY = 150;
private String m_ip;
private String m_port;
/**
* Ctor
*/
ServerConnector() {
m_frame = new JFrame("Sever Side Listener");
m_frame.setDefaultCloseOperation(JFrame.DISPOSE_ON_CLOSE);
m_serverIP = new JTextField(20);
m_serverPort = new JTextField(20);
JPanel gui = new JPanel(new BorderLayout(3, 3));
gui.setBorder(new EmptyBorder(5, 5, 5, 5));
gui.setSize(m_sizeX, m_sizeY);
m_frame.setContentPane(gui);
JPanel labels = new JPanel(new GridLayout(0, 1));
JPanel controls = new JPanel(new GridLayout(0, 1));
gui.add(labels, BorderLayout.WEST);
gui.add(controls, BorderLayout.CENTER);
labels.add(new JLabel("Server IP: "));
controls.add(m_serverIP);
labels.add(new JLabel("Server Port: "));
controls.add(m_serverPort);
m_submitButton = new JButton("Start Listening");
m_submitButton.addActionListener(this);
gui.add(m_submitButton, BorderLayout.SOUTH);
m_frame.setLocation(m_centerX, m_centerY);
m_frame.setSize(m_sizeX, m_sizeY);
m_frame.pack();
m_frame.setVisible(true);
}
public static void main(String[] args) {
new ServerConnector();
}
#Override
public void actionPerformed(ActionEvent event) {
Object object = event.getSource();
if (object == this.m_submitButton) {
// grab all values from the connection box
// if one of them is missing then display an alert message
String ip = this.m_serverIP.getText().trim();
String port = this.m_serverPort.getText().trim();
if (ip.length() == 0) {
JOptionPane.showMessageDialog(null, "Please enter IP address !");
return;
}
if (port.length() == 0) {
JOptionPane.showMessageDialog(null, "Please enter Port number!");
return;
}
int s_port = 0;
try {
// try parse the Port number
// throws exception when an incorrect IP address
// is entered , and caught in the catch block
s_port = Integer.parseInt(port);
}
catch (Exception exp) {
JOptionPane.showMessageDialog(null, "Port number is incorrect!");
return;
}
try {
// try parse the IP address
// throws exception when an incorrect IP address
// is entered , and caught in the catch block
InetAddress.getByName(ip);
}
catch (Exception exp) {
JOptionPane.showMessageDialog(null, "IP address is incorrect!");
return;
}
m_frame.dispose();
this.m_ip = ip;
this.m_port = port;
setReady(true); //!!
// !! ready = true;
// new ServerGUI(ip , s_port);
}
}
// !! added
public void setReady(boolean ready) {
boolean oldValue = this.ready;
boolean newValue = ready;
this.ready = ready;
pcSupport.firePropertyChange(READY, oldValue, newValue);
}
//!! added
public void addPropertyChangeListener(PropertyChangeListener listener) {
pcSupport.addPropertyChangeListener(listener);
}
//!! added
public void removePropertyChangeListener(PropertyChangeListener listener) {
pcSupport.removePropertyChangeListener(listener);
}
public boolean isReady() {
return this.ready;
}
/**
*
* #return
*/
public String[] getIPandPort() {
String[] ipPort = new String[2];
ipPort[0] = this.m_ip;
ipPort[1] = this.m_port;
return ipPort;
}
}

saving and opening objects from a menu

here is my application. I'm having a problem saving objects and opening them. When I try to save it tells me the variable in the save.writeObject(firstName) cannot be resolved to a variable.
The problem is in the ActionPeformed block:
import java.awt.*;
import java.awt.event.*;
import java.io.File;
import java.io.FileInputStream;
import java.io.FileNotFoundException;
import java.io.FileOutputStream;
import java.io.IOException;
import java.io.ObjectInputStream;
import java.io.ObjectOutputStream;
import java.io.Serializable;
import javax.swing.*;
import javax.swing.event.*;
import javax.swing.border.*;
import java.util.*;
public class ClassRoomFrameTest
{
public static void main(String[] args)
{
ClassRoomFrame frame = new ClassRoomFrame();
frame.setSize(600,600);
frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
frame.setVisible(true);
frame.setResizable(false);
frame.setLocationRelativeTo(null);
}
}
class ClassRoomFrame extends JFrame implements ActionListener
{
private JPanel mainPanel = new JPanel();
private JPanel deptPanel = new JPanel(new GridLayout(2,3));
private JPanel studentPanel = new JPanel(new GridLayout(2,5));
private JPanel displayPanel = new JPanel(new BorderLayout());
private JPanel buttonPanel = new JPanel(new GridLayout(1,2));
private JPanel menuBar = new JPanel();
private JTextArea textArea = new JTextArea();
private JScrollPane scrollPane = new JScrollPane(textArea);
private JLabel classLocationLabel = new JLabel("Class Location");
private JLabel classRoomLabel = new JLabel("Class Room Number");
private JLabel classCapacityLabel = new JLabel("Class Capacity");
private JTextField classLocationField = new JTextField();
private JTextField classRoomField = new JTextField();
private JTextField classCapacityField = new JTextField();
private JLabel studentFNameLabel = new JLabel("First name");
private JLabel studentLNameLabel = new JLabel("Last name");
private JLabel studentIDLabel = new JLabel("ID Number");
private JLabel studentMajorLabel = new JLabel("Major");
private JLabel studentCreditsLabel = new JLabel("Credits");
private JTextField studentFNameField = new JTextField();
private JTextField studentLNameField = new JTextField();
private JTextField studentIDField = new JTextField();
private JTextField studentMajorField = new JTextField();
private JTextField studentCreditsField = new JTextField();
private JButton addButton = new JButton("Add");
private JButton displayButton = new JButton("Display");
private JMenuBar menu = new JMenuBar();
private JMenu fileMenu = new JMenu("File");
private JMenuItem save = new JMenuItem("Open");
private JMenuItem open = new JMenuItem("Save");
private JFileChooser chooser = new JFileChooser();
Classroom room = null;
public ClassRoomFrame()
{
deptPanel.setPreferredSize(new Dimension(600,50));
deptPanel.setBorder(new EmptyBorder(new Insets(5,15,5,15)));
deptPanel.add(classLocationLabel);
deptPanel.add(classRoomLabel);
deptPanel.add(classCapacityLabel);
deptPanel.add(classLocationField);
deptPanel.add(classRoomField);
deptPanel.add(classCapacityField);
fileMenu.add(fileMenu);
fileMenu.add(open);
fileMenu.add(save);
menu.add(fileMenu);
studentPanel.setBorder(new EmptyBorder(new Insets(5,15,5,15)));
studentPanel.setPreferredSize(new Dimension(600,50));
studentPanel.setBorder(new EmptyBorder(new Insets(5,15,5,15)));
studentPanel.add(studentFNameLabel);
studentPanel.add(studentLNameLabel);
studentPanel.add(studentIDLabel);
studentPanel.add(studentMajorLabel);
studentPanel.add(studentCreditsLabel);
studentPanel.add(studentFNameField);
studentPanel.add(studentLNameField);
studentPanel.add(studentIDField);
studentPanel.add(studentMajorField);
studentPanel.add(studentCreditsField);
scrollPane.setBorder(new BevelBorder(BevelBorder.LOWERED));
scrollPane.setPreferredSize(new Dimension(600,450));
textArea.setBorder(new EmptyBorder(new Insets(5,15,5,15)));
buttonPanel.setBorder(new BevelBorder(BevelBorder.RAISED));
buttonPanel.setPreferredSize(new Dimension(600, 50));
buttonPanel.add(addButton);
buttonPanel.add(displayButton);
addButton.addActionListener(this);
addButton.setActionCommand("Add");
displayButton.addActionListener(this);
displayButton.setActionCommand("Display");
open.addActionListener(this);
open.setActionCommand("Open");
save.addActionListener(this);
save.setActionCommand("Save");
mainPanel.add(deptPanel);
mainPanel.add(studentPanel);
mainPanel.add(scrollPane);
add(menu, BorderLayout.NORTH);
add(mainPanel, BorderLayout.CENTER);
add(buttonPanel, BorderLayout.SOUTH);
}
#SuppressWarnings("unused")
public void actionPerformed(ActionEvent e)
{
/*---> HERE */if(e.getActionCommand().equals("Save"));
{
FileOutputStream saveFile = null;
ObjectOutputStream save = null;
try
{
saveFile = new FileOutputStream("ObjectData.txt");
save = new ObjectOutputStream(saveFile);
/*--->Error*/ save.writeObject(index);
save.writeObject(new Classroom());
} catch (FileNotFoundException e1)
{
e1.printStackTrace();
} catch (IOException e1)
{
e1.printStackTrace();
}
finally
{
try {saveFile.close();
}catch(Exception exc){
System.out.println(exc.getMessage());
}
}
}
/*---> Here*/if (e.getActionCommand().equals("Open"))
{
ObjectInputStream in = null;
int returnVal = chooser.showOpenDialog(ClassRoomFrame.this);
if (returnVal == JFileChooser.APPROVE_OPTION)
{
File file = chooser.getSelectedFile();
try {
in = new ObjectInputStream(new FileInputStream(file));
} catch (FileNotFoundException e1)
{
e1.printStackTrace();
} catch (IOException e1)
{
e1.printStackTrace();
}
}
try {
Student st = (Student)in.readObject();
Classroom cs = (Classroom)in.readObject();
System.out.println(st);
System.out.println(cs);
} catch (IOException e1) {
e1.printStackTrace();
} catch (ClassNotFoundException e1) {
e1.printStackTrace();
}
try{in.close();}
catch(Exception err){err.getMessage();}
}
if(e.getActionCommand().equals("Add"))
{
if(room == null)
{
room = new Classroom(classLocationField.getText(),
Integer.parseInt(classRoomField.getText()),
Integer.parseInt(classCapacityField.getText()));
room.addStudent(
new Student(studentFNameField.getText(),
studentLNameField.getText(),
studentIDField.getText(),
studentMajorField.getText(),
Integer.parseInt(studentCreditsField.getText())));
classLocationField.setEditable(false);
classRoomField.setEditable(false);
classCapacityField.setEditable(false);
studentFNameField.setText("");
studentLNameField.setText("");
studentIDField.setText("");
studentMajorField.setText("");
studentCreditsField.setText("");
textArea.setText("Class and first student added.");
}
else
{
room.addStudent(
new Student(studentFNameField.getText(),
studentLNameField.getText(),
studentIDField.getText(),
studentMajorField.getText(),
Integer.parseInt(studentCreditsField.getText())));
textArea.setText("Next student added.");
studentFNameField.setText("");
studentLNameField.setText("");
studentIDField.setText("");
studentMajorField.setText("");
studentCreditsField.setText("");
}
}
else if(e.getActionCommand().equals("Display"))
{
if (room != null)
{
textArea.setText(room.toString());
}
else
{
textArea.setText("Nothing to display");
}
}
}
}
class Student implements Serializable
{
public String firstName, lastName, studentIdNumber, studentMajor;
public int totalCourseCredits;
//-----------------------------------------------------------------
// Create an empty studentusing a default constructor.
//-----------------------------------------------------------------
public Student ()
{
}
//-----------------------------------------------------------------
// Creates a Student with the specified information.
//-----------------------------------------------------------------
public Student (String name1, String name2, String identification,
String myMajor, int myTotalCredits)
{
firstName = name1;
lastName = name2;
studentIdNumber = identification;
studentMajor = myMajor;
totalCourseCredits = myTotalCredits;
}
//-----------------------------------------------------------------
// Gets and sets first name.
//-----------------------------------------------------------------
public void setFirstName()
{
Scanner scan = new Scanner (System.in);
System.out.println ("Enter your First Name: ");
firstName = scan.nextLine();
}
//-----------------------------------------------------------------
// Gets and sets last name.
//-----------------------------------------------------------------
public void setLastName()
{
Scanner scan = new Scanner (System.in);
System.out.println ("Enter your Last Name: ");
lastName = scan.nextLine();
}
//-----------------------------------------------------------------
// Gets and sets Total Course Credits.
//-----------------------------------------------------------------
public void setTotalCredits()
{
Scanner scan = new Scanner (System.in);
System.out.println ("Enter your Total Credits: ");
totalCourseCredits = scan.nextInt();
}
//-----------------------------------------------------------------
// Gets and sets Student ID Number.
//-----------------------------------------------------------------
public void setIdNumber()
{
Scanner scan = new Scanner (System.in);
System.out.println ("Enter your ID Number: ");
studentIdNumber = scan.nextLine();
}
//-----------------------------------------------------------------
// Gets and sets Student Major.
//-----------------------------------------------------------------
public void setMajor()
{
Scanner scan = new Scanner (System.in);
System.out.println ("Enter your Major: ");
studentMajor = scan.nextLine();
}
public String toString()
{
String s = "First name: " + firstName + "\n" +
"Last name: " + lastName + "\n" +
"StudentID: " + studentIdNumber + "\n" +
"Student Major: " + studentMajor + "\n" +
"Course Creidts: " + totalCourseCredits + "\n";
return s;
}
}
class Classroom implements Serializable
{
private Student[] classRoster;
private int index = 0;
private int capacityStudents, roomNumber;
private String buildingLocation;
//-----------------------------------------------------------------
// Creates an empty Classroom.
//-----------------------------------------------------------------
public Classroom()
{
capacityStudents = 0;
roomNumber = 0;
buildingLocation = "";
}
//-----------------------------------------------------------------
// Creates a Classroom with the specified information.
//-----------------------------------------------------------------
public Classroom(String location, int room, int cap)
{
capacityStudents = cap;
roomNumber = room;
buildingLocation = location;
classRoster = new Student[capacityStudents];
}
//-----------------------------------------------------------------
// Gets and sets Building Location.
//-----------------------------------------------------------------
public void setBuilding()
{
Scanner scan = new Scanner (System.in);
System.out.println ("Enter the Building Location: ");
buildingLocation = scan.next();
}
//-----------------------------------------------------------------
// Gets and sets Room Number.
//-----------------------------------------------------------------
public void setRoomNumber()
{
Scanner scan = new Scanner (System.in);
System.out.println ("Enter the Room Number: ");
roomNumber = scan.nextInt();
}
//-----------------------------------------------------------------
// Sets Capacity of Students.
//-----------------------------------------------------------------
public void setCapacityStudents()
{
Scanner scan = new Scanner (System.in);
System.out.println ("Enter The Capacity of the Classroom: ");
capacityStudents = scan.nextInt();
classRoster = new Student[capacityStudents];
}
//-----------------------------------------------------------------
// Gets Capacity of Students.
//-----------------------------------------------------------------
public int getCapacityStudents()
{
return capacityStudents;
}
//-----------------------------------------------------------------
// Adds an Individual Student to the Classroom, checking if the
// capacity of the clasroom is full.
//-----------------------------------------------------------------
public void addStudent (Student student)
{
if(index < capacityStudents)
{
classRoster[index] = student;
index++;
}
else
{
System.out.println("Capacity exceeded! - Student cannot be added.");
}
}
//-----------------------------------------------------------------
// Adds an Individual Student to the Classroom, checking if the
// capacity of the clasroom is full.
//-----------------------------------------------------------------
public String toString()
{
StringBuffer sb = new StringBuffer
("Building: " + buildingLocation +
"\nClass room: " + roomNumber +
"\nCapacity: " + capacityStudents + "\n\n"
);
for(int i = 0; i < classRoster.length; i++)
{
if(classRoster[i] != null)
sb.append(classRoster[i].toString() + "\n");
}
return sb.toString();
}
}
The error is telling you that index is not available in the scope of the save method. You would need to do something like save.writeObject( classroom.getIndex()) in the save method, if you want to save the index.
You have declared index variable in ClassRoom class. But you are trying to use it in method actionPerformed of ClassRoomFrame class.
Since scope of index is limited to it's enclosing class, it won't be visible in other classes without using instance on ClassRoom class. And that's what compiler error states: cannot find symbol

DocumentListener Java, How do I prevent empty string in JTextBox?

I have been working on a personal project to get better with programming. My goal is to make it much more robust, I am just starting. I am a current computer science student. Anyway, I am working on making a portion of the program as shown. I calculates the hourly wage and provides some outputs I havent implemented yet. I'm using DocumentListener so it it will automatically calculate. I am getting an error when the the text is removed completely from a box.I tried to fix it with the if statement:
if (tipMon.equals("") || tipMon == null) {
tipMon.setText("0");
}
Here is what I have so far. It's not done yet and I apologize for the noob code. I started 2 months ago with actual coding.
import java.awt.GridLayout;
import java.awt.event.ActionListener;
import java.awt.event.ActionEvent;
import java.awt.event.KeyListener;
import javax.swing.JFrame;
import javax.swing.JLabel;
import javax.swing.JTextField;
import javax.swing.JOptionPane;
import javax.swing.event.DocumentEvent;
import javax.swing.event.DocumentListener;
import javax.swing.text.Document;
import javax.swing.text.FieldView;
public class deliveryDocListener extends JFrame implements ActionListener,
DocumentListener{
private JLabel mon, tues, wed, thurs, fri, sat, sun, hourlyWage, blank, row2, monWage,
tuesWage,wedWage,thursWage, friWage, satWage, sunWage, total, totalTips, totalHours,
totalHourlyEarnings, totalPay, weekPay;
private JTextField hourlyWageInput, tipMon, tipTues, tipWed, tipThurs, tipFri, tipSat, tipSun,
hourMon, hourTues, hourWed, hourThurs, hourFri, hourSat, hourSun;
public deliveryDocListener(){
super("Delivery Helper v0.1 Alpha");
setLayout(new GridLayout(0,4));
hourlyWage = new JLabel("Hourly Wage: ");
add(hourlyWage);
hourlyWageInput = new JTextField("7.25", 5);
add(hourlyWageInput);
blank = new JLabel();
add(blank);
blank = new JLabel();
add(blank);
row2 = new JLabel("Day of the Week");
add(row2);
row2 = new JLabel("Tips");
add(row2);
row2 = new JLabel("Hours Worked");
add(row2);
row2 = new JLabel("Hourly Earnings");
add(row2);
mon = new JLabel("Monday");
add(mon);
tipMon = new JTextField("0");
Document tipMonListener = tipMon.getDocument();
//Document class doc variable stores what happens in the getDocument()
//method, getDocument() i think is what checked it real time we shall see
tipMonListener.addDocumentListener(this);
//add listener to he text field, this refers to most recent object (tipMon = new JTextField("0");"
//notice how its purple is the same as new where the object got made?
add(tipMon);
hourMon = new JTextField("0");
Document hourMonListener = hourMon.getDocument();
hourMonListener.addDocumentListener(this);
add(hourMon);
monWage = new JLabel("0");
add(monWage);
tues = new JLabel("Tuesday");
add(tues);
tipTues = new JTextField("0");
add(tipTues);
hourTues = new JTextField("0");
add(hourTues);
tuesWage = new JLabel("0");
add(tuesWage);
wed = new JLabel("Wednesday");
add(wed);
tipWed = new JTextField("0");
add(tipWed);
hourWed = new JTextField("0");
add(hourWed);
wedWage = new JLabel("0");
add(wedWage);
thurs = new JLabel("Thursday");
add(thurs);
tipThurs = new JTextField("0");
add(tipThurs);
hourThurs = new JTextField("0");
add(hourThurs);
thursWage = new JLabel("0");
add(thursWage);
fri = new JLabel("Friday");
add(fri);
tipFri = new JTextField("0");
add(tipFri);
hourFri = new JTextField("0");
add(hourFri);
friWage = new JLabel("0");
add(friWage);
sat = new JLabel("Saturday");
add(sat);
tipSat = new JTextField("0");
add(tipSat);
hourSat = new JTextField("0");
add(hourSat);
satWage = new JLabel("0");
add(satWage);
sun = new JLabel("Sunday");
add(sun);
tipSun = new JTextField("0");
add(tipSun);
hourSun = new JTextField("0");
add(hourSun);
sunWage = new JLabel("0");
add(sunWage);
blank = new JLabel();
add(blank);
blank = new JLabel();
add(blank);
blank = new JLabel();
add(blank);
blank = new JLabel();
add(blank);
total = new JLabel("Total: ");
add(total);
totalTips = new JLabel("totalTipsOutput");
add(totalTips);
totalHours = new JLabel("totalHoursOutput");
add(totalHours);
totalHourlyEarnings = new JLabel("totalHourlyEarningsOutput");
add(totalHourlyEarnings);
blank = new JLabel();
add(blank);
blank = new JLabel();
add(blank);
blank = new JLabel();
add(blank);
blank = new JLabel();
add(blank);
blank = new JLabel();
add(blank);
blank = new JLabel();
add(blank);
totalPay = new JLabel("Gross Income: ");
add(totalPay);
weekPay = new JLabel("totalPayOutput");
add(weekPay);
}
#Override
public void changedUpdate(DocumentEvent e) {
// TODO Auto-generated method stub
}
#Override
public void insertUpdate(DocumentEvent e) {
//executes when someone enters text into input
String tipMonStr = tipMon.getText();
//monWage.setText(tipMonStr);
String hourMonStr = hourMon.getText();
double x = Double.parseDouble(tipMonStr);
double y = Double.parseDouble(hourMonStr);
double z = Double.parseDouble(hourlyWageInput.getText());
if (tipMonStr.length() == 0) {
tipMon.setText("0");
}
if (hourMonStr.length() == 0) {
y = 0;
hourMonStr = "0";
}
if (hourlyWageInput.getText().length() == 0) {
z = 0;
//String z = "0";
}
monWage.setText(Double.toString((z*y+x)/y));
//bug when nothing in cell because no number (0) to use in math
}
#Override
public void removeUpdate(DocumentEvent e) {
//executes when someone enters text into input
String tipMonStr = tipMon.getText();
//monWage.setText(tipMonStr);
String hourMonStr = hourMon.getText();
double x = Double.parseDouble(tipMonStr);
double y = Double.parseDouble(hourMonStr);
double z = Double.parseDouble(hourlyWageInput.getText());
monWage.setText(Double.toString((z*y+x)/y));
if (tipMon.equals("") || tipMon == null) {
tipMon.setText("0");
}
}
public void updateLog(DocumentEvent e, String action) {
monWage.setText(Double.toString(5));
}
#Override
public void actionPerformed(ActionEvent arg0) {
monWage.setText(Double.toString(5));
}
}
As #HFOE suggests, InputVerifier is the right choice, but verify() "should have no side effects." Instead, invoke calcProduct() in shouldYieldFocus().
/**
* #see http://stackoverflow.com/a/11818946/230513
*/
private class MyInputVerifier extends InputVerifier {
private JTextField field;
private double value;
public MyInputVerifier(JTextField field) {
this.field = field;
}
#Override
public boolean shouldYieldFocus(JComponent input) {
if (verify(input)) {
field.setText(String.valueOf(value));
calcProduct();
return true;
} else {
field.setText(ZERO);
field.selectAll();
return false;
}
}
#Override
public boolean verify(JComponent input) {
try {
value = Double.parseDouble(field.getText());
return true;
} catch (NumberFormatException e) {
return false;
}
}
}
I'll make this an answer: I wouldn't use a DocumentListener for this purpose as it seems to me the wrong tool for the job. For one, it is continually listening and updating the results while the user is still entering data, data that is as yet incomplete, into the JTextField. Much better would be to use an ActionListener added to a JButton or to your JTextFields.
I suppose you could use a FocusListener, but even that concerns me since it is quite low-level.
Also: consider using an InputVerifier to validate your input.
Also: consider displaying your tabular data in a JTable where the 1st and 2nd columns are editable but the others are not.
Edit
I'm not sure if this is kosher, but it could work if you do your calculation from within the verifier. For example, updated for generality:
import javax.swing.*;
/**
* #see http://stackoverflow.com/a/11818183/522444
*/
public class VerifierEg {
private static final String ZERO = "0.0";
private JTextField field1 = new JTextField(ZERO, 5);
private JTextField field2 = new JTextField(ZERO, 5);
private JTextField resultField = new JTextField(ZERO, 10);
private void createAndShowGui() {
resultField.setEditable(false);
resultField.setFocusable(false);
JPanel mainPanel = new JPanel();
final JTextField[] fields = {field1, field2};
mainPanel.add(field1);
mainPanel.add(new JLabel(" x "));
mainPanel.add(field2);
mainPanel.add(new JLabel(" = "));
mainPanel.add(resultField);
for (JTextField field : fields) {
field.setInputVerifier(new MyInputVerifier(field));
}
JFrame frame = new JFrame("VerifierEg");
frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
frame.getContentPane().add(mainPanel);
frame.pack();
frame.setLocationByPlatform(true);
frame.setVisible(true);
}
private void calcProduct() {
double d1 = Double.parseDouble(field1.getText());
double d2 = Double.parseDouble(field2.getText());
double prod = d1 * d2;
resultField.setText(String.valueOf(prod));
}
public static void main(String[] args) {
SwingUtilities.invokeLater(new Runnable() {
#Override
public void run() {
VerifierEg eg = new VerifierEg();
eg.createAndShowGui();
}
});
}
/**
* #see http://stackoverflow.com/a/11818946/230513
*/
private class MyInputVerifier extends InputVerifier {
private JTextField field;
private double value;
public MyInputVerifier(JTextField field) {
this.field = field;
}
#Override
public boolean shouldYieldFocus(JComponent input) {
if (verify(input)) {
field.setText(String.valueOf(value));
calcProduct();
return true;
} else {
field.setText(ZERO);
field.selectAll();
return false;
}
}
#Override
public boolean verify(JComponent input) {
try {
value = Double.parseDouble(field.getText());
return true;
} catch (NumberFormatException e) {
return false;
}
}
}
}
use JSpinner or JFormattedTextField with Number instance, then DocumentListener should be works correctly, no needed to parse String to Number instance
otherwise you have to use DocumentFilter for JTextField for filtering non numeric chars, rest (counting) stays unchanged, stil required robust parsing String to the Number instance

Java guessing game

I am trying to write a program in Java that takes a random number from 1-1000 and then as the guess it the background color changes to blue(cold) or red(warm) if they are in the number. I am new to java GUI, but I think the rest of the logic is right, not sure. It compiles, but the guess button doesn't work. Any guidance will be appreciated.
package guessGame;
import java.awt.*;
import java.awt.event.*;
import javax.swing.*;
import java.awt.color.*;
import java.util.Random;
import java.util.Random;
import java.util.logging.FileHandler;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
import java.awt.event.WindowAdapter;
import java.awt.event.WindowEvent;
public class GuessGame extends JFrame
{
private JFrame mainFrame;
private JButton GuessButton;
private JButton QuitButton;
private JLabel prompt1, prompt2;
private JTextField userInput;
private JLabel comment = new JLabel("What is your destiny?");
private JLabel comment2 = new JLabel (" ");
//private int number, guessCount;
//private int lastGuess;
private int randomNumber;
private Color background;
public GuessGame()
{
mainFrame = new JFrame ("Guessing Game!");
setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
//Creates components
GuessButton = new JButton("Guess");
QuitButton = new JButton("Quit");
prompt1 = new JLabel("I have a number between 1 and 1000.");
prompt2 = new JLabel("Can you guess my number? Enter your Guess:");
comment = new JLabel ("What is your destiny?");
comment2 = new JLabel (" ");
userInput = new JTextField(5);
//userInput.addActionListener(new GuessHandler());
//content pane
Container c = mainFrame.getContentPane();
c.setLayout(new FlowLayout());
//adding component to the pane
c.add(prompt1);
c.add(prompt2);
c.add(userInput);
c.add(comment2);
c.add(GuessButton);
c.add(QuitButton);
c.add(comment);
GuessButton.setMnemonic('G');
QuitButton.setMnemonic('Q');
mainFrame.setSize(300,200);
mainFrame.setLocationRelativeTo(null);
mainFrame.setVisible(true);
mainFrame.setResizable(false);
// define and register window event handler
// mainFrame.addWindowListener(new WindowAdapter() {
// public void windowClosing(WindowEvent e)
// { System.exit(0); }
// });
//creating the handler
GuessButtonHandler ghandler = new GuessButtonHandler(); //instantiate new object
GuessButton.addActionListener(ghandler); // add event listener
QuitButtonHandler qhandler = new QuitButtonHandler();
QuitButton.addActionListener(qhandler);
}
public void paint (Graphics g)
{
super.paint(g);
setBackground(background);
}
class QuitButtonHandler implements ActionListener
{
public void actionPerformed(ActionEvent e)
{
System.exit(0);
}
}
class GuessButtonHandler implements ActionListener
{
public void actionPerformed(ActionEvent e)
{
int getUserInput=0;
int diff;
int Difference;
randomNumber = new Random().nextInt(1001);
try {
getUserInput = Integer.parseInt(
userInput.getText().trim());
} catch (NumberFormatException ex){
comment.setText("Enter a VALID number!");
return;
}
if (getUserInput == randomNumber){
JOptionPane.showMessageDialog(null, "CONGRATULATIONS! You got it!!",
"Random Number: " + randomNumber,
JOptionPane.INFORMATION_MESSAGE);
randomNumber = new Random().nextInt(1000) + 1;
return;
}
if (getUserInput > randomNumber){
comment.setText( "Too High. Try a lower number." );
diff=getUserInput - randomNumber;
Difference=Math.abs(diff);
} else {
comment.setText( "Too Low. Try a higher number." );
diff=randomNumber - getUserInput;
Difference=Math.abs(diff);
}
if(Difference<=25){
comment2.setText("Cold");
setBackgroundColor(Color.blue);
}
if(Difference<=10){
comment2.setText("Warm");
setBackgroundColor(Color.red);
}
else {
}
}
private void setBackgroundColor(Color color) {
setBackgroundColor(color);
}
}
public static void main(String args[]) {
//instantiate gueesgame object
GuessGame app = new GuessGame();
}
}
The colors aren't changing because your setBackgroundColor always uses Color.black. Change it to:
private void setBackgroundColor(Color color) {
setBackground(color);
}
As for the number always being zero. You do not instantiate the randomNumber field. Add this to your constructor:
randomNumber = new Random().nextInt(1001);
Another problem I noticed was you added a window listener to ensure the program exits when you close the window. This is implemented in JFrame. In the constructor add:
setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
Instead of using the deprecated method:
mainFrame.show();
use the not deprecated:
mainFrame.setVisible(true);
Furthermore you have a field, which is never queried:
private Color background;
It's best to do the logic before connecting it to the gui. It's a lot easier to test and find the worst bugs.
Refactored code:
import javax.swing.*;
import java.awt.*;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
import java.util.Random;
public class GuessGame extends JFrame {
private JTextField userInput;
private JLabel comment = new JLabel("What is your destiny?");
private JLabel comment2 = new JLabel(" ");
private int randomNumber;
public GuessGame() {
super("Guessing Game!");
setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
//Creates components
JButton guessButton = new JButton("Guess");
JButton quitButton = new JButton("Quit");
JLabel prompt1 = new JLabel("I have a number between 1 and 1000.");
JLabel prompt2 = new JLabel("Can you guess my number? Enter your Guess:");
comment = new JLabel("What is your destiny?");
comment2 = new JLabel(" ");
userInput = new JTextField(5);
//content pane
Container c = getContentPane();
setLayout(new FlowLayout());
//adding component to the pane
c.add(prompt1);
c.add(prompt2);
c.add(userInput);
c.add(comment2);
c.add(guessButton);
c.add(quitButton);
c.add(comment);
guessButton.setMnemonic('G');
quitButton.setMnemonic('Q');
setSize(300, 200);
setLocationRelativeTo(null);
setVisible(true);
setResizable(false);
initializeNumber();
//creating the handler
GuessButtonHandler ghandler = new GuessButtonHandler(); //instantiate new object
guessButton.addActionListener(ghandler); // add event listener
QuitButtonHandler qhandler = new QuitButtonHandler();
quitButton.addActionListener(qhandler);
}
private void initializeNumber() {
randomNumber = new Random().nextInt(1000) + 1;
}
class QuitButtonHandler implements ActionListener {
public void actionPerformed(ActionEvent e) {
System.exit(0);
}
}
class GuessButtonHandler implements ActionListener {
public void actionPerformed(ActionEvent e) {
int getUserInput;
int diff;
int Difference;
try {
getUserInput = Integer.parseInt(userInput.getText().trim());
if (getUserInput == randomNumber) {
JOptionPane.showMessageDialog(null, "CONGRATULATIONS! You got it!!",
"Random Number: " + randomNumber,
JOptionPane.INFORMATION_MESSAGE);
initializeNumber();
return;
}
if (getUserInput > randomNumber) {
comment.setText("Too High. Try a lower number.");
diff = getUserInput - randomNumber;
Difference = Math.abs(diff);
} else {
comment.setText("Too Low. Try a higher number.");
diff = randomNumber - getUserInput;
Difference = Math.abs(diff);
}
if (Difference <= 25) {
comment2.setText("Cold");
GuessGame.this.setBackgroundColor(Color.blue);
}
if (Difference <= 10) {
comment2.setText("Warm");
GuessGame.this.setBackgroundColor(Color.red);
}
} catch (NumberFormatException ex) {
comment.setText("Enter a VALID number!");
}
}
}
private void setBackgroundColor(Color color) {
getContentPane().setBackground(color);
}
public static void main(String args[]) {
//instantiate gueesgame object
GuessGame app = new GuessGame();
}
}
You have more Swing components than you need, and you seem to be adding one set to the frame while manipulating another set. For example, you have two JTextFields, fieldBox and userInput. You add userInput to the frame, but check fieldBox for input in the Guess button handler. Since fieldBox is always empty, the NumberFormatException is caught by your exception handler (which should really just catch NumberFormatException, not Exception), and comment is updated with "Enter a VALID number!". However, just like with the double text area, comment isn't actually added to the frame, prompt1 and prompt2 are, so you can't see the change
I would write your logic without a UI first and test it until it was 100% correct. Just use a command line, text UI at first. Once that's done, put a GUI in front of it. It'll help to isolate your problems: once the text-driven logic is right, you'll know that future problems are due to UI.
It makes your MVC separation cleaner as well.

Categories