2015-07-03 51 views
0

我有一个标签不在GUI的同一实例中更新。 如果我单击应该更新jLabel(代码块中的“testLabel”)的值的jButton,我必须再次运行java程序才能看到所做的更改。我怎样才能让它出现在同一个实例中的按钮点击? 我知道关于invokelater,我一直在玩它试图让它实时更新,但没有运气。我一直坚持这一段时间,所以任何帮助表示赞赏。 通过下面列出的代码块,我仍然需要运行GUI的新实例来获取更新的值。标签不在GUI的相同实例中更新

相关代码:

public static void main(String[] args) { 
    EventQueue.invokeLater(new Runnable() { 
     public void run() { 
      try { 
       MISControlPanel window = new MISControlPanel(); 
       window.frame.setVisible(true); 
       // testLabel.setText(CN); 
      } catch (Exception e) { 
       e.printStackTrace(); 
      } 
     } 
    }); 
} 

JButton searchComputerButton = new JButton("Search"); 
    searchComputerButton.addActionListener(new ActionListener() { 
     public void actionPerformed(ActionEvent e) { 

      String line; 
      BufferedWriter bw = null; 
      BufferedWriter writer = null; 
      try { 
       writer = new BufferedWriter(new FileWriter(tempFile)); 
      } catch (IOException e1) { 
       // TODO Auto-generated catch block 
       e1.printStackTrace(); 
      } 
      // String lineToRemove = "OU=Workstations"; 

      String s = null; 

      Process p = null; 
      /* 
      * try { // p = Runtime.getRuntime().exec(
      * "cmd /c start c:\\computerQuery.bat computerName"); } catch 
      * (IOException e1) { // TODO Auto-generated catch block 
      * e1.printStackTrace(); } 
      */ 
      try { 

       p = Runtime.getRuntime().exec("c:\\computerQuery.bat"); 

      } catch (IOException e1) { 

       // TODO Auto-generated catch block 

       e1.printStackTrace(); 

      } 
      StringBuffer sbuffer = new StringBuffer(); 
      BufferedReader in = new BufferedReader(new InputStreamReader(p 
        .getInputStream())); 

      try { 

       while ((line = in.readLine()) != null) { 

        System.out.println(line); 

        // textArea.append(line); 

        String dn = "CN=FDCD111304,OU=Workstations,OU=SIM,OU=Accounts,DC=FL,DC=NET"; 
        LdapName ldapName = new LdapName(dn); 
        String commonName = (String) ldapName.getRdn(
          ldapName.size() - 1).getValue(); 

       } 
       ComputerQuery.sendParam(); 

      } catch (IOException e1) { 

       // TODO Auto-generated catch block 

       e1.printStackTrace(); 

      } catch (InvalidNameException e1) { 
       // TODO Auto-generated catch block 
       e1.printStackTrace(); 
      } finally 

      { 
       try { 
        fw.close(); 

       } 

       catch (IOException e1) { 
        // TODO Auto-generated catch block 
        e1.printStackTrace(); 
       } 
      } 

      try { 

       in.close(); 

      } catch (IOException e1) { 

       // TODO Auto-generated catch block 

       e1.printStackTrace(); 

      } 

      ComputerQuery.sendParam(); 

     } 
    }); 

    try (BufferedReader br = new BufferedReader(new FileReader(
      "resultofbatch.txt"))) { 

     final Pattern PATTERN = Pattern.compile("CN=([^,]+).*"); 
     try { 
      while ((sCurrentLine = br.readLine()) != null) { 

       String[] tokens = PATTERN.split(","); // This will return 
                 // you a array, 
                 // containing the 
                 // string array 
                 // splitted by what 
                 // you write inside 
                 // it. 
       // should be in your case the split, since they are 
       // seperated by "," 
       // System.out.println(sCurrentLine); 
       CN = sCurrentLine.split("CN=", -1)[1].split(",", -1)[0]; 

       System.out.println(CN); 
       testLabel.setText(CN); 
      } 

全类代码 http://pastebin.com/havyqMxP

电脑查询类(小类) http://pastebin.com/Q89BCjya

+0

您好user6680 ...我不知道您打算执行此操作的执行流程的哪一部分,您正在使用LDAP,我看到..这意味着您正在连接到LDAP服务器,并且可能执行长时间运行的任务... 你是否试图在组件的任何类型的监听器(因此在事件调度线程)的回调中执行此操作?或者你正在另一个线程上执行此操作? Swing.invokelater将无助于此...我建议开始阅读SwingWorker,并在UI上分割表示的操作(处理swing组件的代码) – Victor

+0

试试这个教程... https://docs.oracle.com/javase/tutorial/uiswing/concurrency /simple.html ... – Victor

+0

我认为我需要它做的是在不同的线程上运行,以便在GUI的同一实例内更新值。我看着你提供的教程链接,但我很困惑。它使用了在done方法中加载图像的示例,但我不确定如何将其实现到我的代码中。我一直试图让这个工作一个多星期。你有没有可能向我展示我想要完成的工作示例? – user6680

回答

2

正如所承诺的......这里是一个获取UR的简单示例L内容使用挥杆工作人员从更新挥杆组件的任务中解除获取内容的任务(长时间运行的任务)。这将显示你应该如何处理这个问题的一个例子...

import java.awt.BorderLayout; 
import java.awt.Dimension; 
import java.awt.event.ActionEvent; 
import java.awt.event.ActionListener; 
import java.io.BufferedReader; 
import java.io.InputStreamReader; 
import java.net.URL; 
import java.util.List; 
import java.util.logging.Level; 
import java.util.logging.Logger; 

import javax.swing.JButton; 
import javax.swing.JFrame; 
import javax.swing.JLabel; 
import javax.swing.SwingWorker; 

/* FrameDemo.java requires no other files. */ 
public class MainWindow extends JFrame { 
    private static final Logger LOOGER = Logger.getLogger(MainWindow.class.getName()); 

    /** 
    * Create the GUI and show it. For thread safety, 
    * this method should be invoked from the 
    * event-dispatching thread. 
    */ 

    private JLabel statusLabel = new JLabel("Status"); 
    private JButton actionButton = new JButton("Push me"); 

    public MainWindow() { 
    super("FrameDemo"); 
    setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE); 

    statusLabel = new JLabel("Status"); 
    actionButton = new JButton("Push me"); 

    statusLabel.setPreferredSize(new Dimension(400, 50)); 
    actionButton.setPreferredSize(new Dimension(100, 50)); 
    getContentPane().setLayout(new BorderLayout()); 
    getContentPane().add(statusLabel, BorderLayout.NORTH); 
    getContentPane().add(actionButton, BorderLayout.CENTER); 

    actionButton.addActionListener(new ActionListener() { 
     @Override 
     public void actionPerformed(ActionEvent e) { 
     // THIS METHOD IS INVOKED WITHIN THE EVENT DISPATCH THREAD!!.. SO IS CRUCIAL TO NOT PERFORM 
     // HERE LONG TIME RUNNING TASKS... 
     actionButton.setEnabled(false); // let's disable this button, in order to avoid invoking 
     // multiple times the same task and messing up the entire app... 
     UrlFechterSwingWorker urlFechterSwingWorker = new UrlFechterSwingWorker(); 
     urlFechterSwingWorker.execute(); 
     } 
    }); 
    } 

    public void display() { 
    pack(); 
    setVisible(true); 
    } 

    private class UrlFechterSwingWorker extends SwingWorker<String, String> { 
    @Override 
    public String doInBackground() { // this method is executed under a worker thread 

     BufferedReader in; 
     StringBuilder sb = new StringBuilder(); 
     try { 
     URL url = new URL("http://www.stackoverflow.com"); 
     in = new BufferedReader(new InputStreamReader(url.openStream())); 
     String line = in.readLine(); 
     while (line != null) { 
      sb.append(line); 
      publish(line); // publish partial results.... 
      line = in.readLine(); 
     } 
     in.close(); 
     } catch (Exception e) { 
     LOOGER.log(Level.SEVERE, "", e); 
     } 
     return sb.toString(); 
    } 

    @Override 
    protected void process(List<String> readedLines) { // this method in the Event dispatch Thread 
     // do what you want to do with the readedLines.... 
     statusLabel.setText("The doInBackground read... " + readedLines.size() + " lines"); 
    } 

    @Override 
    public void done() { // this method in the Event dispatch Thread 
     // do what you want when the process finish 
     actionButton.setEnabled(true); // well.. at least i would like to enable the button again... 
    } 
    } 

    public static void main(String[] args) { 
    MainWindow mainWindow = new MainWindow(); 
    mainWindow.display(); 
    } 
} 

这里有更多的提示:

  1. 在了解(或多或少)事情是如何在上面的例子中工作..你将不得不实施一个适当的doInBackground方法执行所有的LDAP的东西,为此,你将不得不让你的想法设想一种方式告知最终用户的进展...我的意思是,看我的例子,是关于进展的进展非常糟糕......我所说的所有事情是,我们从给定的网址读取“多行”。你应该考虑什么是最好的方式来告知你的任务的进展情况..除了对底层域模型的理解之外,没有模板。

  2. 请记住,摆动工人有两种方式来告知进度。

    • 一种是使用publishprocess方法。 (像上面的例子)
    • 其他的是要修改方法doInBackground内部的内部属性(进度和状态),并将PropertyChangeListener附加到挥杆工。这的PropertyChangeListener对象有其签名是public void propertyChange(PropertyChangeEvent evt)的方法(稍微复杂一点,在我的观点。)
  3. 耐心和好运气!

+1

actionButton.setEnabled(false); == JButton.setMultiClickThreshhold或Swing Action - AbstractAction.setEnabled(false) – mKorbel

+0

加上一个用于相当正确的描述,并且不要将镜头修改为黑暗(SwingWorker),也不会将其单个单独的侦听器删除此建议 – mKorbel

+0

感谢您的建议@mKorbel,我没有使用JButton.setMultiClickThreshhold ......感谢分享。关于“单独的听众”...你的意思是'PropertyChangeListener'?....请自由编辑我的文章并实施你的建议 – Victor