JimBob117
JimBob117

Reputation: 99

Having issues with custom linked list and applying to JTable

I'm having issues creating a JTable using a custom table model and custom linked list. I'm hoping there are some easy changes that I'm missing.

My main class:

import java.util.ArrayList;
import java.util.*;
import java.io.*;
import javax.swing.*;
import java.awt.*;
import java.awt.event.*;
import javax.swing.table.*;
public class StudentInterface {
public static void main(String[] args){
        new StudentInterface();
    }
    //create a linked list       
    MyLinkedList studentPack = new MyLinkedList();

public StudentInterface (){
    //create jFrame
    JFrame jFrame = new JFrame("Student Information Interface");
    jFrame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
    jFrame.setSize(400,300);
    jFrame.setVisible(true);
    jFrame.setDefaultLookAndFeelDecorated(true);
    jFrame.setPreferredSize(new Dimension(600, 400));

    //create content panes
    JPanel headerPanel = new JPanel();
    JPanel tablePanel = new JPanel();
    JPanel buttonPanel = new JPanel();
    JPanel combinedPanel = new JPanel();
    headerPanel.setLayout(new BorderLayout());
    tablePanel.setLayout(new FlowLayout());
    buttonPanel.setLayout(new FlowLayout());
    combinedPanel.setLayout(new BorderLayout());

    //add label to header content panel
    JLabel headerLabel1 = new JLabel("Welcome to the Student Information Interface");
    JLabel headerLabel2 = new JLabel("***Click a cell to edit data***");
    JLabel headerLabel3 = new JLabel("***Click a column header to sort***");
    headerLabel1.setHorizontalAlignment(JLabel.CENTER);
    headerLabel2.setHorizontalAlignment(JLabel.CENTER);
    headerLabel3.setHorizontalAlignment(JLabel.CENTER);
    headerPanel.add(headerLabel1, BorderLayout.NORTH);
    headerPanel.add(headerLabel2, BorderLayout.CENTER);
    headerPanel.add(headerLabel3, BorderLayout.SOUTH);

    //Where the GUI is created:
    JMenuBar menuBar;
    JMenu menu, submenu;
    JMenuItem exitMenuItem;
    JMenuItem saveMenuItem;
    JMenuItem loadMenuItem;

    //Create the menu bar.
    menuBar = new JMenuBar();

    //Build the main menu.
    menu = new JMenu("File");
    menu.setMnemonic(KeyEvent.VK_A);
    menu.getAccessibleContext().setAccessibleDescription("The only menu in this program that has menu items");
    menuBar.add(menu);

    //create menu items
    exitMenuItem = new JMenuItem("Exit",KeyEvent.VK_T);
    menu.add(exitMenuItem);
    jFrame.setJMenuBar(menuBar);

    //create table
    tableModel model;
    model = new tableModel(new MyLinkedList());
    JTable table = new JTable(model);

    //add list to list content panel
    JScrollPane scrollPane = new JScrollPane(table);
    scrollPane.setPreferredSize(new Dimension(580, 400));
    tablePanel.add(scrollPane);

    //add buttons to button content panel
    JButton addButton = new JButton("Add");
    JButton removeButton = new JButton("Remove");
    buttonPanel.add(addButton);
    buttonPanel.add(removeButton);

    addButton.addActionListener(new ActionListener() {
        public void actionPerformed(ActionEvent e) {
        //verify pack is not full
        int packSize = studentPack.size();
        if (packSize >= 10)
            {
            JOptionPane.showMessageDialog(null,
            "The interface is full. Please remove a student first.",
            "Interface Full",
            JOptionPane.WARNING_MESSAGE);
            return;
            }

        JPanel p1 = new JPanel(new GridLayout(2,1));
        JTextField t1 = new JTextField();
        JLabel labell = new JLabel("Please enter the first name of the student you would like to add:");
        p1.add(labell);
        p1.add(t1);
        JOptionPane.showMessageDialog(null,p1,"First Name",JOptionPane.PLAIN_MESSAGE);
        String userFirstName = t1.getText();

        JPanel p2 = new JPanel(new GridLayout(2,1));
        JTextField t2 = new JTextField();
        JLabel label2 = new JLabel("Please enter the last name of the student you would like to add:");
        p2.add(label2);
        p2.add(t2);
        JOptionPane.showMessageDialog(null,p2,"Last Name",JOptionPane.PLAIN_MESSAGE);
        String userLastName = t2.getText();

        JPanel p3 = new JPanel(new GridLayout(2,1));
        JTextField t3 = new JTextField();
        JLabel label3 = new JLabel("Please enter the major of the student you would like to add:");
        p3.add(label3);
        p3.add(t3);
        JOptionPane.showMessageDialog(null,p3,"Major",JOptionPane.PLAIN_MESSAGE);
        String userMajor = t3.getText();

        JPanel p4 = new JPanel(new GridLayout(2,1));
        JTextField t4 = new JTextField();
        JLabel label4 = new JLabel("Please enter the NetID of the student you would like to add:");
        p4.add(label4);
        p4.add(t4);
        JOptionPane.showMessageDialog(null,p4,"NetID",JOptionPane.PLAIN_MESSAGE);
        String userNetID = t4.getText();

        JPanel p5 = new JPanel(new GridLayout(2,1));
        JTextField t5 = new JTextField();
        JLabel label5 = new JLabel("Please enter the gender of the student you would like to add:");
        p5.add(label5);
        p5.add(t5);
        JOptionPane.showMessageDialog(null,p5,"Gender",JOptionPane.PLAIN_MESSAGE);
        String userGender = t5.getText();

        JPanel p6 = new JPanel(new GridLayout(2,1));
        JTextField t6 = new JTextField();
        JLabel label6 = new JLabel("Please enter the UIN of the student you would like to add:");
        p6.add(label6);
        p6.add(t6);
        JOptionPane.showMessageDialog(null,p6,"UIN",JOptionPane.PLAIN_MESSAGE);
        String userUIN = t6.getText();

        JPanel p7 = new JPanel(new GridLayout(2,1));
        JTextField t7 = new JTextField();
        JLabel label7 = new JLabel("Please enter the age of the student you would like to add:");
        p7.add(label7);
        p7.add(t7);
        JOptionPane.showMessageDialog(null,p7,"Age",JOptionPane.PLAIN_MESSAGE);
        String userAgeInput = t7.getText();
        int userAge = Integer.parseInt(userAgeInput);

        JPanel p8 = new JPanel(new GridLayout(2,1));
        JTextField t8 = new JTextField();
        JLabel label8 = new JLabel("Please enter the GPA of the student you would like to add:");
        p8.add(label8);
        p8.add(t8);
        JOptionPane.showMessageDialog(null,p8,"GPA",JOptionPane.PLAIN_MESSAGE);
        String userGPAInput = t8.getText();
        double userGPA = Double.parseDouble(userGPAInput);

        //create student Student
        Student studentStudent = new Student(userFirstName, userLastName, userMajor, userGPA, userUIN, userNetID, userAge, userGender);

        //store Student in linked list
        model.addStudent(studentStudent);
        }
    });

    removeButton.addActionListener(new ActionListener() {
        public void actionPerformed(ActionEvent e) {
        //verify pack is not full
        if (studentPack.size() == 0)
            {
            JOptionPane.showMessageDialog(null,
            "The interface is empty. Please add a student first.",
            "Interface Empty",
            JOptionPane.WARNING_MESSAGE);
            return;
            }

        JPanel p9 = new JPanel(new GridLayout(2,1));
        JTextField t9 = new JTextField();
        JLabel label9 = new JLabel("Please enter the first name of the student you would like to remove: **Case Sensitive**");
        p9.add(label9);
        p9.add(t9);
        JOptionPane.showMessageDialog(null,p9,"First Name",JOptionPane.PLAIN_MESSAGE);
        String userFirstName = t9.getText();

        JPanel p10 = new JPanel(new GridLayout(2,1));
        JTextField t10 = new JTextField();
        JLabel label10 = new JLabel("Please enter the last name of the student you would like to remove: **Case Sensitive**");
        p10.add(label10);
        p10.add(t10);
        JOptionPane.showMessageDialog(null,p10,"First Name",JOptionPane.PLAIN_MESSAGE);
        String userLastName = t10.getText();

        //remove student Student in linked list
        }
    });

    exitMenuItem.addActionListener(new ActionListener() {
        public void actionPerformed(ActionEvent e) {
            System.exit(0);
        }
    });

    //nest button and list panels in combined content panel
    combinedPanel.add(headerPanel, BorderLayout.NORTH);
    combinedPanel.add(tablePanel, BorderLayout.CENTER);
    combinedPanel.add(buttonPanel, BorderLayout.SOUTH);

    //add combined content panel to frame
    jFrame.add(combinedPanel);
    jFrame.pack();
    jFrame.setLocationRelativeTo(null);

    JOptionPane.showMessageDialog(null,
    "***Click a cell to edit data*** \n ***Click a column header to sort***", "How to edit/sort data", JOptionPane.INFORMATION_MESSAGE);
    }

public class tableModel extends AbstractTableModel {

public final String[] columnNames = { "First Name", "Last Name", "Major:", "GPA", "UIN", "NetID", "Age", "Gender" };
private MyLinkedList data;

public tableModel(MyLinkedList data) {
    this.data = data;
}

@Override
public int getColumnCount() {
    return columnNames.length;
}

@Override
public String getColumnName(int column) {
    return columnNames[column];
}

@Override
public int getRowCount() {
    return data.size();
}

public void addStudent(Student student) {
        int row = data.size();
        data.add(student);
        fireTableRowsInserted(row, row);
    }

public void removeStudent(int i) {
        int row = data.size();
        data.remove(i);
        fireTableRowsDeleted(row, row);
    }

@Override
public Student getValueAt(int rowIndex, int columnIndex) {
    Object student = data.getNode(rowIndex);
    if (student == null) {
        return null;
    }
    switch (columnIndex) {
    case 0:
        return student.getFirstName();
    case 1:
        return student.getLastName();
    case 2:
        return student.getMajor();
    case 3:
        return student.getGPA();
    case 4:
        return student.getUIN();
    case 5:
        return student.getNetID();
    case 6:
        return student.getAge();
    case 7:
        return student.getGender();
    default:
        return null;
    }
}
}
}

