主要的蛇的类

import java.awt.Color;
import java.awt.Graphics;
import java.awt.HeadlessException;
import java.awt.Rectangle;
import java.awt.event.KeyEvent;
import java.util.Random; public class Snake { private Node head = null;
private Node tail = null;
int size = 0;
private boolean live = true; /**
* 判断蛇是否活着
* @return true则活着 false则死亡
*/
public boolean isLive() {
return live;
}
/**
* 设置蛇的生死
* @param live true则活着 false则死亡
*/
void setLive(boolean live){
this.live = live;
} private Yard y; Node n = new Node(15, 15, Dir.L);
/**
* 构造方法
* @param y
*/
public Snake(Yard y){
this.y = y;
head = n;
tail = n;
size++;
} /**
* 将一个结点添加到蛇的链表中
*/
void addToTail(){
Node node = null;
switch (tail.dir) {
case L:
node = new Node(tail.row, tail.col+1, tail.dir);
break;
case U:
node = new Node(tail.row+1, tail.col, tail.dir);
break;
case R:
node = new Node(tail.row, tail.col-1, tail.dir);
break;
case D:
node = new Node(tail.row-1, tail.col, tail.dir);
break;
}
tail.next = node;
node.prev = tail;
tail = node;
size++;
} /**
* 将一个结点从蛇的尾巴处删除
*/
void deleteFromTail(){
if(size == 0) return;
tail = tail.prev;
tail.next = null;
size--;
} /**
* 设置使蛇的位置向前移动一步
*/
void move(){
addToHead();
deleteFromTail();
checkDead();
}
/**
* 蛇的重画方法
* @param g
*/
void draw(Graphics g){
if(!isLive() || size == 0) {
return;
}
move();
for(Node node = head ; node != null ; node = node.next){
node.draw(g);
} }
/**
* 将一个结点加到蛇链表的头部
*/
void addToHead(){
Node node = null;
switch (head.dir) {
case L:
node = new Node(head.row, head.col-1, head.dir);
break;
case U:
node = new Node(head.row-1, head.col, head.dir);
break;
case R:
node = new Node(head.row, head.col+1, head.dir);
break;
case D:
node = new Node(head.row+1, head.col, head.dir);
break;
}
node.next = head;
head.prev = node ;
head = node ;
size++;
} /**
* 保存蛇单个结点信息的类
*/
private class Node{
int w = Yard.BLOCK_SIZE;
int h = Yard.BLOCK_SIZE;
Dir dir = Dir.L;
int row,col; Node next = null;
Node prev = null; public Node(int row,int col,Dir dir){
this.row = row;
this.col = col;
this.dir = dir;
}
//蛇单个节点的画法
public void draw(Graphics g){
Color c = g.getColor();
g.setColor(Color.BLACK);
g.fillRect(col*Yard.BLOCK_SIZE, row*Yard.BLOCK_SIZE, w, h);
g.setColor(c);
} }
/**
* 键盘监听
* @param e
*/
public void keyPressed(KeyEvent e) {
int key = e.getKeyCode();
switch(key){
case KeyEvent.VK_LEFT:
if(head.dir != Dir.R) head.dir = Dir.L;
break;
case KeyEvent.VK_UP:
if(head.dir != Dir.D) head.dir = Dir.U;
break;
case KeyEvent.VK_RIGHT:
if(head.dir != Dir.L) head.dir = Dir.R;
break;
case KeyEvent.VK_DOWN:
if(head.dir != Dir.U) head.dir = Dir.D;
break;
case KeyEvent.VK_F2:
if(!this.isLive()){
y.snake = new Snake(y);
}
break;
}
} /**
* 吃食物
* @param f
*/
public void eatFood(Food f){
if(this.getRect().intersects(f.getRect())){
f.setPos();
y.setScore();
this.addToTail();
}
} /**
* 通过检测来设置蛇的生死
*/
public void checkDead(){
if(head.col < 0 || head.col > Yard.COLS || head.row < 3 || head.row > Yard.ROWS-1){
setLive(false);
}
if(size >= 4){
for(Node node = head.next;node != null ; node = node.next){
if(head.row == node.row && head.col == node.col){
setLive(false);
}
}
}
} public Rectangle getRect(){
return new Rectangle(head.col*Yard.BLOCK_SIZE,head.row*Yard.BLOCK_SIZE,Yard.BLOCK_SIZE,Yard.BLOCK_SIZE);
}
}

吃的食物的类

