Question

Je suis en train de configurer une interface graphique où je dois prendre des informations saisies à partir d'éléments de formulaire et les manipuler. Cela nécessite que j'utilise certains éléments pour accéder à d'autres.

Par exemple, j'ai une zone de saisie ( JTextField ) et un bouton ( JButton ) à côté. Lorsque le bouton est enfoncé, je dois pouvoir manipuler le texte saisi dans la zone de saisie. Tout ce que j'ai essayé de faire jusqu'à présent pour y parvenir a échoué.

Voici à quoi ressemble mon code (j'ai intégré mes questions dans les commentaires):

public class MyClass
{
    public static void main(String args[])
    {
        // Form elements are in here
        JTextField myTextField = new JTextField(10);
        JButton myTextFieldSubmit = new JButton("Submit");
        myTextFieldSubmit.addActionListener(new ListenerClass());
    }
}

class ListenerClass implements ActionListener
{
    public void actionPerformed(ActionEvent e)
    {
        // This is what happens when these elements are used
        // I need to be able to access the form elements from MyClass in here, but this doesn't seem possible with my current setup
        // For example, when the Submit button is pressed, I need to be able to myTextField.getText() and edit MyClass members
        // How should my setup be changed to accommodate these needs?
    }
}

Merci pour toute aide!

Était-ce utile?

La solution

C’est vraiment un problème de portée variable.

Actuellement, le champ de texte et le bouton relèvent de la méthode main . Par conséquent, si vous avez une classe distincte pour ActionListener , cela signifie qu'il n'aura pas accès à ces variables.

Il existe plusieurs moyens pour y parvenir:

(1) Créez une classe interne ListenerClass dans MyClass , puis activez myTextField et myTextFieldSubmit . champs de MyClass .

public class MyClass
{
  final static JTextField myTextField = new JTextField(10);
  final static JButton myTextFieldSubmit = new JButton("Submit");

  public static void main(String args[])
  {
    myTextFieldSubmit.addActionListener(new ListenerClass());
  }

  static class ListenerClass implements ActionListener
  {
    public void actionPerformed(ActionEvent e)
    {
      myTextField.setText("");
    }
  }
}

(2) Créez une classe interne anonyme dans la méthode main , ce qui permettra à myTextField et à myTextFieldSubmit de rester au même endroit. , tant qu'ils sont déclarés final .

public class MyClass
{
  public static void main(String args[])
  {
    final JTextField myTextField = new JTextField(10);
    final JButton myTextFieldSubmit = new JButton("Submit");

    myTextFieldSubmit.addActionListener(new ActionListener() {
        public void actionPerformed(ActionEvent e)
        {
            myTextField.setText("");
        }
    });
  }
}

(3) Créez une classe locale locale à la méthode main . Là encore, il faudra que le champ de texte et le bouton soient déclarés final pour permettre l'accès depuis la classe interne.

public class MyClass
{
  public static void main(String args[])
  {
    final JTextField myTextField = new JTextField(10);
    final JButton myTextFieldSubmit = new JButton("Submit");

    class ListenerClass implements ActionListener
    {
      public void actionPerformed(ActionEvent e)
      {
        myTextField.setText("");
      }
    }

    myTextFieldSubmit.addActionListener(new ListenerClass());
  }
}

(4) Définition d'une référence à ListenerClass , par exemple dans le constructeur, et définition de myTextField et de myTextFieldSubmit comme variable d'instance.

public class MyClass
{
  JTextField myTextField = new JTextField(10);
  JButton myTextFieldSubmit = new JButton("Submit");

  public MyClass()
  {
    myTextFieldSubmit.addActionListener(new ListenerClass(this));
  }

  public static void main(String args[])
  {
    new MyClass();
  }
}

class ListenerClass implements ActionListener
{
  MyClass myClass;

  public ListenerClass(MyClass myClass)
  {
    this.myClass = myClass;
  }

  public void actionPerformed(ActionEvent e)
  {
    myClass.myTextField.setText("");
  }
}

(5) Créez myTextField et myTextFieldSubmit dans des champs static , et autorisez l'accès direct à ListerClass .

public class MyClass
{
  static JTextField myTextField = new JTextField(10);
  static JButton myTextFieldSubmit = new JButton("Submit");

  public static void main(String args[])
  {
    myTextFieldSubmit.addActionListener(new ListenerClass());
  }
}

class ListenerClass implements ActionListener
{
  public void actionPerformed(ActionEvent e)
  {
    MyClass.myTextField.setText("");
  }
}

Il existe probablement encore plus de moyens pour atteindre cet objectif, et il existe peut-être de meilleurs moyens pour le mettre en œuvre. Le choix de votre approche dépend vraiment de la conception souhaitée de l'application.

Autres conseils

Vous pouvez transmettre une référence à MyClass dans le constructeur à ListenerClass .

Votre problème est commun à l'utilisation d'écouteurs pour quelque raison que ce soit en Java: comment laisser le gestionnaire accéder à l'objet qui a averti les écouteurs ou ses pairs.

Il existe généralement deux conventions.

L’une consiste à obtenir l’objet directement à partir de l’objet événement. Vous pouvez le faire avec getSource (). Mais vous n’obtiendrez que le widget qui l’a fait.

Une autre option consiste à permettre à la classe d'écoute d'accéder aux widgets. Une solution consiste à utiliser des classes internes non statiques (cela dépend de la façon dont vous le déclarez), auquel cas il est autorisé à accéder aux membres de la classe contenante.

Cependant, dans ce cas, vos widgets sont des variables et non des membres (êtes-vous sûr de vouloir le faire?). Votre seule solution serait donc que les membres les conservent dans la classe Listner, puis au lieu de créer l'écouteur dans l'appel addListener, créez un écouteur, transmettez les widgets appropriés et ajoutez ce dernier. L'auditeur peut maintenant accéder à ces widgets via ses propres références à ceux-ci, qui sont stockées dans les membres.

Licencié sous: CC-BY-SA avec attribution
Non affilié à StackOverflow
scroll top