I have tried to make a chat application that only saves the recieved messages which can then be deleted. I'm having some major problems with it.

Can anyone please point out or correct my coding. I have tried for ages to get this working but with no joy.

Client Code

import java.awt.*;
import java.awt.event.*;
import java.io.EOFException;
import java.io.IOException;
import java.io.ObjectInputStream;
import java.io.ObjectOutputStream;
import java.net.InetAddress;
import java.net.Socket;

import javax.swing.*;
import javax.swing.event.*;

public class Client extends JPanel
                      implements ListSelectionListener {
    private JList save;
    private DefaultListModel saveList;

    private static final String sendString = "Send";
    private static final String deleteString = "Delete";
    private JButton deleteBtn;
    private JTextField enterMsg;   
    private static InetAddress host;
    ObjectOutputStream output;
    ObjectInputStream input;
    String message = "";
    

    public Client() {
        super(new BorderLayout());

        saveList = new DefaultListModel();
        saveList.addElement("Hi How are you?");
        saveList.addElement("I'm ok. How are the kids?");
        saveList.addElement("Thats good to hear. I will have to give you a call for a meeting soon.");
        
        //Create the list and put it in a scroll pane.
        save = new JList(saveList);
        save.setSelectionMode(ListSelectionModel.SINGLE_SELECTION);
        save.setSelectedIndex(0);
        save.addListSelectionListener(this);
        save.setVisibleRowCount(5);
        JScrollPane listScrollPane = new JScrollPane(save);

        JButton sendBtn = new JButton(sendString);
        SendListener sendListener = new SendListener(sendBtn);
        sendBtn.setActionCommand(sendString);
        sendBtn.addActionListener(sendListener);
        sendBtn.setEnabled(false);

        deleteBtn = new JButton(deleteString);
        deleteBtn.setActionCommand(deleteString);
        deleteBtn.addActionListener(new DeleteListener());

        enterMsg = new JTextField(100);
        enterMsg.addActionListener(sendListener);
        enterMsg.getDocument().addDocumentListener(sendListener);
        String name = saveList.getElementAt(
        		save.getSelectedIndex()).toString();

        //Create a panel that uses BoxLayout.
        JPanel buttonPane = new JPanel();
        buttonPane.setLayout(new BoxLayout(buttonPane,
                                           BoxLayout.LINE_AXIS));
        buttonPane.add(deleteBtn);
        buttonPane.add(Box.createHorizontalStrut(5));
        buttonPane.add(new JSeparator(SwingConstants.VERTICAL));
        buttonPane.add(Box.createHorizontalStrut(5));
        buttonPane.add(enterMsg);
        buttonPane.add(sendBtn);
        buttonPane.setBorder(BorderFactory.createEmptyBorder(5,5,5,5));

        add(listScrollPane, BorderLayout.CENTER);
        add(buttonPane, BorderLayout.PAGE_END);
        
    }

    class DeleteListener implements ActionListener {
        public void actionPerformed(ActionEvent e) {
            //This method can be called only if
            //there's a valid selection
            //so go ahead and remove whatever's selected.
            int index = save.getSelectedIndex();
            saveList.remove(index);

            int size = saveList.getSize();

            if (size == 0) { //Nobody's left, disable firing.
            	deleteBtn.setEnabled(false);

            } else { //Select an index.
                if (index == saveList.getSize()) {
                    //removed item in last position
                    index--;
                }

                save.setSelectedIndex(index);
                save.ensureIndexIsVisible(index);
            }
        }
    }

    //This listener is shared by the text field and the send button.
    class SendListener implements ActionListener, DocumentListener {
        private boolean alreadyEnabled = false;
        private JButton sendBtn;

        public SendListener(JButton button) {
            this.sendBtn = button;
        }

        //Required by ActionListener.
        public void actionPerformed(ActionEvent e) {
            String message = enterMsg.getText();

            //User didn't type in a unique name...
            if (message.equals("") || alreadyInList(message)) {
                Toolkit.getDefaultToolkit().beep();
                enterMsg.requestFocusInWindow();
                enterMsg.selectAll();
                return;
            }

            int index = save.getSelectedIndex(); //get selected index
            if (index == -1) { //no selection, so insert at beginning
                index = 0;
            } else {           //add after the selected item
                index++;
            }

            saveList.insertElementAt(enterMsg.getText(), index);
            //If we just wanted to add to the end, we'd do this:
            //listModel.addElement(employeeName.getText());

            //Reset the text field.
            enterMsg.requestFocusInWindow();
            enterMsg.setText("");

            //Select the new item and make it visible.
            save.setSelectedIndex(index);
            save.ensureIndexIsVisible(index);
        }

        protected boolean alreadyInList(String name) {
            return saveList.contains(name);
        }

        //Required by DocumentListener.
        public void insertUpdate(DocumentEvent e) {
            enableButton();
        }

        //Required by DocumentListener.
        public void removeUpdate(DocumentEvent e) {
            handleEmptyTextField(e);
        }

        //Required by DocumentListener.
        public void changedUpdate(DocumentEvent e) {
            if (!handleEmptyTextField(e)) {
                enableButton();
            }
        }

        private void enableButton() {
            if (!alreadyEnabled) {
            	sendBtn.setEnabled(true);
            }
        }

        private boolean handleEmptyTextField(DocumentEvent e) {
            if (e.getDocument().getLength() <= 0) {
                sendBtn.setEnabled(false);
                alreadyEnabled = false;
                return true;
            }
            return false;
        }
    }

    //This method is required by ListSelectionListener.
    public void valueChanged(ListSelectionEvent e) {
        if (e.getValueIsAdjusting() == false) {

            if (save.getSelectedIndex() == -1) {
            //No selection, disable delete button.
            	deleteBtn.setEnabled(false);

            } else {
            //Selection, enable the delete button.
            	deleteBtn.setEnabled(true);
            }
        }
    }


    private static void createAndShowGUI() {
        //Create and set up the window.
        JFrame frame = new JFrame("ListDemo");
        frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);

        //Create and set up the content pane.
        JComponent newContentPane = new ListDemo();
        newContentPane.setOpaque(true); //content panes must be opaque
        frame.setContentPane(newContentPane);

        //Display the window.
        frame.pack();
        frame.setVisible(true);
    }
    
    public void runClient()
    {
       Socket client;

       try {
          // Step 1: Create a Socket to make connection.

          host = InetAddress.getLocalHost();	//...............
          client = new Socket(host, 50000 );

          // Step 2: Get the input and output streams.
          output = new ObjectOutputStream(
                       client.getOutputStream() );
          output.flush();
          input = new ObjectInputStream(
                      client.getInputStream() );

          // Step 3: Process connection.
          enterMsg.setEnabled( true );
          do {
             try {
                message = (String) input.readObject();
                
                enterMsg.setCaretPosition(
                enterMsg.getText().length() );
             }
             catch ( ClassNotFoundException cnfex ) {
             }
             
          } while ( !message.equals( "SERVER>>> TERMINATE" ) );

          // Step 4: Close connection.
          output.close();
          input.close();
          client.close();
       }
       catch ( EOFException eof ) {
          System.out.println( "Server terminated connection" );
       }
       catch ( IOException e ) {
          e.printStackTrace();
       }
    }

    private void sendData( String s )
    {
       try {
          message = s;
          output.writeObject( "CLIENT1>>> " + s );
          output.flush();
       }
       catch ( IOException cnfex ) {

       }

    }

    class FireListener implements ActionListener {
        public void actionPerformed(ActionEvent e) {
            //This method can be called only if
            //there's a valid selection
            //so go ahead and remove whatever's selected.
            int index = save.getSelectedIndex();
            saveList.remove(index);

            int size = saveList.getSize();

            if (size == 0) { //Nobody's left, disable firing.
                deleteBtn.setEnabled(false);

            } else { //Select an index.
                if (index == saveList.getSize()) {
                    //removed item in last position
                    index--;
                }

                save.setSelectedIndex(index);
                save.ensureIndexIsVisible(index);
            }
        }
    }

    public static void main(String[] args) {
        javax.swing.SwingUtilities.invokeLater(new Runnable() {
            public void run() {
                createAndShowGUI();
            }
        });
    }
}

