Android即时通讯--仿QQ即时聊天:(一)初识Socket
2016-02-27 10:19
573 查看
1、即时通讯简介
即时通讯(Instant Messaging,简称IM)是一个终端服务,允许两人或者多人通过网络即时传递文字讯息、档案、语音等。简单的概括就是发送消息时,只要对方在线,就能立即接收到消息。即时通讯的底层使用socket实现。即时通讯按使用用途分为企业即时通讯和网站即时通讯,根据装载的对象又可分为手机即时通讯和PC即时通讯,手机即时通讯代表是微信、QQ、短信、陌陌。在这篇文章中,利用Socket+IO流+Thread线程+监听器的知识,简单的实现了点对点的即时通讯,功能比较丑陋,但是底层实现原理是非常重要的,希望这篇文章对初学者能有所帮助,大神勿进、勿喷。
本项目的效果图如下
2、初识Socket
所谓的Socket通常称为套接字,用于描述IP地址和端口,是一个通信连的句柄。应用程序通过套接字向网络发送请求,或者应答网络请求。Socket套接字,其实就是Java对TCP/IP的实现,Socket和ServerSocket可以形象的比喻为插头和插座,ServerSocket插座提供电源,是服务端;Socket插头要得到电源,是客户端。Socket网络通讯传输数据的过程就好比插头获取插座电源的过程。服务端:利用ServerSocket监听指定的端口,等待客户端的连接请求,客户端建立连接之后,产生会话,完成会话后,关闭连接。
客户端:利用Socket向网络上的某一个端口发出连接请求,一旦连接成功,产生会话,完成回话之后,关闭连接。
服务端接收消息代码
/** * socket服务端 * * @author ZHY * */ public class ServerSocketTest { public static void main(String[] args) throws IOException { final ServerSocket server = new ServerSocket(8090); System.out.println("服务器已经启动" + server); // 开启一个线程,时刻监听客户端发送过来的连接请求 new Thread() { public void run() { super.run(); while (true) { try { Socket client = server.accept();// 服务器接收到链接进来的客户端 System.out.println("有客户端链接进来" + client); // 处理接收到的数据 // 由于服务器不知道客户端什么时候发送数据过来,所以要创建等待线程,时刻等待处理客户端发送过来的额数据 WaitThread waitThread = new WaitThread(client); waitThread.start(); } catch (IOException e) { e.printStackTrace(); } } } }.start(); } // 等待线程 public static class WaitThread extends Thread { private Socket client; // 服务端使用输入流读取数据 private DataInputStream reader; // 在构造等待线程的时候,给客户端赋值 public WaitThread(Socket client) { super(); this.client = client; } public void run() { super.run(); // 循环等待处理数据 while (true) { if (reader == null) { // 根据客户端发来的输入流,创建服务器读取数据的流reader try { reader = new DataInputStream(client.getInputStream()); } catch (IOException e) { e.printStackTrace(); } } try { String msg = reader.readUTF(); System.out.println(msg); } catch (IOException e) { e.printStackTrace(); } } } } }客户端发送消息代码
/** * Socket客户端 * @author ZHY * */ public class MainActivity extends Activity { private Button client; private Button send; private Socket socket; private DataOutputStream writer; @Override protected void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); setContentView(R.layout.activity_main); client = (Button) findViewById(R.id.client);// 连接服务器 send = (Button) findViewById(R.id.send);// 发送数据 client.setOnClickListener(new OnClickListener() { public void onClick(View v) { // 连接服务器,与网络有关,要在子线程中 new Thread() { @Override public void run() { super.run(); try { // 创建socket,连接服务器 socket = new Socket("192.168.0.148", 8090); } catch (Exception e) { e.printStackTrace(); } } }.start(); } }); send.setOnClickListener(new OnClickListener() { public void onClick(View v) { // 客户端向服务端发送消息,通过输出流,在子线程中 new Thread() { @Override public void run() { super.run(); if (socket == null) { // 创建socket,连接服务器 try { socket = new Socket("192.168.0.148", 8090); } catch (UnknownHostException e) { // TODO Auto-generated catch block e.printStackTrace(); } catch (IOException e) { // TODO Auto-generated catch block e.printStackTrace(); } } // 已经建立了连接 if (writer == null) { try { writer = new DataOutputStream(socket .getOutputStream()); } catch (IOException e) { // TODO Auto-generated catch block e.printStackTrace(); } } // writer也不是空 try { writer.writeUTF("我是客户端发送的数据" + socket); } catch (IOException e) { e.printStackTrace(); } } }.start(); } }); } }客户端与服务端的数据交互会话示意图
至此,Socket的基本原理已经交代清楚,了解了底层实现的原理,相信对即时通讯的理解将更深一步。
PS:如果有什么不妥的地方希望大神指出,共同学习进步!!!
相关文章推荐
- Android-实现底部切换标签(fragment)
- 详解Android中AsyncTask的使用
- android管理SD卡 mksdcard
- Android 中的DisplayMetrics类的用法
- android 打造变化多端的SeekBar(垂直和水平)
- xamarin.forms 版本自动更新(针对android)
- android:ListView缓存机制及BaseAdapter的三重境界(逗比式,普通式,文艺式)
- Android 最火的快速开发框架XUtils
- Android如何定制化自己的开关机动画、开关机铃声
- android 让TextView自带滚动条
- Android本地数据安全尝试(中)——Conceal
- 浅谈Android App开发中Fragment的创建与生命周期
- android开发 不注意的异常
- Android如何查看应用签名信息
- Android.mk的一些FAQ
- 应用开机启动及相关文档翻译
- Android不规则瀑布流照片墙的实现+LruCache算法
- 个人进阶之路——自定义控件(5)
- android 8种对话框(Dialog)使用方法汇总
- Android Resources$NotFoundException异常