2016-07-22 26 views
1

Ich habe eine JFrame mit JFileChooser. Es ist notwendig, eine benutzerdefinierte Import-Schaltfläche anstelle der Standard-Dateiauswahl-Aktionsschaltfläche zu haben.JFileChooser.getSelectedFile() gibt null zurück, wenn benutzerdefinierte Aktionsschaltfläche implementiert wird

Wenn ich benutzerdefinierte Aktionstaste verwenden, geben JFileChooser.getSelectedFile() null zurück, wenn ich Wert in Textfeld Dateiname eingeben. Wenn ich dagegen auf die Datei klicke und auf den benutzerdefinierten Import klicke, kann ich die Datei auswählen, die ich ausgewählt habe.

Hier enthalten i den Beispielcode dieses

import java.awt.BorderLayout; 
import java.awt.GridBagConstraints; 
import java.awt.GridBagLayout; 
import java.awt.event.ActionEvent; 
import java.awt.event.ActionListener; 

import javax.swing.JButton; 
import javax.swing.JFileChooser; 
import javax.swing.JFrame; 
import javax.swing.JOptionPane; 
import javax.swing.JPanel; 
import javax.swing.SwingUtilities; 

public class FileChooserDemo extends JPanel 
          implements ActionListener { 
    private static final long serialVersionUID = 1L; 
    JFileChooser importFileChooser; 
    JFrame frame; 

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

     JPanel inputJobDetailsPanel = new JPanel(new BorderLayout(0,5)); 

     importFileChooser = new JFileChooser(); 
     importFileChooser.setControlButtonsAreShown(false); 
     importFileChooser.setFileSelectionMode(JFileChooser.FILES_ONLY); 
     importFileChooser.setMultiSelectionEnabled(false); 
     inputJobDetailsPanel.add(importFileChooser, BorderLayout.CENTER); 

     GridBagLayout importButtonPanelLayout = new GridBagLayout(); 
     importButtonPanelLayout.columnWidths = new int[] {150}; 
     importButtonPanelLayout.rowHeights = new int[] {30}; 

     JPanel importButtonPanel = new JPanel(); 
     importButtonPanel.setLayout(importButtonPanelLayout); 

     JButton importButton = new JButton("Custom Import"); 
     importButton.setActionCommand("import"); 
     importButton.addActionListener(this); 
     importButtonPanel.add(importButton, new GridBagConstraints()); 

     JButton OtherButton = new JButton("Other Action"); 
     OtherButton.setActionCommand("otherImport"); 
     OtherButton.addActionListener(this); 
     importButtonPanel.add(OtherButton, new GridBagConstraints()); 

     inputJobDetailsPanel.add(importButtonPanel, BorderLayout.PAGE_END); 

     frame.add(inputJobDetailsPanel); 
     frame.pack(); 
     frame.setVisible(true); 
    } 

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

    @Override 
    public void actionPerformed(ActionEvent e) { 
     String command = e.getActionCommand(); 
     if(command.equals("import")) { 
      if(importFileChooser.getSelectedFile() == null) { 
       JOptionPane.showMessageDialog(frame, "You entered file name but getSelectedFile() return null"); 
      }else { 
       JOptionPane.showMessageDialog(frame, "Chosen File Name: " + importFileChooser.getSelectedFile().getName()); 
      } 
     }else { 
      JOptionPane.showMessageDialog(frame, "You clicked other action"); 
     } 

    } 
} 

O/P zu reproduzieren:

enter image description here

Schritte zum Reproduzieren:

  1. Führen Sie die Anwendung
  2. eingeben ein gültiger Dateiname i n "Dateiname" Textfeld
  3. Klicken Sie auf Custom Import
  4. Jetzt können Sie sehen, "Sie eingegebene Dateiname aber getSelectedFile() return null"

Hinweis: Wenn i Standardaktion Taste freigegeben durch importFileChooser.setControlButtonsAreShown(true);

