天天看點

制作橫版遊戲KillBear第8課:技能及CD實作

上一節課程中我們實作了攻擊判定,讓你的英雄可以殺死敵人。在這一課中,我們在控制(操作)層多添加一個待冷卻時間顯示的技能按鈕,實作釋放技能,給你的英雄添加大招。

開發環境

Win64 : vs2010

Cocos2d-x v3.4Final

TexturePackerGUI

MapEdit

代碼

Operate

SkillButton

我們建立一個SkillButton

.h

#ifndef _SKILL_BUTTON_H_

#define _SKILL_BUTTON_H_

#include "cocos2d.h"

USING_NS_CC;

#include "Global.h"

class SkillButton : public Node

{

public:

SkillButton();

~SkillButton();

//CREATE_FUNC(SkillButton);

static SkillButton* create(const char* Nomal,const char* Click,const char* Mask,float CDTime);

static SkillButton* create(const char* Nomal,const char* Mask,float CDTime)

{return SkillButton::create(Nomal,Nomal,Mask,CDTime);};

static SkillButton* create(const char* Nomal,const char* Mask)

{return SkillButton::create(Nomal,Nomal,Mask,1.0f);};

static SkillButton* create(const char* Nomal,float CDTime)

{return SkillButton::create(Nomal,Nomal,Nomal,CDTime);};

static SkillButton* create(const char* Nomal)

{return SkillButton::create(Nomal,Nomal,Nomal,1.0f);};

CC_SYNTHESIZE(float,_cdtime,CDTime);

void ClickCallBack(Ref* obj);

void CoolDownCallBack(Node* node);

private:

bool init(const char* Nomal,const char* Click,const char* Mask,float CDTime);

private:

MenuItemImage* _ItemSkill; // 技能按鈕

Sprite* _Mask; // 蒙闆精靈,黑色半透明(這個是為了顯示一個冷卻計時效果)

ProgressTimer* _ProgressTimer; // 時間進度條精靈(360度旋轉)

Label* _atLabel; // 顯示冷卻

float CdTime; // 冷卻時間

void CoolDownReduce(float dt); //冷卻時間顯示定時器

};

#endif

       通過實作creat重載來自定義輸入的圖檔。後面調用的時候我隻用指定2個參數,圖檔顯示效果和CD時間實作調用。

.cpp

#include "SkillButton.h"

SkillButton::SkillButton():

_ItemSkill(NULL),

_Mask(NULL),

_cdtime(1.0f),

_ProgressTimer(NULL)

{

}

SkillButton::~SkillButton()

{

}

SkillButton* SkillButton::create(const char* Normal, const char* Click ,const char* Mask , float CDTime )

{

SkillButton* skillButton = new SkillButton();

if (skillButton && skillButton->init(Normal,Click,Mask,CDTime))

{

skillButton->autorelease();

return skillButton;

}

else

{

CC_SAFE_DELETE(skillButton);

return nullptr;

}

}

bool SkillButton::init(const char* Normal, const char* Click , const char* Mask , float CDTime )

