码迷,mamicode.com
首页 > 其他好文 > 详细

做一个群组聊天页面

时间:2014-06-12 07:54:06      阅读:229      评论:0      收藏:0      [点我收藏+]

标签:style   class   blog   code   java   http   

要做个群组聊天的页面,参考微信的web版本,大致就是分为左右两列,左边是群组列表,右边是群组中的对话

示例图如下:

bubuko.com,布布扣

 

这个页面风格是使用ACE做的,再次啧啧下,ACE真TMD强大,这个页面的风格很招人喜欢。

 

做这个页面刚开始的时候我走了弯路,初步想的是使用iframe,左侧群组聊天页面是页面加载的,右侧的群组对话框是个iframe。然后点击左侧的任意一个群组,右侧的对话iframe就修改src,然后更新对话的时候也超简单,直接iframe重新加载一下就ok了。

但是呢,后来发现,我这样需要写的controller反而更多,一个iframe的controller,一个页面本身的controller,然后在两个iframe需要传递一些东西,特别是群组id。最大的困难就是更新,当我在iframe中发了一条消息之后,iframe中的条目能很快更新,但是外面的页面(由于是使用轮询)就没办法及时更新了。

后来总结了下,我整个页面就使用最统一的方式,html+jsonp的形式,使用一个页面controller,然后每个行为触发一个jsonp,整体做下来,结果就是js量极速增大。但是,不算坏事。

 

页面逻辑是这样:

首先页面初始加载群组列表

其次点击群组名称,同步加载出现右侧的对话框。注意这里是使用同步加载。因为从用户体验上,如果使用异步,点击了群组却没有出现对话框,会有bug的感觉。jquery的ajax是有提供jsonp和同步调用的:

代码:

bubuko.com,布布扣
$("[name=talk_talk]").click(function(event){
    event.preventDefault();

    var target = event.target;
    var mgid = $(target).attr("data-mgid");
    var action = "http://api.test/group/messageList"
    var params = "mgid=" + mgid;

    $.ajax({
        type: "get",
        dataType: "jsonp",
        async:false,
        url: action,
        data: params,
        jsonp: callback,
        jsonpCallback: callback231,
        success: function(data) {
            if (data.msg == ok) {
                var messages = data.messages;
                var users = data.users;
                var message_contents = ‘‘;
                for(var i=0; i< messages.length; i++) {
                    var message = messages[i];
                    var sid = message.sid;
                    var sender = users[sid];
                    message.sender = sender;
                    message_content = getDialogHTML(message);
                    message_contents = message_contents + message_content;
                }    
                $("#messages_show").html(message_contents);
                $("#messages_show").attr("cur_mgid", mgid);
                $("#group_unreadflag_" + mgid).hide();
                $("#widget-box-dialog").show();
            }
        }
    });
});
bubuko.com,布布扣

这里的ajax的dataType设置为jsonp表示是个jsonp请求,加上后面的jsonp和jsonpCallback,表示调用的时候我传递的请求带上了callback=callback231。

这里的jsonpCallback也是可以不写的,但是如果不写jquery会使用形如:callback_321342_324123这样的函数名来替换。但是我希望服务器端使用白名单机制来控制callback只能是字母和数字(Yii):

if (!empty($callback) && ctype_alnum($callback)) {
    echo "{$callback}(" . CJSON::encode($ret) . ")";
    Yii::app()->end();
}

所以我就手动设置了callback函数。相关的安全考虑我记得以前有一篇文章写过:http://www.cnblogs.com/yjf512/p/3222269.html

ajax的默认是异步的,所以要设置同步的话需要设置async:false。

 

接着就是轮询函数

服务端有个jsonp接口能根据我返回的最新时间,返回这个时间后我收到的所有群组消息。

代码几乎同上,不同的就是这个行为应该且必须是异步的。然后做两个事情:一件事情是如果左侧的群组有新消息,设置一个标志表示有新消息。另一个事情是如果右侧的对话显示的是当前这个群组的对话,就增加一个最新的消息放到上面。

 

然后是发送消息,基本同上。

好吧,主要还是秀一下ACE模板,看的爽。

做一个群组聊天页面,布布扣,bubuko.com

做一个群组聊天页面

标签:style   class   blog   code   java   http   

原文地址:http://www.cnblogs.com/yjf512/p/3782587.html

(0)
(0)
   
举报
评论 一句话评论(0
登录后才能评论!
© 2014 mamicode.com 版权所有  联系我们:gaon5@hotmail.com
迷上了代码!