import java.awt.Color;
import java.awt.Graphics;
import java.awt.Rectangle;
import java.util.Random; public class Food {
int row,col;
int h = Yard.BLOCK_SIZE;
int w = Yard.BLOCK_SIZE;
private static Random rd = new Random();
int step = 0; public Food(int row ,int col) {
this.row = row;
this.col = col;
} public void draw(Graphics g){
Color c = g.getColor();
if(step == 0){
g.setColor(Color.RED);
step++;
}else if(step == 1){
g.setColor(Color.green);
step++;
}else {
g.setColor(Color.WHITE);
step = 0;
} g.fillOval(col*Yard.BLOCK_SIZE, row*Yard.BLOCK_SIZE, w, h);
g.setColor(c);
} public Rectangle getRect(){
return new Rectangle(col*Yard.BLOCK_SIZE, row*Yard.BLOCK_SIZE, w, h);
} void setPos(){
this.row = rd.nextInt(Yard.ROWS-3)+3;
this.col = rd.nextInt(Yard.COLS);
}
}

方向的枚举

public enum Dir {
L,U,R,D
}

主界面的类

import java.awt.Color;
import java.awt.Font;
import java.awt.Frame;
import java.awt.Graphics;
import java.awt.Image;
import java.awt.event.KeyAdapter;
import java.awt.event.KeyEvent;
import java.awt.event.WindowAdapter;
import java.awt.event.WindowEvent; class Yard extends Frame{ PaintThread pt = null;
/**
* 速度 设置数字越大 越慢
*/
public static final int SPEED = 4;
/**
* 行数
*/
public static final int ROWS = 30;
/**
* 列数
*/
public static final int COLS = 30;
/**
* 行列的宽度
*/
public static final int BLOCK_SIZE = 15; /**
* 在游戏窗口中加入一条蛇
*/
public Snake snake = new Snake(this); /**
* 在游戏窗口中加入一个食物
*/
public Food food = new Food(10,10); private Font font = new Font("宋体", Font.BOLD,30 ); private Image offScreenImage = null; //分数
private int score = 0; public int getScore() {
return score;
} public void setScore() {
this.score += 5;
} /**
* 窗口构建函数
*/
public void launch(){ pt = new PaintThread();
this.setLocation(200, 200);
this.setSize(COLS * BLOCK_SIZE, ROWS * BLOCK_SIZE);
this.addWindowListener(new WindowAdapter() { public void windowClosing(WindowEvent e) {
System.exit(0);
} }); this.setVisible(true);
this.addKeyListener(new KeyMonitor());
this.setResizable(false);
//开始重画线程
new Thread(pt).start(); } /**
* 主方法
* @param args
*/
public static void main(String[] args){
new Yard().launch();
} /**
* 重写的paint方法 用来画出各个元素
*/
@Override
public void paint(Graphics g) { Color c = g.getColor();
g.setColor(Color.GRAY);
g.fillRect(0, 0, COLS * BLOCK_SIZE, ROWS * BLOCK_SIZE);
g.setColor(Color.DARK_GRAY); //画出横线
for(int i=1; i<ROWS; i++) {
g.drawLine(0, BLOCK_SIZE * i, COLS * BLOCK_SIZE, BLOCK_SIZE * i);
}
for(int i=1; i<COLS; i++) {
g.drawLine(BLOCK_SIZE * i, 0, BLOCK_SIZE * i, BLOCK_SIZE * ROWS);
} snake.eatFood(food);
g.setColor(Color.YELLOW);
g.drawString("score :" + score, 10, 50);
food.draw(g); if(snake.isLive()) {
snake.draw(g);
}else{
g.setColor(Color.YELLOW);
g.setFont(font);
g.drawString("Game Over!", 125, 225);
}
g.setColor(c); } /**
* 重写的update用来防止屏幕闪烁
*/
@Override
public void update(Graphics g) { if(offScreenImage == null){
offScreenImage = this.createImage(COLS*BLOCK_SIZE, ROWS*BLOCK_SIZE);
}
Graphics graphics = offScreenImage.getGraphics();
paint(graphics); g.drawImage(offScreenImage, 0, 0, null);
} /**
* 重画线程
*/
private class PaintThread implements Runnable{
private boolean flag = true; private boolean pause = false;
@Override
public void run() {
while(flag){
if(!pause)
repaint();
try {
Thread.sleep(25*SPEED);
} catch (InterruptedException e) {
e.printStackTrace();
}
}
} public void stopPaintThread(){
flag = !flag;
} public void pausePaintThread(){
pause = !pause;
}
} /**
* 键盘监听类
*/
private class KeyMonitor extends KeyAdapter{ @Override
public void keyPressed(KeyEvent e) {
int key = e.getKeyCode();
if(key == KeyEvent.VK_SPACE){
pt.pausePaintThread();
}
snake.keyPressed(e);
} }
}

