Cocos2d-x 手游聊天系统Demo实现
转载请注明:IT_xiao小巫
本篇博客给大家分享的是一个手游聊天系统,笔者也是第一次使用Cocos2d-x来实现这样一个模块,其中有很多不清楚不明白的地方都是通过自己不断摸索实现的,前面笔者对聊天系统做的简单的需求分析,只是对聊天的一些元素进行的说明还不太够专业。本篇博客会给大家介绍如何实现一个手游聊天Demo,会从代码层面上给大家做相关的说明,如有不对或者错漏的地方请各位明确指出并纠正。
首先来给大家看一下动态效果图:
本篇博客内容大纲:
1. 加载Cocostudio制作的UI
2. Button的触摸事件监听
3. ListView添加列表项并设置列表点击事件
4. 富文本实现(可显示颜色文字和图片、动画)
5. 文本输入框实现(解决pc键盘无法删除字符的bug)
6. 动态往ListView添加列表项
一、加载Cocostudio制作的UI
笔者所分享的这个Demo是通过Cocostudio的UI编辑器制作的,童鞋们也可自己制作更加好看的UI,不过一般都会有美工帮我们做好让我使用的。如下图所示:
UI制作完之后,导出项目,然后把资源复制到我们项目的res目录下,笔者这里是把ChatUI_1复制到了res下,然后我们使用Lua代码实现加载json文件到我们的程序中去:
ChatScene.widget = ccs.GUIReader:getInstance():widgetFromJsonFile( "ChatUI_1/ChatUI_1.json" )
我们在编辑器添加了多个对象:
WorldPanel、PartyPanel、ChatPanel分别对应世界、公会、私聊三个板块,板块下面对应其相应的子节点:WordList、PartyList、ChatList。
我们需要在程序中找到它们:
--[[============================findViews()找到UI控件============================]]--function ChatScene.findViews() ChatScene.widget = ccs.GUIReader:getInstance():widgetFromJsonFile( "ChatUI_1/ChatUI_1.json" ) ChatScene.widget:setPosition( cc.p( 40, 40 ) ) loadListViewItemFromJson() -- 获得UI界面上的3个按钮 worldButton = ChatScene.widget:getChildByTag(6) partyButton = ChatScene.widget:getChildByTag(7) chatButton = ChatScene.widget:getChildByTag(8) -- 获得三个每个按钮对应的三个面板 wordPanel = ChatScene.widget:getChildByTag(5) partyPanel = ChatScene.widget:getChildByTag(9) chatPanel = ChatScene.widget:getChildByTag(10) -- 获得每个面板的ListView worldList = wordPanel:getChildByTag(13) partyList = partyPanel:getChildByTag(14) chatList = chatPanel:getChildByTag(15) -- 获得输入框 inputBox = ChatScene.widget:getChildByTag(11) sendButton = ChatScene.widget:getChildByTag(12) dialog = ChatScene.widget:getChildByTag(20) chat = dialog:getChildByTag(21) lahei = dialog:getChildByTag(22) closeButton = dialog:getChildByTag(27)end
每个UI对象有相应的Tag属性,我们可以通过找到其父节点,然后调用getChildByTag传进tag的值找到控件。只有找到这些控件,我们才能去使用它。
二、Button的触摸事件监听
笔者这个demo,通过监听“世界”、“公会”、“私聊”三个按钮来分别切换不同的板块,按钮的触摸监听事件很简单:
-- 设置按钮监听事件 worldButton:addTouchEventListener(touchEvent) partyButton:addTouchEventListener(touchEvent) chatButton:addTouchEventListener(touchEvent)
--[[touchEvent触摸事件回调方法]]--local function touchEvent( sender, eventType ) if sender:getTag() == TAG_WORLD_BUTTON then wordPanel:setVisible(true) partyPanel:setVisible(false) chatPanel:setVisible(false) dialog:setVisible(false) ChatScene.setCurrentTag( TAG_WORLD ) elseif sender:getTag() == TAG_PARTY_BUTTON then partyPanel:setVisible(true) wordPanel:setVisible(false) chatPanel:setVisible(false) dialog:setVisible(false) ChatScene.setCurrentTag( TAG_PARTY ) elseif sender:getTag() == TAG_CHAT_BUTTON then partyPanel:setVisible(false) wordPanel:setVisible(false) chatPanel:setVisible(true) dialog:setVisible(false) ChatScene.setCurrentTag( TAG_CHAT )end
以上面这种方式就可以实现切换三个板块了。
三、ListView添加列表项并设置列表点击事件
我们可以看到效果图里面每个板块下面有对应的列表,它是使用Cocos2d-x UI中的ListView所呈现的。
笔者感觉使用ListView比较麻烦,这里笔者给出相应的使用方法供大家参考:
--首先我们为ListView提供三组数据
-- 初始化三组数据 local array = {} for i = 1, 20 do array[i] = string.format("请叫我巫大大%d", i - 1) end local array1 = {} for i = 1, 20 do array1[i] = string.format("公会开放啦%d", i - 1 ) end local array2 = {} for i = 1, 20 do array2[i] = string.format("私聊列表项%d", i - 1 ) end
--设置默认模型
-- 创建模型 local default_button = ccui.Button:create("cocosui/backtotoppressed.png", "cocosui/backtotopnormal.png") default_button:setName("Title Button") -- 创建默认item local default_itme = ccui.Layout:create() default_itme:setTouchEnabled(true) default_itme:setContentSize(default_button:getContentSize()) default_button:setPosition(cc.p( default_itme:getContentSize().width / 2.0, default_itme:getContentSize().height / 2.0 )) default_itme:addChild(default_button) -- 设置模型 worldList:setItemModel(default_itme)
--添加自定义项
-- 获得数组的大小 local count = table.getn(array) print("count:"..count) -- 添加自定义item for i = 1, count do -- 创建一个Button local custom_button = ccui.Button:create("cocosui/button.png", "cocosui/buttonHighlighted.png") -- 设置Button名字 custom_button:setName("Title Button") -- 设置按钮使用九宫(scale9)渲染器进行渲染 custom_button:setScale9Enabled(true) -- 设置内容尺寸 custom_button:setContentSize(default_button:getContentSize()) -- 创建一个布局 local custom_item = ccui.Layout:create() -- 设置内容大小 custom_item:setContentSize(custom_button:getContentSize()) -- 设置位置 custom_button:setPosition(cc.p(custom_item:getContentSize().width / 2.0, custom_item:getContentSize().height / 2.0)) -- 往布局中添加一个按钮 custom_item:addChild(custom_button) -- 往ListView中添加一个布局 worldList:addChild(custom_item) end
--每一项数据
-- 设置item data items_count = table.getn(worldList:getItems()) for i = 1, items_count do -- 返回一个索引和参数相同的项. local item = worldList:getItem( i - 1 ) local button = item:getChildByName("Title Button") local index = worldList:getIndex(item) button:setTitleText(array[index + 1]) end
--设置ListView的点击事件和滚动事件
-- 设置ListView的监听事件 worldList:addScrollViewEventListener(scrollViewEvent) worldList:addEventListener(listViewEvent)
-- ListView点击事件回调local function listViewEvent(sender, eventType) -- 事件类型为点击结束 if eventType == ccui.ListViewEventType.ONSELECTEDITEM_END then print("select child index = ",sender:getCurSelectedIndex()) if dialog:isVisible() == true then dialog:setVisible(false) else ChatScene.showDialog() end endend-- 滚动事件方法回调local function scrollViewEvent(sender, eventType) -- 滚动到底部 if eventType == ccui.ScrollviewEventType.scrollToBottom then print("SCROLL_TO_BOTTOM") -- 滚动到顶部 elseif eventType == ccui.ScrollviewEventType.scrollToTop then print("SCROLL_TO_TOP") endend
四、 富文本实现(可显示颜色文字和图片、动画)
何为富文本?笔者的理解是有着丰富文本的展示方式,比如可以展示颜色文本、图片、动画、还有超链接的这种就叫富文本。以前旧的版本Cocos2d-x可能并未提供这方面的支持,至于是哪个版本支持的笔者也没有去深究,笔者这里使用版本是Cocos2d-x 3.2,它就提供了类似富文本的类,满足基本的需求。
代码实现:
--[[==================RichText富文本=================]]--function ChatScene.RichText() local richText = ccui.RichText:create() richText:ignoreContentAdaptWithSize(false) richText:setContentSize(cc.size(100, 100)) local re1 = ccui.RichElementText:create( 1, cc.c3b(255, 255, 255), 255, "This color is white. ", "Helvetica", 10 ) local re2 = ccui.RichElementText:create( 2, cc.c3b(255, 255, 0), 255, "And this is