首先建立一个html:<!DOCTYPE html><html lang="en"><head>    <meta charset="UTF-8">    <title>far</title>    <style>        #chatWindow{            font-family: 微软雅黑;            height:700px;            width:800px;            font-size:12px;/*字体大小*/            position: absolute;/*绝对定位*/            /*margin:auto;自动布局,容器居中*/            /*阴影效果*/            box-shadow: gray 0px 4px 5px;/*阴影:颜色*/

            display: none;/*开始不显示chatWindow这个div*/        }        #title{            height:40px;            line-height:40px;            /**/            /*背景渐变*/            background:-webkit-linear-gradient(left, #4B8CFE 0%,#ffffff 120%);            text-align: center;/*容器中的内容居中*/            color:white;/*字体颜色*/        }        #data{            height:400px;            border-top:1px solid gray;            border-bottom:1px solid gray;            overflow-y:auto;/*溢出部分显示滚动条*/            padding: 2px;        }        #util>a{            display: inline-block;            width: 30px;            height: 25px;            margin: 0 5px;        }        #util>a:hover{            background-color: gray;            border-radius: 4px;        }        #send{            height:180px;            padding: 5px;/*上下左右都和输入内容有点(5px)距离*/            outline: none;/*去掉边框*/            overflow-y:auto;/*溢出部分显示滚动条*/        }        #btns{            text-align: right;            padding-right: 10px;/*盒子的内容距离边框的距离,简称内距离*/        }        .btnSetting{/* .代表class*/            width:72px;            height:28px;            display: inline-block;/*转成行块标签*/            line-height: 28px;            border:1px solid gray;            font-size:12px;font-family:"微软雅黑";text-align: center;            border-radius: 3px;/*圆角*/            text-decoration: none;/*去除下划线*/            margin-right:10px;/*外间距,盒子与别的盒子的距离*/            vertical-align: 1px;/*垂直位置上的调整*/        }        .i1{            background:url("/images/1.jpg") no-repeat center;        }        .i2{            background: url("/images/2.jpg") no-repeat center;        }        .i3{            background: url("/images/3.jpg") no-repeat center;        }        .dataBox{            border-radius: 5px;            padding: 3px;            background-color: #66afe9;            color:black;            width:auto;/*内容不固定大小,多少内容就用多少空间,可换行*/            display: inline-block;            margin-left: 10px;        }        .fright{            float:right;            clear: both;            text-align: right;        }        .fleft{            float:left;            clear: both;        }        .dou{            clear:both;            text-align: center;            line-height: 30px;            border-radius: 5px;            background-color: #4B8CFE;        }        #closeBtn {            color: black; /*字体颜色*/        }        #closeBtn:hover{            background-color: #EFEFF0;        }        #sendBtn {            background-color: #4B8CFE;            color:white;/*字体颜色*/        }        #sendBtn:hover{            background-color: #47C8F8;        }    </style>    <link rel="stylesheet" href="/css/facebox.css">    <script src="js/jquery-2.1.1.min.js"></script>    <script src="js/jquery.qqFace.js"></script>    <script>        var ws;        //#:找到id为chatBtn的节点,绑定一个点击事件 $符号代表框架。        $(document).ready(function () {        $("#chatBtn").click(function () {            //找到nickName获取val值。            var nickName = $("#nickName").val();            if ($.trim(nickName) == "") {//trim()函数的作用是去掉左右两边的空格。                alert("请输入昵称!");                return;//结束该函数            }            var url = "ws://" + window.location.hostname + ":8080/chatHandle/" + nickName;            //var url1="ws://"+window.location.hostname+":8080/chatHandle/"+fang;            //document.write(url+url1);            ws = new WebSocket(url);            //当后台服务器发了消息的时候,获取到后台消息            ws.onmessage=function (chatBtn) {                var index=chatBtn.data.indexOf("\0");                if(index>=0) {                    dou();                }                $("#data").scrollTop(520);                $("#data").append(chatBtn.data+"<br>");            }            $("#join").hide();            $("#chatWindow").show();            /*            关闭按钮            */            $("#closeBtn").click(function () {                ws.close();//关闭客户端与服务端的连接                $("#join").show();                $("#chatWindow").hide();            })            /*            发送按钮            */            $("#sendBtn").click(function () {                var val=$("#send").html();                //清空                $("#send").html("");                //聚焦                $("#send").focus();                //获取并发送                ws.send(val);            })            //添加快捷键            $("#send").keydown(function (event) {                if(event.altKey && event.keyCode==67){                    $("#closeBtn").click();//模拟手动点击,代码点击;                }                if((event.altKey && event.keyCode==83)|| event.keyCode==13){                    $("#sendBtn").click();//模拟手动点击发送按钮,代码点击;                }            })        })            var reader=new FileReader();            var myFile=document.getElementById("myFile");            myFile.onchange=function () {                var chooseFile=myFile.files[0];                reader.readAsDataURL(chooseFile);            }            reader.onload=function () {                var obj=document.createElement("img");                obj.src=reader.result;                $("#send").append(obj);            }            $("#myFile").hide();            $(".i1").click(function () {                $("#myFile").click();            })            $(".i2").qqFace({                id:'facebox',                assign:'send',                path:'arclist/'            })            /*拖拽部分*/            var title=document.getElementById("title");            var pyx,pyy;            title.ondragstart=function (e) {                pyx=e.offsetX;                pyy=e.offsetY;            }            title.ondrag=function (e) {                var x=e.pageX;                var y=e.pageY;                if(x==0&&y==0)   return;                $("#chatWindow").css("left",x-pyx);                $("#chatWindow").css("top",y-pyy);            }            $(".i3").click(function () {                ws.send("\0");            })            function dou() {                var initx=$("#chatWindow").offset().left;                var inity=$("#chatWindow").offset().top;                for(var i=0;i<=10;i++){                    $("#chatWindow").animate({"left":initx-10,"top":inity-10},10);                    $("#chatWindow").animate({"left":initx,"top":inity},10);                    $("#chatWindow").animate({"left":initx+10,"top":inity+10},10);                    $("#chatWindow").animate({"left":initx,"top":inity},10);                }            }        })    </script></head><body><div id="join"><!-----div可以看成一个盒子,容器。固定页面布局。CSS(放head里面)相当对html的"化妆";------->    <input id="nickName" type="text"><br>    <input id="chatBtn" type="button" value="加入聊天室"><br></div><div id="chatWindow">    <div id="title" draggable="true">far away</div>    <div id="data"></div><!----聊天内容------->    <div id="util"><!--工具区域-->    <input type="file" id="myFile">    <a class="i1" href="javascript:;"></a>    <a class="i2" href="javascript:;"></a>    <a class="i3" href="javascript:;"></a></div>    <div id="send" contenteditable="true"></div><!----要发送内容------->    <div id="btns"><!------发送和关闭按钮-------->        <a id="closeBtn" class="btnSetting" href="javascript:;">关闭(<u>C</u>)</a>        <a id="sendBtn" class="btnSetting" href="javascript:;">发送(<u>S</u>)</a>    </div></div></body></html>

