Java飛機大戰小遊戲(二):主角登場,開始騷操作

  • 項目:飛機大戰小遊戲之繪製我方飛機的騷操作
  • 項目簡介:飛機大戰小遊戲的主角,採用兩張圖片交替顯示來達到動態效果,鍵盤事件更改飛機火力(監聽器)
  • 開發工具:eclipse
  • 語言:Java
  • 知識點:模塊化、監聽器、定時器

代碼架構:程序分兩個包,共四個類
在這裏插入圖片描述
操作效果圖:
在這裏插入圖片描述

ImageUtil.java:遊戲加載圖片的工具類

HeroPlane.java:我方飛機

package com.demo.model;

import java.awt.image.BufferedImage;
import java.util.ArrayList;
import java.util.List;

import com.demo.util.ImageUtil;

/**
 * 英雄飛機
 */
public class HeroPlane {
	/**
	 * 飛機的特徵
	 */
	//用數組定義多張圖片
	private static BufferedImage[] images;
	//靜態塊
	static{
		images = new BufferedImage[2];
		for(int i=0;i<images.length;i++){
			images[i] = ImageUtil.readImage("heroplane"+i+".png");
		}
	}
	
	//生命:默認10條
	private int life = 10;	

	//分數:默認0分
	private int score = 0;	
	
	//飛機所在的位置x/y軸
	private int x;
	private int y;
	
	/**
	 * 行爲特徵
	 */
	//移動
	public void move(int x,int y){
		this.x = x;
		this.y = y;
	}

	//射擊
	public List<HeroBullet> fire() {
		List<HeroBullet> list = new ArrayList<HeroBullet>();	
		list.add(new HeroBullet(this.x, this.y));		//發射一枚子彈
		return list;
	}
	
	private boolean flag = true;
	//獲取飛機圖標
	public BufferedImage getImage() {
		flag = !flag;
		return images[flag?0:1];
	}
	
	//getters/setters方法
	//...
	public int getScore() {
		return ++score;			//移動加分
	}
	public void setScore(int score) {
		this.score = score;
	}

}

HeroBullet.java:我方飛機子彈

package com.demo.model;

import java.awt.image.BufferedImage;

import com.demo.util.ImageUtil;

public class HeroBullet{
	
	protected int x;  //畫布的x軸
	protected int y;  //畫布的y軸
	
	//子彈圖片
	private static BufferedImage image = ImageUtil.readImage("herobullet0.png");	
		
	//構造函數
	public HeroBullet(int x,int y){

		this.x = x;
		this.y = y;
	}
	
	//行爲->	移動
	public void move(){
		this.y -= 3; 
	}
	//出界
	public boolean isOutOfBound(){
		return this.y<0;
	}
	
	public static BufferedImage getImage() {
		return image;
	}
	public static void setImage(BufferedImage image) {
		HeroBullet.image = image;
	}
	
	//...x/y的 getters/setters方法
}

GameStart.java:主程序

package com.demo.model;

import java.awt.Color;
import java.awt.Font;
import java.awt.Graphics;
import java.awt.event.KeyAdapter;
import java.awt.event.KeyEvent;
import java.awt.event.MouseAdapter;
import java.awt.event.MouseEvent;
import java.awt.image.BufferedImage;
import java.util.ArrayList;
import java.util.List;
import java.util.Timer;
import java.util.TimerTask;

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

import com.demo.util.ImageUtil;

/**
 * 飛機大戰小遊戲(二):我方飛機騷起來
 * @author suoyue_zhan
 */
public class GameStart extends JPanel {
	public static final int WIDTH = 400;		//遊戲界面寬度
	public static final int HEIGHT = 654; 		//遊戲界面長度

	
	private BufferedImage background1 = ImageUtil.readImage("background.jpg");		// 背景圖片:靜態
	private HeroPlane heroPlane = new HeroPlane(); //英雄機
	//英雄飛機子彈對象->list集合
	private List<HeroBullet> heroBullets = new ArrayList<HeroBullet>();

		
	 //將背景繪製到面板中
	private void paintHeroPlane(Graphics g) {
		BufferedImage image = heroPlane.getImage();
		
		if(heroPlane.getX() == 0) { //飛機剛出來時候
			g.drawImage(image,WIDTH/2-image.getWidth()/2, HEIGHT/2+image.getHeight(), null);
		}else {
			g.drawImage(image,heroPlane.getX()-image.getWidth()/2, heroPlane.getY() - image.getHeight()/2, null);
		}
	}
	
	//繪製飛機的分數與生命
	private void  paintScoreAndLife(Graphics g) {
		g.setColor(new Color(255, 0, 0));				//設置畫筆顏色	紅0	綠0	藍0	(0~255)
		g.setFont(new Font(Font.SANS_SERIF, Font.PLAIN, 20));	//設置字體	字體、樣式、字號
		g.drawString("score: "+heroPlane.getScore(), 10, 25);
		g.drawString("life: "+heroPlane.getLife(), 10, 45);
	}
		
		
	//默認一條火力線
	private boolean flag1 = true;
	//兩條火力線
	private boolean flag2 = false;
	//三條火力線
	private boolean flag3 = false;
	//控制子彈移動速度的標記
	private boolean flagMax = false;
	
