Java Swing线程问题

时间:2011-04-28 19:37:17

标签: java multithreading swing concurrency

我遇到与在swing中使用线程有关的问题。 我将首先解释问题,然后我将发布我的代码。

问题如下。我有两个类,一个包含业务逻辑,另一个包含用户界面。根据接口中的用户操作,我调用包含业务逻辑的类中的方法。 但是,我的下一个任务是让用户点击一个UI元素,然后基于该点击我将一个新的鼠标监听器附加到其他UI元素,我等待用户点击其他UI元素,之后我会喜欢更改初始点击的UI元素。 但是,我的应用程序在单击其他UI元素后阻止。 在示例代码中,初始UI元素和其他UI元素都是相同的,但通常它们不会是。

示例类:

=============================================== =====================

package threadtests;

import java.awt.Color;

public class LogicClass extends Thread {

    FrameClass fc;
    SelectSynchronizerObject mysso;

    public void run() {
        while(true);
    }

    public void startThisFromFrame() {
        MyMouseListener2 m2 = new MyMouseListener2();
        m2.initialize(fc.jp, mysso);
        fc.jp.addMouseListener(m2);
        mysso.getSelected();
        fc.jp.setBackground(new Color(100,100,100));
        fc.jp.removeMouseListener(m2);
    }

    public static void main(String args[]) {
        SelectSynchronizerObject sso = new SelectSynchronizerObject();
        LogicClass lc = new LogicClass();
        lc.mysso = sso;
        lc.start();
        FrameClass fc = new FrameClass();
        fc.lc = lc;
        lc.fc = fc;
        fc.mysso = sso;
        fc.initialize(lc);
    }

}

=============================================== =====================

package threadtests;

import java.awt.Color;

import javax.swing.JFrame;
import javax.swing.JPanel;

public class FrameClass extends JFrame {

    LogicClass lc;
    SelectSynchronizerObject mysso;
    JPanel jp = new JPanel();

    public void initialize(LogicClass arg) {
        lc = arg;
        setSize(100,100);
        MyMouseListener m = new MyMouseListener(); 
        jp.addMouseListener(m);
        m.initialize(jp, lc);
        jp.setBackground(new Color(255,200,200));
        add(jp);

        setVisible(true);
    }

}

=============================================== =====================

package threadtests;

public class SelectSynchronizerObject {

    public int selectednumer = 0;
    public boolean numberset = false;

    public synchronized void panelSelected(int a) {
        selectednumer = a;
        notify();
    }

    public synchronized int getSelected() {
        try {
            wait();
        } catch (InterruptedException e) {
            System.out.println(e);
        }
        return selectednumer;
    }

}

=============================================== =====================

package threadtests;
import java.awt.Color;
import java.awt.event.MouseEvent;
import java.awt.event.MouseListener;
import javax.swing.JPanel;

public class MyMouseListener implements MouseListener  {

    JPanel mypanel;
    LogicClass lc;
    public void initialize(JPanel arg, LogicClass arg2) {
        mypanel = arg;
        lc = arg2;
    }
    public void mouseClicked(MouseEvent e) {
        lc.startThisFromFrame();
    }
    public void mousePressed(MouseEvent e) {

    }
    public void mouseReleased(MouseEvent e) {
    }
    public void mouseEntered(MouseEvent e) {
        mypanel.setBackground(new Color(200,255,200));
    }
    public void mouseExited(MouseEvent e) {
        mypanel.setBackground(new Color(255,200,200));
    }

}

=============================================== =====================

package threadtests;
import java.awt.event.MouseEvent;
import java.awt.event.MouseListener;
import javax.swing.JPanel;

public class MyMouseListener2 implements MouseListener  {

    JPanel mypanel;
    SelectSynchronizerObject sso;
    public void initialize(JPanel arg, SelectSynchronizerObject arg1) {
        mypanel = arg;
        sso = arg1;
    }
    public void mouseClicked(MouseEvent e) {
        sso.panelSelected(1);
    }
    public void mousePressed(MouseEvent e) {
    }
    public void mouseReleased(MouseEvent e) {
    }
    public void mouseEntered(MouseEvent e) {
    }
    public void mouseExited(MouseEvent e) {
    }

}

==========================

感谢您的帮助。

1 个答案:

答案 0 :(得分:2)

第一:

public void run() {
    while(true);
}

只需要CPU从其他东西中取出任何东西。

然后:

wait();

在主线程中被调用,因此阻塞。

实际上你不需要invokelater,swingworker或其他任何东西,你只需要一点GUI事件编程。在开始时将事件侦听器连接在一起,然后您将获得没有任何线程的所选面板。

通常虽然线程对于很多程序是必需的,但是你不需要在不需要的地方强制它们,因为它们给编程增加了很多复杂性。