Here's my class for the student object:

public class Student {
    // Declare attributes here
    String firstName;
    String lastName;
    String major;
    double gpa;
    String uin;
    String netid;
    int age;
    String gender;

    public Student(String newFirstName, String newLastName, String newMajor, double newGPA, String newUIN, String newNetID, int newAge, String newGender){
        setFirstName(newFirstName);
        setLastName(newLastName);
        setMajor(newMajor);
        setGPA(newGPA);
        setUIN(newUIN);
        setNetID(newNetID);
        setAge(newAge);
        setGender(newGender);
    }

    //Mutators
    public void setFirstName(String newFirstName) {
        firstName = newFirstName;
    }

    public void setLastName(String newLastName) {
        lastName = newLastName;
    }

    public void setMajor(String newMajor) {
        major = newMajor;
    }

    public void setGPA(double newGPA) {
        gpa = newGPA;
    }

    public void setUIN(String newUIN) {
        uin = newUIN;
    }

    public void setNetID(String newNetID) {
        netid = newNetID;
    }

    public void setAge(int newAge) {
        age = newAge;
    }

    public void setGender(String newGender) {
        gender = newGender;
    }

    //Accessors
        public String getFirstName() {
        return firstName;
    }

        public String getLastName() {
        return lastName;
    }

        public String getMajor() {
        return major;
    }