Ich kann die GetSelectedFile() sogar in Textbox eingegeben, ohne auf die Datei klicken.

Eigentlich versuche ich ein Automatisierungsskript zu schreiben, also kann ich nur Dateipfad über "Dateiname" Textfeld eingeben.

Irgendeine Idee, um die Dateien von getSelectedFile() ohne Klicken auf die Datei zu bekommen ??

+0

Kann unter Mac OS X nicht reproduziert werden; Die Benutzeroberfläche der Auswahl enthält kein "Textfeld". – trashgod

+0

@trashgod: Hier habe ich den Screenshot aufgenommen. Ich kann das sowohl in Windows als auch in Linux sehen. – Tamil

Antwort

1

Endlich bekam ich die Ausgabe wie erwartet. Aufruf der Standard-Dateiauswahl Schaltfläche Aktion Listener

@SuppressWarnings("serial") 
@Override 
public void actionPerformed(ActionEvent e) { 
    String command = e.getActionCommand(); 
    if(command.equals("import")) { 
     if(importFileChooser.getSelectedFile() == null) { 
      MetalFileChooserUI ui = (MetalFileChooserUI) importFileChooser.getUI(); 
      for(ActionListener a: ui.getDefaultButton(importFileChooser).getActionListeners()) { 
       a.actionPerformed(new ActionEvent(this, ActionEvent.ACTION_PERFORMED, null) { 
          //Nothing need go here, the actionPerformed method (with the above arguments) will trigger the respective listener 
        }); 
      } 
     } 

     if(importFileChooser.getSelectedFile() != null) { 
      JOptionPane.showMessageDialog(frame, "Chosen File Name: " + importFileChooser.getSelectedFile().getName()); 
     } 
     else { 
      JOptionPane.showMessageDialog(frame, "You entered file name but getSelectedFile() return null"); 
     } 
    } 
    else { 
     JOptionPane.showMessageDialog(frame, "You clicked other action"); 
    } 
} 
+0

Nicht unvernünftig, obwohl ich ein Zubehörteil bevorzuge. Einige Einschränkungen sind [hier] (http://stackoverflow.com/a/38566916/230513) erwähnt. – trashgod

1

Da alle nicht & Fühlen Implementierungen für die direkte Eingabe bieten Schauen eines Dateinamens in einem Textfeld *, Sie können einen alternativen Entwurf zu berücksichtigen:

  • Weniger modal: Wie in Providing an Accessory Component gezeigt, können Sie eine Zubehörkomponente in einem Bereich hinzufügen "mit mehr Steuerelementen darauf wie Kontrollkästchen, die zwischen Funktionen wechseln." Die genauen Details hängen von den Funktionen ab, die durch Custom Import und Andere Aktion aktiviert werden.

  • Mehr modal: Präsentieren Sie einen modalen Dialog der Auswahl nach der Benutzer hat einen bestimmten Abschnitt genehmigt.

Der Zwischen Ansatz vorgeschlagen here folgende Einschränkungen:

  1. Geht davon javax.swing.plaf.metal.MetalLookAndFeel.

  2. ActionEvent: „Ein nicht näher beschriebenes Verhalten wird verursacht, wenn die id Parameter einer bestimmten ActionEvent Instanz nicht im Bereich ACTION_FIRST-ACTION_LAST

  3. ActionEvent:.“ Eine null Befehlszeichenfolge ist legal, aber nicht empfohlen.“

* zB com.apple.laf.AquaLookAndFeel

+0

Danke für die Beantwortung meiner Frage. Aber ich verstehe deinen Standpunkt nicht. Sollte ich das LookAndFeel ändern müssen? – Tamil

+0

Ich glaube nicht, dass das helfen wird; Bewegen Sie sich stattdessen zu einer Zubehörkomponente oder einem modalen Dialogfeld. – trashgod

+0

Ich habe meine Antwort geschrieben, können Sie bitte bestätigen und lassen Sie mich wissen, wenn dies andere Probleme verursacht. Vielen Dank!!! – Tamil