	//繪製飛機子彈
	public void paintHeroBullet(Graphics g){
		for(int i=0;i<heroBullets.size();i++){
			//每個英雄的子彈
			HeroBullet heroBullet = heroBullets.get(i);
			BufferedImage image = heroBullet.getImage();
			BufferedImage hImage = heroPlane.getImage();
			
			if(image != null && !heroBullet.isOutOfBound()) {
				if(flag1) {
					g.drawImage(image, heroBullet.getX(), heroBullet.getY(), null);
				}
				if(flag2) {
					g.drawImage(image, heroBullet.getX()-hImage.getWidth()/3, heroBullet.getY(), null);
					g.drawImage(image, heroBullet.getX()+hImage.getWidth()/3, heroBullet.getY(), null);
				}
				if(flag3) {
					g.drawImage(image, heroBullet.getX()-hImage.getWidth()/3, heroBullet.getY(), null);	//左邊
					g.drawImage(image, heroBullet.getX(), heroBullet.getY(), null);						//中間
					g.drawImage(image, heroBullet.getX()+hImage.getWidth()/3, heroBullet.getY(), null);	//右邊
				}

			}
		}
	}
	
	// 重寫JPanel的繪製方法-->>所有圖片都在該方法上執行
	@Override
	public void paint(Graphics g) {
		
		//繪製背景圖
		g.drawImage(background1, 0, 0, null);
		
		//調用方法,繪製飛機
		this.paintHeroPlane(g);
		//調用方法繪製飛機子彈
		this.paintHeroBullet(g);
		//繪製飛機的分數與生命
		this.paintScoreAndLife(g);

	}

	/**
	 *********遊戲邏輯方法--------------
	 */
	//英雄飛機發射子彈
	private void heroPlaneFire(){
		List<HeroBullet> list = heroPlane.fire();
		
		//收集子彈,動態繪製
		heroBullets.addAll(list);
	}
	//英雄子彈移動
	private void heroBulletMove() {
		for (HeroBullet heroBullet : heroBullets) {
			heroBullet.move();
		}
	}
	
	/**
	 * 窗口初始化
	 */
	public void init() {
		JFrame jFrame = new JFrame("飛機大戰"); // 設置窗口標題

		jFrame.add(this); // this表示主類,也表示畫板

		jFrame.setSize(WIDTH, HEIGHT); // 設置窗口大小
		jFrame.setLocationRelativeTo(null); // 設置窗口居中
		jFrame.setAlwaysOnTop(true); // 設置窗口總是在頂端
		jFrame.setResizable(false); // 設置不允許拖拉
		jFrame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE); // 關閉窗口時退出程序
		jFrame.setIconImage(new ImageIcon("./images/icon.png").getImage()); // 設置圖標
		jFrame.setVisible(true); // 使窗口顯示出來
				
		initListener();		//安裝程序監聽器	
		initTimer();		//設置定時器,用於實現遊戲中所有的動態邏輯效果
	}
	
	/**
	 * 監控鼠標的監聽器
	 */
	private void initListener() {
		//使用鼠標監聽器的適配器
		MouseAdapter adapter = new MouseAdapter() {
			@Override
			public void mouseMoved(MouseEvent e) {
				//獲取鼠標的x座標與y座標
				System.out.println("x: " + e.getX() + "y: " + e.getY());
				//飛機跟隨鼠標移動
				heroPlane.move(e.getX(), e.getY());
				repaint();  //重新繪製飛機, 底層是重寫執行paint方法
			}
		};		
		//添加鼠標監聽器
		this.addMouseListener(adapter);
		this.addMouseMotionListener(adapter);
		
		//設置鍵盤監聽事件
		this.setFocusable(true);
		//鍵盤的監控
		KeyAdapter k = new KeyAdapter() {
			//鍵盤按鍵按下時執行方法
			@Override
			public void keyPressed(KeyEvent e) {
				//鍵盤的按鍵編碼
				int keyCode = e.getKeyCode();
				//鍵盤按鍵編碼對應的文字
				String text = KeyEvent.getKeyText(keyCode);

				if("1".equals(text)) {
					flag1 = true;
					flag2 = false;
					flag3 = false;
				}
				if("2".equals(text)) {
					flag1 = false;
					flag2 = true;
					flag3 = false;
				}
				if("3".equals(text)) {
					flag1 = false;
					flag2 = false;
					flag3 = true;
				}
				if("M".equals(text)) {	
					flagMax = !flagMax;			//M鍵快掛
				}				
			}
		};
		this.addKeyListener(k);
				
	}
	
	/**
	 * 定時器
	 */
	private long count = 0;	//控制頻率
	public void initTimer(){
		
		Timer timer = new Timer();		//定時器對象
		long delay = 10; 
		long period = 10;
		//定時執行操作
		//參數1:每隔一段時間執行的操作
		//參數2:幾毫米之後執行定時器
		//參數3:每個幾毫米執行一次
		timer.schedule(new TimerTask() {
			@Override
			public void run() {		
			
				//飛機發射子彈
				if(count % 10 == 0 || flagMax){
					heroPlaneFire(); 	
				}				
				//英雄子彈移動
				//if(count % 2 == 0){
					heroBulletMove();	
				//}
									
				if(count == Long.MAX_VALUE-1){
					count = 0;
				}
				count++;		
			
				repaint(); //重新繪製頁面
			}
		}, delay,period);
	}

	/*
	 * 程序入口main()
	 */
	public static void main(String[] args) {
		System.out.println("遊戲開始了.....");

		GameStart gameStart = new GameStart();
		gameStart.init(); //顯示主界面
	}
	
}
發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章