提示没有获得网络的Wireless 或networks 的权限

本文介绍如何在Android应用中处理无网络连接的情况,包括显示提示对话框、引导用户设置无线网络,以及处理对话框的取消事件。

public static void showNoConnectionDialog(Context ctx1) { 
       
final Context ctx = ctx1; 
       
AlertDialog.Builder builder = new AlertDialog.Builder(ctx); 
        builder
.setCancelable(true); 
        builder
.setMessage(R.string.no_connection); 
        builder
.setTitle(R.string.no_connection_title); 
        builder
.setPositiveButton(R.string.settings, new DialogInterface.OnClickListener() { 
           
public void onClick(DialogInterface dialog, int which) { 
                ctx
.startActivity(new Intent(Settings.ACTION_WIRELESS_SETTINGS)); 
           
} 
       
}); 
        builder
.setNegativeButton(R.string.cancel, new DialogInterface.OnClickListener() { 
           
public void onClick(DialogInterface dialog, int which) { 
               
return; 
           
} 
       
}); 
        builder
.setOnCancelListener(new DialogInterface.OnCancelListener() { 
           
public void onCancel(DialogInterface dialog) { 
               
return; 
           
} 
       
}); 
 
        builder
.show(); 
   
} 

这个对话框就是提示你没有获得网络 不能联通
本问参考http://osdir.com/ml/Android-Developers/2009-11/msg05044.html

lv_timer_t *Wifi_conn_timer; void Wifi_conn_timer_callback(lv_timer_t *timer) { if (load_network_info(&netInfo) == 0) { EventBuf e; e.eventType = EVENT_CONNECTWIFI; strncpy((char *)e.databuf, netInfo.wifi_name, 31); e.databuf[31] = '\0'; strncpy((char *)e.databuf + 32, netInfo.wifi_pass, 31); e.databuf[63] = '\0'; sendImageMsg(e); SW_Network = true; printf("Loaded WiFi: %s\n", netInfo.wifi_name); } else { SW_Network = false; } lv_timer_del(Wifi_conn_timer); Wifi_conn_timer = NULL; } // 函数:检查指定网络接口是否为无线接口 bool is_truly_wireless(const char *interface_name) { char wireless_dir[256]; snprintf(wireless_dir, sizeof(wireless_dir), "/sys/class/net/%s/wireless", interface_name); struct stat st; if (stat(wireless_dir, &st) == 0 && S_ISDIR(st.st_mode)) { // "/sys/class/net/<interface_name>/wireless" 目录存在,表明它是一个无线接口 return true; } return false; } // 函数:检查指定网络接口是否处于UP状态 // 返回 true 如果接口是UP,否则 false bool is_interface_up(const char *interface_name) { int sock_fd; struct ifreq ifr; // 创建一个UDP socket,用于ioctl操作 sock_fd = socket(AF_INET, SOCK_DGRAM, 0); if (sock_fd < 0) { perror("socket error"); return false; } // 设置接口名称 strncpy(ifr.ifr_name, interface_name, IFNAMSIZ - 1); ifr.ifr_name[IFNAMSIZ - 1] = '\0'; // 确保字符串以null结尾 // 获取接口标志 if (ioctl(sock_fd, SIOCGIFFLAGS, &ifr) < 0) { // perror("ioctl SIOCGIFFLAGS error"); // 接口不存在其他错误 close(sock_fd); return false; } close(sock_fd); // 检查IFF_UP标志是否设置 return (ifr.ifr_flags & IFF_UP) != 0; } // 函数:设置指定网络接口的状态 (UP/DOWN) // 参数: interface_name - 接口名称, should_be_up - true为UP,false为DOWN // 返回 true 表示成功,否则 false bool set_interface_state(const char *interface_name, bool should_be_up) { int sock_fd; struct ifreq ifr; sock_fd = socket(AF_INET, SOCK_DGRAM, 0); if (sock_fd < 0) { perror("socket error in set_interface_state"); return false; } strncpy(ifr.ifr_name, interface_name, IFNAMSIZ - 1); ifr.ifr_name[IFNAMSIZ - 1] = '\0'; // 首先获取当前标志 if (ioctl(sock_fd, SIOCGIFFLAGS, &ifr) < 0) { perror("ioctl SIOCGIFFLAGS error in set_interface_state"); close(sock_fd); return false; } if (should_be_up) { ifr.ifr_flags |= IFF_UP; // 设置IFF_UP标志 } else { ifr.ifr_flags &= ~IFF_UP; // 清除IFF_UP标志 } // 设置新的标志 if (ioctl(sock_fd, SIOCSIFFLAGS, &ifr) < 0) { // 常见的错误是 EPERM (Operation not permitted),表示没有权限 perror("ioctl SIOCSIFFLAGS error in set_interface_state"); close(sock_fd); return false; } close(sock_fd); return true; } // 函数:检查指定无线接口是否被RF-killed (射频阻断) // 注意:rfkill通常是针对整个无线设备,而不是单个接口 // 返回 true 如果未被RF-killed,否则 false bool is_wireless_rf_unblocked() { DIR *d; struct dirent *dir_entry; char path[256]; char buf[16]; FILE *fp; d = opendir("/sys/class/rfkill/"); if (d == NULL) { // 如果rfkill子系统不存在无法访问,假定没有rfkill阻断 // 在某些嵌入式系统中可能没有rfkill // perror("Error opening /sys/class/rfkill/"); return true; } while ((dir_entry = readdir(d)) != NULL) { if (strncmp(dir_entry->d_name, "rfkill", 6) == 0) // 查找类似 rfkill0, rfkill1 的目录 { // 检查rfkill设备的类型 snprintf(path, sizeof(path), "/sys/class/rfkill/%s/type", dir_entry->d_name); fp = fopen(path, "r"); if (fp) { if (fgets(buf, sizeof(buf), fp) != NULL) { // 去除换行符 buf[strcspn(buf, "\n")] = 0; if (strcmp(buf, "wlan") == 0) // 如果是无线LAN设备 { fclose(fp); // 关闭type文件 // 检查其状态 snprintf(path, sizeof(path), "/sys/class/rfkill/%s/state", dir_entry->d_name); fp = fopen(path, "r"); if (fp) { if (fgets(buf, sizeof(buf), fp) != NULL) { if (strcmp(buf, "1\n") == 0) // '1' 表示被阻断 (blocked) { fclose(fp); closedir(d); return false; // 发现无线被RF-killed } } fclose(fp); } } else { fclose(fp); // 如果不是wlan类型,也要关闭文件 } } else { fclose(fp); // fgets failed } } } } closedir(d); return true; // 没有发现无线被RF-killed } // 函数:检查系统中是否存在任何活动的无线网络接口 bool check_for_active_wlan() { DIR *d; struct dirent *dir_entry; bool wlan_found = false; d = opendir("/sys/class/net/"); if (d == NULL) { perror("Error opening /sys/class/net/"); return false; } while ((dir_entry = readdir(d)) != NULL) { if (strcmp(dir_entry->d_name, ".") == 0 || strcmp(dir_entry->d_name, "..") == 0) { continue; } if (strncmp(dir_entry->d_name, "wlan", 4) == 0 || strncmp(dir_entry->d_name, "wlp", 3) == 0 || strncmp(dir_entry->d_name, "wifi", 4) == 0) { if (is_truly_wireless(dir_entry->d_name)) { // printf("Found active wireless interface: %s\n", dir_entry->d_name); wlan_found = true; break; } } } closedir(d); return wlan_found; } // 函数:检查系统中是否存在任何活动的、未被阻断的无线网络接口 // 如果找到一个可用的无线接口,则返回 true,否则 false bool check_for_act_wlan_interf() { DIR *d; struct dirent *dir_entry; bool wlan_fully_ready = false; // 修改变量名以反映更全面的检查 char found_interface_name[IFNAMSIZ]; // 存储找到的接口名 // 首先检查是否存在全局的RF-kill阻断 //if (!is_wireless_rf_unblocked()) //{ // printf("Wireless is RF-killed (soft/hard blocked).\n"); // return false; // 如果被rf-killed,直接返回false //} d = opendir("/sys/class/net/"); if (d == NULL) { perror("Error opening /sys/class/net/"); return false; } while ((dir_entry = readdir(d)) != NULL) { if (strcmp(dir_entry->d_name, ".") == 0 || strcmp(dir_entry->d_name, "..") == 0) { continue; } // 过滤可能的无线接口名称 if (strncmp(dir_entry->d_name, "wlan", 4) == 0 || strncmp(dir_entry->d_name, "wlp", 3) == 0 || strncmp(dir_entry->d_name, "wifi", 4) == 0) { // 1. 检查是否真的是无线接口 if (is_truly_wireless(dir_entry->d_name)) { // 2. 检查无线接口是否处于UP状态 if (is_interface_up(dir_entry->d_name)) { // 如果代码执行到这里,说明: // - 接口是无线接口 // - 接口处于UP状态 // - 且全局没有RF-kill阻断(已在函数开头检查) // 可以选择在这里存储接口名称,如果只需要一个可用的接口 strncpy(found_interface_name, dir_entry->d_name, IFNAMSIZ); found_interface_name[IFNAMSIZ - 1] = '\0'; printf("Found a fully ready wireless interface: %s\n", found_interface_name); wlan_fully_ready = true; break; // 找到一个就足够了,如果需要列出所有,则移除break } else { printf("Found wireless interface %s, but it is DOWN.\n", dir_entry->d_name); } } } } closedir(d); return wlan_fully_ready; } void FindWlanProc(EventBuf evt) { bool is_wlan_up = check_for_active_wlan(); if (is_wlan_up) { // WLAN 接口实际存在 if (!FindWlanFlag) { // 如果之前的状态是“未加载” FindWlanFlag = true; // 更新状态:wifi已经加载 printf("Wlan in (verified by direct system check)!!!\n"); Wifi_conn_timer = lv_timer_create(Wifi_conn_timer_callback, 10000, NULL); if (Wifi_conn_timer == NULL) { printf("Error: Failed to create Wifi_conn_timer!\n"); } printf("Debug: Wifi_conn_timer would be created/reset here.\n"); } } else { // WLAN 接口不存在未被识别 if (FindWlanFlag) { // 如果之前的状态是“已加载” FindWlanFlag = false; // 更新状态:wifi没有加载 printf("Wlan out (verified by direct system check)!!!\n"); } // 1. 获取输入框内容 const char *ip = "127.0.0.1"; const char *port_str = "9003"; // 3. 复制IP(字符串形式) strncpy(socketconnInfo.ip, ip, sizeof(socketconnInfo.ip) - 1); socketconnInfo.ip[sizeof(socketconnInfo.ip) - 1] = '\0'; // 2. 输入验证 if (!ip || !port_str) { printf("ERROR: IP端口不能为空\n"); return; } // IP格式验证 struct in_addr addr; if (inet_pton(AF_INET, ip, &addr) != 1) { printf("ERROR: 无效的IP地址格式\n"); lv_label_set_text(guider_ui.SettingScreen_label_server_conn_status, "Wrong IP!"); return; } // 端口号转换和验证 char *endptr; long port = strtol(port_str, &endptr, 10); if (*endptr != '\0' || port < 0 || port > 65535) { printf("ERROR: 端口号必须为0-65535的整数\n"); lv_label_set_text(guider_ui.SettingScreen_label_server_conn_status, "Wrong PORT!"); return; } socketconnInfo.port = (uint16_t)port; // htons((uint16_t)port) // 3. 构造数据缓冲区 uint8_t buffer[21] = {0}; // 16+4+1=21字节 // 格式化IP部分(16字节) size_t ip_len = strlen(ip); if (ip_len > 15) { printf("WARNING: IP地址超过15字符将被截断\n"); ip_len = 15; } memcpy(buffer, ip, ip_len); // 填充空格 if (ip_len < 15) { memset(buffer + ip_len, ' ', 15 - ip_len); } // 格式化端口部分(4字节网络序) uint32_t net_port = htonl(port); memcpy(buffer + 16, &net_port, 4); // 添加状态码(1字节) buffer[20] = 0x01; // 连接成功状态 // 4. 发送网络消息 int ret = sendNetMsg(EVENT_SOCKET_CONNECT, (const char *)buffer); // 5. 处理发送结果 if (ret == 0) { printf("INFO: 连接信息发送成功\n"); printf("IP: %-15s Port: %-5d\n", ip, (int)port); } else { printf("ERROR: 发送失败,错误码: %d\n", ret); } } } 我现在的机器连接无线网稍微有点问题,就是在连接无线网的时候,如果此时直接把路由器的电直接断掉,此时就会断开,但是断开后在重启机器就会有问题,此时会一直去连接上次的那个WiFi,但是由于路由器断电了,导致了无法连接,此时WiFi列表也没有其他的WiFi了,并且其他的一些界面的按钮点不动,你觉得会不会是上面的代码的问题,我的想法是在重连的时候,如果重连的有10s以后还是无法连接就判断超时了,然后显示WiFi列表,这样可行吗,并且我发现有如下的问题, Found a fully ready wireless interface: wlan0 WiFi SSID: 你好 我发现即使路由器断电了,这个WiFi也是一样的显示有,但是其实WiFi已经没有了,这就导致了重试连接以后会显示已经连接上了,因此不会因为超时而显示WiFi列表,这个应该怎么办,按理说检测实际的物理接口应该可以判断出是否在线吧
09-10
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值