1.新建一个ShakeLayer类文件
分别在项目中添加:ShakeLayer.h,ShakeLayer.cpp文件
2.在ShakeLayer.h文件中写如代码如下:
#ifndef __SHAKELAYER_HEAD__
#define __SHAKELAYER_HEAD__
#include "cocos2d.h"
//声明一个结构体类型FPoint
struct FPoint {
float x;
float y;
};
class ShakeLayer:public cocos2d::Layer
{
public:
ShakeLayer();
~ShakeLayer();
CREATE_FUNC(ShakeLayer);
static cocos2d::Scene* createScene();
virtual bool init();
public:
void loadBg();
public:
void ShakeScreen(); //屏幕震动函数
void UpdateShakeScreen(float delta_time); //屏幕震动的调度
void clickEventFun(); //按钮点击事件
public:
FPoint shake_offset_; //偏移量
float since_last_frame_;
int current_shake_frame_;
bool shake_screen_;
};
#endif
3.ShakeLayer.cpp添加代码如下:
#include "ShakeLayer.h"
#include "ui/cocosGUI.h"
USING_NS_CC;
using namespace ui;
const float kShakeFPS = 30.f; //震动频率控制系数
const int kShakeFrames = 20; //总判断次数
ShakeLayer::ShakeLayer()
{
//构造函数对其进行初始化
shake_offset_.x = 0;
shake_offset_.y = 0;
since_last_frame_ = 0;
current_shake_frame_ = 0;
shake_screen_ = false;
}
ShakeLayer::~ShakeLayer()
{
this->removeAllChildren();
}
//创建震动层的场景(布景层是不可能脱离场景而单独存在的)
Scene* ShakeLayer::createScene()
{
//1.创建一个场景
Scene* shakeScene = Scene::create();
//2.创建一个层
ShakeLayer* layer = ShakeLayer::create();
//3.将帮助层添加到新建的场景
shakeScene ->addChild(layer);
//4.返回这个场景
return shakeScene;
}
//主函数
bool ShakeLayer::init()
{
if (!Layer::init())
{
return false;
}
//添加背景
loadBg();
return true;
}
//添加背景
void ShakeLayer::loadBg()
{
//添加一个自定义类型的时间调度器((每隔0.1秒)刷新一次)
schedule(schedule_selector(ShakeLayer::UpdateShakeScreen),0.1);
Size winSize = Director::getInstance()->getWinSize();
Sprite* bgSpr = Sprite::create("Scene/shake.png");
bgSpr->setPosition(Vec2(winSize.width/2,winSize.height/2));
addChild(bgSpr);
Button* btn_shake = Button::create("Scene/btn.png");
btn_shake->setPosition(Vec2(winSize.width/2,winSize.height/2));
addChild(btn_shake);
//点击按钮开始震动
btn_shake->addClickEventListener(CC_CALLBACK_0(ShakeLayer::clickEventFun,this));
}
void ShakeLayer::clickEventFun()
{
ShakeScreen();
}
void ShakeLayer::ShakeScreen()
{
shake_offset_.x = 0.f; //x轴抖动偏移量
shake_offset_.y = 0.f; //y轴抖动偏移量
since_last_frame_= -1.f; //控制震动的频率(每经过几次kSpeed帧,进行一次有效震动)
current_shake_frame_ = 0; //判断震动的总次数(总共是kShakeFrames=20次)
shake_screen_ = true; //是否震动
}
void ShakeLayer::UpdateShakeScreen(float delta_time)
{
if (!shake_screen_) return;
if (since_last_frame_ == -1.f)since_last_frame_ = 0.f;
else
{
since_last_frame_ += delta_time;
}
static const float kSpeed = 1.0 / kShakeFPS;
printf("kSpeed=%f,since_last_frame_=%f\n", kSpeed,since_last_frame_);
while (since_last_frame_ >= kSpeed)
{
since_last_frame_ -= kSpeed;
if (current_shake_frame_ + 1 == kShakeFrames)
{
shake_screen_ = false;
shake_offset_.x = 0; //x轴抖动偏移量
shake_offset_.y = 0; //y轴抖动偏移量
break;
}
else
{
++current_shake_frame_; //判断震动次数+1
shake_offset_.x = rand() % 2 == 0 ? (10.f + rand() % 5) : (-10.f - rand() % 5);
shake_offset_.y = rand() % 2 == 1 ? (10.f + rand() % 5) : (-10.f - rand() % 5);
}
printf("current_shake_frame_ = %d\n", current_shake_frame_);
}
this->setPosition(Vec2(shake_offset_.x, shake_offset_.y));
}
4.验证效果:
两种方式:
第一种:
在新建项目的AppDelegate.cpp中引入头文件:
#include "ShakeLayer.h"
找到
auto scene = HelloWorldScene::createScene();
director->runWithScene(scene);
改为
auto scene = ShakeLayer::createScene();
director->runWithScene(scene);
第二种:
在当前场景中添加ShakeLayer层:
在当前场景的头文件中引入
#include "ShakeLayer.h"
在当前场景的init()中:
ShakeLayer* shake_layer = ShakeLayer::create();
this->addChild(shake_layer);
点击震动按钮看一下震动效果吧!!!
先自我满足一下,如有更好方法!请不吝赐教,感激不尽。
源码下载点这里哦!