所以我的问题是,有时当我在JFrame中按下JButton时,整个框架会冻结,并且只能通过在Eclipse中终止来退出整个框架。所有的JButton都有动作侦听器,我不明白为什么它们有时会导致JFrame冻结,而其他时候却没有。
任何帮助表示赞赏。
这是我的代码:
//objects
static JFrame frame = new JFrame("Flash cards revision");
static JButton beginButton = new JButton();
static JButton continueButton = new JButton("CONTINUE");
static JButton def1Button;
static JButton def2Button;
static JButton def3Button;
static JLabel keywordLabel = new JLabel();
static JLabel title = new JLabel("BIOLOGY FLASH CARDS");
static JLabel completionCount = new JLabel("Number of keywords completed - 0/15");
static JLabel message = new JLabel();
//variables
static Color backgroundColor = new Color(255, 204, 0);
static Color labelColor = new Color(44, 103, 0);
static Color buttonColor = new Color(146, 205, 0);
static Color highlightedButtonColor = new Color(255, 105, 0);
static Font textFont = new Font("Myriad Pro", Font.PLAIN, 15);
static Border border = BorderFactory.createLineBorder(Color.BLACK);
static String[] keywordsArray = new String[15];
static String[] definitionsArray = new String[15];
static boolean[] beenUsed = new boolean[15];
static int rDefNum;
static int rButtonNum;
static int rWDefNum;
static int numTimesCorrect = 0;
static int numComplete = 0;
static int originalY = 0;
static String keyword;
static String definition;
static String wDef1;
static String wDef2;
public static void main(String[] args) throws IOException
{
prepareFrame();
occupyKeywordsArray();
occupyDefinitionsArray();
prepareMenu();
beginButton.addActionListener(new ActionListener()
{
public void actionPerformed(ActionEvent e)
{
beginButton.removeActionListener(beginButton.getActionListeners()[0]);
prepareTest();
getNewKeyword();
getWrongDefinitions();
prepareNewDefinition();
addActionListeners();
}
});
}
static void prepareFrame()
{
frame.setVisible(true);
frame.setResizable(false);
frame.setLayout(null);
frame.setSize(800,600);
frame.setLocation(500,200);
frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
frame.getContentPane().setBackground(backgroundColor);
frame.setIconImage(Toolkit.getDefaultToolkit().getImage("biologyIcon.png"));
}
static void prepareMenu()
{
beginButton = new JButton("BEGIN TEST");
frame.add(title);
frame.add(beginButton);
title.setOpaque(true);
title.setSize(650,100);
title.setLocation(75,60);
title.setHorizontalAlignment(SwingConstants.CENTER);
title.setBackground(labelColor);
title.setForeground(buttonColor);
title.setFont(textFont);
title.setFont(title.getFont().deriveFont(60.0f));
title.setBorder(border);
beginButton.setBackground(buttonColor);
beginButton.setLocation(240,220);
beginButton.setForeground(labelColor);
beginButton.setFont(textFont);
beginButton.setFont(beginButton.getFont().deriveFont(55.0f));
beginButton.setSize(320,100);
beginButton.setFocusable(false);
beginButton.setBorder(border);
}
static void prepareTest()
{
def1Button = new JButton();
def2Button = new JButton();
def3Button = new JButton();
continueButton = new JButton("CONTINUE");
frame.remove(title);
frame.remove(beginButton);
frame.add(keywordLabel);
frame.add(message);
frame.add(completionCount);
frame.add(def1Button);
frame.add(def2Button);
frame.add(def3Button);
frame.add(continueButton);
frame.repaint();
frame.revalidate();
keywordLabel.setOpaque(true);
keywordLabel.setHorizontalAlignment(SwingConstants.CENTER);
keywordLabel.setBackground(labelColor);
keywordLabel.setForeground(buttonColor);
keywordLabel.setFont(textFont);
keywordLabel.setFont(keywordLabel.getFont().deriveFont(60.0f));
keywordLabel.setBorder(border);
message.setOpaque(true);
message.setText("Try to match the keyword to the correct definition");
message.setSize(450,35);
message.setLocation(175,370);
message.setHorizontalAlignment(SwingConstants.CENTER);
message.setBackground(labelColor);
message.setForeground(buttonColor);
message.setFont(textFont);
message.setFont(keywordLabel.getFont().deriveFont(20.0f));
message.setBorder(border);
completionCount.setOpaque(true);
completionCount.setSize(340,35);
completionCount.setLocation(230,20);
completionCount.setHorizontalAlignment(SwingConstants.CENTER);
completionCount.setBackground(labelColor);
completionCount.setForeground(buttonColor);
completionCount.setFont(textFont);
completionCount.setFont(keywordLabel.getFont().deriveFont(20.0f));
completionCount.setBorder(border);
continueButton.setVisible(false);
continueButton.setSize(300,100);
continueButton.setLocation(250,370);
continueButton.setBackground(buttonColor);
continueButton.setForeground(labelColor);
continueButton.setFont(textFont);
continueButton.setFont(def1Button.getFont().deriveFont(50.0f));
continueButton.setFocusable(false);
continueButton.setBorder(border);
def1Button.setBackground(buttonColor);
def1Button.setForeground(labelColor);
def1Button.setFont(textFont);
def1Button.setFont(def1Button.getFont().deriveFont(20.0f));
def1Button.setFocusable(false);
def1Button.setBorder(border);
def2Button.setBackground(buttonColor);
def2Button.setForeground(labelColor);
def2Button.setFont(textFont);
def2Button.setFont(def2Button.getFont().deriveFont(20.0f));
def2Button.setFocusable(false);
def2Button.setBorder(border);
def3Button.setBackground(buttonColor);
def3Button.setForeground(labelColor);
def3Button.setFont(textFont);
def3Button.setFont(def3Button.getFont().deriveFont(20.0f));
def3Button.setFocusable(false);
def3Button.setBorder(border);
}
static void prepareNewDefinition()
{
rButtonNum = r.nextInt(3)+1;//Chooses a random number - 1, 2 or 3
switch(rButtonNum)
{
case 1:
def1Button.setText(definition);
def2Button.setText(wDef1);
def3Button.setText(wDef2);
break;
case 2:
def1Button.setText(wDef1);
def2Button.setText(definition);
def3Button.setText(wDef2);
break;
case 3:
def1Button.setText(wDef1);
def2Button.setText(wDef2);
def3Button.setText(definition);
break;
}
int b1Width = def1Button.getFontMetrics(def1Button.getFont()).stringWidth(def1Button.getText()) + 45;
int b2Width = def2Button.getFontMetrics(def2Button.getFont()).stringWidth(def2Button.getText()) + 45;
int b3Width = def3Button.getFontMetrics(def3Button.getFont()).stringWidth(def3Button.getText()) + 45;
keywordLabel.setText(keyword);
keywordLabel.setSize(keyword.length()*40,100);
keywordLabel.setLocation(400-((keyword.length()*40)/2),80);
def1Button.setSize(b1Width,30);
def1Button.setLocation(400 - def1Button.getWidth() / 2,210);
def2Button.setSize(b2Width,30);
def2Button.setLocation(400 - def2Button.getWidth() / 2,260);
def3Button.setSize(b3Width,30);
def3Button.setLocation(400- def3Button.getWidth() / 2,310);
optionsListener = new ActionListener()
{
public void actionPerformed(ActionEvent e)
{
def1Button.removeActionListener(optionsListener);
def2Button.removeActionListener(optionsListener);
def3Button.removeActionListener(optionsListener);
if(e.getActionCommand().equals(definition))
{
correct();
}
else
{
incorrect();
}
}
};
}
static void correct()
{
numTimesCorrect++;
if(numTimesCorrect == 1)
{
message.setText("Correct! Match this correctly once more to complete this keyword");
message.setSize(550,35);
message.setLocation(125,message.getY());
}
else
{
numComplete++;
completionCount.setText("Number of keywords completed - "+numComplete+"/15");
message.setText("Correct! Keyword complete!");
message.setSize(250,35);
message.setLocation(275,message.getY());
}
moveMessageDown();
continueButton.addActionListener(new ActionListener()
{
public void actionPerformed(ActionEvent e)
{
System.out.println(continueButton.getActionListeners()[0]);
continueButton.setVisible(false);
continueButton.removeActionListener(continueButton.getActionListeners()[0]);
if(numTimesCorrect == 1)
{
message.setSize(510,35);
message.setLocation(145,message.getY());
message.setText("Match this correctly once more to complete this keyword");
}
if(numTimesCorrect == 2)
{
message.setSize(450,35);
message.setLocation(175,message.getY());
message.setText("Try to match the keyword to the correct definition");
getNewKeyword();
numTimesCorrect = 0;
}
getWrongDefinitions();
prepareNewDefinition();
addActionListeners();
moveMessageUp();
}
});
}
static void incorrect()
{
numTimesCorrect = 0;
message.setText("Incorrect! The correct definition is now highlighted");
message.setForeground(highlightedButtonColor);
if(def1Button.getText().equals(definition))
{
def1Button.setBackground(highlightedButtonColor);
}
if(def2Button.getText().equals(definition))
{
def2Button.setBackground(highlightedButtonColor);
}
if(def3Button.getText().equals(definition))
{
def3Button.setBackground(highlightedButtonColor);
}
message.setSize(450,35);
message.setLocation(175,message.getY());
moveMessageDown();
continueButton.addActionListener(new ActionListener()
{
public void actionPerformed(ActionEvent e)
{
continueButton.setVisible(false);
continueButton.removeActionListener(continueButton.getActionListeners()[0]);
message.setForeground(buttonColor);
getWrongDefinitions();
prepareNewDefinition();
def1Button.setBackground(buttonColor);
def2Button.setBackground(buttonColor);
def3Button.setBackground(buttonColor);
message.setLocation(175,500);
message.setText("Try to match the keyword to the correct definition");
addActionListeners();
moveMessageUp();
}
});
}
static void getNewKeyword()
{
boolean validDef = false;
while(validDef == false)
{
rDefNum = r.nextInt(15);
if(beenUsed[rDefNum] == false)
{
validDef = true;
beenUsed[rDefNum] = true;
keyword = keywordsArray[rDefNum];
definition = definitionsArray[rDefNum];
}
}
}
static void getWrongDefinitions()
{
rWDefNum = r.nextInt(15);
wDef1 = definitionsArray[rWDefNum];
rWDefNum = r.nextInt(15);
wDef2 = definitionsArray[rWDefNum];
while(wDef1.equals(wDef2) || definition.equals(wDef1) || definition.equals(wDef2))
{
rWDefNum = r.nextInt(15);
wDef1 = definitionsArray[rWDefNum];
wDef2 = definitionsArray[rWDefNum];
}
}
static void moveMessageDown()
{
moveUpThread.stop();
originalY = message.getY();
moveDownThread = new Thread()
{
public void run()
{
try
{
Thread.sleep(200);
}catch (InterruptedException e){}
for(int loop = 0; loop <= 500-originalY; loop++)
{
try
{
Thread.sleep(6);
} catch (InterruptedException e){}
message.setLocation(message.getX(),originalY+loop);
}
continueButton.setVisible(true);
}
};
moveDownThread.start();
}
static void moveMessageUp()
{
originalY = message.getY();
moveUpThread = new Thread()
{
public void run()
{
try
{
Thread.sleep(200);
}catch (InterruptedException e){}
for(int loop = 0; loop <= 630 - originalY; loop++)
{
try
{
Thread.sleep(6);
} catch (InterruptedException e){}
message.setLocation(message.getX(),500-loop);
}
}
};
moveUpThread.start();
}
static void addActionListeners()
{
def1Button.addActionListener(optionsListener);
def2Button.addActionListener(optionsListener);
def3Button.addActionListener(optionsListener);
}
static void occupyKeywordsArray() throws IOException
{
BufferedReader keywordsReader = new BufferedReader(new FileReader("keywords.txt"));
for(int keywordsLoop = 0; keywordsLoop <= 14; keywordsLoop++)
{
keywordsArray[keywordsLoop] = keywordsReader.readLine();
keywordsReader.readLine();
}
keywordsReader.close();
}
static void occupyDefinitionsArray() throws IOException
{
BufferedReader definitionsReader = new BufferedReader(new FileReader("keywords.txt"));
for(int definitionsLoop = 0; definitionsLoop <= 14; definitionsLoop++)
{
definitionsReader.readLine();
definitionsArray[definitionsLoop] = definitionsReader.readLine();
}
definitionsReader.close();
}
}
最佳答案
您必须在侦听器内部创建一个线程。像这样:
button.addActionListener(new ActionListener() {
public void actionPerformed(ActionEvent arg0) {
Thread hilo = new Thread(new Runnable() {
@Override
public void run() {
//here your code
}
});
hilo.start();
}
});
如果JFrame不冻结,仅是因为执行速度快并且没有时间冻结,但是如果执行需要超过几秒钟的时间,JFrame就会冻结。