Android局域网内快速查找某个设备的IP地址(UDP通信)

news/2024/5/18 14:08:59 标签: udp, 局域网

需求:通过udp传输方式,快速找到同局域网内某设备
思路:需要某设备发送,手机接收。或者手机发送,设备接收,两个设备需在同一局域网
1、建立udpsocket服务
2、提供数据,并将数据封装到数据包中
3、通过socket服务的发送功能,将数据包发送出去。
4、关闭资源。
DatagramSocket:此类表示用来发送和接收数据报包的套接字。在 DatagramSocket 上总是启用 UDP 广播发送。
DatagramPacket:此类表示数据报包。数据报包用来实现无连接包投递服务。每条报文仅根据该包中包含的信息从一台机器路由到另一台机器。从一台机器发送到另一台机器的多个包可能选择不同的路由,也可能按不同的顺序到达。不对包投递做出保证。

先看个图:

UDP发送数据
在这里插入图片描述
UDP接收数据
在这里插入图片描述

具体代码如下:

<?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=".ui.activity.TestActivity">

    <Button
        android:id="@+id/btn_send"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:text="发送" />

    <Button
        android:id="@+id/btn_wait"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:text="开始等待接收" />

    <ScrollView
        android:layout_width="match_parent"
        android:layout_height="wrap_content">


        <TextView
            android:id="@+id/tv_data"
            android:layout_width="wrap_content"
            android:layout_height="wrap_content"
            android:text="-------------" />
    </ScrollView>
</LinearLayout>
package com.fzm.coldwallet.ui.activity;

import android.os.Bundle;
import android.os.Handler;
import android.os.Message;
import android.util.Log;
import android.view.View;
import android.widget.Button;
import android.widget.TextView;

import com.fzm.coldwallet.R;
import com.fzm.coldwallet.ui.base.BaseActivity;
import com.fzm.coldwallet.utils.ToastUtils;

import java.io.IOException;
import java.net.DatagramPacket;
import java.net.DatagramSocket;
import java.net.InetAddress;
import java.net.SocketException;
import java.text.SimpleDateFormat;
import java.util.Date;
import java.util.Timer;
import java.util.TimerTask;

import butterknife.BindView;
import butterknife.ButterKnife;
import butterknife.OnClick;

public class TestActivity extends BaseActivity {

    @BindView(R.id.btn_send)
    Button btnSend;
    @BindView(R.id.btn_wait)
    Button btnWait;
    @BindView(R.id.tv_data)
    TextView tvData;
    private MainHandle mMainHandle;

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_test);
        ButterKnife.bind(this);
        mMainHandle = new MainHandle();

    }

    @OnClick({R.id.btn_send, R.id.btn_wait})
    public void onViewClicked(View view) {
        switch (view.getId()) {
            case R.id.btn_send:
                sendMsg();
                break;
            case R.id.btn_wait:
                new Thread(new Runnable() {
                    @Override
                    public void run() {
                        waitMsg();
                    }
                }).start();
                break;
        }
    }

    private String sLog = "";

    private void sendMsg() {
        try {
            final DatagramSocket hostSocket = new DatagramSocket();
            // 设置接收超时时间
            hostSocket.setSoTimeout(1500);
            final String sendData = "my name is zzz";
            InetAddress broadIP = InetAddress.getByName("255.255.255.255");
            final DatagramPacket sendPack = new DatagramPacket(sendData.getBytes(), sendData.length(), broadIP, 9901);

            new Timer().schedule(new TimerTask() {
                @Override
                public void run() {
                    String log = sendData + new SimpleDateFormat("yyyy-MM-dd HH:mm:ss").format(new Date()) + "\n";
                    Log.v("tag", Thread.currentThread() + log);
                    if (sLog.split("\n").length > 10) {
                        sLog = "";
                    }
                    try {
                        hostSocket.send(sendPack);
                        sLog += log;
                        runOnUiThread(new Runnable() {
                            @Override
                            public void run() {
                                tvData.setText(sLog);
                            }
                        });
                    } catch (Exception e) {
                        e.printStackTrace();
                    }

                }
            }, 0, 1000);


        } catch (Exception e) {
            e.printStackTrace();
        }

    }


    private String rLog = "";

    private void waitMsg() {
        byte[] buffer = new byte[1024];
        /*在这里同样使用约定好的端口*/
        int port = 9901;
        DatagramSocket server = null;
        try {
            server = new DatagramSocket(port);
            final DatagramPacket packet = new DatagramPacket(buffer, buffer.length);
            while (true) {
                // 等待主机的搜索
                try {
                    server.receive(packet);
                    final String s = new String(packet.getData(), 0, packet.getLength(), "UTF-8");
                    String log = packet.getAddress() + ",port:" + packet.getPort() + "," + s + "\n";
                    Log.v("tag", log);
                    rLog += log;
                    if (rLog.split("\n").length > 10) {
                        rLog = "";
                    }
                    mMainHandle.sendEmptyMessage(1);

                } catch (IOException e) {
                    e.printStackTrace();
                }
            }
        } catch (SocketException e) {
            e.printStackTrace();
        } finally {
            if (server != null)
                server.close();
        }
    }

    class MainHandle extends Handler {
        @Override
        public void handleMessage(Message msg) {
            super.handleMessage(msg);
            tvData.setText(rLog);
        }
    }
}

