簡體   English   中英

如何在沒有服務器的情況下通過套接字連接兩個Android設備

[英]How can I connect two Android device by socket without server

我正在嘗試開發一個Android應用程序,可以在沒有服務器的情況下與其他設備進行對等連接的數據交換。 所以請建議我該怎么做。 先感謝您。

這是一個沒有服務器的SocketProgramming聊天的完整代碼。

在我的應用程序中,首先您是客戶端並搜索服務器。 當您找不到任何服務器時,您將成為服務器並等待客戶端。

public class MainActivity extends ActionBarActivity {

private Handler handler = new Handler();
private TextView text;
private EditText input;
private Button send;
private Socket socket;
private DataOutputStream outputStream;
private BufferedReader inputStream;
private String DeviceName = "Device";

private boolean searchNetwork() {
    log("Connecting");
    String range = "192.168.56.";
    for (int i = 1; i <= 255; i++) {
        String ip = range + i;
        try {
            socket = new Socket();
            socket.connect(new InetSocketAddress(ip, 9000), 50);
            outputStream = new DataOutputStream(socket.getOutputStream());
            inputStream = new BufferedReader(new InputStreamReader(
                    socket.getInputStream()));
            DeviceName += "1";
            Log.i("Server", DeviceName);
            log("Connected");
            return true;
        } catch (Exception e) {
        }
    }
    return false;

}

private void runNewChatServer() {
    ServerSocket serverSocket;
    try {
        serverSocket = new ServerSocket(9000);
        log("Waiting for client...");
        socket = serverSocket.accept();
        DeviceName += "2";
        log("a new client Connected");
    } catch (IOException e) {
    }

}

@Override
protected void onCreate(Bundle savedInstanceState) {
    super.onCreate(savedInstanceState);
    setContentView(R.layout.activity_main);
    text = (TextView) findViewById(R.id.text);
    input = (EditText) findViewById(R.id.input);
    send = (Button) findViewById(R.id.send);
    Thread thread = new Thread(new Runnable() {

        @Override
        public void run() {
            try {
                if (!searchNetwork()) {
                    runNewChatServer();

                }

                outputStream = new DataOutputStream(
                        socket.getOutputStream());
                inputStream = new BufferedReader(new InputStreamReader(
                        socket.getInputStream()));
                while (true) {

                    String Message = inputStream.readLine();
                    if (Message != null) {
                        log(Message);
                    }
                }
            } catch (IOException e) {
                log("Error: IO Exception");
                e.printStackTrace();
            }
        }
    });
    send.setOnClickListener(new OnClickListener() {

        @Override
        public void onClick(View arg0) {
            if (outputStream == null) {
                return;
            }
            try {
                String Message = input.getText().toString() + "\n";
                outputStream.write(Message.getBytes());
                log2(input.getText().toString());
            } catch (IOException e) {
                e.printStackTrace();
            }
            input.setText("");
        }
    });
    thread.start();

}

private void log(final String message) {
    handler.post(new Runnable() {
        String DeviceName2="";
        @Override
        public void run() {
            if (DeviceName.equals("Device1")) {
                DeviceName2 = "Device2";
            }else if(DeviceName.equals("Device2")) {
                DeviceName2 = "Device1";
            }else{
                DeviceName2 = "UnknowDevice";
            }

            text.setText(text.getText() + "\n" + DeviceName2 + " :"
                    + message);

        }
    });
}
private void log2(final String message) {
    handler.post(new Runnable() {

        @Override
        public void run() {


            text.setText(text.getText() + "\n" + "you" + " :"
                    + message);

        }
    });
}

@Override
public boolean onKeyDown(int keyCode, KeyEvent event) {
    if (keyCode == KeyEvent.KEYCODE_BACK) {
        if (socket != null) {
            try {
                socket.close();
            } catch (IOException e) {
                // TODO Auto-generated catch block
                e.printStackTrace();
            }
        }
        System.exit(0);
        return true;
    }
    return super.onKeyDown(keyCode, event);
}

}

Java提供ServerSocketSocket來與b / w設備進行通信。 您可以將其中一個設備作為服務器和其他設備,您可以作為客戶端進行通信,而無需在某些計算機上引入托管服務器。

其他更好的選擇是使用Wi-Fi Peer-to-Peer WifiP2pManager幫助您實現目標。 是一個例子。

如果您正在通過本地網絡尋找此類P2P,則有兩個部分:

  1. 發現同行
  2. 與同行溝通

在Android API中,您可以使用網絡服務發現APIWifi P2P服務發現API

有一個包裝庫,它在內部使用它們並具有相對更好的文檔 - Salut,也可以使用。

我還為P2P創建了一個庫 - Near ,它直接使用套接字。 我在Android API面臨的問題是,每次發現都沒有確定性,而且潛在的問題是未知的。

如果您正在尋找互聯網上的P2P, 套接字IO是一種流行的解決方案。 如果您提供IP地址並且它們不在NAT防火牆之后,即使近,也應該能夠促進傳輸。

你的設計有一個大問題:......

如果沒有中央服務器,一些Android設備應該充當客戶端而其他設備充當服務器但是在某些情況下這不起作用:

  • 當移動電話提供商分配私有和非公共IP時

  • 當設備連接到Wi-Fi網絡但路由器上未定義NAT規則時。

在這兩種情況下,問題是必須充當服務器的設備的偵聽端口是不可達的。

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM