Cocos(Cocos2d-x 或 Cocos Creator)中获取设备的 ​​本地 IP 地址​​ 和 ​​地区

举报
William 发表于 2025/07/31 09:18:02 2025/07/31
【摘要】 1. 获取本地 IP 地址​​​​(1) Android 实现​​在 Android 上获取本地 IP 地址,可以使用 NetworkInterface 类遍历网络接口,过滤出非回环地址(127.0.0.1)的 IPv4 地址。​​Java 代码(Android 原生)​​import android.content.Context;import java.net.Inet4Address;...

1. 获取本地 IP 地址​

​(1) Android 实现​

在 Android 上获取本地 IP 地址,可以使用 NetworkInterface 类遍历网络接口,过滤出非回环地址(127.0.0.1)的 IPv4 地址。

​Java 代码(Android 原生)​

import android.content.Context;
import java.net.Inet4Address;
import java.net.InetAddress;
import java.net.NetworkInterface;
import java.util.Collections;
import java.util.List;

public class NetworkUtils {
    public static String getLocalIpAddress(Context context) {
        try {
            List<NetworkInterface> interfaces = Collections.list(NetworkInterface.getNetworkInterfaces());
            for (NetworkInterface intf : interfaces) {
                List<InetAddress> addrs = Collections.list(intf.getInetAddresses());
                for (InetAddress addr : addrs) {
                    if (!addr.isLoopbackAddress() && addr instanceof Inet4Address) {
                        return addr.getHostAddress();
                    }
                }
            }
        } catch (Exception e) {
            e.printStackTrace();
        }
        return "0.0.0.0"; // 默认返回无效 IP
    }
}

​JSB 绑定(Cocos2d-x)​

如果使用 Cocos2d-x,需要通过 ​​JSB​​ 绑定 Java 方法到 JavaScript:

// NetworkUtilsBridge.cpp
#include "cocos2d.h"
#include "platform/android/jni/JniHelper.h"

extern "C" {
    JNIEXPORT jstring JNICALL Java_com_yourgame_NetworkUtils_getLocalIpAddress(JNIEnv* env, jobject obj) {
        std::string ip = NetworkUtils::getLocalIpAddress(); // 调用 Java 方法
        return env->NewStringUTF(ip.c_str());
    }
}

然后在 JavaScript 中调用:

const ip = jsb.reflection.callStaticMethod(
    "com/yourgame/NetworkUtils",
    "getLocalIpAddress",
    "()Ljava/lang/String;"
);
console.log("Local IP:", ip);

​Cocos Creator 实现​

Cocos Creator 支持 ​​Native 插件​​,可以通过 ​​Android Plugin​​ 方式调用 Java 代码:

  1. android/app/src/main/java/com/yourgame/ 下创建 NetworkUtils.java
  2. 在 Cocos Creator 的 native/plugins/android 下配置插件。
  3. 在 JS 中调用:
const { exec } = require('cordova/exec');
exec((ip) => {
    console.log("Local IP:", ip);
}, (error) => {
    console.error("Failed to get IP:", error);
}, "NetworkUtils", "getLocalIpAddress", []);

​(2) iOS 实现​

在 iOS 上获取本地 IP 地址,可以使用 Network 框架(iOS 12+)或 getifaddrs(兼容旧版本)。

​Objective-C 代码(iOS 原生)​

#import <ifaddrs.h>
#import <arpa/inet.h>

NSString* getLocalIPAddress() {
    struct ifaddrs *interfaces = NULL;
    struct ifaddrs *temp_addr = NULL;
    NSString *ipAddress = @"0.0.0.0";

    if (getifaddrs(&interfaces) == 0) {
        temp_addr = interfaces;
        while (temp_addr != NULL) {
            if (temp_addr->ifa_addr->sa_family == AF_INET) { // IPv4
                struct sockaddr_in *addr = (struct sockaddr_in *)temp_addr->ifa_addr;
                char addrBuf[INET_ADDRSTRLEN];
                if (inet_ntop(AF_INET, &addr->sin_addr, addrBuf, INET_ADDRSTRLEN)) {
                    NSString *ifName = [NSString stringWithUTF8String:temp_addr->ifa_name];
                    if ([ifName isEqualToString:@"en0"] || [ifName isEqualToString:@"en1"]) { // Wi-Fi 或蜂窝网络
                        ipAddress = [NSString stringWithUTF8String:addrBuf];
                        break;
                    }
                }
            }
            temp_addr = temp_addr->ifa_next;
        }
        freeifaddrs(interfaces);
    }
    return ipAddress;
}

​JSB 绑定(Cocos2d-x)​

类似 Android,通过 ​​JSB​​ 绑定 Objective-C 方法到 JavaScript。

​Cocos Creator 实现​

  1. ios/YourGame/Plugins 下创建 NetworkUtils.m
  2. 在 Cocos Creator 的 native/plugins/ios 下配置插件。
  3. 在 JS 中调用:
const { exec } = require('cordova/exec');
exec((ip) => {
    console.log("Local IP:", ip);
}, (error) => {
    console.error("Failed to get IP:", error);
}, "NetworkUtils", "getLocalIPAddress", []);

​2. 获取设备地区(国家/地区代码)​

