2015-10-11 34 views
0

我正在写一个小程序,根据按下哪个按钮来运行三个代码示例之一。使用第三个按钮,应该运行一个代码示例,直到JFrame关闭,或者直到按下按钮(我真的不介意它是如何停止的,只要用户有一个停止循环的方法)。代码已运行,并且添加了8秒的延迟以确保代码在循环之前完成运行。如何在Java中运行进程直到按下按钮?

我该如何实施?当循环时程序似乎不会终止,即使我试图通过单击JFrame中的关闭按钮来关闭程序。

该计划的主要部分如下所示:

public class WaspmoteSim extends JFrame implements ActionListener { 
public WaspmoteSim() { 
    setDefaultCloseOperation(EXIT_ON_CLOSE); 

    //getContentPane().setLayout(new GridLayout(1, 3, 10, 10)); 
    getContentPane().setLayout(new GridBagLayout()); 
    GridBagConstraints c = new GridBagConstraints(); 
    c.insets = new Insets(30,30,30,30); 
    c.ipadx = 10; 
    c.ipady = 30; 
    setSize(700, 150); 
    setLocation(100, 100); 

    JButton button1 = new JButton("Demonstration Mode"); 
    button1.addActionListener(this); 
    add(button1, c); 

    JButton button2 = new JButton("Distribution Fitting Mode"); 
    button2.addActionListener(this); 
    add(button2, c); 

    JButton button3 = new JButton("Operational Mode"); 
    button3.addActionListener(this); 
    add(button3, c); 

    setVisible(true); 
} 
public static void main(String[] args) { 
    new WaspmoteSim(); 
} 

@Override 
public void actionPerformed(ActionEvent e) { 
    String command = e.getActionCommand(); 

    if (command.equals("Demonstration Mode")) { 
     try { 
      DemoMethod(); 
     } catch (IOException ex) { 
      Logger.getLogger(WaspmoteSim.class.getName()).log(Level.SEVERE, null, ex); 
     } 
    } 
    if (command.equals("Distribution Fitting Mode")) { 
     try { 
      FittingMethod(); 
     } catch (IOException ex) { 
      Logger.getLogger(WaspmoteSim.class.getName()).log(Level.SEVERE, null, ex); 
     } 
    } 
    if (command.equals("Operational Mode")) { 
     try { 
      OperationsMethod(); 
     } catch (IOException ex) { 
      Logger.getLogger(WaspmoteSim.class.getName()).log(Level.SEVERE, null, ex); 
     } catch (InterruptedException ex) { 
      Logger.getLogger(WaspmoteSim.class.getName()).log(Level.SEVERE, null, ex); 
     } 
    } 
} 

,我想在一个循环中运行的代码看起来是这样的:

public void OperationsMethod() throws IOException, InterruptedException { 
     while(true) { 
      String workingDir = System.getProperty("user.dir"); 
      System.out.println(workingDir); 
      Process proc; 
      proc = Runtime.getRuntime().exec("cmd.exe /C C:\\Progra~1\\R\\R-3.2.1.\\bin\\Rscript.exe " + workingDir + "\\Fitter.r"); 
      TimeUnit.SECONDS.sleep(8); 
     } 
    } 

回答

1

可以遵循的程序是这样的:

1)使用ProcessBuilder创建一个Process并存储它以备后用(您可以使用一个持有者单例类“ProcessHolder”)。

2)向您的按钮注册事件功能您可以将事件功能注册到可访问ProcessHolder的按钮,并使用destroy()方法终止该过程。

查看更多here

//Process Holder singleton 
public class ProcessHolder { 
    private Map<String, Process> _processes; 

    private static ProcessHolder _processHolder; 

    private ProcessHolder() { 
     _processes = new HashMap<>(); 
    } 

    public static ProcessHolder getInstance() { 
     if(_processHolder == null) { 
      _processHolder = new ProcessHolder(); 
     } 
     return _processHolder; 
    } 

    public void getProcesses() { 
     return _processes; 
    } 

} 

//...... 
public class WaspmoteSim extends JFrame implements ActionListener { 

    public static final String YOUR_PROCESS_NAME = "Rscript.exe"; 

    public WaspmoteSim() { 
     //.... 
     JButton button = new JButton("Destroy Process"); 

     Process process = Runtime.getRuntime().exec(
      System.getenv("cmd.exe /C C:\\Progra~1\\R\\R-3.2.1.\\bin\\" + YOUR_PROCESS_NAME + " + workingDir + "\\Fitter.r"); 
     ProcessHolder.getInstance().getProcesses().put(processName, p); 
     button.addActionListener(this); 
     //.... 
    } 

    //Callback: 
    @Override 
    public void actionPerformed(ActionEvent e) { 
     ProcessHolder.getInstance().getProcesses().get(YOUR_PROCESS_NAME).destroy(); 
    } 

} 

另外一个通知:

你正在做的:

while(true) { 
    Process proc; 
    proc = Runtime.getRuntime().exec("cmd.exe /C C:\\Progra~1\\R\\R-3.2.1.\\bin\\Rscript.exe " + workingDir + "\\Fitter.r"); 
    TimeUnit.SECONDS.sleep(8); 
} 

这将尝试启动一个新的进程每8秒(!)。为了启动一个进程,执行一次,存储它,然后在需要时使用destroy来杀死它,除非您的目标是创建像这样的新进程。

+0

我仍然有执行你的例子有些麻烦; Java指出抽象方法Process需要一个空的列表来实例化,而不是一个String(这是我正在创建的进程名称)。我在做别的事吗? – Martin

+0

回答更新,你这样做,你使用'Runtime.getRuntime()。exec(....)'来创建它。 –

+0

谢谢;我会在一两个小时后回家,然后再尝试。非常感谢您的时间! – Martin

0

首先在你的JFrame定义一个新的布尔变量isClosed添加关闭监听到你的JFrame,并设置一个布尔变量设置为true

addWindowListener(new WindowAdapter() 
{ 
    public void windowClosing(WindowEvent e) 
    { 
     isClosed = true; 
    } 
}); 

现在改变你的while(true)while(!isClosed)

相关问题