利用Socket实现即时通信
在MyEclipse中写Server端
工程结构如图
SocketMessage.java
该类是一个消息类,用于表示消息是由谁发给谁的、消息内容是什么、接收时间是多少,只有几个属性,比较简单。
import server.MyServer.SocketThread;
public class SocketMessage {
public int to;//socketID,指发送给谁
public int from;//socketID,指谁发送过来的
public String msg;//消息内容
public String time;//接收时间
public SocketThread thread;//socketThread下面有介绍
}
MyServer.java
为Server的主要处理,详解在代码注释中
public class MyServer {
private boolean isStartServer;
private ServerSocket mServer;
/**
* 消息队列,用于保存SocketServer接收来自于客户机(手机端)的消息
*/
private ArrayList<SocketMessage> mMsgList = new ArrayList<SocketMessage>();
/**
* 线程队列,用于接收消息。每个客户机拥有一个线程,每个线程只接收发送给自己的消息
*/
private ArrayList<SocketThread> mThreadList = new ArrayList<SocketThread>();
/**
* 开启SocketServer
*/
private void startSocket() {
try {
isStartServer = true;
int prot = 2018;//端口可以自己设置,但要和Client端的端口保持一致
mServer = new ServerSocket(prot);//创建一个ServerSocket
System.out.println("启动server,端口:"+prot);
Socket socket = null;
int socketID = 0;//Android(SocketClient)客户机的唯一标志,每个socketID表示一个Android客户机
//分配给第一台设备的socketID为0
//开启发送消息线程
startSendMessageThread();
//用一个循环来检测是否有新的客户机加入
while(isStartServer) {
//accept()方法是一个阻塞的方法,调用该方法后,
//该线程会一直阻塞,直到有新的客户机加入,代码才会继续往下走
socket = mServer.accept();
//有新的客户机加入后,则创建一个新的SocketThread线程对象
SocketThread thread = new SocketThread(socket, socketID++);//为新加入的客户端分配的socketid默认自增
thread.start();
//将该线程添加到线程队列
mThreadList.add(thread);
}
} catch (Exception e) {
e.printStackTrace();
}
}
/**
* 开启推送消息线程,如果mMsgList中有SocketMessage,则把该消息推送到Android客户机
*/
public void startSendMessageThread() {
new Thread(){
@Override
public void run() {
super.run();
try {
/*如果isStartServer=true,则说明SocketServer已启动,
用一个循环来检测消息队列中是否有消息,如果有,则推送消息到相应的客户机*/
while(isStartServer) {
//判断消息队列中的长度是否大于0,大于0则说明消息队列不为空
if(mMsgList.size() > 0) {
//读取消息队列中的第一个消息
SocketMessage from = mMsgList.get(0);
for(SocketThread to : mThreadList) {
if(to.socketID == from.to) {