​(1) Android 实现​

Android 可以通过 TelephonyManagerLocale 获取国家代码。

​Java 代码​

import android.content.Context;
import android.telephony.TelephonyManager;
import java.util.Locale;

public class DeviceUtils {
    public static String getCountryCode(Context context) {
        // 方法1:通过 SIM 卡获取(需要权限)
        try {
            TelephonyManager tm = (TelephonyManager) context.getSystemService(Context.TELEPHONY_SERVICE);
            if (tm != null) {
                String countryCode = tm.getNetworkCountryIso(); // 如 "CN", "US"
                if (countryCode != null && !countryCode.isEmpty()) {
                    return countryCode.toUpperCase();
                }
            }
        } catch (Exception e) {
            e.printStackTrace();
        }

        // 方法2:通过系统语言设置获取(不需要权限)
        return Locale.getDefault().getCountry(); // 如 "CN", "US"
    }
}

​JSB 绑定​

类似 IP 获取方式,通过 ​​JSB​​ 绑定 Java 方法到 JavaScript。


​(2) iOS 实现​

iOS 可以通过 NSLocale 获取国家代码。

​Objective-C 代码​

#import <Foundation/Foundation.h>

NSString* getCountryCode() {
    NSLocale *locale = [NSLocale currentLocale];
    return [locale objectForKey:NSLocaleCountryCode]; // 如 "CN", "US"
}

​JSB 绑定​

类似 Android,通过 ​​JSB​​ 绑定 Objective-C 方法到 JavaScript。

​Cocos Creator 实现​

  1. ios/YourGame/Plugins 下创建 DeviceUtils.m
  2. 在 Cocos Creator 的 native/plugins/ios 下配置插件。
  3. 在 JS 中调用:
const { exec } = require('cordova/exec');
exec((countryCode) => {
    console.log("Country Code:", countryCode);
}, (error) => {
    console.error("Failed to get country code:", error);
}, "DeviceUtils", "getCountryCode", []);

​3. 完整方案(Cocos Creator + Native 插件)​

​(1) Android 插件​

  1. android/app/src/main/java/com/yourgame/ 下创建 NetworkUtils.javaDeviceUtils.java
  2. assets/plugins/android 下配置 plugin.xml
<platform name="android">
    <source-file src="src/android/NetworkUtils.java" target-dir="src/com/yourgame" />
    <source-file src="src/android/DeviceUtils.java" target-dir="src/com/yourgame" />
</platform>
  1. 在 JS 中调用:
const { exec } = require('cordova/exec');
exec((ip) => {
    console.log("Local IP:", ip);
}, (error) => {
    console.error("Failed to get IP:", error);
}, "NetworkUtils", "getLocalIpAddress", []);

exec((countryCode) => {
    console.log("Country Code:", countryCode);
}, (error) => {
    console.error("Failed to get country code:", error);
}, "DeviceUtils", "getCountryCode", []);

​(2) iOS 插件​

  1. ios/YourGame/Plugins 下创建 NetworkUtils.mDeviceUtils.m
  2. plugins/ios 下配置 plugin.xml
<platform name="ios">
    <source-file src="src/ios/NetworkUtils.m" />
    <source-file src="src/ios/DeviceUtils.m" />
</platform>
  1. 在 JS 中调用方式同 Android。

​4. 注意事项​

  1. ​Android 权限​​:
    • 如果使用 TelephonyManager 获取 SIM 卡国家代码,需要 READ_PHONE_STATE 权限:
      <uses-permission android:name="android.permission.READ_PHONE_STATE" />
  2. ​iOS 权限​​:
    • 获取设备信息不需要额外权限。
  3. ​Wi-Fi IP 可能变化​​:
    • 设备可能连接不同网络,IP 地址可能动态变化。
  4. ​模拟器/测试环境​​:
    • 模拟器可能返回 10.0.2.15(Android)或 127.0.0.1(iOS),需注意测试。

​总结​

​功能​ ​Android 实现​ ​iOS 实现​ ​Cocos 调用方式​
​本地 IP​ NetworkInterface getifaddrs JSB / Native 插件
​国家代码​ TelephonyManager / Locale NSLocale JSB / Native 插件

推荐使用 ​​Cocos Creator + Native 插件​​ 方式,兼容性最好,适用于 ​​Android 和 iOS​​ 双平台。

【声明】本内容来自华为云开发者社区博主,不代表华为云及华为云开发者社区的观点和立场。转载时必须标注文章的来源(华为云社区)、文章链接、文章作者等基本信息,否则作者和本社区有权追究责任。如果您发现本社区中有涉嫌抄袭的内容,欢迎发送邮件进行举报,并提供相关证据,一经查实,本社区将立刻删除涉嫌侵权内容,举报邮箱: cloudbbs@huaweicloud.com
  • 点赞
  • 收藏
  • 关注作者

评论(0

0/1000
抱歉,系统识别当前为高风险访问,暂不支持该操作

全部回复

上滑加载中

设置昵称

在此一键设置昵称,即可参与社区互动!

*长度不超过10个汉字或20个英文字符,设置后3个月内不可修改。

*长度不超过10个汉字或20个英文字符,设置后3个月内不可修改。