最后别忘了网络权限:

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

http://www.niftyadmin.cn/n/1248993.html

相关文章

《Kotlin从零到精通Android开发》欧阳燊(二)

第六章 Kotlin使用简单控件 6.1使用按钮控件 按钮button 按钮事件三种Kotlin编码方式&#xff1a;匿名函数&#xff0c;内部类&#xff0c;接口实现 1.匿名函数方式 btn_click_anonymos.setOnClickListener { v -> //Kotlin变量类型转换使用as toast("${(v as But…

ElasticSearch基础(二)

接上篇 java-api-client 一、ElasticSearch常用编程操作 1、索引相关操作 1.1创建索引 Testpublic void createIndex() {//准备创建索引 &#xff0c;指定索引名 执行创建的动作&#xff08;get方法&#xff09;transportClient.admin().indices().prepareCreate("blo…

使用本地索引提速5倍+

记录&#xff1a;NO.252 场景 在Oracle数据库一张数据表T_SENSOR_DATA&#xff0c;每日增加1000万条数据。使用日期字段GATHER_DATE建立分区表。 全局索引 初期&#xff0c;由于业务使用频繁&#xff0c;为了提高查询速度&#xff0c;在T_SENSOR_DATA建立一个联合索引和一个联合…

Android Jetpack(一) 介绍

Jetpack 是一套库、工具和指南&#xff0c;可帮助开发者更轻松地编写优质应用。这些组件可帮助您遵循最佳做法、让您摆脱编写样板代码的工作并简化复杂任务&#xff0c;以便您将精力集中放在所需的代码上。 Jetpack 包含与平台 API 解除捆绑的 androidx.* 软件包库。这意味着&…

Dump View Hierarchy for UI Automator(UI层次结构)工具

使用步骤&#xff1a; 1.连接上手机&#xff0c;打开手机的某个应用 2.打开安卓SDK目录\tools\monitor.bat 下的 Dump View Hierarchy for UI Automator 3.点击如图所示图标

Android Jetpack(二) 基础

1、Android KTX - 编写更简洁、惯用的 Kotlin 代码 KTX 拥有的一些 扩展程序列表 dependencies { //androidx.activity implementation "androidx.activity:activity-ktx:1.1.0" //androidx.benchmark implementation "androidx.benchmark:benchmark-junit4:1…

Android Jetpack(三) 架构

1、数据绑定 - 以声明方式将可观察数据绑定到界面元素 数据绑定库是一种支持库&#xff0c;借助该库&#xff0c;您可以使用声明性格式&#xff08;而非程序化地&#xff09;将布局中的界面组件绑定到应用中的数据源。 一般调用 findViewById() 来查找 TextView 并将其绑定到…

ES 相关知识点

1、关闭索引的作用 关闭索引的作用 关闭索引 POST /my_index/_close 关闭索引后, 不能再对索引进行读写. 否则都会报错. 索引数据会持久化到磁盘, 不再占用内存资源 如果需要时, 可以再开启索引 POST /my_index/_open 2、Elasticsearch与Mysql数据同步 Elasticsearch与Mysql…