1. 程式人生 > >死磕Java系列之GUI 元件和事件監聽

死磕Java系列之GUI 元件和事件監聽

當我們搭建好圖形介面窗體的時候,需要向窗體中加入各種元件,便於使用者操作,使用者在窗體中都會有哪些操作呢?窗體是程式與使用者可互動的介面,比如說登入介面,使用者可以輸入姓名和密碼,點選登入按鈕,登入到另一個介面,在下一個介面有更多的操作,比如說有多個選擇組成的選單,需要輸入文字的文字框,用來標記的標籤等。綜上,一個窗體中有多個元件,元件有文字元件,按鈕元件,標籤元件和列表元件。當然了,一個窗體中有元件是不夠的,還需要在窗體中加入監聽事件,監聽事件也就是說當用戶點選相應的元件的時候,程式作出的響應反應,比如說登入介面點選登入按鈕以後,監聽器事件就是檢測密碼是否正確,然後選擇跳入到另一個介面,這樣的話,如何在窗體中加入元件呢?監聽器事件有哪些型別,如何定義呢?

(一)元件

在窗體中加入各種元件便於使用者操作,元件有文字元件,按鈕元件,標籤元件和列表元件。
在這裡插入圖片描述
具體的元件設計方式可見Java Swing 圖形介面開發(目錄)

1. 文字元件

  1. JTextField 是一個輕量級元件,它允許編輯單行文字。
    JavaSwing_2.6: JTextField(文字框)
    在這裡插入圖片描述在這裡插入圖片描述

  2. JPasswordField 是一個輕量級元件,允許編輯單行文字,其檢視指示鍵入內容,但不顯示原始字元,顯示為密碼框。
    JavaSwing_2.7: JPasswordField(密碼框)
    在這裡插入圖片描述

  3. JTextArea 是一個顯示純文字的多行區域。
    JavaSwing_2.8: JTextArea(文字區域)


    在這裡插入圖片描述
    示例程式碼:

package VideoTest;
import javax.swing.JFrame;
import javax.swing.JPanel;
import javax.swing.JPasswordField;
import javax.swing.JTextArea;
import javax.swing.JTextField;

public class TEST02 extends JFrame
{
   public TEST02()
   {
      super("SwingDemo");//定義名稱
      JPanel root = new JPanel();//例項化容器
      root.add(new JTextField("我是JTextField"));//加入文字框
      root.add(new JPasswordField("我是JPasswordField"));//加入密碼框
      root.add(new JTextArea("我是JTextArea"));//加入文字域
      add(root);
      //定義窗體相關引數
      setSize(400, 300);
      setDefaultCloseOperation(EXIT_ON_CLOSE);
      setVisible(true);
   }

   public static void main(String[] args)
   {
      new TEST02();
   }
}

執行結果:
在這裡插入圖片描述

2. 按鈕元件

-單選按鈕(JRadioButton), 實現一個單選按鈕,此按鈕項可被選擇或取消選擇,並可為使用者顯示其狀態。與 ButtonGroup 物件配合使用可建立一組按鈕,一次只能選擇其中的一個按鈕。
JavaSwing_2.3: JRadioButton(單選按鈕)在這裡插入圖片描述

3. 標籤元件

  • 標籤 ,使用JComponent的子類JLabel類建立標籤,標籤為使用者提供資訊提示。
    JavaSwing_2.1: JLabel(標籤)
    4. 列表元件
    視窗中的選單條、選單、選單項是我們所熟悉的元件,選單放在選單條裡,選單項放在選單中選單條 。選單條,選單,選單項的關係是:選單項是選單的具體名稱,選單加入到選單條中,選單條加入容器中,選單條是將選單放入窗體的方法,具體而言,飯店的選單上,選單條就是大飯店的選單本,選單就是飯店選單的選單頁, 選單項就是具體的某一個菜的名稱。
  • JMenubar 是一個選單條,JFrame類用一個把選單條放到視窗的方法:

setJMenuBar( JMenuBar bar);
該方法將選單條新增到視窗的頂端,需要注意的是,只能向視窗新增一個選單條。
JavaSwing_4.5: JMenuBar(選單欄)

  • 選單 JMenu負責建立選單。
  • 選單項 JMenuItem負責建立選單項

JMenuItem(String text, Icon icon)

package VideoTest;

