Warning: file_get_contents(/data/phpspider/zhask/data//catemap/9/java/328.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Java JOptionPane按钮和自定义面板之间的通信_Java_Swing_Modal Dialog_Jdialog - Fatal编程技术网

Java JOptionPane按钮和自定义面板之间的通信

Java JOptionPane按钮和自定义面板之间的通信,java,swing,modal-dialog,jdialog,Java,Swing,Modal Dialog,Jdialog,我已经创建了一个多输入对话框,通过构建一个带有我想要的字段的JPanel并将其添加到一个JOption窗格中 JMainPanel mainPanel = new JMainPanel(mensaje, parametros, mgr); int i = JOptionPane.showOptionDialog(null, mainPanel, "Sirena", JOptionPane.DEFAULT_OPTION, JOptionPane.PLAIN_MESSAGE, nu

我已经创建了一个多输入对话框,通过构建一个带有我想要的字段的JPanel并将其添加到一个JOption窗格中

JMainPanel mainPanel = new JMainPanel(mensaje, parametros, mgr);

int i = JOptionPane.showOptionDialog(null, mainPanel, "Sirena",
        JOptionPane.DEFAULT_OPTION, JOptionPane.PLAIN_MESSAGE, null,
        new String[] {"Aceptar", "Cancelar"}, "Aceptar");
但是,我在按钮方面遇到了问题,因为有些字段是必需的。如何使“确定”按钮在每个必填字段打开后启用,或单击按钮进行验证,直到每个必填字段都填写完毕后才关闭窗格

从Java API中,我发现:

选项-指示用户可能选择的对象数组 能使;如果对象是组件,则会正确渲染它们; 非字符串对象使用其toString方法进行渲染;如果这 参数为null,选项由外观决定

那么,我不能将自定义按钮作为参数传递吗

看来我得自己做JDialog了?对于这种情况,我不知道如何让它像JOptionPane一样返回一个
int
,有推荐的教程吗

在示例中,选项是显示的按钮

另外,我可以完全控制我添加到JPanel的字段

这是JOptionPane的屏幕截图:


我建议您在JPanel扩展类中定义一些属性,并使用来侦听发生的更改和启用/禁用相关按钮

这是一个例子

另一个问题可能是在组件的层次结构中找到ok/cancel按钮,因为JDialog是通过JOptionPane创建的,您没有对按钮的引用。这里有一个有用的例子

可以使用方法将属性添加到JComponent。 当给定属性发生更改时,将引发PropertyChanged事件


因此,在您的示例中,您可以定义一个布尔属性,指示插入JDialog中的必需属性。然后添加一个PropertyChangeListener,在收到通知时启用/禁用ok按钮。

我不认为您可以取消激活JOptionPane的selections按钮,但仍然使用JOptionPane的一种方法是,如果未设置所需字段,只需重新显示它。您可以先显示一条描述错误的错误消息JOptionPane,然后显示一个新的JOptionPane,其中包含与第二个参数相同的JPanel,这样已经输入的数据就不会丢失。否则,您可能需要创建自己的JDialog,顺便说一句,这并不难做到

编辑
我错了。如果使用一点递归,可以启用和禁用对话框按钮

例如:

import java.awt.Component;
import java.awt.Container;
import java.awt.event.*;
import java.util.HashSet;
import java.util.Set;

import javax.swing.*;

public class Foo extends JPanel {
   private static final String[] DIALOG_BUTTON_TITLES = new String[] { "Aceptar", "Cancelar" };
   private JCheckBox checkBox = new JCheckBox("Buttons Enabled", true);
   private Set<AbstractButton> exemptButtons = new HashSet<AbstractButton>();

   public Foo() {
      JButton exemptBtn = new JButton("Exempt Button");
      JButton nonExemptBtn = new JButton("Non-Exempt Button");

      add(checkBox);
      add(exemptBtn);
      add(nonExemptBtn);
      exemptButtons.add(checkBox);
      exemptButtons.add(exemptBtn);

      checkBox.addActionListener(new ActionListener() {

         @Override
         public void actionPerformed(ActionEvent evt) {
            allBtnsSetEnabled(checkBox.isSelected());
         }
      });

   }

   private void allBtnsSetEnabled(boolean enabled) {
      JRootPane rootPane = SwingUtilities.getRootPane(checkBox);
      if (rootPane != null) {
         Container container = rootPane.getContentPane();
         recursiveBtnEnable(enabled, container);
      }
   }

   private void recursiveBtnEnable(boolean enabled, Container container) {
      Component[] components = container.getComponents();
      for (Component component : components) {
         if (component instanceof AbstractButton && !exemptButtons.contains(component)) {
            ((AbstractButton) component).setEnabled(enabled);
         } else if (component instanceof Container) {
            recursiveBtnEnable(enabled, (Container) component);
         }
      }
   }

   public int showDialog() {
      return JOptionPane.showOptionDialog(null, this, "Sirena",
            JOptionPane.DEFAULT_OPTION, JOptionPane.PLAIN_MESSAGE, null,
            DIALOG_BUTTON_TITLES, "Aceptar");
   }


   private static void createAndShowGui() {
      Foo foo = new Foo();
      int result = foo.showDialog();
      System.out.println(DIALOG_BUTTON_TITLES[result]);
   }

   public static void main(String[] args) {
      SwingUtilities.invokeLater(new Runnable() {
         public void run() {
            createAndShowGui();
         }
      });
   }
}
导入java.awt.Component;
导入java.awt.Container;
导入java.awt.event.*;
导入java.util.HashSet;
导入java.util.Set;
导入javax.swing.*;
公共类Foo扩展了JPanel{
私有静态最终字符串[]对话框\按钮\标题=新字符串[]{“Aceptar”,“Cancelar”};
私有JCheckBox复选框=新的JCheckBox(“按钮已启用”,true);
private Set exemptButtons=new HashSet();
公共食物({
JButton exemptBtn=新JButton(“豁免按钮”);
JButton nonExemptBtn=新JButton(“非豁免按钮”);
添加(复选框);
添加(豁免BTN);
添加(非豁免BTN);
豁免按钮。添加(复选框);
添加(exemptBtn);
checkBox.addActionListener(新建ActionListener()){
@凌驾
已执行的公共无效操作(操作事件evt){
allBtnsSetEnabled(checkBox.isSelected());
}
});
}
私有void allBtnsSetEnabled(布尔启用){
JRootPane rootPane=SwingUtilities.getRootPane(复选框);
if(rootPane!=null){
Container Container=rootPane.getContentPane();
RecursiveBtenable(已启用,容器);
}
}
私有void recursiveBtnEnable(已启用布尔值,容器){
Component[]components=container.getComponents();
用于(组件:组件){
if(AbstractButton&!ExcemptButtons.contains(组件))的组件实例{
((AbstractButton)组件).setEnabled(已启用);
}else if(容器的组件实例){
RecursiveBtenable(已启用,(容器)组件);
}
}
}
公共int showDialog(){
return JOptionPane.showOptionDialog(空,这是“Sirena”,
JOptionPane.DEFAULT_选项,JOptionPane.PLAIN_消息,null,
对话框按钮标题,“Aceptar”);
}
私有静态void createAndShowGui(){
Foo-Foo=新的Foo();
int result=foo.showDialog();
System.out.println(对话框按钮标题[结果]);
}
公共静态void main(字符串[]args){
SwingUtilities.invokeLater(新的Runnable(){
公开募捐{
createAndShowGui();
}
});
}
}
这段代码使用监听器来检查JCheckBox的状态,但是如果您想知道文本字段文档是否有数据,可以让监听器(DocumentListeners)监听文本字段文档。然后,代码将获得包含JCheckBox的JRootPane,然后是根窗格的contentPane,对话框的所有组件都由它保存。然后,它在对话框持有的所有组件中递归。如果组件是一个容器,它将通过该容器递归。如果组件是一个AbstractButton(如任何JButton或复选框),那么它将启用或禁用--除了在豁免按钮集中保留的按钮

文档侦听器的更好示例

import java.awt.*;
import java.awt.event.*;
import java.util.HashSet;
import java.util.Set;
import javax.swing.*;
import javax.swing.event.DocumentEvent;
import javax.swing.event.DocumentListener;

public class Foo2 extends JPanel {
   private static final String[] DIALOG_BUTTON_TITLES = new String[] {
         "Aceptar", "Cancelar" };
   private static final int FIELD_COUNT = 10;
   private Set<AbstractButton> exemptButtons = new HashSet<AbstractButton>();
   private JTextField[] fields = new JTextField[FIELD_COUNT];

   public Foo2() {
      setLayout(new GridLayout(0, 5, 5, 5));
      DocumentListener myDocListener = new MyDocumentListener();
      for (int i = 0; i < fields.length; i++) {
         fields[i] = new JTextField(10);
         add(fields[i]);
         fields[i].getDocument().addDocumentListener(myDocListener);
      }

      // cheating here

      int timerDelay = 200;
      Timer timer = new Timer(timerDelay , new ActionListener() {

         @Override
         public void actionPerformed(ActionEvent arg0) {
            checkDocsForText();            
         }
      });
      timer.setRepeats(false);
      timer.setInitialDelay(timerDelay);
      timer.start();

   }

   private void checkDocsForText() {
      for (JTextField field : fields) {
         if (field.getText().trim().isEmpty()) {
            allBtnsSetEnabled(false);
            return;
         }
      }
      allBtnsSetEnabled(true);
   }

   private void allBtnsSetEnabled(boolean enabled) {
      JRootPane rootPane = SwingUtilities.getRootPane(this);
      if (rootPane != null) {
         Container container = rootPane.getContentPane();
         recursiveBtnEnable(enabled, container);
      }
   }

   private void recursiveBtnEnable(boolean enabled, Container container) {
      Component[] components = container.getComponents();
      for (Component component : components) {
         if (component instanceof AbstractButton && !exemptButtons.contains(component)) {
            ((AbstractButton) component).setEnabled(enabled);
         } else if (component instanceof Container) {
            recursiveBtnEnable(enabled, (Container) component);
         }
      }
   }

   public int showDialog() {
      return JOptionPane.showOptionDialog(null, this, "Sirena",
            JOptionPane.DEFAULT_OPTION, JOptionPane.PLAIN_MESSAGE, null,
            DIALOG_BUTTON_TITLES, "Aceptar");
   }

   private class MyDocumentListener implements DocumentListener {

      public void removeUpdate(DocumentEvent arg0) {
         checkDocsForText();
      }

      public void insertUpdate(DocumentEvent arg0) {
         checkDocsForText();
      }

      public void changedUpdate(DocumentEvent arg0) {
         checkDocsForText();
      }
   }


   private static void createAndShowGui() {
      Foo2 foo = new Foo2();
      int result = foo.showDialog();
      if (result >= 0) {
         System.out.println(DIALOG_BUTTON_TITLES[result]);
      }
   }

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

}
import java.awt.*;
导入java.awt.event.*;
导入java.util.HashSet;
导入java.util.Set;
导入javax.swing.*;
导入javax.swing.event.DocumentEvent;
导入javax.swing.event.DocumentListener;
公共类Foo2扩展了JPanel{
私有静态最终字符串[]对话框\按钮\标题=新字符串[]{
“Aceptar”、“Cancelar”};
私有静态最终整型字段计数=10;
private Set exemptButtons=new HashSet();
私有JTextField[]字段=新JTextField[FIE