Server Code

import java.awt.*;
import java.awt.event.*;
import java.io.EOFException;
import java.io.IOException;
import java.io.ObjectInputStream;
import java.io.ObjectOutputStream;
import java.net.InetAddress;
import java.net.ServerSocket;
import java.net.Socket;
import javax.swing.*;
import javax.swing.event.*;

public class Server extends JPanel
                      implements ListSelectionListener {
    private JList save;
    private DefaultListModel saveList;

    private static final String sendString = "Send";
    private static final String deleteString = "Delete";
    private JButton deleteBtn;
    private JTextField enterMsg;   
    private static InetAddress host;
    ObjectOutputStream output;
    ObjectInputStream input;
    String message = "";
    

    public Server() {
        super(new BorderLayout());

        saveList = new DefaultListModel();
        saveList.addElement("Hi How are you?");
        saveList.addElement("I'm ok. How are the kids?");
        saveList.addElement("Thats good to hear. I will have to give you a call for a meeting soon.");
        
        //Create the list and put it in a scroll pane.
        save = new JList(saveList);
        save.setSelectionMode(ListSelectionModel.SINGLE_SELECTION);
        save.setSelectedIndex(0);
        save.addListSelectionListener(this);
        save.setVisibleRowCount(5);
        JScrollPane listScrollPane = new JScrollPane(save);

        JButton sendBtn = new JButton(sendString);
        SendListener sendListener = new SendListener(sendBtn);
        sendBtn.setActionCommand(sendString);
        sendBtn.addActionListener(sendListener);
        sendBtn.setEnabled(false);

        deleteBtn = new JButton(deleteString);
        deleteBtn.setActionCommand(deleteString);
        deleteBtn.addActionListener(new DeleteListener());

        enterMsg = new JTextField(100);
        enterMsg.addActionListener(sendListener);
        enterMsg.getDocument().addDocumentListener(sendListener);
        String name = saveList.getElementAt(
        		save.getSelectedIndex()).toString();

        //Create a panel that uses BoxLayout.
        JPanel buttonPane = new JPanel();
        buttonPane.setLayout(new BoxLayout(buttonPane,
                                           BoxLayout.LINE_AXIS));
        buttonPane.add(deleteBtn);
        buttonPane.add(Box.createHorizontalStrut(5));
        buttonPane.add(new JSeparator(SwingConstants.VERTICAL));
        buttonPane.add(Box.createHorizontalStrut(5));
        buttonPane.add(enterMsg);
        buttonPane.add(sendBtn);
        buttonPane.setBorder(BorderFactory.createEmptyBorder(5,5,5,5));

        add(listScrollPane, BorderLayout.CENTER);
        add(buttonPane, BorderLayout.PAGE_END);
        
    }

    class DeleteListener implements ActionListener {
        public void actionPerformed(ActionEvent e) {
            //This method can be called only if
            //there's a valid selection
            //so go ahead and remove whatever's selected.
            int index = save.getSelectedIndex();
            saveList.remove(index);

            int size = saveList.getSize();

            if (size == 0) { //Nobody's left, disable firing.
            	deleteBtn.setEnabled(false);

            } else { //Select an index.
                if (index == saveList.getSize()) {
                    //removed item in last position
                    index--;
                }

                save.setSelectedIndex(index);
                save.ensureIndexIsVisible(index);
            }
        }
    }

    //This listener is shared by the text field and the send button.
    class SendListener implements ActionListener, DocumentListener {
        private boolean alreadyEnabled = false;
        private JButton sendBtn;

        public SendListener(JButton button) {
            this.sendBtn = button;
        }

        //Required by ActionListener.
        public void actionPerformed(ActionEvent e) {
            String message = enterMsg.getText();

            //User didn't type in a unique name...
            if (message.equals("") || alreadyInList(message)) {
                Toolkit.getDefaultToolkit().beep();
                enterMsg.requestFocusInWindow();
                enterMsg.selectAll();
                return;
            }

            int index = save.getSelectedIndex(); //get selected index
            if (index == -1) { //no selection, so insert at beginning
                index = 0;
            } else {           //add after the selected item
                index++;
            }

            saveList.insertElementAt(enterMsg.getText(), index);
            //If we just wanted to add to the end, we'd do this:
            //listModel.addElement(employeeName.getText());

            //Reset the text field.
            enterMsg.requestFocusInWindow();
            enterMsg.setText("");

            //Select the new item and make it visible.
            save.setSelectedIndex(index);
            save.ensureIndexIsVisible(index);
        }

        protected boolean alreadyInList(String name) {
            return saveList.contains(name);
        }

        //Required by DocumentListener.
        public void insertUpdate(DocumentEvent e) {
            enableButton();
        }

        //Required by DocumentListener.
        public void removeUpdate(DocumentEvent e) {
            handleEmptyTextField(e);
        }

        //Required by DocumentListener.
        public void changedUpdate(DocumentEvent e) {
            if (!handleEmptyTextField(e)) {
                enableButton();
            }
        }

        private void enableButton() {
            if (!alreadyEnabled) {
            	sendBtn.setEnabled(true);
            }
        }

        private boolean handleEmptyTextField(DocumentEvent e) {
            if (e.getDocument().getLength() <= 0) {
                sendBtn.setEnabled(false);
                alreadyEnabled = false;
                return true;
            }
            return false;
        }
    }

    //This method is required by ListSelectionListener.
    public void valueChanged(ListSelectionEvent e) {
        if (e.getValueIsAdjusting() == false) {

            if (save.getSelectedIndex() == -1) {
            //No selection, disable delete button.
            	deleteBtn.setEnabled(false);

            } else {
            //Selection, enable the delete button.
            	deleteBtn.setEnabled(true);
            }
        }
    }


    private static void createAndShowGUI() {
        //Create and set up the window.
        JFrame frame = new JFrame("ListDemo");
        frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);

        //Create and set up the content pane.
        JComponent newContentPane = new ListDemo();
        newContentPane.setOpaque(true); //content panes must be opaque
        frame.setContentPane(newContentPane);

        //Display the window.
        frame.pack();
        frame.setVisible(true);
 
    }
    
    public void runServer()
    {
       ServerSocket server;
       Socket connection;
       int counter = 1;

       try {
          // Step 1: Create a ServerSocket.
          server = new ServerSocket(50000 );

          while ( true ) {
             // Step 2: Wait for a connection.
             display.setText( "Waiting for connection\n" );
             connection = server.accept();

             display.append( "Connection " + counter +
                " received from: " +
                connection.getInetAddress().getHostName() );

             // Step 3: Get input and output streams.
             output = new ObjectOutputStream(
                          connection.getOutputStream() );
             output.flush();
             input = new ObjectInputStream(
                         connection.getInputStream() );
             display.append( "\nGot I/O streams\n" );

             // Step 4: Process connection.
             String message =
                "SERVER>>> Connection successful";
             output.writeObject( message );
             output.flush();
             enter.setEnabled( true );

             do {
                try {
                   message = (String) input.readObject();
                   display.append( "\n" + message );
                   display.setCaretPosition(
                      display.getText().length() );
                }
                catch ( ClassNotFoundException cnfex ) {
                   display.append(
                      "\nUnknown object type received" );
                }
             } while ( !message.equals( "CLIENT>>> TERMINATE" ) );

             // Step 5: Close connection.
             display.append( "\nUser terminated connection" );
             enter.setEnabled( false );
             output.close();
             input.close();
             connection.close();

             ++counter;
          }
       }
       catch ( EOFException eof ) {
          System.out.println( "Client terminated connection" );
       }
       catch ( IOException io ) {
          io.printStackTrace();
       }
    }

    private void sendData( String s )
    {
       try {
          output.writeObject( "CLIENT2>>> " + s );
          output.flush();
          display.append( "\nCLIENT2>>>" + s );
       }
       catch ( IOException cnfex ) {
          display.append(
             "\nError writing object" );
       }
    }

    public static void main( String args[] )
    {
       Server app = new Server();

       app.runServer();
    }
 }//end of Server

