javascript实现贪吃蛇小游戏


Posted in Javascript onJuly 28, 2020

本文实例为大家分享了js实现贪吃蛇小游戏的具体代码,供大家参考,具体内容如下

<!DOCTYPE html>
<html>
<head>
 <meta charset="UTF-8">
 <title>Document</title>
</head>
<body>
</body>
<script>
 // 贪吃蛇:
 // 键盘的方向键,控制蛇的方向,碰撞食物,实现增加长度的效果,撞到墙壁或自身,游戏结束
 // 分析:
 // 地图:提供边界
 // 食物:随机出现,可以被碰撞(坐标重复)
 // 蛇:初始的固定长度,移动,改变方向,碰撞食物,碰撞墙,碰撞自己(坐标重复)
 
 class Map{
 constructor(){
 // 提前设定将来的地图的样式数据
 this.w = 800;
 this.h = 400;
 this.c = "#ccc";
 // 执行创建地图方法
 this.createEle();
 }
 createEle(){
 this.mapEle = document.createElement("div");
 this.mapEle.style.cssText = `width:${this.w}px;height:${this.h}px;background:${this.c};margin:0 auto;position:relative;border:solid 10px black;`;
 document.body.appendChild(this.mapEle);
 }
 }
 class Food{
 constructor(){
 // 提前设定将来的食物的样式数据
 this.w = 20;
 this.h = 20;
 this.c = "red";
 this.x = 0;
 this.y = 0;
 // 执行创建食物方法
 this.createEle();
 }
 createEle(){
 this.foodEle = document.createElement("div");
 // 设置left和top时要注意,将地图假设成了20个像素的一个格子,注意位置的换算
 this.foodEle.style.cssText = `width:${this.w}px;height:${this.h}px;background:${this.c};position:absolute;left:${this.x * this.w}px;top:${this.y * this.h}px;`;
 // console.log(m.mapEle);
 m.mapEle.appendChild(this.foodEle);
 }
 randomPos(){
 // 随机位置,随机产生的是格子的位置,不是真正的像素
 this.x = random(0,(m.w-this.w) / this.w);
 this.y = random(0,(m.h-this.h) / this.h);
 // 设置位置时,要换算成像素,然后再生效
 this.foodEle.style.left = this.x * this.w + "px";
 this.foodEle.style.top = this.y * this.h + "px";
 }
 }

 // 至少得有多个元素(蛇节)组成
 // 每个元素都要有自己的标签,位置,宽高,颜色
 // 单个元素,使用对象包含所有信息
 // 所有元素怎么办?来个数组,包裹起来
 class Snake{
 constructor(){
 // 1.提前设定将来的蛇节的样式数据
 this.w = 20;
 this.h = 20;
 // 2.因为蛇由多个设计组成,每个蛇节都有自己的独立信息,所以数据结构设计成如下格式
 this.body = [{
 ele:null,
 x:4,
 y:3,
 c:randomColor()
 },{
 ele:null,
 x:3,
 y:3,
 c:randomColor()
 },{
 ele:null,
 x:2,
 y:3,
 c:randomColor()
 }];

 // 7-1.提前设置默认方向
 this.d = "right";

 // 3.开始创建蛇节元素,设置样式
 this.createEle();
 }
 createEle(){
 // 4.使用循环多次创建,因为有多个蛇节
 for(var i=0;i<this.body.length;i++){
 // 12.创建之前,需要判断元素是否已经存在,如果已经存在,不需要创建
 if(!this.body[i].ele){
  this.body[i].ele = document.createElement("div");
  m.mapEle.appendChild(this.body[i].ele);
 }
 this.body[i].ele.style.cssText = `width:${this.w}px;height:${this.h}px;background:${this.body[i].c};position:absolute;left:${this.body[i].x * this.w}px;top:${this.body[i].y * this.h}px;`;
 }
 // 找到蛇头
 this.body[0].ele.innerHTML = "0";

 // 5.延迟之后,开始移动
 setTimeout(()=>{
 this.move();
 },300);
 }
 move(){
 // 6.从最后一个元素向前找前一个元素的坐标,直到第一个
 for(var i=this.body.length-1; i>0; i--){
 this.body[i].x = this.body[i-1].x;
 this.body[i].y = this.body[i-1].y;
 }
 // 7.第一个元素根据默认方向,决定想哪走
 switch(this.d){
 case "left":
  this.body[0].x -= 1;
  break;
 case "right":
  this.body[0].x += 1;
  break;
 case "top":
  this.body[0].y -= 1;
  break;
 case "bottom":
  this.body[0].y += 1;
  break;
 }
 
 // 8.移动过程中,判断是否撞到边界,任意一个边界都不行
 if(this.body[0].x < 0 || this.body[0].y < 0 || this.body[0].x > ((m.w-this.w) / this.w) || this.body[0].y > ((m.h-this.h) / this.h)){
 alert("撞墙了");
 // 利用return的停止,结束程序
 return;
 }

 // 9.移动过程中,判断是否与食物的坐标重复,如果重复
 if(this.body[0].x === f.x && this.body[0].y === f.y){
 // 给蛇增加一个蛇节
 this.body.push({
  ele:null,
  x:this.body[this.body.length-1].x,
  y:this.body[this.body.length-1].y,
  c:randomColor()
 })
 // 刷新食物的坐标
 f.randomPos();
 }

 // 10.移动过程中,判断蛇头的坐标是否与某个任意一个蛇节的坐标重复
 for(var i=1;i<this.body.length;i++){
 if(this.body[0].x == this.body[i].x && this.body[0].y == this.body[i].y){
  // 如果重复,撞到自己,结束程序
  alert("撞到自己了");
  return;
 }
 }

 // 以上只是在修改坐标,生效了么?设置回去了么?
 // 走的过程中有可能吃到食物,增加一个蛇节(元素),创建元素
 // 11.所以,使用创建蛇节方法,重新设置蛇节的位置以及判断是否需要创建新元素
 this.createEle();
 }
 direct(type){
 // 14.处理键盘穿件来的code值
 // 处理之前要先判断,当前是否按下了相反方向
 // 如果是相反方向,直接结束判断,不执行
 // 如果不是相反方向,改变初始的默认方向
 switch(type){
 case 37:
  if(this.d === "right") break;
  this.d = "left";
  break;
 case 38:
  if(this.d === "bottom") break;
  this.d = "top";
  break;
 case 39:
  if(this.d === "left") break;
  this.d = "right";
  break;
 case 40:
  if(this.d === "top") break;
  this.d = "bottom";
  break;
 }
 }
 }

 function random(a,b){
 return Math.round(Math.random()*(a-b)+b)
 }
 function randomColor(){
 return `rgb(${random(0,255)},${random(0,255)},${random(0,255)})`
 }

 var m = new Map();
 
 var f = new Food();
 // 为了测试,先用计时器,重复执行,看一看随机效果
 // setInterval(() => {
 f.randomPos();
 // }, 500);

 var s = new Snake();
 // 13.当按下键盘时,将按下的键盘的code值,传给蛇的专属处理方法
 document.onkeydown = function(eve){
 var e = eve || window.event;
 var code = e.keyCode || e.which;
 s.direct(code);
 }


 // 因为后期要做不允许掉头的效果
 // 所以,采取当前方法:两个分支处理方向