后台控制代码:
package com.seecon.Chat.handle;

import javax.websocket.OnClose;import javax.websocket.OnMessage;import javax.websocket.OnOpen;import javax.websocket.Session;import javax.websocket.server.ServerEndpoint;import javax.websocket.server.PathParam;import java.util.ArrayList;import java.util.Calendar;import java.util.List;

@ServerEndpoint("/chatHandle/{nickName}")public class ChatHandle {    //创建一个静态的“袋子”(跟对象无关),用来装所有的session,也就是所有用户的会话;    private static List<Session> users=new ArrayList<Session>();//static可以共享。    public static synchronized void add(Session session){//静态方法不依赖对象        users.add(session);    }    public synchronized  static void remove(Session session){        users.remove(session);    }    private void sendAll(String message){        for (Session user : users) {            user.getAsyncRemote().sendText(message);        }    }    private String nickName;/*当前会话的昵称*/    @OnOpen    public void connect(Session session,@PathParam("nickName") String nickName) throws Exception {        System.out.println(nickName + "连接上了后台服务器程序" + session);        add(session);        sendAll("<div class='fleft'>-----欢迎[" + nickName + "]------加入聊天室  "+"当前聊天室人数:"+users.size()+"</div>");        this.nickName=nickName;    }    @OnClose    public void exit(Session session,@PathParam("nickName") String nickName) throws Exception{        remove(session);        sendAll("<div class='fright'>----[" + nickName + "]------退出聊天室"+"当前聊天室人数:"+users.size()+"</div>");    }    @OnMessage    public void receiveMessage(Session session,String message) throws Exception{        Calendar c=Calendar.getInstance();        int hour=c.get(Calendar.HOUR_OF_DAY);        String hourStr=hour>=10?hour+"":"0"+hour;        int minute=c.get(Calendar.MINUTE);        String minuteStr=minute>=10?minute+"":"0"+minute;        int second=c.get(Calendar.SECOND);        String secondStr=second>=10?second+"":"0"+second;        String fullTime=hourStr+":"+minuteStr+":"+secondStr;        //构建message        if(message.equals("\0")){            message="<div class='dou'>"+nickName+"给您发送了一个窗口抖动</div>";            String str="&nbsp;&nbsp;"+fullTime+"<br>"+message;            sendAll("\0"+str);        }else {            message = "<div class='dataBox'>" + message + "</div>";            String str = nickName + "&nbsp&nbsp" + fullTime + "<br>" + message;            sendAllMessage(str, session);        }    }    private void sendAllMessage(String message,Session session){        //把Message的数据通知给所有会话        for(Session user:users){            if(user==session){                user.getAsyncRemote().sendText("<div class='fright'>"+message+"</div>");            }            else{                user.getAsyncRemote().sendText("<div class='fleft'>"+message+"</div>");

            }        }    }

}

