0

I have a JTabbedPane with a custom tab that displays a filename, followed by a button. When The button is pressed, I would like to close that tab. My first thought was that (hopefully) when I click on the button, it would first switch to that tab, then I'd be able to just close the tab at that index. However that is not the case. I'm looking for a way to retrieve the tab index that the button is on, then I could close that tab. I tried researching and came up with indexOfComponent, but I'm unsure of how to use it in my situation. My tabs are created dynamically, therefore I store stuff inside of a vector, that creates JPanels, then displays the current information based on the selected index. (tab 0 would have all its components inside of vec[0], tab 1 = vec[1], etc).

My TextEdit class is setup like this:

public class TextEdit extends JTabbedPane {
  private Vector<JTextArea> vec; // User can make and edit files
  private Vector<JPanel> tabPanel; // Panel that has a JLabel for fileName and JButton to close file
  private Vector<JLabel> absolutePath; // Path to which file will be saved

  public TextEdit() {
    // Sets up actionlisteners, initializes variables, etc
  }

  protected void AddTab(String fileName) {
    JPanel panel = new JPanel; // Where textarea will be
    panel.setLayout(new GridLayout(0,1));
    JTextArea ta = new JTextArea();
    JScrollPane sp = new JScrollPane(ta);
    panel.add(sp);

    JPanel tp = new JPanel(); // The tab panel
    tp.setLayout(new FlowLayout(FlowLayout.LEFT, 10, 2));
    JLabel label = new JLabel(fileName);
    JButton button = new JButton("X");
    button.addActionListener(CloseOne); // My Action that will close the file
    tp.add(label);
    tp.add(button);

    this.addTab(fileName, panel); // Sets the text area into the tab
    this.setTabComponentAt(this.getSelectedIndex, tp); // Sets the tab to the fileName and button

    vec.add(ta); // Add textarea to vector for future use
    tabPanel.add(tp); // Add the tabpanel for future use. this is where the button is, I need to setSelectedIndex to the tab that the button resides onclick

}

TextEditor.java

Action CloseOne = new AbstractAction("CloseOne") {
  @Override
  public void actionPerformed(ActionEvent e) {
    // This is where I need to set the selected tab to the tab in which the button was pressed.
  }
};

The TextEditor class is what has all my actions in, and hold a TextEdit (where the tabs, etc are at).

My textedit has methods to set and get the selected index.

Going back to indexOfComponent, I would need to specify which component I'm using, however, my components are added dynamically, and I'd have to figure out the selectedindex to get into the vector or JPanels to even use that. Or am I missing something? Any suggestions?

Hovercraft Full Of Eels
  • 283,665
  • 25
  • 256
  • 373
Vince
  • 2,596
  • 11
  • 43
  • 76
  • An [MCVE] would help immensely. Otherwise you can find out the parent container by calling `getParent()` recursively if need be. Better to make your tab JPanel into its own class. – Hovercraft Full Of Eels Sep 02 '18 at 20:39
  • Somehow that managed to help along with a little googling. I forgot all about e.getSource. I just had to get the parent of the button, which got the JPanel, which I was able to use to get indexOfTabComponent(panel), Then I was able to setSelectedIndex accordingly. – Vince Sep 02 '18 at 20:51
  • Good. It also looks to be a duplicate of [this question answered by MadProgrammer](https://stackoverflow.com/a/11553266/522444) – Hovercraft Full Of Eels Sep 02 '18 at 21:06

1 Answers1

0

In your AddTab method set actionCommand to your close button as the index of newly added tab as below

JButton button = new JButton("X");
button.setActionCommand( "" + tabPanel.size() );
button.addActionListener(CloseOne);

Add removeTabComponentAtmethod in TextEdit class

  public void removeTabComponentAt( int index ) {
       vec.removeElementAt(index );  
       tabPanel.removeElementAt(index );
       this.removeTabAt( index );

  }

In your Close action get the index of clicked button

Action CloseOne = new AbstractAction("CloseOne") {

    public Component getTextEdit ( Component comp) {
         if( comp instanceof TextEdit ) {
            return ( TextEdit  ) comp;
         } 
         if( comp.getParent() != null ) {
              return getTextEdit ( comp.getParent() );
         }  else {
              return null;
         }
    }
   @Override
    public void actionPerformed(ActionEvent e) {

         String indexStr = e.getActionCommand();
         int index=-1; 
         try {
              index = Integer.parseInt( indexStr );

         } catch( NumberFormatException ex ) {
         }
         if( index > -1 ) {
            TextEdit textEdit = getTextEdit( ( Component ) e.getSource() ) ;
              if( textEdit  != null ) {
                 textEdit.removeTabComponentAt( index );
              }
         }
    }
};