import java.awt.event.InputEvent;
import java.awt.event.KeyEvent;
import javax.swing.JFrame;
import javax.swing.JMenu;
import javax.swing.JMenuBar;
import javax.swing.JMenuItem;
import javax.swing.KeyStroke;
import javax.swing.WindowConstants;

/**
 * 選單條,選單,選單項的關係是:選單項是選單的具體名稱,選單加入到選單條中,選單條加入容器中,
 * 選單條是將選單放入窗體的方法,具體而言,飯店的選單上,選單條就是大飯店的選單本,選單就是飯店選單的選單頁
 * 選單項就是具體的某一個菜的名稱。
 */
public class TEST02 extends JFrame {
    JMenuBar menubar;//例項化 選單條
    JMenu menu, subMenu;//例項化選單
    JMenuItem item1, item2;//例項化選單項
    public static void main(String[] args) {
        TEST02 win = new TEST02("帶視窗的選單", 20, 30, 400, 500);
    }
    public TEST02() {
    }
    //定義方法設定窗體的引數,輸入窗體的大小,名稱,和位置
    public TEST02(String s, int x, int y, int w, int h) {
        init(s);
        setLocation(x, y);
        setSize(w, h);
        setVisible(true);
        setDefaultCloseOperation(WindowConstants.DISPOSE_ON_CLOSE);
    }
   
    void init(String s) {
        setTitle(s);
        menubar = new JMenuBar();
        menu = new JMenu("選單"); // JMnud的例項就是一個選單
        /**
         * 一級選單項
         */
        subMenu = new JMenu("軟體專案"); // 子選單
        item1 = new JMenuItem("Java話題"); // 建立選單項
       
        //使用JMenuItem的構造方法設定圖示
        item2 = new JMenuItem("動畫話題" );
        item1.setAccelerator(KeyStroke.getKeyStroke('A'));
        item2.setAccelerator(KeyStroke.getKeyStroke(KeyEvent.VK_S, InputEvent.CTRL_MASK));
       
        //選單項加入選單中。
        menu.add(item1);
        menu.addSeparator();
        menu.add(item2);
        menu.add(subMenu);
        /**
         * 新增二級選單項
         */
        subMenu.add(new JMenuItem("汽車銷售系統" ));
        subMenu.add(new JMenuItem("農場資訊系統" ));
        menubar.add(menu); // 選單條中加入選單
        setJMenuBar(menubar); // 新增一個選單條

    }
}
 

執行結果:
在這裡插入圖片描述

常見元件組合的例項:


import java.awt.FlowLayout;

import javax.swing.ButtonGroup;
import javax.swing.JButton;
import javax.swing.JCheckBox;
import javax.swing.JComboBox;
import javax.swing.JFrame;
import javax.swing.JLabel;
import javax.swing.JPasswordField;
import javax.swing.JRadioButton;
import javax.swing.JScrollPane;
import javax.swing.JTextArea;
import javax.swing.JTextField;

/*
 * 這個裡最包含了JavaGUI中的多個元件,
 */
public class TEST02 extends JFrame {

    JTextField text;//例項化文字
    JButton button;//例項化按鈕
    JCheckBox checkBox1, checkBox2, checkBox3;
    JRadioButton radio1, radio2;//例項化單選按鈕
    ButtonGroup group;//例項化按鈕元件
    JComboBox<Object> comBox;
    JTextArea area;//定義文字域
    JPasswordField password;//定義密碼框
    public static void main(String[] args) {
    	TEST02 win = new   TEST02();
        win.setBounds(100, 100, 520, 510);
        win.setTitle("常用元件");
    }
 
    public TEST02() {
        init();
        setVisible(true);
        setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
    }

