Android开发(三):Android手机与Ubuntu系统使用socket无线通信(TCP协议)

一、准备工作

 

Android手机和和Ubuntu系统连接同一台路由器,即它们处在同一个网段下。

Android ip地址为:192.168.3.11

Ubuntu ip地址为:192.168.3.18

二、Ubuntu服务器(server)端

我们将Ubuntu设为服务器端,服务器端Python代码为:

import socket

HOST_IP = "192.168.3.18"  # 主机作为AP热点的ip地址
HOST_PORT = 7654  # 端口号

print("Starting socket: TCP...")
socket_tcp = socket.socket(socket.AF_INET, socket.SOCK_STREAM)  # 创建socket

print("TCP server listen @ %s:%d!" % (HOST_IP, HOST_PORT))
host_addr = (HOST_IP, HOST_PORT)
socket_tcp.bind(host_addr)  # 绑定主机的ip地址和端口号
socket_tcp.listen(1)  # listen函数的参数是监听客户端的个数,这里只监听一个,即只允许与一个客户端创建连接

while True:
    print('waiting for connection...')
    socket_con, (client_ip, client_port) = socket_tcp.accept()  # 接收客户端的请求
    print("Connection accepted from %s." % client_ip)

    send_str = "this is string example....wow!!!"
    send_byte=send_str.encode()
    socket_con.send(send_byte)  # 发送数据

    while True:
        data = socket_con.recv(1024)  # 接收数据

        if data:  # 如果数据不为空,则打印数据,并将数据转发给客户端
            print(data)
            socket_con.send(data)
            
socket_tcp.close()

三、Android客户(client)端

1、AndroidManifest.xml中添加权限

<uses-permission android:name="android.permission.INTERNET"/>
<uses-permission android:name="android.permission.ACCESS_WIFI_STATE"/>

2、activity_main.xml

<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
    xmlns:app="http://schemas.android.com/apk/res-auto"
    xmlns:tools="http://schemas.android.com/tools"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    android:orientation="vertical"
    tools:context=".MainActivity">

<TextView
    android:layout_width="match_parent"
    android:layout_height="wrap_content"
    android:text="设备控制"/>

<EditText
    android:layout_width="match_parent"
    android:layout_height="wrap_content"
    android:id="@+id/et_send"/>
<Button
    android:layout_width="match_parent"
    android:layout_height="wrap_content"
    android:text="发送"
    android:id="@+id/bt_send"/>

<TextView
    android:layout_width="match_parent"
    android:layout_height="wrap_content"
    android:text="接收到的信息:"/>

<TextView
    android:layout_width="match_parent"
    android:layout_height="wrap_content"
    android:id="@+id/tv_recv"/>

</LinearLayout>

3、MainActivity.java

package com.example.mysocket;

import android.os.Bundle;


import android.os.Handler;
import android.support.v7.app.AppCompatActivity;
import android.os.Bundle;
import android.view.View;
import android.widget.Button;
import android.widget.EditText;
import android.widget.TextView;

import java.io.BufferedReader;
import java.io.BufferedWriter;
import java.io.IOException;
import java.io.InputStream;
import java.io.InputStreamReader;
import java.io.OutputStream;
import java.io.OutputStreamWriter;
import java.io.PrintWriter;
import java.net.Socket;


public class MainActivity extends AppCompatActivity {

    private EditText et_send;
    private Button bt_send;
    private TextView tv_recv;

    private String send_buff=null;
    private String recv_buff=null;

    private Handler handler = null;

    Socket socket = null;

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);

        initView();

        handler = new Handler();

        //单开一个线程来进行socket通信
        new Thread(new Runnable() {
            @Override
            public void run() {
                try {
                    socket = new Socket("192.168.3.18" , 7654);
                    if (socket!=null) {
                        System.out.println("###################");
                        while (true) {      //循环进行收发
                            recv();
                            send();
                        }
                    }
                    else
                        System.out.println("socket is null");
                } catch (IOException e) {
                    e.printStackTrace();
                }
            }
        }).start();
        send();
    }


    private void recv() {

        //单开一个线程循环接收来自服务器端的消息
        InputStream inputStream = null;
        try {
            inputStream = socket.getInputStream();
        } catch (IOException e) {
            e.printStackTrace();
        }

        if (inputStream!=null){
            try {
                byte[] buffer = new byte[1024];
                int count = inputStream.read(buffer);//count是传输的字节数
                recv_buff = new String(buffer);//socket通信传输的是byte类型,需要转为String类型
                System.out.println(recv_buff);

            } catch (IOException e) {
                e.printStackTrace();
            }
        }
        //将受到的数据显示在TextView上
        if (recv_buff!=null){
            handler.post(runnableUi);

        }
    }

    //不能在子线程中刷新UI,应为textView是主线程建立的
    Runnable runnableUi = new Runnable() {
        @Override
        public void run() {
            tv_recv.append("\n"+recv_buff);
        }
    };

    private void send() {
        bt_send.setOnClickListener(new View.OnClickListener() {
            @Override
            public void onClick(View v) {
                new Thread(new Runnable() {
                    @Override
                    public void run() {
                        send_buff = et_send.getText().toString();
                        //向服务器端发送消息
                        System.out.println("------------------------");
                        OutputStream outputStream=null;
                        try {
                            outputStream = socket.getOutputStream();
                        } catch (IOException e) {
                            e.printStackTrace();
                        }

                        if(outputStream!=null){
                            try {
                                outputStream.write(send_buff.getBytes());
                                System.out.println("1111111111111111111111");
                                outputStream.flush();
                            } catch (IOException e) {
                                e.printStackTrace();
                            }
                        }

                    }
                }).start();

            }
        });
    }

    private void initView() {
        et_send = (EditText) findViewById(R.id.et_send);
        bt_send = (Button) findViewById(R.id.bt_send);
        tv_recv = (TextView) findViewById(R.id.tv_recv);
    }
}

四、测试结果

服务器端:

客户端:

 

五、参考

树莓派与Android客户端进行socket通信

安卓编程WiFi TCP通信错误

  • 1
    点赞
  • 17
    收藏
    觉得还不错? 一键收藏
  • 1
    评论
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值