0

因此,我正在尝试为从网络检索结果的搜索 JTextField 编写代码(有点像 Google 的精美搜索提示)。唯一的问题是……可能是我缺乏编程经验。更具体地说,我将它设置为每当用户点击一个键时,它都会通过 HttpURLConnection 发送带有 JTextField 输入的请求,并检索结果然后更新。但是每当 HttpURLConnection 运行时,它会在执行它的操作时冻结程序几秒钟,如果我不介意其他任何事情,这主要是禁止在搜索字段中输入更多字符。我考虑过使用单独的线程,但我不确定如何正确中断线程并让它重新开始使用新数据,同时让其他一切都在等待它但仍接受新数据。我考虑过使用

thread.stop();

帮助管理这个问题,但从我读过的内容来看,这似乎是禁忌(对吗?)。无论如何,这几乎是我正在使用的:

public class SearchField extends JTextField implements KeyListener {
    public SearchField() {
        addkeyListener(this);
    }

    public void updateData(ArrayList<String results) {
        /*Pass the data off the the GUI*/
    {

    @Override
    public void keyTyped(KeyEvent e) {
        SearchQuery query = new SearchQuery(this.getText());
        updateData(query.getResults());
    }
}


public class SearchQuery {

    ArrayList<String> results = new ArrayList<String>();

    public SearchQuery(String search) {
        String search_path = "http://www.whatever.com/" + search;
        URL url = new URL(search_path);
        conn = (HttpURLConnection) url.openConnection();
        conn.addRequestProperty("User-Agent", "Mozilla/4.76"); 
        in = new BufferedReader(
                                new InputStreamReader(conn.getInputStream()));
        StringBuffer buf = new StringBuffer();
        int i;
        while((i = in.read()) != -1) {
            buf.append((char) i);
        }
        String data = buf.toString();

        parse(data);
    }

    public void parse(String data) {
        /*Parse a bunch of JSON, return the results in an array*/
        results.add(data);
    }

    public ArrayList<String> getResults() {
        return results;
    }
}

我只是不知道如何同步接收连续输入,同时为每个击键获得新结果,并在下一次击键无效时解除未完成的连接及其各自的数据处理。

4

1 回答 1

0

您正在响应用户事件的同一线程中进行下载。您需要在另一个线程中进行下载,可能是通过SearchQuery扩展Thread并在run方法中进行查询。当需要更新文本字段时,您可以使用SwingUtilities.invokeLater来更新文本字段。这是一个例子:

public class SearchQuery extends Thread {
    private SearchField f;
    public SearchQuery(JTextField f) {
        this.f = f;
    }

    public void run() {
        // do the query here
        SwingUtilities.invokeLater(new Runnable() {
            public void run() {
                f.updateData(results);
            }
        });
    }
}

然后换行:

SearchQuery query = new SearchQuery(this.getText());

对此:

SearchQuery query = new SearchQuery(this);
于 2013-07-30T07:06:55.087 回答