Android中socket初体验

  最近要做一个Android的项目,用到socket和服务器之间交互,研究了一个小demo。主要遇到了以下几个问题:

  1.客户端创建socket对象时一直失败NetworkOnMainThreadException,查了一下,原因是4.0之后在主线程中执行http请求会报这个错。解决办法是将代码放到了一个新线程中,问题就解决了。

  2.服务器接收到客户端信息后反馈给客户端信息,将该信息表示在客户端UI上时报“android.view.ViewRoot$CalledFromWrongThreadException: Only the original thread that created a view hierarchy can touch its views.”异常。该问题原因是,在主线线程之外的线程中直接更新页面显示常会报错。解决办法是通过runOnUiThread方法将线程对象传过去,这样在主线程中就能执行该线程的内容了,当然还有其他办法。可参考链接http://blog.csdn.net/shenyuemei/article/details/11030679

  

  下面是程序代码:

  布局文件

<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    android:orientation="vertical" >
    
    <EditText
        android:id="@+id/content"
        android:layout_width="match_parent"
        android:layout_height="wrap_content"
        android:hint="@string/et_hint" />

    <Button
        android:id="@+id/send"
        android:layout_width="match_parent"
        android:layout_height="wrap_content"
        android:text="@string/txt_send" />
    
       <TextView
        android:id="@+id/tv"
        android:layout_width="match_parent"
        android:layout_height="wrap_content" />
</LinearLayout>

服务端代码

package testDemo;

import java.io.BufferedReader;
import java.io.BufferedWriter;
import java.io.InputStreamReader;
import java.io.OutputStreamWriter;
import java.io.PrintWriter;
import java.net.ServerSocket;
import java.net.Socket;

public class Server implements Runnable {
    public static void main(String[] args) {
        Thread desktopServerThread = new Thread(new Server());
        desktopServerThread.start();
    }

    @Override
    public void run() {
        try {
            ServerSocket serverSocket = new ServerSocket(8888);
            while (true) {
                
                // 阻塞,等待接收客户请求。
                Socket client = serverSocket.accept();
                System.out.println("接受到客户端的请求。");
                try {
                    BufferedReader in = new BufferedReader(
                            new InputStreamReader(client.getInputStream()));
                    // 读取客户端发过来的信息
                    String read = in.readLine();
                    System.out.println("客户端发送消息为 : " + read);

                    // 向客户端返回信息
                    PrintWriter out = new PrintWriter(new BufferedWriter(
                            new OutputStreamWriter(client.getOutputStream())));
                    if (read != null) {
                        out.println("你发送给服务器的信息为 : " + read);
                        out.flush();
                    }    

                    out.close();
                    in.close();

                } catch (Exception e) {
                    e.printStackTrace();
                } finally {
                    client.close();
                }
            }
        } catch (Exception e) {
            e.printStackTrace();
        }

    }

}

客户端代码

import java.io.BufferedReader;
import java.io.BufferedWriter;
import java.io.IOException;
import java.io.InputStreamReader;
import java.io.OutputStreamWriter;
import java.io.PrintWriter;
import java.net.InetAddress;
import java.net.Socket;
import java.net.UnknownHostException;

import android.app.Activity;
import android.os.Bundle;
import android.os.Handler;
import android.os.Message;
import android.view.View;
import android.view.View.OnClickListener;
import android.widget.Button;
import android.widget.EditText;
import android.widget.TextView;

public class ClientActivity extends Activity {

    private Button send = null;
    private EditText content = null;
    private TextView tv = null;
    String msg = null;
    
    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.socket2);
        
        send = (Button)findViewById(R.id.send);
        content = (EditText)findViewById(R.id.content);
        tv = (TextView)findViewById(R.id.tv);
        
        send.setOnClickListener(new OnClickListener(){

            @Override
            public void onClick(View v) {
                setTitle("socket");
                new Thread(thread1).start();
            }
            
        });
    }
    
    /*Handler myHandler = new Handler() {
        
        @Override
        public void handleMessage(Message msg) {
            myHandler.post(thread1);
        }
    };*/
    
    /**
     * 该线程主要是向服务器发送消息和接收消息
     */
    Runnable thread1 = new Runnable() {

        @Override
        public void run() {
            Socket socket = null;
            try {
                InetAddress serverAddr = InetAddress.getByName("192.168.1.110");
                
                socket = new Socket(serverAddr, 8888);
                //想服务器发送消息
                PrintWriter out = new PrintWriter(new BufferedWriter(new OutputStreamWriter(socket.getOutputStream())));
                out.println(content.getText().toString());
                out.flush();
                
                //读取服务器返回的消息
                BufferedReader in = new BufferedReader(new InputStreamReader(socket.getInputStream()));
                msg = in.readLine();
                //把该子线程当做参数传递,这样在主UI线程就可更新UI
                ClientActivity.this.runOnUiThread(updateThread);
                
            } catch (UnknownHostException e) {
                e.printStackTrace();
            } catch (IOException e) {
                e.printStackTrace();
            }
        }
        
    };
    
    Runnable updateThread = new Runnable() {

        @Override
        public void run() {
            if (msg != null) {
                tv.setText(msg);
            } else {
                tv.setText("data error.");
            }
        }
        
    };

}

 

Android中socket初体验,布布扣,bubuko.com

Android中socket初体验

上一篇:dr-helper项目设计介绍(一个包含移动端和Web端的点餐管理系统)


下一篇:安卓Activity生命周期(转)