cocos2d-x 弹窗

PopupLayer.h

#include "cocos2d.h"
#include "cocos-ext.h"
USING_NS_CC;
USING_NS_CC_EXT;

class PopupLayer : public CCLayer{
public:
    PopupLayer();
    ~PopupLayer();
    virtual bool init();

    //需要重写触摸注册函数,重新给定触摸级别
    virtual void registerWithTouchDispatcher();
    //重写触摸函数,返回true,屏蔽其它层,达到“模态”效果
    bool ccTouchBegan(CCTouch *pTouch, CCEvent *pEvent);

    //静态创建函数,创建一个弹出层,设置背景图片
    static PopupLayer* create(const char* backgroundImage);

    //设置标题
    void setTitle(const char* title, int fontsize = 20);
        //设置文本内容,padding 为文字到对话框两边预留的距离,这是可控的,距上方的距离亦是如此
    void setContentText(const char* text, int fontsize=20, int padding=50, int paddingTop=100);

    //设置上层对象和上层回调函数,用于回调时传递CCNode参数
    void setCallBackFunc(CCObject* target, SEL_CallFuncN callfun);

    //添加menuItem按钮,封装了一个函数,传入些必要的参数
    bool addButton(const char* normalImage, const char* selectedImage, const char* title, int tag=0);

    //为了在显示层时的属性生效,选择在onEnter里动态生成
    virtual void onEnter();
    virtual void onExit();

    CREATE_FUNC(PopupLayer);

private:
    void buttonCallBack(CCObject* pSender);

    //文字内容两边的空白区域
    int m_contentPadding;
    int m_contentPaddingTop;
    CCObject* m_callbackListener;
    SEL_CallFuncN m_callback;
    //定义了CCMenu*类型变量m_pMenu, 并且直接定义默认的set/get方法
    CC_SYNTHESIZE_RETAIN(CCMenu*, m_pMenu, MenuButton);
    CC_SYNTHESIZE_RETAIN(CCSprite*, m_sfBackGround, SpriteBackGround);
    CC_SYNTHESIZE_RETAIN(CCScale9Sprite*, m_s9BackGround, Sprite9BackGround);
    CC_SYNTHESIZE_RETAIN(CCLabelTTF*, m_ltTitle, LabelTitle);
    CC_SYNTHESIZE_RETAIN(CCLabelTTF*, m_ltContentText, LabelContentText);
};

PopupLayer.cpp

#include "PopupLayer.h"
USING_NS_CC;

// 构造函数中变量设初值
PopupLayer::PopupLayer()
{
    m_contentPadding = 0;
    m_contentPaddingTop = 0;
    m_pMenu = NULL;
    m_callbackListener = NULL;
    m_callback = NULL;
    m_sfBackGround = NULL;
    m_s9BackGround = NULL;
    m_ltContentText = NULL;
    m_ltTitle = NULL;
}

//释放
PopupLayer::~PopupLayer()
{
    CC_SAFE_RELEASE(m_pMenu);
    CC_SAFE_RELEASE(m_sfBackGround);
    CC_SAFE_RELEASE(m_s9BackGround);
    CC_SAFE_RELEASE(m_ltContentText);
    CC_SAFE_RELEASE(m_ltTitle);
}

//初始化
bool PopupLayer::init()
{
    if ( !CCLayer::init() )
    {
    return false;
    }

    this->setContentSize(CCSizeZero);
    //初始化需要的Menu
    CCMenu* menu = CCMenu::create();
    menu->setPosition(CCPointZero);
    setMenuButton(menu);  //set()方法

    setTouchEnabled(true);  //开启触摸响应
    return true;
}

//重写触摸注册函数,重新给定触摸级别
void PopupLayer::registerWithTouchDispatcher()
{
    // 这里的触摸优先级设置为-128,与CCMenu同级,保证了屏蔽下方的触摸
    CCDirector::sharedDirector()->getTouchDispatcher()->addTargetedDelegate(this, -128, true);
}

//触摸函数ccTouchBegan,返回true
bool PopupLayer::ccTouchBegan( CCTouch *pTouch, CCEvent *pEvent )
{
    return true;
}

//创建一个弹出层,给背景精灵变量赋值
PopupLayer* PopupLayer::create( const char* backgroundImage ){
    PopupLayer* popup = PopupLayer::create();
    popup->setSpriteBackGround(CCSprite::create(backgroundImage));
    popup->setSprite9BackGround(CCScale9Sprite::create(backgroundImage));
    return popup;
}

//给标题变量赋值
void PopupLayer::setTitle( const char* title, int fontsize ){
    CCLabelTTF* ltfTitle = CCLabelTTF::create(title, "Arial", fontsize);
    ltfTitle->setColor(ccc3(0, 0, 0));
    setLabelTitle(ltfTitle);
}

