gadget2k
gadget2k
  • 发布:2015-10-15 16:50
  • 更新:2017-07-20 17:51
  • 阅读:5578

利用Native.JS让web app也能通过UDP获取服务器IP

分类:Native.js
function Str2Bytes(str){ // 因为datapacket发送接收的都是数据流,所以要转换为bytes数组,相当于java里的getBytes()  
    var ch, st, re = [];    
    for (var i = 0; i < str.length; i++ ) {    
        ch = str.charCodeAt(i);   
        st = [];   
        do {    
          st.push( ch & 0xFF );    
          ch = ch >> 8;    
        }      
    while ( ch );    
        re = re.concat( st.reverse() );    
    }    
    return re;        
}  
function Bytes2Str(arr){ //收到的bytes数组还得转回字符才能看懂。因为只返回ip,所以只处理了ascii码  
    var str = "";  
    for(var i=0; i<arr.length; i++) {  
       var tmp = String.fromCharCode(arr[i]);  
       str += tmp;  
    }  
    return str;  
}  
document.addEventListener( "plusready", function(){ // 开始udp的广播和接收  
    // 要是做跨平台的app, 这里得先判断一下平台,我下面代码仅针对android  
    var DatagramPacket = plus.android.importClass("java.net.DatagramPacket");  
    var DatagramSocket = plus.android.importClass("java.net.DatagramSocket");  
    var InetAddress = plus.android.importClass("java.net.InetAddress");  

    var ds = new DatagramSocket();  
    var messageReceived = false;  
    var serverAddress = "";  
    var data = [];  
    data = Str2Bytes("hello"); // 服务器已设好,随便问一句就可以,不一定是hello。  
    var port = 9989; // 服务器设定好的监听端口  
    var iAdd = new InetAddress();  
    var dp = new DatagramPacket(data, data.length,iAdd.getByName("255.255.255.255"), port);  
    while (!messageReceived){  
        var d = [];  
        d = Str2Bytes("http://255.255.255.255:8898"); // 原java代码 byte[] data = new byte[1024]不知道如何改写,就随便写一个足够ip长度的string  
        var dp2 = new DatagramPacket(d, d.length);  
        ds.send(dp); // 发出udp广播  
        ds.receive(dp2); //这里要是服务器没开就会卡住了。原java代码是另开一个线程,js是单线程,所以最好写一个10秒后断开再重试的代码。另,已发现HTML5支持多线程的web workers无法初始化plusready。  
        var dpData = Bytes2Str(dp2.getData()); // 转换数据流为我要的地址  
        var arrUrl = dpData.split("//"); //以下两句是为了只要ip段,去掉不相干的字符  
        serverAddress = arrUrl[1].substring(0,arrUrl[1].indexOf(":"));  
        document.getElementById("ipAddress").value = serverAddress;  
        messageReceived=true;  
        ds.close();  
    }  
}, false );
2015-10-15 16:50 负责人:无 分享
已邀请:
gadget2k

gadget2k (作者)

算了,没人理睬。自己动手,丰衣足食。我这个唯一的功能就是通过UDP获取本局域网内某服务器的IP地址。以下代码未考虑线程和出错处理,大家自己改。已确认可行。

        function Str2Bytes(str){          
            var ch, st, re = [];    
            for (var i = 0; i < str.length; i++ ) {    
                ch = str.charCodeAt(i);  // get char     
                st = [];                 // set up "stack"    
                do {    
                  st.push( ch & 0xFF );  // push byte to stack    
                  ch = ch >> 8;          // shift value down by 1 byte    
                }      
                while ( ch );    
                // add stack contents to result    
                // done because chars have "wrong" endianness    
                re = re.concat( st.reverse() );    
            }    
              // return an array of bytes    
            return re;        
        }  
        function Bytes2Str(arr){  
            var str = "";  
            for(var i=0; i<arr.length; i++) {  
               var tmp = String.fromCharCode(arr[i]);  
               str += tmp;  
            }  
            return str;  
        }  
        document.addEventListener( "plusready", function(){  
            var DatagramPacket = plus.android.importClass("java.net.DatagramPacket");  
            var DatagramSocket = plus.android.importClass("java.net.DatagramSocket");  
            var InetAddress = plus.android.importClass("java.net.InetAddress");  

            var ds = new DatagramSocket();  
            var messageReceived = false;  
            var serverAddress = "Server not found";  
            var data = [];  
            data = Str2Bytes("hello");  
            var port = 9989;  
            var iAdd = new InetAddress();  
            var dp = new DatagramPacket(data, data.length,iAdd.getByName("255.255.255.255"), port);  
            while (!messageReceived){  
                var d = [];  
                d = Str2Bytes("http://255.255.255.255:8898"); //因为不知道怎么用js设定一个1024字节的byte数组,就随便写一个足够长度的string  
                var dp2 = new DatagramPacket(d, d.length);  
                ds.send(dp);  
                ds.receive(dp2); //这里要是服务器没开就会卡住了。所以最好开一个线程,或者写一个10秒后断开的代码。听说HTML5支持多线程了。  
                var dpData = Bytes2Str(dp2.getData());  
                var arrUrl = dpData.split("//");  
                serverAddress = arrUrl[1].substring(0,arrUrl[1].indexOf(":"));  
                document.getElementById("ipAddress").value = serverAddress;  
                messageReceived=true;  
                ds.close();  
            }  
        }, false );
gadget2k

gadget2k (作者)

完全是初学者,希望抛砖引玉能有大神把我这个粗糙的代码改的更好。

viney

viney - app的春天来了

Uncaught receive;java.lang.reflect.InvocationTargetException你这段代码报异常了,不知道问题出在哪儿?

  • viney

    解决了,端口是int类型

    2015-12-22 11:36

  • gadget2k (作者)

    解决了就好。

    2015-12-22 11:49

  • gadget2k (作者)

    顺便说下,这一版的云打包有bug,这一段无法执行。我跟他们反映了,说是下次更新解决。

    2015-12-22 11:50

viney

viney - app的春天来了

console.log(resPacket.getAddress().getHostAddress());

Uncaught TypeError: Object #<h> has no method 'getHostAddress'

怎么会没有getHostAddress这个方法呢?怎么获取ip?

  • Android_磊子

    对于java对象要使用.操作符就需要先import,所以你的写法应该是:

    var address = resPacket.getAddress();

    plus.android.importClass(address);//当之前代码没有引入过此类时,必须有此行代码

    console.log(address.getHostAddress());

    2015-12-25 12:50

诸葛胖子

诸葛胖子

我有一个问题,我要用udp发送的是一个byte数组,例如:
byte[] data={0x66,(byte) 0xad,0x0d,0x31,0x01,0x11,0x31,(byte) 0xc0,(byte) 0xff,0x55,0x02,0x2d,0x33};
但是JavaScript无法定义byte类型,怎么解决?

  • 诸葛胖子

    自己动手丰衣足食,byte(0xad)就是处理溢出的情况,当>128的数,从-127开始计,byte(0xad)=-127+(0xad-128)-1

    2016-02-24 23:48

7***@qq.com

7***@qq.com

如果要发送udp广播用js该怎么写

7***@qq.com

7***@qq.com

大神 线程出错怎么解决啊 ?android.os.NetworkOnMainThreadException;at java.net

.DatagramSocket.send??

该问题目前已经被锁定, 无法添加新回复