#ifndef DROPDOWNLIST_H_INCLUDED
#define DROPDOWNLIST_H_INCLUDED

namespace azl
{

#define DROPDOWNLIST_NORMAL_COLOR       cocos2d::ccc4(128, 128, 128, 255)
#define DROPDOWNLIST_SELECTED_COLOR     cocos2d::ccc4(200, 200, 200, 255)
#define DROPDOWNLIST_HIGHLIGHT_COLOR    cocos2d::ccc4(60, 60, 200, 255)

#define DROPDOWNLIST_NORMAL_COLOR3       cocos2d::ccc3(128, 128, 128)
#define DROPDOWNLIST_SELECTED_COLOR3     cocos2d::ccc3(200, 200, 200)
#define DROPDOWNLIST_HIGHLIGHT_COLOR3    cocos2d::ccc3(60, 60, 200)

class DropDownList : public cocos2d::CCLayer
{
public:
    class TouchHelper : public cocos2d::CCObject, public cocos2d::CCTouchDelegate
    {
    protected:
        TouchHelper(DropDownList& list)
            : list_(list)
        {
            cocos2d::CCDirector::sharedDirector()->getTouchDispatcher()->addTargetedDelegate(this, cocos2d::kCCMenuHandlerPriority, true);
        }

public:
        static TouchHelper* create(DropDownList& list)
        {
            return new TouchHelper(list);
        }

void destroy()
        {
            cocos2d::CCDirector::sharedDirector()->getTouchDispatcher()->removeDelegate(this);
            autorelease();
        }

virtual bool ccTouchBegan(cocos2d::CCTouch *touch, cocos2d::CCEvent *event)
        {
            list_.onClose();
            return true;
        }

DropDownList& list_;
    };

protected:
    DropDownList(cocos2d::CCLabelTTF* label, cocos2d::CCSize size)
        : label_(label)
        , show_(false)
        , lastSelectedIndex_(0)
        , helper_(NULL)
        , item_(NULL)
    {
        menu_ = cocos2d::CCMenu::create();
        menu_->setPosition(cocos2d::CCPoint(size.width / 2, size.height / 2));
        menu_->setVertexZ(0.1f);
        menu_->retain();

label_->setPosition(cocos2d::CCPoint(size.width / 2, size.height / 2));
        addChild(label_);

setContentSize(size);
    }

public:
    ~DropDownList()
    {
        menu_->release();
    }

static DropDownList* create(cocos2d::CCLabelTTF* label, cocos2d::CCSize size)
    {
        DropDownList* list = new DropDownList(label, size);
        list->autorelease();
        return list;
    }

std::string getString()
    {
        return label_->getString();
    }

int getSelectedIndex()
    {
        return lastSelectedIndex_;
    }

void setSelectedIndex(int index)
    {
        lastSelectedIndex_ = index;

for (int i = 0, j = (int)labels_.size(); i < j; ++i)
        {
            if (i == lastSelectedIndex_)
            {
                layers_[i]->setColor(DROPDOWNLIST_HIGHLIGHT_COLOR3);
                label_->setString(labels_[i]->getString());
            }
            else
            {
                layers_[i]->setColor(DROPDOWNLIST_NORMAL_COLOR3);
            }
        }
    }

void setDropMenuItem(cocos2d::CCMenuItem* item)
    {
        CC_ASSERT(item_ == NULL);
        item_ = item;

addChild(item_);

cocos2d::CCSize size = getContentSize();
        item_->setAnchorPoint(cocos2d::CCPoint(1.0f, 0.5f));
        item_->setPosition(size.width, size.height / 2.0f);

label_->setAnchorPoint(cocos2d::CCPoint(0.0f, 0.5f));
        label_->setPosition(cocos2d::CCPoint(4, size.height / 2.0f));
    }

public:
    void onEnter()
    {
        setTouchEnabled(true);
        cocos2d::CCLayer::onEnter();
    }

void registerWithTouchDispatcher()
    {
        cocos2d::CCDirector* pDirector = cocos2d::CCDirector::sharedDirector();
        pDirector->getTouchDispatcher()->addTargetedDelegate(this, cocos2d::kCCMenuHandlerPriority, true);
    }

virtual bool ccTouchBegan(cocos2d::CCTouch *touch, cocos2d::CCEvent *event)
    {
        if (!show_)
        {
            cocos2d::CCRect rect;
            rect.origin = cocos2d::CCPointZero;
            rect.size = getContentSize();
            cocos2d::CCPoint position = convertTouchToNodeSpace(touch);

if (rect.containsPoint(position))
            {
                show_ = true;
                helper_ = TouchHelper::create(*this);
                addChild(menu_);

for (int i = 0, j = (int)labels_.size(); i < j; ++i)
                {
                    if (i == lastSelectedIndex_)
                    {
                        layers_[i]->setColor(DROPDOWNLIST_HIGHLIGHT_COLOR3);
                    }
                    else
                    {
                        layers_[i]->setColor(DROPDOWNLIST_NORMAL_COLOR3);
                    }
                }

if (item_)
                {
                    item_->selected();
                }

return true;
            }
        }
       
        return false;
    }

void addLabel(cocos2d::CCLabelTTF* label)
    {
        cocos2d::CCSize size = getContentSize();

cocos2d::CCLayerColor* normal   = cocos2d::CCLayerColor::create(DROPDOWNLIST_NORMAL_COLOR, size.width, size.height);
        cocos2d::CCLayerColor* selected = cocos2d::CCLayerColor::create(DROPDOWNLIST_SELECTED_COLOR, size.width, size.height);

layers_.push_back(normal);
        labels_.push_back(label);
        
        cocos2d::CCMenuItem* item = cocos2d::CCMenuItemSprite::create(
                normal, 
                selected, 
                NULL,
                this,
                cocos2d::SEL_MenuHandler(&DropDownList::onSelected)
            );

label->setPosition(cocos2d::CCPoint(size.width / 2, size.height / 2));
        item->addChild(label);
        item->setTag((int)labels_.size() - 1);
        item->setPosition(0, - (int)labels_.size() * size.height);

menu_->addChild(item);
    }

void onSelected(cocos2d::CCObject* sender)
    {
        cocos2d::CCMenuItem* item = dynamic_cast<cocos2d::CCMenuItem*>(sender);

if (item)
        {
            lastSelectedIndex_ = item->getTag();
            label_->setString(labels_[item->getTag()]->getString());
        }

onClose();
    }

void onClose()
    {
        removeChild(menu_, true);
        
        helper_->destroy();
        helper_ = NULL;

show_ = false;

if (item_)
        {
            item_->unselected();
        }
    }

private:
    cocos2d::CCMenu* menu_;
    cocos2d::CCLabelTTF* label_;
    std::vector<cocos2d::CCLabelTTF*> labels_;
    std::vector<cocos2d::CCLayerColor*> layers_;
    bool show_;
    int lastSelectedIndex_;
    TouchHelper* helper_;
    cocos2d::CCMenuItem* item_;
};

}

#endif

cpp blog上面看到一哥们写的 下拉列表的更多相关文章

  1. c++ cpp和hpp

    首先,我们可以将所有东西都放在一个.cpp文件内,编译器会将这个.cpp编译成.obj,即编译单元.一个程序可以由一个编译单元组成,也可以由多个编译单元组成.一个.cpp对应一个.obj,然后将所有的 ...

  2. [转载]新功能:用微软的Live Writer离线写博文

    原文地址:Writer离线写博文">新功能:用微软的Live Writer离线写博文作者:新浪博客 Writer离线写博文" title="[转载]新功能:用微软的 ...

  3. C语言中头文件和cpp文件解析

    务必提前预读这里的内容:http://www.cnblogs.com/stemon/p/3999844.html 回到cpp文件与头文件各写什么内容的话题上: 理论上来说cpp文件与头文件里的内容,只 ...

  4. windows下用vscode写C++

    [本文参考:https://www.cnblogs.com/zhuzhenwei918/p/9057289.html  和 https://www.zhihu.com/question/3031589 ...

  5. Matlab与C++混合编程 1--在C++中调用自己写的matlab函数

    在Visual Studio中使用C++中调用MATLAB程序 在matlab中可以通过mbuild工具将.m文件编译成dll文件供外部的C++程序调用,这样就可以实现matlab和C++混合编程的目 ...

  6. 开始写博客的第一天,如何用c实现“hello wolrd”

    “hello world” 应该是大多数人学习的第一个代码 那也就作为我第一篇博客的开端吧 实现的代码如下 #include <stdio.h> int main() { printf(& ...

  7. 面向对象进阶时,if语句写错位置

    这周blog我也不知道要写什么,因为这章我其实学得有点懵,前面那几天我纠结了好久代码,一直不知道原因错在哪里.后来经过询问老师才知道自己调用错了构造方法,相信也有跟我一样的新手会犯这个错误.我在创建关 ...

  8. 写个续集,填坑来了!关于“Thread.sleep(0)这一行‘看似无用’的代码”里面留下的坑。

    "我报名参加金石计划1期挑战--瓜分10万奖池,这是我的第2篇文章,点击查看活动详情" 你好呀,我是居家十三天只出了一次小区门的歪歪. 这篇文章是来填坑的,我以前写文章的时候也会去 ...

  9. luac++

    Cocos2d-x下Lua调用自定义C++类和函数的最佳实践 洪亮 305 2014年08月09日 发布   1 推荐 21 收藏,14.9k 浏览 关于cocos2d-x下Lua调用C++的文档看了 ...

随机推荐

  1. 详解依赖注入(DI)和Ioc容器

    简单的来说,关键技术就是:注册器模式. 场景需求 我们知道写一个类的时候,类本身是有个目的的,类里面有很多方法,每个方法搞定一些事情:我们叫这个类为主类. 另外这个主类会依赖一些其他类的帮忙,我们叫这 ...

  2. RabbitMQ使用相关笔记

    #运行各示例脚本 [1] 1. 下载各语言的示例代码 https://github.com/rabbitmq/rabbitmq-tutorials 2. 安装pip,命令"yum -y in ...

  3. 关于Matrix的深入理解(对应值的功能)

    matrix是css3里面transform的一个集成表达式,它是以一个矩阵的方式来计算 transform:translate(apx,bpx)位移 transform: scale(a,b) 放缩 ...

  4. centos7下更改java环境

    1.上传下载的java包,如http://download.oracle.com/otn-pub/java/jdk/8u77-b03/jre-8u77-linux-x64.rpm,目录可以自己定义一个 ...

  5. C#编程利器之一:类(Class)【转】

    C#编程利器之一:类(Class) 面向对象的程序设计(Object-Oriented Programming,简记为OOP)是一种功能非常强大的编程方法,立意于创建软件重用代码,以类为基础去思考编程 ...

  6. php闭包实现函数的自调用,也是递归

    php的闭包可能不常用,但是在某些场合之下还是可以考虑用php的闭包来实现某些功能的,比如递归,这里讲一下用php的闭包实现递归 //php闭包实现函数的自调用,也就是实现递归 function cl ...

  7. IEnumerable 使用foreach 详解

    自己实现迭代器 yield的使用 怎样高性能的随机取IEnumerable中的值 我们先思考几个问题: 为什么在foreach中不能修改item的值? 要实现foreach需要满足什么条件? 为什么L ...

  8. [BS-27] 创建NSURL的几个方法的区别

    创建NSURL的几个方法的区别     URL的基本格式 = 协议://主机地址/路径 URL和Path的区别 * URL:统一资源定位符,格式 “协议+主机名称+路径”   例如:[NSURL UR ...

  9. synchronized同步块和volatile同步变量

    Java语言包含两种内在的同步机制:同步块(或方法)和 volatile 变量.这两种机制的提出都是为了实现代码线程的安全性.其中 Volatile 变量的同步性较差(但有时它更简单并且开销更低),而 ...

  10. 学习OpenCV——SVM 手写数字检测

    转自http://blog.csdn.net/firefight/article/details/6452188 是MNIST手写数字图片库:http://code.google.com/p/supp ...