//给文本变量赋值
void PopupLayer::setContentText( const char* text, int fontsize, int padding, int paddingTop ){
    CCLabelTTF* content = CCLabelTTF::create(text, "Arial", fontsize);
    content->setColor(ccc3(0, 0, 0));
    setLabelContentText(content);
    m_contentPadding = padding;
    m_contentPaddingTop = paddingTop;
}

//给下层层变量和回调函数变量赋值
void PopupLayer::setCallBackFunc( CCObject* target, SEL_CallFuncN callfun ){
    m_callbackListener = target;
    m_callback = callfun;
}

//给menu菜单变量添加Item
bool PopupLayer::addButton( const char* normalImage, const char* selectedImage, const char* title, int tag ){
    CCSize winSize = CCDirector::sharedDirector()->getWinSize();
    CCPoint center = ccp(winSize.width/2, winSize.height/2);

    // 创建图片菜单按钮
    CCMenuItemImage* menuImage = CCMenuItemImage::create(
    normalImage, selectedImage, this, menu_selector(PopupLayer::buttonCallBack));
    menuImage->setTag(tag);
    menuImage->setPosition(center);

    // 添加文字说明并设置位置
    CCSize menuSize = menuImage->getContentSize();
    CCLabelTTF* ttf = CCLabelTTF::create(title, "Arial", 15);
    ttf->setColor(ccc3(0, 0, 0));
    ttf->setPosition(ccp(menuSize.width/2, menuSize.height/2));
    menuImage->addChild(ttf);

    getMenuButton()->addChild(menuImage);
    return true;
}

//销毁弹出框,传递参数node给下层
void PopupLayer::buttonCallBack( CCObject* pSender ){
    CCNode* node = (CCNode *)pSender;
    CCLog("touch tag: %d", node->getTag());
    if (m_callback && m_callbackListener)
    {
    //执行HelloWorld层的回调函数,传递node参数
    (m_callbackListener->*m_callback)(node);
    }
    this->removeFromParentAndCleanup(true);
}

//全部参数都设定好后,在运行时动态加载
void PopupLayer::onEnter(){
    CCLayer::onEnter();

    CCSize winSize = CCDirector::sharedDirector()->getWinSize();
    CCPoint center = ccp(winSize.width/2, winSize.height/2);
    CCSize contentSize;
    // 设定好参数,在运行时加载
    if (getContentSize().equals(CCSizeZero)){
    getSpriteBackGround()->setPosition(center);
    this->addChild(getSpriteBackGround(),0,0);
    contentSize = getSpriteBackGround()->getTexture()->getContentSize();
    }
    else{
    CCScale9Sprite* background = getSprite9BackGround();
    background->setContentSize(getContentSize());
    background->setPosition(center);
    this->addChild(background, 0);
    contentSize = getContentSize();
    }

    //添加按钮,并根据Item的个数设置其位置
    this->addChild(getMenuButton());
    float btnWidth = contentSize.width / (getMenuButton()->getChildrenCount()+1);
    CCArray* array = getMenuButton()->getChildren();
    CCObject* pObj = NULL;
    int i = 0;
    CCARRAY_FOREACH(array, pObj){
        CCNode* node = (CCNode *)pObj;
        node->setPosition(ccp(winSize.width/2 - contentSize.width/2 + btnWidth*(i+1),
                                       winSize.height/2 - contentSize.height/3));
        i++;
    }

    // 显示对话框标题
    if (getLabelTitle()){
    getLabelTitle()->setPosition(ccpAdd(center, ccp(0, contentSize.height/2 - 25.0f)));
    this->addChild(getLabelTitle());
    }

    //显示文本内容
    if (getLabelContentText()){
    CCLabelTTF* ltf = getLabelContentText();
    ltf->setPosition(center);
    ltf->setDimensions(CCSizeMake(contentSize.width - m_contentPadding*2, contentSize.height - m_contentPaddingTop));
    ltf->setHorizontalAlignment(kCCTextAlignmentLeft);
    this->addChild(ltf);
    }

    //弹出效果
    CCSequence *popupActions = CCSequence::create(
    CCScaleTo::create(0.0, 0.0),
    CCScaleTo::create(0.06, 1.05),
    CCScaleTo::create(0.08, 0.95),
    CCScaleTo::create(0.08, 1.0), NULL);
    this->runAction(popupActions);
}

//退出
void PopupLayer::onExit(){
    CCLayer::onExit();
}

HelloWorldScene.h

#ifndef __HELLOWORLD_SCENE_H__
#define __HELLOWORLD_SCENE_H__

