做的过程没有删掉 这是从一个字符版升级为图形版的
Main
import java.io.IOException;
public class Main {
static Thread thread;
public static void main(String[] args) throws InterruptedException, IOException {
start();
/*
Scanner scanner = new Scanner(System.in);
while(scanner.hasNext()){
String str = null;
if("w".equals(str)){
game.moveUp();
}else if("a".equals(str)){
game.moveLeft();
}else if("s".equals(str)){
game.moveDown();
}else if("d".equals(str)){
game.moveRight();
}
}
*/
}
public static void start(){
SnakeGame game = new SnakeGame();
thread = new Thread(game);
//初始化地图
game.initBackground();
//初始化食物
//不知道为什么必须在view里面进行函数才不会空指针异常?????? static 之后 就可以了 为何之前不用
//这个事情需要最后的时候搞清楚
game.initThing();
//game.picture();
game.view();
game.readKey();
//game.startThread();
//System.out.println("主函数输出"+game.direction);
thread.start();
}
}
Screen
import javax.swing.*;
import java.awt.*;
/**
* Created by LiJing on 2017/7/9.
*/
public class Screen {
public static void init(JFrame jFrame,int width,int hight){
jFrame.setVisible(true);
Toolkit toolkit = Toolkit.getDefaultToolkit();
Dimension dimension = toolkit.getScreenSize();
jFrame.setBounds((int)dimension.getWidth()/2-width/2, (int)dimension.getHeight()/2-hight/2, width, hight);
jFrame.setVisible(true);
jFrame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
}
}
SnakeGame
import javax.swing.*;
import java.awt.*;
import java.awt.event.KeyAdapter;
import java.awt.event.KeyEvent;
import java.awt.event.MouseAdapter;
import java.awt.event.MouseEvent;
import java.io.IOException;
import java.util.LinkedList;
import java.util.Random;
public class SnakeGame extends JPanel implements Runnable{
static LinkedList<Point> snake;
static Point head;
public static boolean isGameOver = false;
static SnakeGame snakeGame =new SnakeGame();
public static final int SNAKE_UP = 1;
public static final int SNAKE_DOWN = -1;
public static final int SNAKE_LEFT = 2;
public static final int SNAKE_RIGHT = -2;
/* //是否可以移动
static boolean moveFlag = true;*/
static JFrame frame = new JFrame("贪吃蛇");
//监听器里的line
static int line;
//蛇的方向 因为画的是蛇头朝右的 所以-2
int direction = -2;
//食物对象
static Point food;
static Point stone;
//高
public static final int HIGH =25;
//宽
public static final int WEIGHT=45;
//格子边长
public static final int LONG = 20;
//生成地图
static boolean[][] map =new boolean[HIGH][WEIGHT];
/*//食物可以生成的旗标
static boolean flag = true;*/
//初始化地图
public void initBackground(){
for (int k = 0; k < map.length; k++) {
for (int j = 0; j < map[k].length; j++) {
map[k][j] = false;
}
}
for(int i=0;i<map.length;i++){
if(i==0||i==map.length-1) {
for (int j = 0; j < map[i].length; j++) {
map[i][j] = true;
}
}else{
for (int j = 0; j < map[i].length; j++) {
if(j==0||j==map[i].length-1){
map[i][j] = true;
}
}
}
}
}
//图形化界面
@Override
public void paint(Graphics g) {
//画地图
for (int i = 0; i < map.length; i++) {
for (int j = 0; j < map[i].length; j++) {
if(map[i][j]){
g.setColor(Color.GRAY);
}else{
g.setColor(Color.WHITE);
}
g.fill3DRect(j* LONG, i* LONG, LONG, LONG, true);
}
}
//画蛇
head = snake.getFirst();
g.setColor(Color.RED);
g.fill3DRect(head.y* LONG, head.x* LONG, LONG, LONG, true);
// System.out.println("蛇头"+head.y);
//蛇身 蛇集合中 除了蛇头都是蛇身
for(int i = 1; i<snake.size()-1;i++){
Point body = snake.get(i);
g.setColor(Color.YELLOW);
g.fill3DRect(body.y* LONG, body.x* LONG, LONG, LONG, true);
// System.out.println(body.y);
}
Point tail = snake.getLast();
g.setColor(Color.black);
g.fill3DRect(tail.y* LONG, tail.x* LONG, LONG, LONG, true);
/*//隐形蛇尾
Point body = snake.get(snake.size()-1);
g.setColor(Color.WHITE);
g.fill3DRect(body.y* LONG, body.x* LONG, LONG, LONG, true);*/
//画食物
g.setColor(Color.GREEN);
g.fill3DRect(food.y*LONG, food.x*LONG, LONG, LONG, true);
/*//gameover的标志
if(isGameOver) {
g.setColor(Color.RED);
//设置画笔 的字体
g.setFont(new Font("宋体", Font.BOLD, 30));
g.drawString("GAME OVER 你的分数是: " + (snake.size()-3), (WEIGHT * LONG -50)/2,(HIGH * LONG)/2);
snakeGame.repaint();
}*/
}
//判断是否gameover
public void isGameOver(){
for(int i = 2; i<snake.size();i++){
Point body = snake.get(i);
// System.out.println("body.x = "+body.x+" head.x ="+head.x+" body.y = "+body.y+" head.y ="+head.y);
if(body.x==head.x&&body.y==head.y){
isGameOver = true ;
}
}
if(map[head.x][head.y]){
isGameOver = true ;
}
if(isGameOver==true){
final JFrame jFrame = new JFrame("啪! 你死了");
JPanel jPanel = new JPanel();
jFrame.setContentPane(jPanel);
JButton jButton = new JButton(" 你的分数是 "+ (snake.size()-3));
JButton jButton1 = new JButton("充值1分钱可以继续玩");
JButton jButton2 = new JButton("重新开始");
jButton1.addMouseListener(new MouseAdapter() {
@Override
public void mouseClicked(MouseEvent e) {
try {
Runtime.getRuntime().exec("rundll32 url.dll,FileProtocolHandler " + "http://blog.csdn.net/\n");
} catch (IOException e1) {
e1.printStackTrace();
}
}
});
jButton2.addMouseListener(new MouseAdapter(){
@Override
public void mouseClicked(MouseEvent e) {
direction = -2;
isGameOver=false;
//初始化地图
initBackground();
//初始化食物
//不知道为什么必须在view里面进行函数才不会空指针异常?????? static 之后 就可以了 为何之前不用
//这个事情需要最后的时候搞清楚
initThing();
initSnake();
snakeGame.repaint();
Main main1 = new Main();
main1.start();
jFrame.dispose();
}
});
jFrame.add(jButton);
jFrame.add(jButton1);
jFrame.add(jButton2);
Screen.init(jFrame,300,100);
}
/*//重置游戏
if(isGameOver==true){
isGameOver=false;
//初始化地图
initBackground();
//初始化食物
//不知道为什么必须在view里面进行函数才不会空指针异常?????? static 之后 就可以了 为何之前不用
//这个事情需要最后的时候搞清楚
initThing();
initSnake();
snakeGame.repaint();
}*/
}
//初始化蛇
public void initSnake(){
snake = new LinkedList<Point>();
int x = HIGH/2;
int y = WEIGHT /2;
// snake.addFirst(new Point(x,y-2));//隐形蛇尾 为了避免game over判断错误
snake.addFirst(new Point(x,y-1));
snake.addFirst(new Point(x,y));
snake.addFirst(new Point(x,y+1));
}
//蛇改变方向
public void changeDirection(int direction) throws InterruptedException {
if(this.direction+direction!=0){
this.direction=direction;
// move(direction);
}
}
//蛇移动的函数
public void move(int direction) throws InterruptedException {
switch (direction) {
case SNAKE_UP: {
head = snake.getFirst();
// snake.addFirst(new Point(head.x,head.y));
while(isGameOver);
snake.addFirst(new Point(head.x - 1, head.y));
if (!(head.x == food.x && head.y == food.y)) {
head = snake.getFirst();//每次移动完了都更新一下蛇头的坐标
snake.removeLast();
snakeGame.repaint();
isGameOver();
} else {
head = snake.getFirst();//每次移动完了都更新一下蛇头的坐标
initThing();
snakeGame.repaint();
isGameOver();
}
break;
}
case SNAKE_DOWN: {
head = snake.getFirst();
// snake.addFirst(new Point(head.x,head.y));
while(isGameOver);
snake.addFirst(new Point(head.x + 1, head.y));
if (!(head.x == food.x && head.y == food.y)) {
head = snake.getFirst();//每次移动完了都更新一下蛇头的坐标
snake.removeLast();
snakeGame.repaint();
isGameOver();
} else {
head = snake.getFirst();//每次移动完了都更新一下蛇头的坐标
initThing();
snakeGame.repaint();
isGameOver();
}
break;
}
case SNAKE_LEFT: {
head = snake.getFirst();
// snake.addFirst(new Point(head.x,head.y));
while(isGameOver);
snake.addFirst(new Point(head.x, head.y - 1));
if (!(head.x == food.x && head.y == food.y)) {
head = snake.getFirst();//每次移动完了都更新一下蛇头的坐标
snake.removeLast();
snakeGame.repaint();
isGameOver();
} else {
head = snake.getFirst();//每次移动完了都更新一下蛇头的坐标
initThing();
snakeGame.repaint();
isGameOver();
}
break;
}
case SNAKE_RIGHT: {
head = snake.getFirst();
// snake.addFirst(new Point(head.x,head.y));
while(isGameOver);
snake.addFirst(new Point(head.x, head.y + 1));
if (!(head.x == food.x && head.y == food.y)) {
head = snake.getFirst();//每次移动完了都更新一下蛇头的坐标
snake.removeLast();
snakeGame.repaint();
isGameOver();
} else {
head = snake.getFirst();//每次移动完了都更新一下蛇头的坐标
initThing();
snakeGame.repaint();
isGameOver();
}
break;
}
}
}
//初始化食物
public void initThing(){
Random random = new Random();
Random random1 = new Random();
while(true){
int x = random.nextInt(HIGH);
int x1 = random1.nextInt(HIGH);
int y = random.nextInt(WEIGHT);
int y1 = random1.nextInt(WEIGHT);
if(map[x1][y1] != true){
map[x1][y1] = true;
/*System.out.println(x1);
System.out.println(y1);*/
}
if(map[x][y]!=true){
food = new Point(x,y);
break;
}
}
}
//图形
public void view(){
snakeGame.initBackground();
snakeGame.initSnake();
frame.add(snakeGame);
}
//识别按键
public void readKey(){
//给窗口添加事件监听
frame.addKeyListener(new KeyAdapter() {
@Override
public void keyPressed(KeyEvent e) {
line=e.getKeyCode();
switch(line){
case KeyEvent.VK_UP:
try {
//System.out.println("尝试....");
changeDirection(SNAKE_UP);
//System.out.println("发送....");
} catch (InterruptedException e1) {
e1.printStackTrace();
}
break;
case KeyEvent.VK_LEFT:
try {
changeDirection(SNAKE_LEFT);
} catch (InterruptedException e1) {
e1.printStackTrace();
}
break;
case KeyEvent.VK_DOWN:
try {
changeDirection(SNAKE_DOWN);
} catch (InterruptedException e1) {
e1.printStackTrace();
}
break;
case KeyEvent.VK_RIGHT:
try {
changeDirection(SNAKE_RIGHT);
} catch (InterruptedException e1) {
e1.printStackTrace();
}
break;
}
}
});
Screen.init(frame, WEIGHT * LONG + 20, HIGH * LONG + 35);
snakeGame.repaint();
}
@Override
public void run() {
while(true){
try {
move(direction);
Thread.sleep(200 - snake.size()*5);
} catch (InterruptedException e) {
e.printStackTrace();
}
}
}
}
/*public void reFresh() throws InterruptedException {
//初始化地图
initBackground();
//显示蛇
showSnake();
//显示食物
showFood();
//打印地图
print();
Thread.sleep(50);
}*/
/* public static void main(String[] args) throws InterruptedException, IOException {
SnakeGame game = new SnakeGame();
//初始化地图
game.initBackground();
//初始化蛇
game.initSnake();
//初始化食物
game.initThing();
game.picture();
*//* Scanner scanner = new Scanner(System.in);
while(scanner.hasNext()){
String str = null;
if("w".equals(str)){
game.moveUp();
}else if("a".equals(str)){
game.moveLeft();
}else if("s".equals(str)){
game.moveDown();
}else if("d".equals(str)){
game.moveRight();
}
}*//*
}*/
/*//移动 注释掉的地方,加上后出现错误:是转弯不增加 ,直行增加. 我认为是蛇的长度都要增加的,但是并没有
public void moveUp() throws InterruptedException {
Point head = snake.getFirst();
// snake.addFirst(new Point(head.x,head.y));
snake.addFirst(new Point(head.x - 1, head.y));
if (!(head.x == food.x && head.y == food.y)) {
snake.removeLast();
reFresh();
} else {
initThing();
reFresh();
}
}
public void moveDown() throws InterruptedException {
Point head = snake.getFirst();
// snake.addFirst(new Point(head.x,head.y));
snake.addFirst(new Point(head.x+1,head.y));
if(!(head.x==food.x&&head.y==food.y)){
snake.removeLast();
reFresh();
}else {
initThing();
reFresh();
}
}
public void moveLeft() throws InterruptedException {
Point head = snake.getFirst();
// snake.addFirst(new Point(head.x,head.y));
snake.addFirst(new Point(head.x,head.y-1));
if(!(head.x==food.x&&head.y==food.y)){
snake.removeLast();
reFresh();
}else {
initThing();
reFresh();
}
}
public void moveRight() throws InterruptedException {
Point head = snake.getFirst();
// snake.addFirst(new Point(head.x,head.y));
snake.addFirst(new Point(head.x,head.y+1));
if(!(head.x==food.x&&head.y==food.y)){
snake.removeLast();
reFresh();
}else {
initThing();
reFresh();
}
}*/
//图形化方向盘及其控制
/* public void picture(){
JFrame jFrame = new JFrame("方向盘");
JButton jButton = new JButton("点击后用小键盘控制");
jFrame.add(jButton);
jButton.addKeyListener(new KeyAdapter() {
@Override
public void keyPressed(KeyEvent e) {
line=e.getKeyCode();
switch(line){
case KeyEvent.VK_UP:
try {
changeDirection(SNAKE_UP);
} catch (InterruptedException e1) {
e1.printStackTrace();
}
break;
case KeyEvent.VK_LEFT:
try {
changeDirection(SNAKE_LEFT);
} catch (InterruptedException e1) {
e1.printStackTrace();
}
break;
case KeyEvent.VK_DOWN:
try {
changeDirection(SNAKE_DOWN);
} catch (InterruptedException e1) {
e1.printStackTrace();
}
break;
case KeyEvent.VK_RIGHT:
try {
changeDirection(SNAKE_RIGHT);
} catch (InterruptedException e1) {
e1.printStackTrace();
}
break;
}
}
});
Screen.init(jFrame,250,250);
}*/