类似QQ的聊天工程的更多相关文章

  1. java网络编程(三):一个类似QQ的聊天程序

    客户端: package QQ; import javax.swing.*; import java.awt.*; import java.awt.event.ActionEvent; import ...

  2. AndroidRichText 让Textview轻松的支持富文本(图像ImageSpan、点击效果等等类似QQ微信聊天)

    代码地址:https://github.com/Luction/AndroidRichText AndroidRichText帮助实现像QQ,微信一样的,一个TextView里既有文字又有表情又有图片 ...

  3. 实现类似QQ对话聊天功能脚本

    var skin : GUISkin; var showChat = false;private var inputField = "";private var display = ...

  4. [C# 网络编程系列]专题九:实现类似QQ的即时通信程序

    转自:http://www.cnblogs.com/zhili/archive/2012/09/23/2666987.html 引言: 前面专题中介绍了UDP.TCP和P2P编程,并且通过一些小的示例 ...

  5. 基于Qt的类QQ气泡聊天的界面开发

    近期在写IM 聊天界面,想设计出一个类似QQ气泡聊天的样式 使用了几种办法 1:使用Qt以下的QListview来实现QQ类似效果.差强人意 2:使用QWebview载入html css样式来完毕.发 ...

  6. 详解C# 网络编程系列:实现类似QQ的即时通信程序

    https://www.jb51.net/article/101289.htm 引言: 前面专题中介绍了UDP.TCP和P2P编程,并且通过一些小的示例来让大家更好的理解它们的工作原理以及怎样.Net ...

  7. 转:【专题九】实现类似QQ的即时通信程序

    引言: 前面专题中介绍了UDP.TCP和P2P编程,并且通过一些小的示例来让大家更好的理解它们的工作原理以及怎样.Net类库去实现它们的.为了让大家更好的理解我们平常中常见的软件QQ的工作原理,所以在 ...

  8. 专题九:实现类似QQ的即时通信程序

    引言: 前面专题中介绍了UDP.TCP和P2P编程,并且通过一些小的示例来让大家更好的理解它们的工作原理以及怎样.Net类库去实现它们的.为了让大家更好的理解我们平常中常见的软件QQ的工作原理,所以在 ...

  9. MVC实现类似QQ的网页聊天功能-ajax(下)

    此篇文章主要是对MVC实现类似QQ的网页聊天功能(上)的部分代码的解释. 首先说一下显示框的滚动条置底的问题: 结构很简单一个大的div(高度一定.overflow:auto)包含着两个小的div第一 ...

随机推荐

  1. Css3新增背景属性

    1.background-origin 背景的起始位置 background-origin: border-box || padding-box || content-box; 案例初始化: 代码: ...

  2. js常用代码-笔记

    1.字符串截取substr(str,length)返回从指定位置开始,截取length长度的子字符串.substring(start,end)返回从start开始到end结束的字符串.end不写就到结 ...

  3. 织梦后台添加友情链接的方法(flink标签)

    标记名称:flink[标签简介][功能说明]:用于获取友情链接,其对应后台文件为"includetaglibflink.lib.php".[适用范围]:全局标记,适用V55,V56 ...

  4. Java集合排序

    [ 1.对普通的包装类基本数据类型的list数组排序(Integer,Long,Double) ] Collections.sort(List list) [例] List<Long> m ...

  5. WebService性能测试

    什么是WebService?(本文也会在最下面通俗的介绍) 这里给一个站内大哥的讲解:http://www.cnblogs.com/Leo_wl/archive/2010/05/20/1740205. ...

  6. js前台检测上传图片大小的总结

    最近一直在做上传图片的前端检测,不通过后台就完成这个动作.但实际是,实际效果差强人意. html5的fileApi出来后,对文件的处理才变得方便了些,对它的简单介绍可以看我的前面的博客.现在支持的浏览 ...

  7. SQL Server ->> 利用CONVERT/STR/FORMAT函数把浮点型数据格式化/转换成字符串

    在SQL Server下想把数字(包括浮点型和整型)转换成字符串,保留数据原本的样子或者根据需要转换成另外指定的格式可能就不仅仅是一条CAST(XXXX AS NVARCHAR)这么简单的事情了. 无 ...

  8. 24点-code1

    #include <iostream> #include <string> #include <cstdlib> #include <cmath> us ...

  9. C++ 源代码到可执行代码的详细过程

    编译,编译程序读取源程序(字符流),对之进行词法和语法的分析,将高级语言指令转换为功能等效的汇编代码,再由汇编程序转换为机器语言,并且按照操作系统对可执行文件格式的要求链接生成可执行程序. 源代码-- ...

  10. 电脑断电后Everything部分文件搜索不到的解决办法

    常规检查:查看选项→索引→NTFS,确认所有分区都[包含到数据库],确认后,再删除数据库文件,点击[强制重建] 下面方法是亲身经历,是断电造成的,费了不少时间才解决,现分享出来: 断电后,Everyt ...