</script>
</html>

javascript实现贪吃蛇小游戏

更多有趣的经典小游戏实现专题,分享给大家:

以上就是本文的全部内容,希望对大家的学习有所帮助,也希望大家多多支持三水点靠木。

Javascript 相关文章推荐
jquery tools系列 expose 学习
Sep 06 Javascript
Javascript数组的排序 sort()方法和reverse()方法
Jun 04 Javascript
jquery实现简单的拖拽效果实例兼容所有主流浏览器(优化篇)
Jun 28 Javascript
JS实现鼠标单击与双击事件共存
Mar 08 Javascript
js用闭包遍历树状数组的方法
Mar 19 Javascript
对js中回调函数的一些看法
Aug 29 Javascript
Vue.js每天必学之组件与组件间的通信
Sep 08 Javascript
微信小程序实现下拉菜单切换效果
Mar 30 Javascript
vue子传父关于.sync与$emit的实现
Nov 05 Javascript
ES6中Promise的使用方法实例总结
Feb 18 Javascript
原生JavaScript实现随机点名表
Jan 14 Javascript
实现一个简单得数据响应系统
Nov 11 Javascript
Element DateTimePicker日期时间选择器的使用示例
Jul 27 #Javascript
Js图片点击切换轮播实现代码
Jul 27 #Javascript
在vue中实现echarts随窗体变化
Jul 27 #Javascript
Vue组件跨层级获取组件操作
Jul 27 #Javascript
vue 解决兄弟组件、跨组件深层次的通信操作
Jul 27 #Javascript
vue中组件通信详解(父子组件, 爷孙组件, 兄弟组件)
Jul 27 #Javascript
JS的时间格式化和时间戳转换函数示例详解
Jul 27 #Javascript
You might like
PHP4与PHP3中一个不兼容问题的解决方法
2006/10/09 PHP
PHP编程计算文件或数组中单词出现频率的方法
2017/05/22 PHP
javascript getElementsByClassName 和js取地址栏参数
2010/01/02 Javascript
使用jQuery插件创建常规模态窗口登陆效果
2013/08/23 Javascript
JavaScript核心语法总结(推荐)
2016/06/02 Javascript
Bootstrap笔记之缩略图、警告框实例详解
2017/03/09 Javascript
easyui-datagrid特殊字符不能显示的处理方法
2017/04/12 Javascript
javascript实现Java中的Map对象功能的实例详解
2017/08/21 Javascript
Vue组件开发之LeanCloud带图形校验码的短信发送功能
2017/11/07 Javascript
微信小程序实现上传图片功能
2018/05/28 Javascript
JS实现音量控制拖动
2020/01/15 Javascript
[01:05:36]VP vs TNC Supermajor小组赛B组 BO3 第二场 6.2
2018/06/03 DOTA
用Python计算三角函数之acos()方法的使用
2015/05/15 Python
Python中基本的日期时间处理的学习教程
2015/10/16 Python
Python图片裁剪实例代码(如头像裁剪)
2017/06/21 Python
浅谈使用Python变量时要避免的3个错误
2017/10/30 Python
Python设计模式之MVC模式简单示例
2018/01/10 Python
pyqt5简介及安装方法介绍
2018/01/31 Python
浅谈django orm 优化
2018/08/18 Python
python根据url地址下载小文件的实例
2018/12/18 Python
python自定义线程池控制线程数量的示例
2019/02/22 Python
python join方法使用详解
2019/07/30 Python
详解从Django Allauth中进行登录改造小结
2019/12/18 Python
PyCharm 专业版安装图文教程
2020/02/20 Python
CSS3 3D酷炫立方体变换动画的实现
2019/03/26 HTML / CSS
局域网标准
2016/09/10 面试题
华为python面试题
2016/05/03 面试题
公司副总经理岗位职责
2014/10/01 职场文书
工作作风整顿个人剖析材料
2014/10/11 职场文书
2015年世界环境日活动方案
2015/05/05 职场文书
2015年教研工作总结
2015/05/23 职场文书
企业愿景口号
2015/12/25 职场文书
JavaScript 去重和重复次数统计
2021/03/31 Javascript
分布式锁为什么要选择Zookeeper而不是Redis?看完这篇你就明白了
2021/05/21 Redis
详解MongoDB排序时内存大小限制与创建索引的注意事项
2022/05/06 MongoDB
JavaScript中reduce()的用法
2022/05/11 Javascript