#include "cocos2d.h"

class HelloWorld : public cocos2d::CCLayer
{
public:
    // Method ‘init‘ in cocos2d-x returns bool, instead of ‘id‘ in cocos2d-iphone (an object pointer)
    virtual bool init();

    // there‘s no ‘id‘ in cpp, so we recommend to return the class instance pointer
    static cocos2d::CCScene* scene();

    // a selector callback
    void menuCloseCallback(CCObject* pSender);

    // preprocessor macro for "static create()" constructor ( node() deprecated )
    CREATE_FUNC(HelloWorld);

    void menuCallback(cocos2d::CCObject *pSender);
    void popupLayer();
    void buttonCallback(cocos2d::CCNode *pNode);
};

#endif // __HELLOWORLD_SCENE_H__

HelloWorldScene.cpp

#include "HelloWorldScene.h"
#include "SimpleAudioEngine.h"
#include "PopupLayer.h"

using namespace cocos2d;
using namespace CocosDenshion;

CCScene* HelloWorld::scene()
{
    // ‘scene‘ is an autorelease object
    CCScene *scene = CCScene::create();

    // ‘layer‘ is an autorelease object
    HelloWorld *layer = HelloWorld::create();

    // add layer as a child to scene
    scene->addChild(layer);

    // return the scene
    return scene;
}

// on "init" you need to initialize your instance
bool HelloWorld::init()
{
    //////////////////////////////
    // 1. super init first
    if ( !CCLayer::init() )
    {
        return false;
    }

    CCSize winSize = CCDirector::sharedDirector()->getWinSize();
    CCPoint pointCenter = ccp(winSize.width / 2, winSize.height / 2);

    // 添加背景图片
    CCSprite* background = CCSprite::create("HelloWorld.png");
    background->setPosition(pointCenter);
    background->setScale(1.5f);
    this->addChild(background);

     // 添加菜单
    CCMenu* menu = CCMenu::create();

    CCMenuItemFont* menuItem = CCMenuItemFont::create("popup", this, menu_selector(HelloWorld::menuCallback));
    menuItem->setPosition(ccp(winSize.width / 2, winSize.height / 2));
    menuItem->setColor(ccc3(0, 0, 0));
    menu->addChild(menuItem);

    menu->setPosition(CCPointZero);
    this->addChild(menu);

    return true;
}

void HelloWorld::menuCallback(cocos2d::CCObject *pSender){
    popupLayer();
}

void HelloWorld::popupLayer()
{
    // 定义一个弹出层,传入一张背景图片
    PopupLayer* popup = PopupLayer::create("HelloWorld.png");
    // ContentSize是可选的设置,可以不设置,如果设置则把它当做9图缩放
    popup->setContentSize(CCSizeMake(250, 260));
    popup->setTitle("Message");
    popup->setContentText("Most people... ", 20, 50, 150);
    // 设置回调函数,回调传回一个CCNode以获取tag判断点击的按钮
    // 这只是作为一种封装实现,如果使用delegate那就能够更灵活的控制参数了
    popup->setCallBackFunc(this, callfuncN_selector(HelloWorld::buttonCallback));
    //添加按钮,设置图片、文字,tag信息
    popup->addButton("CloseNormal.png", "CloseSelected.png", "Ok", 0);
    popup->addButton("CloseNormal.png", "CloseSelected.png", "Cancel", 1);
    this->addChild(popup);
}

void HelloWorld::buttonCallback(cocos2d::CCNode *pNode){
    CCLog("button call back. tag: %d", pNode->getTag());
}

void HelloWorld::menuCloseCallback(CCObject* pSender)
{
    CCDirector::sharedDirector()->end();

#if (CC_TARGET_PLATFORM == CC_PLATFORM_IOS)
    exit(0);
#endif
}

参考图:

转载自

http://blog.sina.com.cn/s/blog_705a5ff00101ox4s.html

http://www.tuicool.com/articles/VzAFJr

时间: 2024-08-03 10:26:44

cocos2d-x 弹窗的相关文章

cocos2dx --- 关于模态弹窗中按钮响应的问题

