FlyBird笔记

FlyBird小游戏是css、js、html相结合制作的。

整体思路:

首先将窗体做出,把背景图放在面板中,然后添加计分和游戏结束游戏开始的画面,把游戏背景中地面移动实现把柱子在面板中实现进场及移动,小鸟放在面板中鼠标点击控制小鸟上升下降,最后写判断小鸟与柱子碰撞、地面碰撞和窗体顶部碰撞的方法。

 

HTML代码如下:

 

  <!DOCTYPE html>
  <html>
  <head>
  <meta charset="UTF-8">
  <title>Title</title>
  <link rel="stylesheet" href="css/main.css">
  </head>
  <body>
  <div id="box">
   
  <div id="header">
  <img src="img/head.jpg" alt="">
  <div>
  <img src="img/bird0.png" alt="">
  </div>
  </div>
  <img src="img/bird0.png" id="flyBird" alt="">
  <ul id="pipeBox">
  <!-- <li>-->
  <!-- <div>-->
  <!-- <img src="img/up_pipe.png" alt="">-->
  <!-- </div>-->
  <!-- <div>-->
  <!-- <img src="img/down_pipe.png" alt="">-->
  <!-- </div>-->
  <!-- </li>-->
  </ul>
  <img src="img/start.jpg" alt="" id="start">
  <div id="gameOver">
  <img src="img/game_over.jpg" alt="">
  <br><br><br>
  <img src="img/ok.jpg" id="ok" alt="">
  </div>
  <div id="slider">
  <img src="img/slider.jpg" alt="">
  <img src="img/slider.jpg" alt="">
  </div>
  <div id="scoreBoard">
  <img src="img/0.jpg" alt="">
  </div>
  </div>
  <audio src="source/game_music.mp3" loop></audio>
  <audio src="source/bullet.mp3"></audio>
  <audio src="source/game_over2.mp3"></audio>
  </body>
  </html>
  <script src="js/main.js"></script>

HTML引用css 、js来实现动画效果,audio src添加了背景音乐以及声音特效。

css代码如下:

 

#box {
width: 343px;
height: 480px;
background: url("../img/bg.jpg");
margin: 100px auto 0;
position: relative;
user-select: none;
overflow: hidden
}

#scoreBoard {
text-align: center;
position: absolute;
top: 30px;
width: 100%
}

@keyframes header {
from {
top: 75px
}
50% {
top: 115px
}
to {
top: 75px
}
}

#header {
width: 80%;
position: absolute;
left: 10%;
top: 75px;
animation: header 1.2s linear infinite
}

#header > div {
position: absolute;
right: 10px;
top: 20px;
background: url("../img/bird1.png") no-repeat
}

@keyframes bird {
0% {
opacity: 1
}
50% {
opacity: 0
}
100% {
opacity: 1;
}
}

#header > div > img {
animation: bird .3s linear infinite
}

#start {
position: absolute;
left: 129px;
top: 300px
}

@keyframes slider {
0% {
left: 0
}
100% {
left: -343px
}
}

#slider {
width: 999px;
position: absolute;
top: 422px;
animation: slider 5s linear infinite
}

#slider > img {
float: left
}

#flyBird {
display: none;
position: absolute;
left: 40px;
top: 75px
}

#pipeBox {
width: 100%;
height: 422px;
position: absolute;
left: 0;
top: 0;
margin: 0;
padding: 0;
list-style: none
}

#pipeBox > li {
width: 62px;
height: 100%;
position: absolute;
left: 400px;
}

#pipeBox > li > div:nth-child(1) {
width: 100%;
background: url("../img/up_mod.png");
position: absolute
}

#pipeBox > li > div:nth-child(1) > img {
position: absolute;
bottom: 0
}

#pipeBox > li > div:nth-child(2) {
width: 100%;
background: url("../img/down_mod.png");
position: absolute;
bottom: 0
}
@keyframes gameOver {
from{top:-200px;}
to{top:150px}
}
#gameOver {
position: absolute;
top: 150px;
width: 100%;
text-align: center;
display: none;
animation: gameOver 1s linear;
}

 

js代码如下:

 
const start = document.getElementById('start')
const header = document.getElementById('header')
const flyBird = document.getElementById('flyBird')
const box = document.getElementById('box')
const pipeBox = document.getElementById('pipeBox')
const scoreBoard = document.getElementById('scoreBoard')
const gameOver = document.getElementById('gameOver')
const ok = document.getElementById('ok')

const audios = document.getElementsByTagName('audio')

let speed = 0
const maxSpeed = 8

