Warning: file_get_contents(/data/phpspider/zhask/data//catemap/9/csharp-4.0/2.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:如何让线程等待来自用户的IO,然后继续_Java_Multithreading_Swing_Io - Fatal编程技术网

Java:如何让线程等待来自用户的IO,然后继续

Java:如何让线程等待来自用户的IO,然后继续,java,multithreading,swing,io,Java,Multithreading,Swing,Io,在DbInterface类中,函数openDB()打开与服务器上Oracle DB的连接。出于安全原因,用户必须在JFrame文本区域中输入密码,然后程序才能继续连接。现在,这个Jframe有一个操作侦听器,它等待用户输入密码并调用OpenDBContinue()方法 现在的问题是:openDB()不等待Jframe IO完成,假设DB已经打开,则将控制权返回给调用类(调用openDB()的人),然后他们继续并开始查询DB,这显然失败了 现在如何让openDB()等待Jframe IO完成?这是

在DbInterface类中,函数openDB()打开与服务器上Oracle DB的连接。出于安全原因,用户必须在JFrame文本区域中输入密码,然后程序才能继续连接。现在,这个Jframe有一个操作侦听器,它等待用户输入密码并调用OpenDBContinue()方法

现在的问题是:openDB()不等待Jframe IO完成,假设DB已经打开,则将控制权返回给调用类(调用openDB()的人),然后他们继续并开始查询DB,这显然失败了

现在如何让openDB()等待Jframe IO完成?这是给你一个想法的代码

public void openDB(int inFileInx,String inRemoteDBURLFull) throws FileNotFoundException
{   
    if(this.password!=null)
        try
        {   openDBcontinue(inFileInx,inRemoteDBURLFull);
        }
        catch(Exception exp)
            {   DpmLogger.dtlException("SPDBInterfaceException:OpenDB", exp);
            }
    else {
            passwd  =       new JFrame();
            passwd.setLocation(SpdMain.bTabbedPanel.getWidth()/2,SpdMain.bTabbedPanel.getHeight()/2);
            passwd.setTitle("Enter Passwd for user "+username);
            JPasswordField p =new JPasswordField(10);
            p.addActionListener(this);
            p.setActionCommand(inFileInx+","+inRemoteDBURLFull);
            passwd.add(p);
            passwd.setPreferredSize(new Dimension(300,50));
            passwd.pack();
            passwd.setVisible(true);
            pass=new Thread(new Runnable()  
            {   
                public void run() {
                    DpmLogger.dtlTraceOut("The password thread has completed and has got password from the user",DpmLogger.TRACE_RARE,myId);
                }

            });

            try {
                    pass.join();
                } catch (InterruptedException e) 
                    {
                        DpmLogger.dtlTraceOut("Password thread unable to join",DpmLogger.TRACE_RARE,myId);
                    }

                DpmLogger.dtlTraceOut("Password thread now joined",DpmLogger.TRACE_RARE,myId);
        }

}


public void actionPerformed(ActionEvent e) 
{   JTextField p=(JTextField)e.getSource();
    if(password==null)
    password=p.getText();
    passwd.setVisible(false);

    String[] inVars=e.getActionCommand().split(",");
    try
    {   openDBcontinue(Integer.parseInt(inVars[0]),inVars[1]);
             pass.start();
    }
    catch(Exception exp)
    {   DpmLogger.dtlException("SPDBInterfaceException:OpenDB", exp);
    }
}
如您所见,我正试图使用join()使该方法在“pass”线程上等待。操作侦听器在IO完成时启动传递线程。但它不起作用。OpenDB()返回,无需等待“pass”运行。这是因为该方法不在线程内吗?我必须让这个DBInterface类扩展线程类吗?我糊涂了

出于安全原因,用户必须在JFrame文本区域中输入密码

用于:

  • 方便(也是一种可能的解决方案)将
    JFrame
    交换为模式对话框或
    JOptionPane
    。例如,如中所示。
  • 安全性使用
    JPassWordField
    代替中的“textarea”
  • 出于安全原因,用户必须在JFrame文本区域中输入密码

    用于:

  • 方便(也是一种可能的解决方案)将
    JFrame
    交换为模式对话框或
    JOptionPane
    。例如,如中所示。
  • 安全性使用
    JPassWordField
    代替中的“textarea”

  • 您可以使用
    JDialog
    ,但这需要您管理关闭操作(添加按钮并处理状态),或者您可以简单地使用
    JOptionPane

    其中一个(设置为modal时)将导致事件调度线程在该点暂停执行,直到它们关闭

    public class TestDialog01 {
    
        public static void main(String[] args) {
            new TestDialog01();
        }
    
        public TestDialog01() {
            EventQueue.invokeLater(new Runnable() {
                @Override
                public void run() {
                    try {
                        UIManager.setLookAndFeel(UIManager.getSystemLookAndFeelClassName());
                    } catch (ClassNotFoundException | InstantiationException | IllegalAccessException | UnsupportedLookAndFeelException ex) {
                    }
    
                    PasswordPane pane = new PasswordPane();
                    int result = JOptionPane.showConfirmDialog(null, pane, "Password", JOptionPane.OK_CANCEL_OPTION, JOptionPane.QUESTION_MESSAGE);
                    if (result == JOptionPane.OK_OPTION) {
                        // get the result...
                    }
    
                }
            });
        }
    
        public class PasswordPane extends JPanel {
    
            private JTextField userName;
            private JPasswordField password;
    
            public PasswordPane() {
                userName = new JTextField(12);
                password = new JPasswordField(12);
    
                setLayout(new GridBagLayout());
                GridBagConstraints gbc = new GridBagConstraints();
                gbc.insets = new Insets(2, 2, 2, 2);
                gbc.gridx = 0;
                gbc.gridy = 0;
                add(new JLabel("User Name:"), gbc);
                gbc.gridx++;
                add(userName, gbc);
    
                gbc.gridy++;
                gbc.gridx = 0;
                add(new JLabel("Password:"), gbc);
                gbc.gridx++;
                add(password, gbc);
            }
    
            public String getUserName() {
    
                return userName.getText();
    
            }
    
            public char[] getPassword() {
    
                return password.getPassword();
    
            }
        }
    }
    


    查看更多信息

    您可以使用
    JDialog
    ,但这需要您管理关闭操作(添加按钮并处理状态),或者您可以简单地使用
    作业窗格

    其中一个(设置为modal时)将导致事件调度线程在该点暂停执行,直到它们关闭

    public class TestDialog01 {
    
        public static void main(String[] args) {
            new TestDialog01();
        }
    
        public TestDialog01() {
            EventQueue.invokeLater(new Runnable() {
                @Override
                public void run() {
                    try {
                        UIManager.setLookAndFeel(UIManager.getSystemLookAndFeelClassName());
                    } catch (ClassNotFoundException | InstantiationException | IllegalAccessException | UnsupportedLookAndFeelException ex) {
                    }
    
                    PasswordPane pane = new PasswordPane();
                    int result = JOptionPane.showConfirmDialog(null, pane, "Password", JOptionPane.OK_CANCEL_OPTION, JOptionPane.QUESTION_MESSAGE);
                    if (result == JOptionPane.OK_OPTION) {
                        // get the result...
                    }
    
                }
            });
        }
    
        public class PasswordPane extends JPanel {
    
            private JTextField userName;
            private JPasswordField password;
    
            public PasswordPane() {
                userName = new JTextField(12);
                password = new JPasswordField(12);
    
                setLayout(new GridBagLayout());
                GridBagConstraints gbc = new GridBagConstraints();
                gbc.insets = new Insets(2, 2, 2, 2);
                gbc.gridx = 0;
                gbc.gridy = 0;
                add(new JLabel("User Name:"), gbc);
                gbc.gridx++;
                add(userName, gbc);
    
                gbc.gridy++;
                gbc.gridx = 0;
                add(new JLabel("Password:"), gbc);
                gbc.gridx++;
                add(password, gbc);
            }
    
            public String getUserName() {
    
                return userName.getText();
    
            }
    
            public char[] getPassword() {
    
                return password.getPassword();
    
            }
        }
    }
    


    查看更多信息

    a有什么问题?所有事件都在swing中的单独线程(事件调度程序线程)中处理。我认为您在错误的线程中应用了
    pass.join()
    (这使得当前线程等待pass完成),而您希望等待JFrame IO完成。如果有任何耗时的事情要处理,你应该考虑<代码> SvigWorks,这样你的UI就不会被冻结了,抱歉我使用了JPasswordField(你可以在代码中看到它)。我一定忘了提到这一点,但这不是我的问题。a怎么了?所有事件都在swing中的一个单独线程(事件调度程序线程)中处理。我认为您在错误的线程中应用了
    pass.join()
    (这使得当前线程等待pass完成),而您希望等待JFrame IO完成。如果有任何耗时的事情要处理,你应该考虑<代码> SvigWorks,这样你的UI就不会被冻结了,抱歉我使用了JPasswordField(你可以在代码中看到它)。我一定忘了提这一点,但这不是我的问题,我用的是JPasswordField。请仔细查看代码。无论如何谢谢你!正确地拼写类名。如果需要,复制/粘贴它们。“textarea”不是
    JPasswordField
    。我使用JPasswordField。请仔细查看代码。无论如何谢谢你!正确地拼写类名。如果需要,复制/粘贴它们。“textarea”不是
    JPasswordField
    。因此,您没有从事件调度线程中调用OpenDB。仍然无法工作。OpenDB()总是返回,而不是等待JOptionPane返回OK_选项。发生的情况如下:调用openDB joptionPane后,openDBcalled joptionPane将显示openDBreturns to filemgr对话框:密码记录为test
    joptionPane
    必须在EDT内可见,才能阻止线程。你有一些示例代码吗?那么,你不是从事件调度线程中调用OpenDB。仍然不能工作。OpenDB()总是返回,而不是等待JOptionPane返回OK_选项。发生的情况如下:调用openDB joptionPane后,openDBcalled joptionPane将显示openDBreturns to filemgr对话框:密码记录为test
    joptionPane
    必须在EDT内可见,才能阻止线程。你有一些示例代码吗?