    void init() {
        setLayout(new FlowLayout()); // 設定佈局
        
        //定義文字框及其相關引數
        add(new JLabel("文字框:"));
        text = new JTextField(10);
        add(text);
     
        //定義按鈕及其相關引數
        add(new JLabel("按鈕:"));
        button = new JButton("確認");
        add(button);
     
        //定義密碼框及其相關引數
        add(new JLabel("密碼框:"));
        password = new JPasswordField(10);
        add(password);
   
        //定義按鈕標籤及其相關引數
        add(new JLabel("按鈕:"));
        button = new JButton("確認");
        add(button);
     
        //定義 選擇框及其相關引數
        add(new JLabel("選擇框:"));
        checkBox1 = new JCheckBox("喜歡音樂");
        checkBox2 = new JCheckBox("喜歡旅遊");
        checkBox3 = new JCheckBox("喜歡籃球");
        add(checkBox1);
        add(checkBox2);
        add(checkBox3);

      //定義單選按鈕及其相關引數
        add(new JLabel("單選按鈕:"));
        group = new ButtonGroup();
        radio1 = new JRadioButton("男");
        radio2 = new JRadioButton("女");
        group.add(radio1);
        group.add(radio2);
        add(radio1);
        add(radio2);

      //定義 下拉列表及其相關引數
        add(new JLabel("下拉列表:"));
        comBox = new JComboBox<>();
        comBox.addItem("音樂天地");
        comBox.addItem("武術天地");
        comBox.addItem("象棋樂園");
        add(comBox);

      //定義文字區及其相關引數
        add(new JLabel("文字區"));
        area = new JTextArea(6, 13);// 文字區設定行數和列數
        add(new JScrollPane(area));
    }
}

執行結果:
在這裡插入圖片描述
在元件的設計中,樹和表格是比較少用的,

(二)監聽器事件

任何支援GUI的操作環境都需要不斷地監聽按鍵或者點選滑鼠這樣的事件,操作環境將這些事件報告給正在執行的程式,如果事件發生,每個程式將決定如何對他們做出反應,當事件發生時,事件源將事件物件傳遞給註冊的監聽器物件,監聽器物件將利用事件的資訊決定如何對事件做出反應。
Java監聽器事件主要有事件源,事件監聽器和事件組成。
1.事件物件
一般繼承自java.util.EventObject物件,由開發者自行定義.
2.事件源
就是觸發事件的源頭,註冊監聽器物件,併發送事件物件,不同的事件源會觸發不同的事件型別.
3.事件監聽器
事件監聽器負責監聽事件源發出的事件.一個事件監聽器通常實現java.util.EventListener這個標識介面.
在這裡插入圖片描述

監聽器事件的處理流程: 事件源可以註冊事件監聽器物件,並可以向事件監聽器物件傳送事件物件.事件發生後,事件源將事件物件發給已經註冊的所有事件監聽器.
監聽器物件隨後會根據事件物件內的相應方法響應這個事件.換句話來說,事件監聽器監聽到事件源的發生以後,執行事件的行為。

在這裡插入圖片描述
常見的監聽器型別有:
常見的監聽器型別
基於滑鼠的監聽器事件:

import java.awt.*;
import java.awt.event.*;
import javax.swing.*;
/**
 *  這段程式的作用在於在窗體中加入三個按鈕,點選不同的按鈕,窗體的顏色會發生變化。
 */
public class Test01 extends JFrame{
   private JPanel buttonPanel;
   private static final int DEFAULT_WIDTH = 300;
   private static final int DEFAULT_HEIGHT = 200;
   public static void main(String[] args)
      {
      EventQueue.invokeLater(new Runnable()
         {
            public void run()
            {
            	//定義窗體
             Test01 frame = new Test01();
               frame.setTitle("ButtonTest");
               frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
               frame.setVisible(true);
            }
         });
   }
   public Test01()
   {      
     setSize(DEFAULT_WIDTH, DEFAULT_HEIGHT);
      // create buttons
      JButton yellowButton = new JButton("Yellow");
      JButton blueButton = new JButton("Blue");
      JButton redButton = new JButton("Red");     
      buttonPanel = new JPanel();
      // add buttons to panel
      buttonPanel.add(yellowButton);
      buttonPanel.add(blueButton);
      buttonPanel.add(redButton);
       // add panel to frame
      add(buttonPanel);

      // create button actions
      ColorAction yellowAction = new ColorAction(Color.YELLOW);
      ColorAction blueAction = new ColorAction(Color.BLUE);
      ColorAction redAction = new ColorAction(Color.RED);

      // associate actions with buttons
      yellowButton.addActionListener(yellowAction);
      blueButton.addActionListener(blueAction);
      redButton.addActionListener(redAction);    
   }
   /**
    * An action listener that sets the panel's background color.
    */
   private class ColorAction implements ActionListener
   {
      private Color backgroundColor;
      public ColorAction(Color c)
      {
         backgroundColor = c;
      }
      public void actionPerformed(ActionEvent event)
      {        
    	  buttonPanel.setBackground(backgroundColor);
      }
   }
}
 

執行結果:
在這裡插入圖片描述

基於滑鼠的監聽器事件:

