(七) 控制器的实现

最后更新于:2022-04-01 16:12:20

控制器中的功能并不多,主要是下面这些 ~~~ //对玩家分数的操作 CC_SYNTHESIZE_READONLY(SaveData *, m_saveData, SaveData); void update(float tm); //游戏暂停与恢复 void menuPauseCallback(cocos2d::Ref* pSender); //声音控制 void menuMusicCallback(cocos2d::Ref* pSender); ~~~ 下面是这些功能的实现 ~~~ bool Controller::init() { if (!Layer::init()) { return false; } bool bRect = false; do { Size winSize = Director::getInstance()->getWinSize(); //从xml文件中读取中文显示出来 auto dictionary = Dictionary::createWithContentsOfFile("fonts/AboutMe.xml"); score_label = Label::createWithTTF( ((__String *)(dictionary->objectForKey("score")))->getCString(), "fonts/DFPShaoNvW5-GB.ttf", 25); score_label->setPosition(score_label->getContentSize().width / 2, winSize.height - score_label->getContentSize().height * 2); CC_BREAK_IF(!score_label); this->addChild(score_label); //添加显示分数的标签 m_saveData = SaveData::create(); //这里一定要retain一下saveData,在析构函数中release一下 m_saveData->retain(); auto str = __String::createWithFormat("%d", m_saveData->getScore()); m_score = Label::createWithTTF(str->getCString(), "fonts/DFPShaoNvW5-GB.ttf", 25); m_score->setPosition(Point(score_label->getContentSize().width + m_score->getContentSize().width / 2 + 30, winSize.height - score_label->getContentSize().height * 2)); CC_BREAK_IF(!m_score); this->addChild(m_score); //记得更新分数的显示 this->scheduleUpdate(); //游戏声音控制按钮 Sprite *normalMusic = Sprite::createWithSpriteFrame(SpriteFrameCache::getInstance()->getSpriteFrameByName("game_musicPause.png")); Sprite *pressedMusic = Sprite::createWithSpriteFrame(SpriteFrameCache::getInstance()->getSpriteFrameByName("game_musicPause.png")); pMusicItem = MenuItemSprite::create( normalMusic, normalMusic, NULL, CC_CALLBACK_1(Controller::menuMusicCallback, this)); //游戏暂停按钮 Sprite *normalPause = Sprite::createWithSpriteFrame(SpriteFrameCache::getInstance()->getSpriteFrameByName("game_resume_nor.png")); Sprite *pressedPause = Sprite::createWithSpriteFrame(SpriteFrameCache::getInstance()->getSpriteFrameByName("game_resume_pressed.png")); pPauseItem = MenuItemSprite::create( normalPause, pressedPause, NULL, CC_CALLBACK_1(Controller::menuPauseCallback, this)); Menu *menuPause = Menu::create(pMusicItem,pPauseItem, NULL); menuPause->alignItemsHorizontallyWithPadding(pPauseItem->getContentSize().width/2); menuPause->setPosition( Point(winSize.width - pPauseItem->getContentSize().width*2, winSize.height - normalPause->getContentSize().height)); this->addChild(menuPause); } while (0); return true; } //游戏暂停 void Controller::menuPauseCallback(cocos2d::Ref* pSender) { CocosDenshion::SimpleAudioEngine::getInstance()->playEffect("sound/button.mp3"); if (!Director::getInstance()->isPaused()) { // 图标状态设置 pPauseItem->setNormalImage(Sprite::createWithSpriteFrame(SpriteFrameCache::getInstance()->getSpriteFrameByName("game_pause_nor.png"))); pPauseItem->setSelectedImage(Sprite::createWithSpriteFrame(SpriteFrameCache::getInstance()->getSpriteFrameByName("game_pause_press.png"))); CocosDenshion::SimpleAudioEngine::getInstance()->pauseBackgroundMusic(); // 停止背景音乐 CocosDenshion::SimpleAudioEngine::getInstance()->stopAllEffects(); // 停止所有的特效 Director::getInstance()->pause(); // 停止所有的动作,敌机飞行,子弹前进等 } else { pPauseItem->setNormalImage(Sprite::createWithSpriteFrame(SpriteFrameCache::getInstance()->getSpriteFrameByName("game_resume_nor.png"))); pPauseItem->setSelectedImage(Sprite::createWithSpriteFrame(SpriteFrameCache::getInstance()->getSpriteFrameByName("game_resume_pressed.png"))); CocosDenshion::SimpleAudioEngine::getInstance()->resumeBackgroundMusic();// 恢复 Director::getInstance()->resume(); // 恢复 } } void Controller::menuMusicCallback(cocos2d::Ref* pSender) { CocosDenshion::SimpleAudioEngine::getInstance()->playEffect("sound/button.mp3"); if (CocosDenshion::SimpleAudioEngine::getInstance()->isBackgroundMusicPlaying()) { // 图标状态设置 pMusicItem->setNormalImage(Sprite::createWithSpriteFrame(SpriteFrameCache::getInstance()->getSpriteFrameByName("game_music.png"))); pMusicItem->setSelectedImage(Sprite::createWithSpriteFrame(SpriteFrameCache::getInstance()->getSpriteFrameByName("game_music.png"))); CocosDenshion::SimpleAudioEngine::getInstance()->stopBackgroundMusic(); // 停止背景音乐 // CocosDenshion::SimpleAudioEngine::getInstance()->stopAllEffects(); // 停止所有的特效 } else { pMusicItem->setNormalImage(Sprite::createWithSpriteFrame(SpriteFrameCache::getInstance()->getSpriteFrameByName("game_musicPause.png"))); pMusicItem->setSelectedImage(Sprite::createWithSpriteFrame(SpriteFrameCache::getInstance()->getSpriteFrameByName("game_musicPause.png"))); CocosDenshion::SimpleAudioEngine::getInstance()->playBackgroundMusic("sound/BackgroundMusic.mp3", true);// 恢复 // CocosDenshion::SimpleAudioEngine::getInstance()->resumeAllEffects(); } } void Controller::update(float tm) { auto str = __String::createWithFormat("%d", m_saveData->getScore()); //更新分数和坐标 m_score->setColor(Color3B(255, 0, 0)); m_score->setString(str->getCString()); m_score->setPositionX(score_label->getContentSize().width + m_score->getContentSize().width / 2 + 30); } ~~~ 要实现游戏的暂停功能,可以直接将当前运行的场景暂停,而要实现声音的暂停,通过简单的停止背景音乐、音效却不行。因为不断有新的子弹在发射、新的敌机在爆炸等。所以,我使用的方法是 将背景音乐与其他音效绑定。 比如下面子弹类中的代码 ~~~ if (CocosDenshion::SimpleAudioEngine::getInstance()->isBackgroundMusicPlaying()) { CocosDenshion::SimpleAudioEngine::getInstance()->playEffect("sound/bullet.wav"); } ~~~ 只有背景音乐处于播放状态,音效才会播放。 虽然功能实现了,不过总感觉方法太水了。。。谁有更好的方式欢迎告知。
';