자바의 GUI(Graphical User Interface) 기반으로 응용프로그램을 작성해보자.
이제 이벤트 처리를 배움으로써 '작동하는 프로그램'을 생성할 수 있다. 이벤트 기반 프로그래밍은 이벤트의 발생에 의해 프로그램 실행 흐름이 결정되는 방식의 프로그래밍 패러다임이다. 이벤트는 키 입력, 마우스 클릭, 마우스 드래그 등 사용자의 액션이나 센서 같은 외부 장치로부터의 입력, 네트워크를 통한 데이터 수신 등에 의해 발생된다.
이를 위해서는 각 이벤트를 처리하는 이벤트 리스너(Event Listener)를 implement 하고 컴포넌트에 이벤트 처리 객체를 등록해야 하는데, 이벤트가 발생될 때마다 리스너가 실행된다.
java.awt.event.*; 를 추가적으로 import 해줘야 한다.
사실 이건 예시를 직접 해봐야 이해가 쉽다. 예시는 이벤트 리스너의 종류에 따라 하나씩 보겠다.
(1) ActionListener
버튼을 누르는 Action 이벤트를 발생시킬 때 사용한다. ActionListener의 인터페이스는 자바 패키지에 선언되어 있는데, 다음과 같음. 우리는 actionPerformed 메소드를 반드시 오버라이드 해줘야 한다는 것을 알 수 있다.
interface ActionListener {
public void actionPerformed(ActionEvent e); //Action 이벤트 발생 처리
}
"증가"라는 버튼을 누르면 카운터 값이 0부터 순차적으로 증가하는 프로그램을 구현해보자. 이벤트를 처리하는 방법(말이 이상한데... 클래스를 어떻게 구성할 건지에 따라 나눈다)에는 크게 3가지가 있다.
- 프레임 클래스가 이벤트를 처리
- 무명 클래스가 이벤트를 처리
- 클래스를 따로 생성
3번은 비효율적이다. 필자는 2번이 제일 편하지만 시험 공부를 위해서는 1번 2번 둘다 해봐야하기 때문에^^ 일단 프레임 클래스가 이벤트를 처리하는 방식으로 코드를 짜봤다. 프레임 클래스가 이벤트를 처리한다 = implement 해주기
import javax.swing.*;
import java.awt.*;
import java.awt.event.*;
class MyFrame extends JFrame implements ActionListener{
private JButton button;
private JLabel label;
private int counter = 0; //카운터값 초기화
public void actionPerformed(ActionEvent e) {
counter++;
label.setText("현재의 카운터값: " + counter); //레이블에 출력되는 텍스트 counter에 따라 바꿔줌
}
public MyFrame() {
setSize(400, 150);
setLocation(200, 300);
setTitle("이벤트 예제");
setLayout(new FlowLayout());
button = new JButton("증가");
label = new JLabel("현재의 카운터값: " + counter);
button.addActionListener(this);
add(label, "Center");
add(button, "East");
setVisible(true);
}
}
public class FinalTermTest {
public static void main(String[] args) {
MyFrame frame = new MyFrame();
}
}
이번에는 무명 클래스가 이벤트를 처리한다.
import javax.swing.*;
import java.awt.*;
import java.awt.event.*;
class MyFrame extends JFrame {
private JButton button;
private JLabel label;
private int counter = 0;
public MyFrame() {
setSize(400, 150);
setTitle("이벤트 예제");
setLayout(new FlowLayout());
button = new JButton("증가");
label = new JLabel("현재의 가운터값: " + counter);
//무명 클래스 생성
button.addActionListener(new ActionListener() {
public void actionPerformed(ActionEvent e) {
counter++;
label.setText("현재의 카운터값: " + counter);
}
}); //괄호 닫는거 조심해라!!!
add(label, "Center");
add(button, "East");
setVisible(true);
}
}
public class FinalTermTest {
public static void main(String[] args) {
MyFrame frame = new MyFrame();
}
}
버튼을 누를 때 이벤트가 발생하니까 button.addactionPerformed를 해준다.
(2) KeyListener
사용자가 키보드를 이용하여 입력하는 하는 경우에 발생한다.
interface KeyListener {
public void KeyPressed(KeyEvent e);
public void KeyReleased(KeyEvent e);
public void KeyTyped(KeyEvent e);
}
키 이벤트가 발생하려면 키보드 포커스가 맞아야 하는데, 다음 두 코드를 꼭 포함해줘야 한다.
이거 없으면 입력이 안됨(경험담이다)
- panel.requestFocus();
- panel.setFocusable(true);
엔터를 누를 때마다 랜덤 숫자를 보여주는 프로그램을 짜보자.
import javax.swing.*;
import java.awt.*;
import java.awt.event.*;
class MyFrame extends JFrame {
int n1, n2, n3; //발생되는 숫자들
JButton b1, b2, b3;
public MyFrame() {
setSize(300, 150);
setLocation(200, 300);
setTitle("Simple Game Machine");
JPanel p = new JPanel();
b1 = new JButton(""+n1); //강제 형변환 숫자->문자
p.add(b1);
b2 = new JButton(""+n2); //강제 형변환 숫자->문자
p.add(b2);
b3 = new JButton(""+n3); //강제 형변환 숫자->문자
p.add(b3);
p.requestFocus();
p.setFocusable(true);
p.addKeyListener(new KeyListener() {
public void keyPressed(KeyEvent e) {
int keycode = e.getKeyCode();
if(keycode == KeyEvent.VK_ENTER) {
n1 = (int)(Math.random()*10); //0~9사이의 값
n2 = (int)(Math.random()*10); //0~9사이의 값
n3 = (int)(Math.random()*10); //0~9사이의 값
b1.setText(""+n1);
b2.setText(""+n2);
b3.setText(""+n3);
}
}
//나머지 두 메소드는 안쓰니깐 열고닫기만 해서 재정의 끝
@Override
public void keyTyped(KeyEvent e) {}
@Override
public void keyReleased(KeyEvent e) {}
});
add(p);
setVisible(true);
}
}
public class FinalTermTest {
public static void main(String[] args) {
MyFrame frame = new MyFrame();
}
}
방향키를 이용해 자동차를 움직이는 프로그램.
mport javax.swing.*;
import java.awt.*;
import java.awt.event.*;
class MyFrame extends JFrame {
private int x; //x축 좌표
private int y; //y축 좌표
public MyFrame() {
x = 150;
y = 150;
setSize(600, 300);
JButton b = new JButton();
//이미지 작업
ImageIcon icon = new ImageIcon("car.png"); //이미지 경로 써주기
b.setIcon(icon); //버튼에 아이콘 넣기
b.setLocation(x, y);
JPanel p = new JPanel();
p.add(b);
p.requestFocus();
p.setFocusable(true);
//이벤트 처리(무명클래스)
p.addKeyListener(new KeyListener() {
public void keyPressed(KeyEvent e) {
int keycode = e.getKeyCode();
switch(keycode) {
case KeyEvent.VK_UP: y-=10; break;
case KeyEvent.VK_DOWN: y+=10; break;
case KeyEvent.VK_LEFT: x-=10; break;
case KeyEvent.VK_RIGHT: x+=10; break;
}
System.out.println("x="+x+" y="+y);
b.setLocation(x, y); //바뀐거 적용
}
@Override
public void keyTyped(KeyEvent e) {}
@Override
public void keyReleased(KeyEvent e) {}
});
add(p);
setVisible(true);
}
}
public class FinalTermTest {
public static void main(String[] args) {
// TODO Auto-generated method stub
MyFrame frame = new MyFrame();
}
}
'coding > Java' 카테고리의 다른 글
[Java] GUI 응용프로그램(1) - Layout, Panel, Component (0) | 2020.12.21 |
---|---|
[Java] 예외처리와 제네릭 (0) | 2020.12.21 |
[Java] 배열과 상속 연습문제(1~3) (0) | 2020.12.21 |
[Java] 추상클래스, 추상메소드, 인터페이스 (0) | 2020.12.20 |
[Java] 상속과 참조변수, instanceof 연산자 (0) | 2020.12.20 |