import java.awt.*;
import java.awt.event.KeyEvent;
import java.awt.event.KeyListener;
import java.awt.event.MouseEvent;
import java.awt.event.MouseListener;
import java.awt.event.MouseMotionListener; 
import javax.swing.*;
/*
*這個程式定義一個窗體,然後窗體監聽滑鼠事件,當鼠標出現在窗體中時,通過監聽滑鼠事件
*點選窗體,則顯示滑鼠所在的位置,以及點選次數等
**/
public class Test01 extends JFrame{
	My_Panel mp = null;
	public Test01() {
		 
		mp = new My_Panel();
		this.add(mp);
		// 註冊監聽
		this.addMouseListener(mp); // 監聽滑鼠
		this.addKeyListener(mp); // 監聽鍵盤
		this.addMouseMotionListener(mp); // 監聽滑鼠移動
		//定義窗體的相關引數
		this.setSize(300, 300); // 設定框體大小
		this.setLocation(400,150); //設定框體顯示的位置
		this.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE); // 設定框體退出
		this.setVisible(true); // 顯示框體
	}
	public static void main(String[] args) {
	 
		Test01 d = new Test01();
	}
 
}
 
class My_Panel extends JPanel implements MouseListener,KeyListener,MouseMotionListener{
	public void paint(Graphics g){
		super.paint(g);
	}
	//滑鼠點選
	@Override
	public void mouseClicked(MouseEvent e) {
		// TODO Auto-generated method stub
		System.out.println("滑鼠點選");
		System.out.println("滑鼠位置 x = "+e.getX()+" y = "+e.getY());
		System.out.println("滑鼠鍵 = "+e.getButton() + " 點選次數 "+e.getClickCount()); // 輸出1是左鍵,2是中鍵,3是右鍵
	}



	//滑鼠移動到My_Panel
	@Override
	public void mouseEntered(MouseEvent e) {
		// TODO Auto-generated method stub
	//	System.out.println("滑鼠移動到My_Panel");
	}
	//滑鼠離開My_Panel
	@Override
	public void mouseExited(MouseEvent e) {
		// TODO Auto-generated method stub
	//	System.out.println("滑鼠離開My_Panel");
	}
	//滑鼠按下
	@Override
	public void mousePressed(MouseEvent e) {
		// TODO Auto-generated method stub
	//	System.out.println("滑鼠按下");
	}
	//滑鼠鬆開
	@Override
	public void mouseReleased(MouseEvent e) {
		// TODO Auto-generated method stub
	//	System.out.println("滑鼠鬆開");
	}
	//鍵按下
	@Override
	public void keyPressed(KeyEvent e) {
		// TODO Auto-generated method stub
		System.out.println("鍵  = "+e.getKeyChar());
		
	}
	//鍵鬆開
	@Override
	public void keyReleased(KeyEvent e) {
		// TODO Auto-generated method stub
		
	}
	//鍵輸入
	@Override
	public void keyTyped(KeyEvent e) {
		// TODO Auto-generated method stub
		
	}
	//滑鼠按鍵在元件上按下並拖動時呼叫
	@Override
	public void mouseDragged(MouseEvent e) {
		// TODO Auto-generated method stub
	//	System.out.println("滑鼠按鍵在元件上按下並拖動時呼叫");
	}
	//滑鼠游標移動到元件上但無按鍵按下時呼叫
	@Override
	public void mouseMoved(MouseEvent e) {
		// TODO Auto-generated method stub
	//	System.out.println("滑鼠游標移動到元件上但無按鍵按下時呼叫");
	}
}

執行效果如圖:

在這裡插入圖片描述

以上

JAVA圖形介面設計部分完成了,整個模組包括常用窗體,佈局方式,常用元件和監聽事件這四個部分,圖形介面設計和在飯店點菜的邏輯類似,進入大飯店點菜就是監聽器事件,出事做好飯後端上來放在桌子上,桌子就是窗體,當然了,飯菜不能說直接放在桌子上要盤子盛著,盤子就是中層容器面板,桌子上有很多的菜,也有很多其他的小東西,如牙籤,筷子,餐巾紙等,那麼,這些東西就和圖形介面設計中的元件一樣,在窗體中有一些作用,那麼用吃飯來形容監聽器事件或許更加形象一點,綜上,圖形介面設計是Java設計程式時和使用者互動的工具,設計窗體並加入元件,當使用者採取下一步行動以後,監聽器事件發生作用,監聽事件的發生,並決定如何行動。