        public double getGPA() {
        return gpa;
    }

        public String getUIN() {
        return uin;
    }

        public String getNetID() {
        return netid;
    }

        public int getAge() {
        return age;
    }

        public String getGender() {
        return gender;
    }
}

Here's my reworked linked list class:

public class MyLinkedList<Student>{
    private Node<Student> lastNode;
    private int nodeCount;

    public MyLinkedList(){
        this.lastNode = null;
        this.nodeCount = 0;
    }

    public int size() {
        return nodeCount;
    }

    public boolean isEmpty() {
        return this.nodeCount == 0;
    }

    public void add(Student student) {
        Node<Student> currentNode = new Node<Student>(student);
        if (this.lastNode != null) {
            currentNode.index = lastNode.index + 1;
            currentNode.previousNode = lastNode;
            lastNode.nextNode = currentNode;
        }else {
            currentNode.previousNode = null;
            currentNode.index = 0;
        }
        this.lastNode = currentNode;
        this.nodeCount++;
    }

    public Student get(int index){
        //error handling
        if(this.isEmpty() || index < 0 || index > this.nodeCount){
            return null;
        }
        //
        Node<Student> currentNode;
        int count = lastNode.index - index;
        currentNode = lastNode;

        while (count > 0) {
            currentNode = currentNode.previousNode;
            count--;
        }

        return currentNode.student;
    }

