cocos实现一个中秋月饼消除类小游戏 Published on Dec 3, 2020 in javascript前端 with 0 comment ## 资源加载 首先我们可以把需要加载的资源放到一个数组里,这里也包含媒体资源 ```js const source = [ './assets/textures/btn_eat.png', './assets/textures/btn_threw.png', './assets/textures/moon_cake_1.png', './assets/textures/moon_cake_0.png', './assets/textures/bg.png', './assets/textures/icon_music.png', './assets/textures/icon_star.png', './assets/audios/game.mp3' ] ``` 通过加载器将资源加载进去 ```js cc.loader.load(source, function (result, count, loadedCount) { // 资源加载过程中回调函数 // ...... }, function () { // 资源加载完成回调函数 }); ``` ## 场景布置 给背景换一个想要的颜色 ```js const colorBackground = new cc.LayerColor(cc.color(67, 36, 99)) this.addChild(colorBackground) ``` 摆上背景图 ```js const bg = cc.Sprite.create('./assets/textures/bg.png') // 这只背景图的位置到正中央 bg.setPosition(cc.visibleRect.center) this.addChild(bg) ``` 添加音乐控制按钮 ```js const size = cc.winSize const musicPhoto = cc.Sprite.create('./assets/textures/icon_music.png') musicPhoto.setPosition(size.width / 1.1, size.height / 2 + size.width * .7) musicPhoto.setContentSize(71, 71) this.addChild(musicPhoto) ``` 我们先来手捏一个月饼 ```js const ratio = 0.9 const MoonCake = cc.Sprite.extend({ moonCakeTypes: [0, 1], // 这里两种月饼类型我们用 `0` 和 `1` 表示 moonCakeZIndexs: [19, 18, 17,16,15,14,13,12,11,10], moonCakeScales: [ 1, 1 * ratio, 1 * ratio * ratio, 1 * ratio * ratio * ratio, 1 * ratio * ratio * ratio * .9, 1 * ratio * ratio * ratio * ratio, 1 * ratio * ratio * ratio * ratio * .99, ], ctor: function () { let type = arguments[0] let texture if (this.moonCakeTypes.includes(type)) { texture = './assets/textures/moon_cake_'+type+'.png' } else { throw new Error('月饼类型错误! 你传入的月饼类型是: ' + type) } this._super(texture) this.x = cc.winSize.width / 2 this.type = type }, setZIndex: function (zIndex) { let moonCakesPositions = [ 327.5, 327.5 + 119*1, 327.5 + 119*2, 327.5 + 119*3, 327.5 + 119*4, 327.5 + 119*5, 327.5 + 119*6 ] if (this.__zIndex == null) { this.__zIndex = zIndex this.y = moonCakesPositions[zIndex] this.setScale(this.moonCakeScales[zIndex]) this.setLocalZOrder(this.moonCakeZIndexs[zIndex]) } else if (zIndex !== this.__zIndex) { this.setLocalZOrder(this.moonCakeZIndexs[zIndex]) let actionMove = cc.moveTo(.3, {x: cc.winSize.width / 2, y: moonCakesPositions[zIndex]}) var actionScale = cc.scaleTo(.3, this.moonCakeScales[zIndex]) var moonCakeAction = cc.spawn(actionMove, actionScale) this.stopAllActions() this.runAction(moonCakeAction) } } }) ``` 创建月饼 ```js function createMoonCake() { const moonCakes = [] // 这里我们创建7个月饼 for (let i = 0; i < 7; i++) { let moonCakeInstance = new MoonCake(Math.random()*10 > 5 ? 1 : 0) moonCakeInstance.setZIndex(i) moonCakes.push(moonCakeInstance) this.addChild(moonCakeInstance) } } ``` 当月饼被吃掉,我们要把最前的月饼移除掉,让排在后面的月饼站到前面来 ```js let currentMoonCake = this.moonCakes.shift() this.moonCakes.forEach(function (moonCakeInstance, i) { moonCakeInstance.setZIndex(i) }) currentMoonCake.removeFromParent(true) ``` 我们让背景音乐自动播放 ```js // 这里设置的是自动播放 cc.audioEngine.playMusic('./assets/audios/game.mp3', true) ``` 也可以让播放中的音乐暂停播放 ```js cc.audioEngine.pauseMusic() ``` 当然,还可以让暂停的音乐恢复播放 ```js cc.audioEngine.resumeMusic() ``` 处理音乐的播放和暂停 ```js function toggleBackgroundMusic(boolean) { let self = this let musicPhoto = this.musicPhoto if (boolean) { return play() } if (boolean === false) { return stop() } if (musicPhoto.isPlaying) { stop() } else { play() } function play() { musicPhoto.runAction(self.musicActionRotate()); if (!this.notFirst) { this.notFirst = true cc.audioEngine.playMusic('./assets/audios/game.mp3', true); } else { cc.audioEngine.resumeMusic(); } } function stop() { musicPhoto.isPlaying = false musicPhoto.stopAllActions() cc.audioEngine.pauseMusic() } } ``` 给音乐按钮添加交互事件 ```js const self = this this.addTap(musicPhoto, function () { self.toggleBackgroundMusic() }) ``` ### 给场景中的元素添加事件 我们把事件封装到 addTap 函数里 ```js function addTap(target, callbackFun) { cc.eventManager.addListener({ event: cc.EventListener.TOUCH_ONE_BY_ONE, onTouchBegan: function (touch, event) { const touchLocation = touch.getLocation() const targetConvertLocation = { x: target.x - touchLocation.x, y: target.y - touchLocation.y } const targetSize = target.getContentSize() const rect = cc.rect(-target.width / 2, -target.height / 2, target.width, target.height) return cc.rectContainsPoint(rect, targetConvertLocation) }, onTouchEnded: function () { typeof callbackFun === 'function' && callbackFun() } }, target) } ``` ### 分数 ```js const size = cc.winSize // 默认0分,这里我们选用 微软雅黑字体,字体大小是36 const scoreLabel = cc.LabelTTF.create('0分', 'MicrosoftYaHei', 36) scoreLabel.setPosition(size.width * 0.2, size.height / 2 + this.bg.height / 2 - scoreLabel.getContentSize().height - 20) this.addChild(scoreLabel) ``` 给分数旁边摆上星星 ```js const tagStar = cc.Sprite.create('./assets/textures/icon_star.png') // 我们把星星放到分数的左边 tagStar.setPosition(scoreLabel.x - tagStar.getContentSize().width * 1.7, scoreLabel.y + 15) this.addChild(tagStar) ``` ## 加入倒计时 加入倒计时的显示文字 ```js this.countTime = 60 * 1000 const timeLabel = cc.LabelTTF.create('60s', 'MicrosoftYaHei', 40) // 设置倒计时文字颜色为白色 timeLabel.setColor(cc.color(255, 255, 255)) timeLabel.countTime = this.countTime / 1000 this.addChild(timeLabel) ``` 倒计时执行内容 ```js function countDownAction(t) { timeLabel.counttime -= t if (timeLabel.countTime <= 0) { timeLabel.countTime = 0 // 倒计时结束,我们让游戏结束 this.gameOver() } timeLabel.string = timeLabel.countTime.toFixed(2) + 's' } ``` 我们让倒计时每隔 0.03秒执行一次 ```js this.schedule(countDownAction, .03) ``` ### 游戏结束 游戏结束了,我们来做一些处理 * 取消所有交互事件 * 停止背景音乐播放 * 停止所有动作和定时器的执行 ```js function gameOver() { cc.eventManager.setEnabled(false) this.toggleBackgroundMusic(false) this.unscheduleAllCallbacks() } ``` 本文由 tutustack 创作,采用 知识共享署名4.0 国际许可协议进行许可本站文章除注明转载/出处外,均为本站原创或翻译,转载前请务必署名