Thanks in advance

Recommended Answers

All 13 Replies

Hello, pjpro.
There're some variables/methods in your code, that you use but haven't declared (such as "ListDemo", "display", "enter"). That is the source of the compilation errors.

If I was you - I'd use another strategy to develop:
1. Write simple code for client-server interaction.
2. Increasing this code step by step by a little portions.

That will help you to understand better what you're doing there (also as to have better control over it :P)

>I'm having some major problems with it.
What that stands for?

I've got a basic chat client and server. That was my attempt to add in a JList into it.
If i just started again with the chat part how would i go about adding in the JList for saving recieved messages?

Well, if your client-server interaction part works fine (I mean, that you're able to establish connection and transfer some data). Then all you have to do is somehow (depends on in which view you want to keep it in the JList) parse your data to add into list or withdraw from it.

Some examples of using JList you can find here:
Class JList
Advanced JList Programming

i will hav a look at them and see what i can do.

i've tried to add in the JList into the basic chat program.

i can't work out how to add the received messages to the list.

Client Code

import java.io.*;
import java.net.*;
import java.awt.*;
import java.awt.event.*;
import javax.swing.*;

public class Client extends JFrame {
	
   private static InetAddress host;   //........
   private JTextField enter;
   private JTextArea display, saved;
   ObjectOutputStream output;
   ObjectInputStream input;
   String message = "";
   private JList save;
   private ListModel saveList;
   private Icon deleteString;
   private JButton deleteBtn;

   public Client()
   {
      super( "Client" );

      enter = new JTextField(75);
      enter.setEnabled( false );
      enter.addActionListener(
         new ActionListener() {
            public void actionPerformed( ActionEvent e )
            {
               sendData( e.getActionCommand() );
            }
         }
      );
      add( enter, BorderLayout.NORTH );

      display = new JTextArea();
      add( new JScrollPane( display ),
             BorderLayout.SOUTH );
      setSize( 600, 300 );
      setVisible(true);
      
      deleteBtn = new JButton(deleteString);
      add( new JButton( "Delete"), BorderLayout.EAST);
      
      saved = new JTextArea();
      saved.setPreferredSize(new Dimension( 600, 300));
      
      save = new JList(saveList); //data has type Object[]
      save.setSelectionMode(ListSelectionModel.SINGLE_INTERVAL_SELECTION);
      save.setLayoutOrientation(JList.HORIZONTAL_WRAP);
      save.setVisibleRowCount(-1);
      add( new JScrollPane( saved ),
             BorderLayout.CENTER );
      
      
      setSize( 600, 300 );
      setVisible(true);
   }
   public void runClient()
   {
      Socket client;

      try {
         // Step 1: Create a Socket to make connection.
         display.setText( "Attempting connection\n" );

         host = InetAddress.getLocalHost();	//...............
         client = new Socket(host, 50600 );

         display.append( "Connected to: " +
            client.getInetAddress().getHostName() );

         // Step 2: Get the input and output streams.
         output = new ObjectOutputStream(
                      client.getOutputStream() );
         output.flush();
         input = new ObjectInputStream(
                     client.getInputStream() );
         display.append( "\nGot I/O streams\n" );

         // Step 3: Process connection.
         enter.setEnabled( true );
         do {
            try {
               message = (String) input.readObject();
               display.append( "\n" + message );
               display.setCaretPosition(
                  display.getText().length() );
            }
            catch ( ClassNotFoundException cnfex ) {
               display.append(
                  "\nUnknown object type received" );
            }
         } while ( !message.equals( "SERVER>>> TERMINATE" ) );

         // Step 4: Close connection.
         display.append( "Closing connection.\n" );
         output.close();
         input.close();
         client.close();
      }
      catch ( EOFException eof ) {
         System.out.println( "Server terminated connection" );
      }
      catch ( IOException e ) {
         e.printStackTrace();
      }
   }

   private void sendData( String s )
   {
      try {
         message = s;
         output.writeObject( "CLIENT>>> " + s );
         output.flush();
         display.append( "\nCLIENT>>>" + s );
      }
      catch ( IOException cnfex ) {
         display.append(
            "\nError writing object" );
      }
   }
   
   public void actionPerformed(ActionEvent e) {
	    int index = save.getSelectedIndex();
	    save.remove(index);

	    int size = saveList.getSize();

	    if (size == 0) { //No messages left, disable delete.
	    	deleteBtn.setEnabled(false);

	    } else { //Select an index.
	        if (index == saveList.getSize()) {
	            //removed item in last position
	            index--;
	        }

	        save.setSelectedIndex(index);
	        save.ensureIndexIsVisible(index);
	    }
	}


   public static void main( String args[] )
   {
      Client app = new Client();
      app.runClient();
   }
}// end of Client

In one of the links, that I gave you (Advanced JList Programming) there is a potion for you. "Lists with Dynamic Contents" .. with example to play around :)