    public Node<Student> getNode(int index){
        //error handling
        if(this.isEmpty() || index < 0 || index > this.nodeCount){
            return null;
        }
        //
        int count = lastNode.index - index;
        Node<Student> currentNode = lastNode;

        while (count > 0){
            currentNode = currentNode.previousNode;
            count--;
        }

        return currentNode;
    }

    public boolean insert(Student student, int index){
        Node<Student> currentNode;

        if (this.getNode(index) != null)
            {
            Node<Student> newNode = new Node<Student>(student);
            currentNode = this.getNode(index);
            newNode.index = index;

            if ( null != currentNode.previousNode )
                {
                currentNode.previousNode.nextNode = newNode;
                newNode.previousNode = currentNode.previousNode;
                }

            currentNode.previousNode = newNode;
            newNode.nextNode = currentNode;
            currentNode = newNode;

            while (currentNode.nextNode != null)
                {
                currentNode = currentNode.nextNode;
                currentNode.index++;
                }

                this.nodeCount++;
                return true;
            }
        else
            {
            return false; // error handling
            }
    }

    public boolean remove(int index){
        Node<Student> currentNode;

        if (this.getNode(index) != null){
            currentNode = this.getNode(index);

            if(currentNode.previousNode != null) {
                currentNode.nextNode.previousNode = currentNode.previousNode;
                currentNode.previousNode.nextNode = currentNode.nextNode;
            } else if (currentNode.nextNode != null){
                currentNode.nextNode.previousNode = null;
            } else if (this.isEmpty()){
                this.lastNode = null;
            }

            while (currentNode.nextNode != null){
                currentNode = currentNode.nextNode;
                currentNode.index--;
            }

            this.nodeCount--;
            return true;
        }else {
            return false;
        }
    }

    private static class Node<Student>{
    public Node<Student> nextNode = null;
    public Node<Student> previousNode = null;
    public int index;
    public Student student;

    public Node(Student student){
        this.student = student;
    }
    }
}

Upvotes: 0

Views: 42

Answers (1)

MadProgrammer
MadProgrammer

Reputation: 347294

This...

public class tableModel extends AbstractTableModel {
    //...    
    @Override
    public Student getValueAt(int rowIndex, int columnIndex) {
        Object student = data.getNode(rowIndex);
        if (student == null) {
            return null;
        }
        switch (columnIndex) {
            case 0:
                return student.getFirstName();
            case 1:
                return student.getLastName();
            case 2:
                return student.getMajor();
            case 3:
                return student.getGPA();
            case 4:
                return student.getUIN();
            case 5:
                return student.getNetID();
            case 6:
                return student.getAge();
            case 7:
                return student.getGender();
            default:
                return null;
        }
    }
}

is giving me a compiler error, because student is an Object and Object does not have any of the methods you are trying to use.

The obvious fix is to use...

@Override
public Student getValueAt(int rowIndex, int columnIndex) {
    Student student = data.getNode(rowIndex);

Okay, there are now two problems. First getValueAt shouldn't be returning Student, it should be returning Object and two getNode returns Node<Student>

So instead, it should probably be something more like...

@Override
public Object getValueAt(int rowIndex, int columnIndex) {
    Student student = data.get(rowIndex);

Okay, but now this is causing a compiler error, but why? get returns a Student?

I tracked the problem down to public class MyLinkedList<Student> { ... Instead, if we make it public class MyLinkedList { all the errors go away.

Your MyLinkedList doesn't actually need the generic signature <Student>, the compiler was seeing it as the "generic" token and was replacing it with Object in your code, so the get method became public Object get(int index) as the instance of MyLinkedList didn't provide a base object from which to start from ... yea for generics :P

Now, end up with something that can generate...

Show me the table

Upvotes: 1

Related Questions