let downTimer = null
let upTimer = null
let pipeTimer = null
let crashTimer = null

let scoreNum = 0

function birdDown() {
//小鸟头朝下
flyBird.src = 'img/down_bird0.png'
// speed=speed+.3//0.3 0.6 0.9 1.2 1.5 1.8
// if(speed>=maxSpeed){
// speed=maxSpeed
// }
speed = speed < maxSpeed ? speed + .3 : maxSpeed
flyBird.style.top = flyBird.offsetTop + speed + 'px'
}

function crash(obj1, obj2) {
if (obj1.offsetLeft + obj1.offsetWidth < obj2.parentElement.offsetLeft ||
obj2.parentElement.offsetLeft + obj2.offsetWidth < obj1.offsetLeft ||
obj1.offsetTop + obj1.offsetHeight < obj2.offsetTop ||
obj2.offsetTop + obj2.offsetHeight < obj1.offsetTop)
return false
return true
}

function death() {
clearInterval(downTimer)//
const lis = pipeBox.getElementsByTagName('li')
for (let i = 0; i < lis.length; i++) {
clearInterval(lis[i].appearTimer)
}
clearInterval(pipeTimer)
clearInterval(upTimer)
clearInterval(crashTimer)
box.onclick = null
audios[2].play()
audios[0].pause()
gameOver.style.display = 'block'
ok.onclick = function () {
window.location.reload()
}
}

start.onclick = function (event) {
let ev = event || window.event
if (ev.stopPropagation) {
ev.stopPropagation()//部分浏览器清除事件冒泡的方式
} else {
ev.cancelBubble = true//另一部分浏览器清除事件冒泡的方式
}
//1.start和header消失
start.style.display = 'none'
header.style.display = 'none'
//2.出现小鸟,并且工作
flyBird.style.display = 'inline-block'
downTimer = setInterval(birdDown, 30)

box.onclick = function () {
//小鸟头朝上
flyBird.src = 'img/up_bird0.png'
//停止下落
clearInterval(downTimer)
//
clearInterval(upTimer)
audios[1].play()
speed = maxSpeed
upTimer = setInterval(function () {
speed = speed - .7
if (speed <= 0) {
//清除当前定时器,使小鸟不上升
clearInterval(upTimer)
//再次调用downTimer
downTimer = setInterval(birdDown, 30)
}
flyBird.style.top = flyBird.offsetTop - speed + 'px'
}, 30)
}
//3.出现柱子,并且工作
pipeTimer = setInterval(function () {
let li = document.createElement('li')//
let topH = Math.random() * (240 - 60) + 60
let bottomH = 300 - topH
li.innerHTML = `
<div style="height: ${topH}px">
<img src="img/up_pipe.png" alt="">
</div>
<div style="height: ${bottomH}px">
<img src="img/down_pipe.png" alt="">
</div>
`
li.lock = false

li.appearTimer = setInterval(function () {
li.style.left = li.offsetLeft - 3 + 'px'
if (!li.lock && li.offsetLeft + li.offsetWidth < flyBird.offsetLeft) {

//加分函数
!function () {
scoreNum++
console.log(scoreNum)
let scoreStr = String(scoreNum)//380
scoreBoard.innerHTML = ''
for (let i = 0; i < scoreStr.length; i++) {
scoreBoard.innerHTML = scoreBoard.innerHTML + '<img src="img/' + scoreStr[i] + '.jpg">'
}
}()
li.lock = true
}
if (li.offsetLeft < -70) {
pipeBox.removeChild(li)
}
}, 30)
pipeBox.appendChild(li)
/*let topH = Math.random() * 180 + 60
let bottomH = 300 - topH
console.log()
pipeBox.innerHTML=`
${pipeBox.innerHTML}
<li>
<div style="height: ${topH}px">
<img src="img/up_pipe.png" alt="">
</div>
<div style="height: ${bottomH}px" >
<img src="img/down_pipe.png" alt="">
</div>
</li>
`*/
}, 3000)
//4.死亡
crashTimer = setInterval(function () {
//天花板或地板死亡
if (flyBird.offsetTop <= 0 || flyBird.offsetTop + flyBird.offsetHeight >= 422) {
death()
}
//碰到管道
const lis = pipeBox.getElementsByTagName('li')
for (let i = 0; i < lis.length; i++) {
if (crash(flyBird, lis[i].children[0]) ||
crash(flyBird, lis[i].children[1])) {
death()
}
}


}, 30)
//5.BGM
audios[0].play()
}
posted @ 2021-12-06 10:04  南风轻语、  阅读(223)  评论(0)    收藏  举报