{

bool ret = false;

do {

CC_BREAK_IF( !Node::init());

//斷點宏啊,其實在本Demo中去掉沒啥影響

CCAssert(Mask, "SkillButton::init Mask != NULL");

CCAssert(Normal, "SkillButton::init Normal != NULL");

CCAssert(Click, "SkillButton::init Click != NULL");

// Notice:添加child時要注意上下層

// 最下方是MenuItemImage 其次是蒙版圖檔 最上方是ProgressTimer

// 添加技能按鈕

_ItemSkill = MenuItemImage::create(Normal, Click, CC_CALLBACK_1(SkillButton::ClickCallBack,this));

_ItemSkill->setPosition(Vec2::ZERO);

auto MenuSkill = Menu::create(_ItemSkill, NULL);

MenuSkill->setPosition(Vec2::ZERO);

addChild(MenuSkill, -100);

// 添加蒙版

if(Normal==Mask)

{

_Mask = Sprite::create();

_Mask->setTexture(Normal);

_Mask->setColor(Color3B(0,0,0));

_Mask->setOpacity(100);

}

else

{

_Mask = Sprite::create(Mask);

}

_Mask->setPosition(Vec2::ZERO);

_Mask->setVisible(false);

addChild(_Mask,0);

// 添加旋轉進度條精靈,設定為順時針扇形進度計時器

_ProgressTimer = ProgressTimer::create(Sprite::create(Normal));

_ProgressTimer->setType(ProgressTimer::Type::RADIAL);

_ProgressTimer->setPosition(Vec2::ZERO);

_ProgressTimer->setVisible(false);

addChild(_ProgressTimer, 100);

this->setCDTime(CDTime);

CdTime=CDTime;

_atLabel = Label::create();

_atLabel->setSystemFontSize(_Mask->getContentSize().width/3);

_atLabel->setColor(Color3B(0,0,0));

_atLabel->setPosition(Vec2::ZERO);

addChild(_atLabel,200);

_atLabel->setVisible(false);

ret = true;

} while(0);

return ret;

}

void SkillButton::ClickCallBack(Ref* obj)

{

// 設定技能按鈕不可點選

_ItemSkill->setEnabled(false);

// 設定蒙版可見

_Mask->setVisible(true);

// 設定進度條可見

_ProgressTimer->setVisible(true);

//設定剩餘時間可見

_atLabel->setVisible(true);

//開啟定時器

this->schedule(schedule_selector(SkillButton::CoolDownReduce),0.1f);

//Hero釋放技能A

global->hero->runChangeAttack();

//準備一個持續時間為CDTime秒,旋轉360度*100% 的動畫(逐漸覆寫半透模闆形成冷卻效果;這裡進行計時冷卻動畫的實作和時間控制)

//ActionInterval持續動作是需要持續運作一段時間的動作。 它有一個啟動時間和結束時間。結束時間由啟動時間加上周期得出

ActionInterval* action_progress_to = Sequence::create(

ProgressTo::create(this->getCDTime(), 100),

NULL);

CallFunc* action_callback = CallFuncN::create(CC_CALLBACK_1(SkillButton::CoolDownCallBack,this));

_ProgressTimer->runAction(Sequence::create(action_progress_to, action_callback, NULL));

}

void SkillButton::CoolDownReduce(float dt)

{

_atLabel->setString(__String::createWithFormat("%.1f",CdTime-=0.1f)->getCString());

}

void SkillButton::CoolDownCallBack(Node* node)

{

// 按鈕置為可用

_ItemSkill->setEnabled(true);

// 設定蒙闆不可見

_Mask->setVisible(false);

// 進度條技能不可見

_ProgressTimer->setVisible(false);

_ProgressTimer->setPercentage(0);

//設定剩餘時間不可見

_atLabel->setVisible(false);

CdTime=this->getCDTime();

//取消定時器

this->unschedule(schedule_selector(SkillButton::CoolDownReduce));

}

蒙版是當技能CD時顯示的樣子,可以自己指定一些圖檔顯示:

當按下時,使這個技能按鈕不可點選,然後顯示一個Progress持續時間為CD,從0-100%順時針旋轉的程序;

技能冷卻完畢時重新時它可點選,隐藏蒙版;

剩餘時間顯示通過定時器設定,當然最後别忘了取消;

然後将這個SkillButton添加入我們的控制層。不要忘了#include。

Operate

.cpp

auto skillA = SkillButton::create("SkillButton.png",3.0f);

skillA->setPosition(attackItem->getPosition()-Vec2(50,0));

this->addChild(skillA);

效果

結語

       建立了一個SkillButton類,來實作技能攻擊效果。如果技能太快了,找到他的動畫改改幀數。

       受限于素材,相當的搓,可以稍稍改改這個代碼,從外部改善它。

       我還是比較希望直接用原來的技能圖檔,通過改變這個圖檔的紋理(灰階,可見度)實作冷卻展示,而不是用新的圖檔。

       本篇展示結束。下一篇我們添加一個暫停按鈕,實作暫停功能。

繼續閱讀