贪吃蛇java版的更多相关文章

  1. 原生js写的贪吃蛇网页版游戏特效

    <meta http-equiv="Content-Type" content="text/html; charset=utf-8"> <bo ...

  2. c/c++ 贪吃蛇控制台版

    贪吃蛇控制台版(操作系统win7 64位:编译环境gcc, vs2017通过,其它环境未测试 不保证一定通过) 运行效果: #include <iomanip> #include < ...

  3. 贪吃蛇 Java实现(一)

    贪吃蛇  Java实现 1.面向对象思想 1.创建antition包它是包含sanke  Ground Food类 2.创建Controller包controller类 3.创建Game包有game类 ...

  4. js贪吃蛇-简单版

    分享个用原生js写的贪吃蛇,最近在学java,按照当年写的 js的思路,转换成java,换汤不换药 <!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1 ...

  5. 如何用python制作贪吃蛇以及AI版贪吃蛇

    用python制作普通贪吃蛇 哈喽,大家不知道是上午好还是中午好还是下午好还是晚上好! 很多人学习python,不知道从何学起.很多人学习python,掌握了基本语法过后,不知道在哪里寻找案例上手.很 ...

  6. C语言 贪吃蛇

    贪吃蛇(单人版): 本人先来介绍一个函数 -- bioskey函数: int bioskey (int cmd) 参数 (cmd) 基本功能 0 返回下一个从键盘键入的值(若不键入任何值,则将等下一个 ...

  7. 原生JavaScript贪吃蛇

    在实例开发过程中还是能认识到很多不足的,并且加强了一些基础. 简单写一下制作过程: 1.创建画布 2.创建蛇和老鼠 坐标不能重叠 3.让蛇移动起来 4.添加死亡方法 5.添加转点坐标和方向 6.添加吃 ...

  8. 原生Js贪吃蛇游戏实战开发笔记

    前言 本课程是通过JavaScript结合WebAPI DOM实现的一版网页游戏---贪吃蛇的开发全过程,采用面向以象的思想设计开发.通过这个小游戏的开发, 不仅可以掌握JS的语法的应用,还可以学会D ...

  9. 用GUI实现java版贪吃蛇小游戏

    项目结构 新建一个JFrame窗口,作为程序入口 public class GameStart{ public static void main(String[] args) { JFrame jFr ...

随机推荐

  1. 多密钥ssh-key生成与管理

    由于 git 大文件用 http 方式难以传输,必须使用 ssh-key,而 ssh-key 又生成了好多个.最近在各种折腾 ssh,公钥私钥上花费了很多时间,现将一些问题总结如下.系统为 Mac/L ...

  2. [IR] Advanced XML Compression - XBW

    思考:与ISX对比后能得出什么结论 原理解析: We proposed the XBW-transform that mimics on trees the nice structural prope ...

  3. 【中间件安全】Apache 安全加固规范

    1. 适用情况 适用于使用Apahce进行部署的Web网站. 2. 技能要求 熟悉Apache配置文件,能够利用Apache进行建站,并能针对站点使用Apache进行安全加固. 3. 前置条件 1. ...

  4. ElasticSearch6(三)-- Java API实现简单的增删改查

    基于ElasticSearch6.2.4, Java API创建索引.查询.修改.删除,pom依赖和获取es连接 可查看此文章. package com.xsjt.learn; import java ...

  5. MySql表结构修改详解

    修改表的语法=========================增加列[add 列名]=========================①alter table 表名 add 列名 列类型 列参数[加的 ...

  6. mac环境变量

    环境: 当前已经有 .bash_profile文件了 打开.bash_profile: open -e .bash_proile open -e .bash_profile 查看node安装路径: w ...

  7. ASP.NET MVC与ASP.NET Web Form简单区别

    概论: Asp.net  微软 提供web开发框架或者技术.分Web Form和ASP.NET MVC.下面简单说明各自优缺点及使用场景. Web Form 优点: 1.支持丰富的服务器控件.如:Gr ...

  8. celery 原理理解

    这里有一篇写的不错的:http://www.jianshu.com/p/1840035cb510 自己的“格式化”后的内容备忘下: 我们总在说c10k的问题, 也做了不少优化, 然后优化总是不够的. ...

  9. day_4.30 py

    2018-4-30 13:02:32 ''' 多态:只有当调用方法的时候才知道调用父类 还是子类的方法(随变化而变化,等到真正实行的时候才知道结果) 面向对象三个特点: 封装 继承 多态 ''' cl ...

  10. Spring实战系列

    作者:arccosxy  转载请注明出处:http://www.cnblogs.com/arccosxy/ 稀里糊涂的做了2年的Java Web后端开发,很多东西连蒙带猜外加百度,也算是完成了几个重要 ...