i still have no idea at all.

Well, let's look closer to example given there (I mean the points of attention):

//create a model
final DefaultListModel model = new DefaultListModel();

//creating JList based on our model
JList list = new JList(model);

//add element to the model
model.addElement("Element");

This 3 lines describes all the process: working with JList using model (look at MVC pattern).

So, we can make this example even more simple:

public static void main(String[] args)
    {
	final DefaultListModel model = new DefaultListModel();
	JList list = new JList(model);	
       //adding 2 elements
       model.addElement("Element 1");
       model.addElement("Element 2");


	JFrame frame = new JFrame("DefaultListModel JList Demo");
	JScrollPane scrollPane = new JScrollPane(list);
	frame.getContentPane().add(scrollPane, BorderLayout.CENTER);
	frame.pack();
	frame.setVisible(true);

    }
commented: Nice examples +17

i'v played around with a JList prog. i'm tryin to work it into my prog but with no success.

All this (working with JList using model) you have in your server code.

it'l need to be in both. i'v been trying to figure it out in each. mainly the server because the coding behind it is easier to understand.

Ok, if I understand you correctly, you need to write to the JList the messages, recieved from server (for client). Step by step, using given example:
1. Create model

DefaultListModel saveList = new DefaultListModel();

(in your code, you use ListModel. It's abstract class and you can't create an instance of it. So I took for this DefaultListModel (as you do in server side))

2. Create your JList basing on this model:

save = new JList(saveList);

(you already do this)

3. Take the message from server and then pass it to your model:

message = (String) input.readObject();
saveList.addElement(message);
Be a part of the DaniWeb community

We're a friendly, industry-focused community of developers, IT pros, digital marketers, and technology enthusiasts meeting, networking, learning, and sharing knowledge.