<span style="font-size:14px;">在自定义的模态弹窗中,因为注册了: </span> <span style="font-size:14px;">void WWDialog::registerWithTouchDispatcher(){ cocos2d::CCDirector::sharedDirector()->getTouchDispatcher()->addTargetedDelegat

ExtJs基础知识总结:弹窗(四)

概述 Extjs弹窗可以分为消息弹窗.对话框,这些弹窗的方式ExtJs自带的Ext.Msg.alert就已经可以满足简单消息提示,但是相对复杂的提示,比如如何将Ext.grid.Panel的控件显示嵌套到widget.window,然后随着widget.window的show方法展示到页面上哪?下面有几种方案思路 思路一.直接将gridpandel填充到widget.window对应的Items 代码如下: var InvoiceItemGrid = Ext.create('Ext.grid.P

android开发技巧——仿新版QQ锁屏下弹窗(转)

新版的qq,可以在锁屏下弹窗显示qq消息,正好目前在做的项目也需要这一功能.经过各种试验和资料查找,终于实现,过程不难,但是却有一些地方需要注意. 下面是实现过程. 1,使用Activity,而不是View QQ的弹窗一开始我以为是悬浮View,用WindowManager去添加,但是无论如何就是不显示,后来在朋友提示下换成Activity来实现,在锁屏状态下就能弹窗了. 2.Activity的设置 Activity需要进行以下设置,才可以在锁屏状态下弹窗. 首先是onCreate方法,需要添加

cocos2d::Vector

v3.0 beta加入 定义在"COCOS2DX_ROOT/cocos/base"的"CCVector.h"头文件中. template<class T>class CC_DLL Vector; cocos2d::Vector<T>是一个封装好的能动态增长顺序访问的容器. cocos2d::Vector<T>中的元素是按序存取的,它的低层实现数据结构是标准模版库中的标准顺序容器std::vector. 在Cocos2d-x v3.

VB.NET-QQ新闻弹窗样式图片制作工具

〇.下载地址 本程序的下载地址(百度网盘):http://pan.baidu.com/s/1qWBGGGG 一.关于本程序 Gnaea是一个QQ新闻弹窗的填字工具,可以在输入新闻标题和新闻内容后生成一张类似QQ新闻弹窗的图片.生成的图片可以被保存为BMP和PNG两种格式,或是直接复制到剪贴板. 效果如下图(注:内容纯属虚构) 二.程序控件 三.程序资源 被用作素材的资源:My.Resources.PopUp,取材于一张PNG格式的图片 四.程序代码 Imports System.Text Pub

背景为透明黑幕的遮罩弹窗

对整个页面进行透明黑色遮罩:单独显示一个框图,类似弹窗.用户可以看到整个页面,但只能对显示的框图内容进行操作:并且背景下的整个页面禁止用户操作. 代码: 1 <!DOCTYPE html> 2 <html> 3 <head> 4 <meta charset="utf-8"> 5 <title>测试</title> 6 7 8 9 <style type="text/css"> 10

Cocos2D中Action的进阶使用技巧(一)

大熊猫猪·侯佩原创或翻译作品.欢迎转载,转载请注明出处. 假设认为写的不好请多提意见,假设认为不错请多多支持点赞.谢谢! hopy ;) 大家对Cocos2d中动作的使用大概都非常清楚了,事实上本身action的概念也不复杂. 可是在某些情况下,一般的动作不能满足我们需求的时候,我们就必须使用更高级的Action方法来解决这个问题. 比方,串行化(不是序列化哦,这是两个全然不同的概念)不同Action的执行-有些童鞋可能会说非常easy,直接用CCActionSequence不就结了,可是等等我

Windows 关闭错误报告/弹窗

项目中需要第三方一个后台的第三方应用, 这就需要守护进程, 保证他一直在运行, 然而应用并不稳定. 在Win7,Win8,Win10中某些程序出错会出现Windows错误报告, 并且暂停应用不会退出, 这时候进程守护就会失效. 所以需要把错误报告弹窗关闭, 让程序发生错误后直接退出.  这样才能使守护进程生效. 一:注册表关闭弹窗(这个方法即可, 另一个可以顺便) 1.使用组合键"Win+R"打开运行窗口并输入"regedit"打开注册表编辑器窗口; 2.打开注册表

AJAX里使用的弹窗样式 tanchuang.js tanchuang.css

tanchuang.js // 每个弹窗的标识 var x =0; var idzt = new Array(); var Window = function(config){ //ID不重复 idzt[x] = "zhuti"+x; //弹窗ID //初始化,接收参数 this.config = { width : config.width || 300, //宽度 height : config.height || 200, //高度 buttons : config.button

定位弹窗广告软件

两个发现广告的经历,分享一下 前段时间曾经发现电脑有关于聚划算,天猫等的弹窗广告,找了很久发现一个隐藏在用户目录App Data下某个地方的Dandelion.exe(路径类似C:\Users\Administrator\AppData\Roaming\Dandelion) 软件签名是阿里巴巴,程序的日志连接了UC的服务器,如下: 最近又发现类似的广告,使用金山毒霸的弹窗定位器定位,竟然发现广告是金山弹出的,曾经有装完驱动精灵后出现弹窗广告的情况,而金山和驱动精灵的关系........