├── .gitignore
├── .idea
├── caches
│ ├── build_file_checksums.ser
│ └── gradle_models.ser
├── codeStyles
│ └── Project.xml
├── compiler.xml
├── copyright
│ └── profiles_settings.xml
├── gradle.xml
├── inspectionProfiles
│ └── Project_Default.xml
├── markdown-navigator.xml
├── markdown-navigator
│ └── profiles_settings.xml
├── misc.xml
├── modules.xml
├── runConfigurations.xml
└── vcs.xml
├── README.md
├── WiFiLibrary
├── .gitignore
├── build.gradle
├── proguard-rules.pro
└── src
│ └── main
│ ├── AndroidManifest.xml
│ ├── java
│ └── com
│ │ └── kongqw
│ │ └── wifilibrary
│ │ ├── BaseWiFiManager.java
│ │ ├── SecurityModeEnum.java
│ │ ├── WiFiManager.java
│ │ └── listener
│ │ ├── OnWifiConnectListener.java
│ │ ├── OnWifiEnabledListener.java
│ │ └── OnWifiScanResultsListener.java
│ └── res
│ └── values
│ └── strings.xml
├── app
├── .gitignore
├── build.gradle
├── proguard-rules.pro
└── src
│ └── main
│ ├── AndroidManifest.xml
│ ├── java
│ └── kong
│ │ └── qingwei
│ │ └── kqwwifimanagerdemo
│ │ ├── MainActivity.java
│ │ ├── MyApplication.java
│ │ ├── adapter
│ │ └── WifiListAdapter.java
│ │ ├── util
│ │ └── VlanUtil.java
│ │ └── view
│ │ └── ConnectWifiDialog.java
│ └── res
│ ├── anim
│ ├── dialog_bottom_in.xml
│ └── dialog_bottom_out.xml
│ ├── layout
│ ├── activity_main.xml
│ ├── dialog_connect_wifi.xml
│ └── item_wifi.xml
│ ├── mipmap-hdpi
│ ├── alipay.png
│ └── ic_launcher.png
│ ├── mipmap-mdpi
│ └── ic_launcher.png
│ ├── mipmap-xhdpi
│ └── ic_launcher.png
│ ├── mipmap-xxhdpi
│ └── ic_launcher.png
│ ├── mipmap-xxxhdpi
│ └── ic_launcher.png
│ ├── values-v21
│ └── styles.xml
│ ├── values-w820dp
│ └── dimens.xml
│ └── values
│ ├── colors.xml
│ ├── dimens.xml
│ ├── strings.xml
│ └── styles.xml
├── build.gradle
├── gradle.properties
├── gradle
└── wrapper
│ ├── gradle-wrapper.jar
│ └── gradle-wrapper.properties
├── gradlew
├── gradlew.bat
└── settings.gradle
/.gitignore:
--------------------------------------------------------------------------------
1 | *.iml
2 | .gradle
3 | /local.properties
4 | /.idea/workspace.xml
5 | /.idea/libraries
6 | .DS_Store
7 | /build
8 | /captures
9 |
--------------------------------------------------------------------------------
/.idea/caches/build_file_checksums.ser:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/YanInfo/WiFiManager/eb4268220db99ffa1778583acd4fa88252088f9f/.idea/caches/build_file_checksums.ser
--------------------------------------------------------------------------------
/.idea/caches/gradle_models.ser:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/YanInfo/WiFiManager/eb4268220db99ffa1778583acd4fa88252088f9f/.idea/caches/gradle_models.ser
--------------------------------------------------------------------------------
/.idea/codeStyles/Project.xml:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 |
6 |
7 |
8 |
9 |
10 |
11 |
12 |
13 |
14 |
15 |
16 |
17 |
18 |
19 |
20 |
21 |
22 |
23 |
24 |
25 |
26 |
27 |
28 |
29 |
--------------------------------------------------------------------------------
/.idea/compiler.xml:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 |
6 |
7 |
8 |
9 |
10 |
11 |
12 |
13 |
14 |
15 |
16 |
17 |
18 |
19 |
20 |
21 |
22 |
--------------------------------------------------------------------------------
/.idea/copyright/profiles_settings.xml:
--------------------------------------------------------------------------------
1 |
2 |
3 |
--------------------------------------------------------------------------------
/.idea/gradle.xml:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
21 |
22 |
--------------------------------------------------------------------------------
/.idea/inspectionProfiles/Project_Default.xml:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 |
6 |
7 |
8 |
9 |
10 |
11 |
12 |
13 |
14 |
15 |
16 |
17 |
18 |
19 |
20 |
21 |
22 |
23 |
24 |
25 |
26 |
27 |
28 |
29 |
30 |
31 |
32 |
33 |
34 |
35 |
36 |
--------------------------------------------------------------------------------
/.idea/markdown-navigator.xml:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 |
6 |
7 |
8 |
9 |
10 |
11 |
12 |
13 |
14 |
15 |
16 |
17 |
18 |
19 |
20 |
21 |
22 |
23 |
24 |
25 |
26 |
27 |
28 |
29 |
30 |
31 |
32 |
33 |
34 |
35 |
36 |
37 |
38 |
39 |
40 |
41 |
42 |
43 |
44 |
45 |
46 |
47 |
48 |
49 |
50 |
51 |
52 |
53 |
54 |
55 |
56 |
57 |
58 |
59 |
60 |
61 |
62 |
63 |
64 |
65 |
66 |
67 |
68 |
69 |
--------------------------------------------------------------------------------
/.idea/markdown-navigator/profiles_settings.xml:
--------------------------------------------------------------------------------
1 |
2 |
3 |
--------------------------------------------------------------------------------
/.idea/misc.xml:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 |
6 |
7 |
8 |
9 |
10 |
11 |
12 |
13 |
14 |
15 |
16 |
17 |
18 |
19 |
20 |
21 |
22 |
23 |
24 |
25 |
26 |
27 |
28 |
29 |
30 |
31 |
32 |
33 |
34 |
35 |
36 |
37 |
38 |
39 |
40 |
41 |
42 |
43 |
44 |
45 |
46 | C/C++
47 |
48 |
49 | General
50 |
51 |
52 | Unused codeC/C++
53 |
54 |
55 |
56 |
57 | Android
58 |
59 |
60 |
61 |
62 |
63 |
64 |
65 |
66 |
67 |
68 |
69 |
--------------------------------------------------------------------------------
/.idea/modules.xml:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 |
6 |
7 |
8 |
9 |
10 |
--------------------------------------------------------------------------------
/.idea/runConfigurations.xml:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 |
6 |
7 |
8 |
9 |
10 |
11 |
12 |
--------------------------------------------------------------------------------
/.idea/vcs.xml:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 |
6 |
--------------------------------------------------------------------------------
/README.md:
--------------------------------------------------------------------------------
1 |
2 | ## 初始化
3 |
4 | ``` java
5 | /**
6 | * WIFI管理器
7 | **/
8 | mWiFiManager = new WiFiManager(getApplicationContext());
9 | ```
10 |
11 | ## 打开WIFI
12 |
13 | ``` java
14 | mWiFiManager.openWiFi();
15 | ```
16 |
17 | ## 关闭WIFI
18 |
19 | ``` java
20 | mWiFiManager.closeWiFi();
21 | ```
22 |
23 | ## 添加WIFI开关状态的监听
24 |
25 | ``` java
26 | mWiFiManager.setOnWifiEnabledListener(this);
27 | ```
28 |
29 | ### 回调
30 |
31 | ``` java
32 | /**
33 | * WIFI开关状态的回调
34 | *
35 | * @param enabled true 打开 false 关闭
36 | */
37 | @Override
38 | public void onWifiEnabled(boolean enabled) {
39 | // TODO
40 | }
41 | ```
42 |
43 | ## 移除WIFI开关状态的监听
44 |
45 | ``` java
46 | mWiFiManager.removeOnWifiEnabledListener();
47 | ```
48 |
49 | ## 获取WIFI列表
50 |
51 | ``` java
52 | List scanResults = mWiFiManager.getScanResults();
53 | ```
54 |
55 | ### 获取WIFI加密方式
56 |
57 | ``` java
58 | mWiFiManager.getSecurityMode(scanResult)
59 | ```
60 |
61 | > 注意:Android 6.0需要动态获取 Manifest.permission.ACCESS_FINE_LOCATION 或 Manifest.permission.ACCESS_COARSE_LOCATION 后,才能正常获取到WIFI列表。
62 |
63 | ## 添加获取WIFI列表的监听
64 |
65 | ``` java
66 | mWiFiManager.setOnWifiScanResultsListener(this);
67 | ```
68 |
69 | ### 回调
70 |
71 | ``` java
72 | /**
73 | * WIFI列表刷新后的回调
74 | *
75 | * @param scanResults 扫描结果
76 | */
77 | @Override
78 | public void onScanResults(List scanResults) {
79 | // TODO
80 | }
81 | ```
82 |
83 | > mWiFiManager.getScanResults(); 是返回当前的WIFI列表,回调返回的是扫描更新以后新的WIFI列表。
84 |
85 | ## 移除获取WIFI列表的监听
86 |
87 | ``` java
88 | mWiFiManager.removeOnWifiScanResultsListener();
89 | ```
90 |
91 | ## 连接到开放网络
92 |
93 | ``` java
94 | mWiFiManager.connectOpenNetwork(scanResult.SSID);
95 | ```
96 |
97 | ## 连接到WPA/WPA2网络
98 |
99 | ``` java
100 | mWiFiManager.connectWPA2Network(scanResult.SSID, password);
101 | ```
102 |
103 | ## 连接到WEP网络
104 |
105 | ``` java
106 | mWiFiManager.connectWEPNetwork(scanResult.SSID, password);
107 | ```
108 |
109 | ## 添加连接WIFI的监听
110 |
111 | ``` java
112 | mWiFiManager.setOnWifiConnectListener(this);
113 | ```
114 |
115 | ### 回调
116 |
117 | ``` java
118 | /**
119 | * WIFI连接的Log得回调
120 | *
121 | * @param log log
122 | */
123 | @Override
124 | public void onWiFiConnectLog(String log) {
125 | Log.i(TAG, "onWiFiConnectLog: " + log);
126 | // TODO
127 | }
128 |
129 | /**
130 | * WIFI连接成功的回调
131 | *
132 | * @param SSID 热点名
133 | */
134 | @Override
135 | public void onWiFiConnectSuccess(String SSID) {
136 | Log.i(TAG, "onWiFiConnectSuccess: [ " + SSID + " ] 连接成功");
137 | // TODO
138 | }
139 |
140 | /**
141 | * WIFI连接失败的回调
142 | *
143 | * @param SSID 热点名
144 | */
145 | @Override
146 | public void onWiFiConnectFailure(String SSID) {
147 | Log.i(TAG, "onWiFiConnectFailure: [ " + SSID + " ] 连接失败");
148 | // TODO
149 | }
150 | ```
151 |
152 | ## 移除连接WIFI的监听
153 |
154 | ``` java
155 | mWiFiManager.removeOnWifiConnectListener();
156 | ```
157 |
158 | ## 断开网络连接
159 |
160 | ``` java
161 | mWiFiManager.disconnectWifi(connectionInfo.getNetworkId());
162 | ```
163 |
164 | ## 删除网络配置
165 |
166 | > 只能删除自己创建的配置,其他应用生成的配置需要Root权限才可以删除。
167 |
168 | ``` java
169 | mWiFiManager.deleteConfig(wifiConfiguration.networkId);
170 | ```
171 |
172 |
--------------------------------------------------------------------------------
/WiFiLibrary/.gitignore:
--------------------------------------------------------------------------------
1 | /build
2 |
--------------------------------------------------------------------------------
/WiFiLibrary/build.gradle:
--------------------------------------------------------------------------------
1 | apply plugin: 'com.android.library'
2 |
3 | android {
4 | compileSdkVersion 25
5 | buildToolsVersion "25.0.2"
6 |
7 | defaultConfig {
8 | minSdkVersion 14
9 | targetSdkVersion 25
10 | versionCode 1
11 | versionName "1.0"
12 |
13 | testInstrumentationRunner "android.support.test.runner.AndroidJUnitRunner"
14 |
15 | }
16 | buildTypes {
17 | release {
18 | minifyEnabled false
19 | proguardFiles getDefaultProguardFile('proguard-android.txt'), 'proguard-rules.pro'
20 | }
21 | }
22 | }
23 |
24 | dependencies {
25 | compile fileTree(dir: 'libs', include: ['*.jar'])
26 | androidTestCompile('com.android.support.test.espresso:espresso-core:2.2.2', {
27 | exclude group: 'com.android.support', module: 'support-annotations'
28 | })
29 | compile 'com.android.support:appcompat-v7:25.2.0'
30 | testCompile 'junit:junit:4.12'
31 | }
32 |
--------------------------------------------------------------------------------
/WiFiLibrary/proguard-rules.pro:
--------------------------------------------------------------------------------
1 | # Add project specific ProGuard rules here.
2 | # By default, the flags in this file are appended to flags specified
3 | # in /Users/kongqingwei/Library/Android/sdk/tools/proguard/proguard-android.txt
4 | # You can edit the include path and order by changing the proguardFiles
5 | # directive in build.gradle.
6 | #
7 | # For more details, see
8 | # http://developer.android.com/guide/developing/tools/proguard.html
9 |
10 | # Add any project specific keep options here:
11 |
12 | # If your project uses WebView with JS, uncomment the following
13 | # and specify the fully qualified class name to the JavaScript interface
14 | # class:
15 | #-keepclassmembers class fqcn.of.javascript.interface.for.webview {
16 | # public *;
17 | #}
18 |
--------------------------------------------------------------------------------
/WiFiLibrary/src/main/AndroidManifest.xml:
--------------------------------------------------------------------------------
1 |
3 |
4 |
5 |
6 |
7 |
8 |
9 |
10 |
11 |
12 |
17 |
18 |
19 |
20 |
21 |
22 |
23 |
24 |
25 |
26 |
27 |
28 |
29 |
30 |
31 |
32 |
33 |
--------------------------------------------------------------------------------
/WiFiLibrary/src/main/java/com/kongqw/wifilibrary/BaseWiFiManager.java:
--------------------------------------------------------------------------------
1 | package com.kongqw.wifilibrary;
2 |
3 | import android.content.Context;
4 | import android.net.ConnectivityManager;
5 | import android.net.NetworkInfo;
6 | import android.net.wifi.ScanResult;
7 | import android.net.wifi.WifiConfiguration;
8 | import android.net.wifi.WifiInfo;
9 | import android.net.wifi.WifiManager;
10 | import android.support.annotation.NonNull;
11 | import android.text.TextUtils;
12 |
13 | import java.util.ArrayList;
14 | import java.util.HashMap;
15 | import java.util.List;
16 | import java.util.Map;
17 |
18 | /**
19 | * @Author: zhangyan
20 | * @Date: 2019/4/10 10:15
21 | * WiFiManager基础类
22 | */
23 | public class BaseWiFiManager {
24 |
25 | static WifiManager mWifiManager;
26 |
27 | private static ConnectivityManager mConnectivityManager;
28 |
29 | BaseWiFiManager(Context context) {
30 | // 取得WifiManager对象
31 | mWifiManager = (WifiManager) context.getApplicationContext().getSystemService(Context.WIFI_SERVICE);
32 |
33 | mConnectivityManager = (ConnectivityManager) context.getSystemService(Context.CONNECTIVITY_SERVICE);
34 | }
35 |
36 | /**
37 | * 添加开放网络配置
38 | *
39 | * @param ssid SSID
40 | * @return NetworkId
41 | */
42 | int setOpenNetwork(@NonNull String ssid) {
43 | if (TextUtils.isEmpty(ssid)) {
44 | return -1;
45 | }
46 | WifiConfiguration wifiConfiguration = getConfigFromConfiguredNetworksBySsid(ssid);
47 | if (null == wifiConfiguration) {
48 | // 生成配置
49 | WifiConfiguration wifiConfig = new WifiConfiguration();
50 | wifiConfig.SSID = addDoubleQuotation(ssid);
51 | wifiConfig.allowedKeyManagement.set(WifiConfiguration.KeyMgmt.NONE);
52 | wifiConfig.allowedProtocols.set(WifiConfiguration.Protocol.RSN);
53 | wifiConfig.allowedProtocols.set(WifiConfiguration.Protocol.WPA);
54 | wifiConfig.allowedAuthAlgorithms.clear();
55 | wifiConfig.allowedPairwiseCiphers.set(WifiConfiguration.PairwiseCipher.CCMP);
56 | wifiConfig.allowedPairwiseCiphers.set(WifiConfiguration.PairwiseCipher.TKIP);
57 | wifiConfig.allowedGroupCiphers.set(WifiConfiguration.GroupCipher.WEP40);
58 | wifiConfig.allowedGroupCiphers.set(WifiConfiguration.GroupCipher.WEP104);
59 | wifiConfig.allowedGroupCiphers.set(WifiConfiguration.GroupCipher.CCMP);
60 | wifiConfig.allowedGroupCiphers.set(WifiConfiguration.GroupCipher.TKIP);
61 | // 添加配置并返回NetworkID
62 | return addNetwork(wifiConfig);
63 | } else {
64 | // 返回NetworkID
65 | return wifiConfiguration.networkId;
66 | }
67 | }
68 |
69 | /**
70 | * 添加WEP网络配置
71 | *
72 | * @param ssid SSID
73 | * @param password 密码
74 | * @return NetworkId
75 | */
76 | int setWEPNetwork(@NonNull String ssid, @NonNull String password) {
77 | if (TextUtils.isEmpty(ssid) || TextUtils.isEmpty(password)) {
78 | return -1;
79 | }
80 | WifiConfiguration wifiConfiguration = getConfigFromConfiguredNetworksBySsid(ssid);
81 | if (null == wifiConfiguration) {
82 | // 添加配置
83 | WifiConfiguration wifiConfig = new WifiConfiguration();
84 | wifiConfig.SSID = addDoubleQuotation(ssid);
85 | wifiConfig.wepKeys[0] = "\"" + password + "\"";
86 | wifiConfig.allowedKeyManagement.set(WifiConfiguration.KeyMgmt.NONE);
87 | wifiConfig.allowedProtocols.set(WifiConfiguration.Protocol.RSN);
88 | wifiConfig.allowedProtocols.set(WifiConfiguration.Protocol.WPA);
89 | wifiConfig.allowedAuthAlgorithms.set(WifiConfiguration.AuthAlgorithm.OPEN);
90 | wifiConfig.allowedAuthAlgorithms.set(WifiConfiguration.AuthAlgorithm.SHARED);
91 | wifiConfig.allowedPairwiseCiphers.set(WifiConfiguration.PairwiseCipher.CCMP);
92 | wifiConfig.allowedPairwiseCiphers.set(WifiConfiguration.PairwiseCipher.TKIP);
93 | wifiConfig.allowedGroupCiphers.set(WifiConfiguration.GroupCipher.WEP40);
94 | wifiConfig.allowedGroupCiphers.set(WifiConfiguration.GroupCipher.WEP104);
95 | // 添加配置并返回NetworkID
96 | return addNetwork(wifiConfig);
97 | } else {
98 | // 更新配置并返回NetworkID
99 | wifiConfiguration.wepKeys[0] = "\"" + password + "\"";
100 | return updateNetwork(wifiConfiguration);
101 | }
102 | }
103 |
104 | /**
105 | * 添加WPA网络配置
106 | *
107 | * @param ssid SSID
108 | * @param password 密码
109 | * @return NetworkId
110 | */
111 | int setWPA2Network(@NonNull String ssid, @NonNull String password) {
112 | if (TextUtils.isEmpty(ssid) || TextUtils.isEmpty(password)) {
113 | return -1;
114 | }
115 | WifiConfiguration wifiConfiguration = getConfigFromConfiguredNetworksBySsid(ssid);
116 | if (null == wifiConfiguration) {
117 | WifiConfiguration wifiConfig = new WifiConfiguration();
118 | wifiConfig.SSID = addDoubleQuotation(ssid);
119 | wifiConfig.preSharedKey = "\"" + password + "\"";
120 | wifiConfig.allowedProtocols.set(WifiConfiguration.Protocol.RSN);
121 | wifiConfig.allowedKeyManagement.set(WifiConfiguration.KeyMgmt.WPA_PSK);
122 | wifiConfig.status = WifiConfiguration.Status.ENABLED;
123 | wifiConfig.allowedGroupCiphers.set(WifiConfiguration.GroupCipher.TKIP);
124 | wifiConfig.allowedGroupCiphers.set(WifiConfiguration.GroupCipher.CCMP);
125 | wifiConfig.allowedPairwiseCiphers.set(WifiConfiguration.PairwiseCipher.TKIP);
126 | wifiConfig.allowedPairwiseCiphers.set(WifiConfiguration.PairwiseCipher.CCMP);
127 | wifiConfig.allowedProtocols.set(WifiConfiguration.Protocol.RSN);
128 | wifiConfig.allowedProtocols.set(WifiConfiguration.Protocol.WPA);
129 | wifiConfig.allowedGroupCiphers.set(WifiConfiguration.GroupCipher.CCMP);
130 | wifiConfig.allowedPairwiseCiphers.set(WifiConfiguration.PairwiseCipher.CCMP);
131 | // 添加配置并返回NetworkID
132 | return addNetwork(wifiConfig);
133 | } else {
134 | // 更新配置并返回NetworkID
135 | wifiConfiguration.preSharedKey = "\"" + password + "\"";
136 | return updateNetwork(wifiConfiguration);
137 | }
138 | }
139 |
140 | /**
141 | * 通过热点名获取热点配置
142 | *
143 | * @param ssid 热点名
144 | * @return 配置信息
145 | */
146 | public WifiConfiguration getConfigFromConfiguredNetworksBySsid(@NonNull String ssid) {
147 | ssid = addDoubleQuotation(ssid);
148 | List existingConfigs = getConfiguredNetworks();
149 | if (null != existingConfigs) {
150 | for (WifiConfiguration existingConfig : existingConfigs) {
151 | if (existingConfig.SSID.equals(ssid)) {
152 | return existingConfig;
153 | }
154 | }
155 | }
156 | return null;
157 | }
158 |
159 |
160 | /**
161 | * 获取WIFI的开关状态
162 | *
163 | * @return WIFI的可用状态
164 | */
165 | public boolean isWifiEnabled() {
166 | return null != mWifiManager && mWifiManager.isWifiEnabled();
167 | }
168 |
169 | /**
170 | * 判断WIFI是否连接
171 | *
172 | * @return 是否连接
173 | */
174 | boolean isWifiConnected() {
175 | if (null != mConnectivityManager) {
176 | NetworkInfo networkInfo = mConnectivityManager.getActiveNetworkInfo();
177 | return null != networkInfo && networkInfo.isConnected() && networkInfo.getType() == ConnectivityManager.TYPE_WIFI;
178 | }
179 | return false;
180 | }
181 |
182 | /**
183 | * 判断设备是否有网
184 | *
185 | * @return 网络状态
186 | */
187 | boolean hasNetwork() {
188 | if (null != mConnectivityManager) {
189 | NetworkInfo networkInfo = mConnectivityManager.getActiveNetworkInfo();
190 | return networkInfo != null && networkInfo.isAvailable();
191 | }
192 | return false;
193 | }
194 |
195 | /**
196 | * 获取当前正在连接的WIFI信息
197 | *
198 | * @return 当前正在连接的WIFI信息
199 | */
200 | public WifiInfo getConnectionInfo() {
201 | if (null != mWifiManager) {
202 | return mWifiManager.getConnectionInfo();
203 | }
204 | return null;
205 | }
206 |
207 | /**
208 | * 扫描附近的WIFI
209 | */
210 | public void startScan() {
211 | if (null != mWifiManager) {
212 | mWifiManager.startScan();
213 | }
214 | }
215 |
216 | /**
217 | * 获取最近扫描的WIFI热点
218 | *
219 | * @return WIFI热点列表
220 | */
221 | public List getScanResults() {
222 | // 得到扫描结果
223 | if (null != mWifiManager) {
224 | return mWifiManager.getScanResults();
225 | }
226 | return null;
227 | }
228 |
229 | /**
230 | * 排除重复
231 | *
232 | * @param scanResults 带处理的数据
233 | * @return 去重数据
234 | */
235 | public static ArrayList excludeRepetition(List scanResults) {
236 | HashMap hashMap = new HashMap<>();
237 |
238 | for (ScanResult scanResult : scanResults) {
239 | String ssid = scanResult.SSID;
240 |
241 | if (TextUtils.isEmpty(ssid)) {
242 | continue;
243 | }
244 |
245 | ScanResult tempResult = hashMap.get(ssid);
246 | if (null == tempResult) {
247 | hashMap.put(ssid, scanResult);
248 | continue;
249 | }
250 |
251 | if (WifiManager.calculateSignalLevel(tempResult.level, 100) < WifiManager.calculateSignalLevel(scanResult.level, 100)) {
252 | hashMap.put(ssid, scanResult);
253 | }
254 | }
255 |
256 | ArrayList results = new ArrayList<>();
257 | for (Map.Entry entry : hashMap.entrySet()) {
258 | results.add(entry.getValue());
259 | }
260 |
261 | return results;
262 | }
263 |
264 | /**
265 | * 获取配置过的WIFI信息
266 | *
267 | * @return 配置信息
268 | */
269 | private List getConfiguredNetworks() {
270 | if (null != mWifiManager) {
271 | return mWifiManager.getConfiguredNetworks();
272 | }
273 | return null;
274 | }
275 |
276 | /**
277 | * 保持配置
278 | *
279 | * @return 保持是否成功
280 | */
281 | boolean saveConfiguration() {
282 | return null != mWifiManager && mWifiManager.saveConfiguration();
283 | }
284 |
285 | /**
286 | * 连接到网络
287 | *
288 | * @param networkId NetworkId
289 | * @return 连接结果
290 | */
291 | boolean enableNetwork(int networkId) {
292 | if (null != mWifiManager) {
293 | boolean isDisconnect = disconnectCurrentWifi();
294 | boolean isEnableNetwork = mWifiManager.enableNetwork(networkId, true);
295 | boolean isSave = mWifiManager.saveConfiguration();
296 | boolean isReconnect = mWifiManager.reconnect();
297 | return isDisconnect && isEnableNetwork && isSave && isReconnect;
298 | }
299 | return false;
300 | }
301 |
302 | /**
303 | * 添加网络配置
304 | *
305 | * @param wifiConfig 配置信息
306 | * @return NetworkId
307 | */
308 | private int addNetwork(WifiConfiguration wifiConfig) {
309 | if (null != mWifiManager) {
310 | int networkId = mWifiManager.addNetwork(wifiConfig);
311 | if (-1 != networkId) {
312 | boolean isSave = mWifiManager.saveConfiguration();
313 | if (isSave) {
314 | return networkId;
315 | }
316 | }
317 | }
318 | return -1;
319 | }
320 |
321 | /**
322 | * 更新网络配置
323 | *
324 | * @param wifiConfig 配置信息
325 | * @return NetworkId
326 | */
327 | private int updateNetwork(WifiConfiguration wifiConfig) {
328 | if (null != mWifiManager) {
329 | int networkId = mWifiManager.updateNetwork(wifiConfig);
330 | if (-1 != networkId) {
331 | boolean isSave = mWifiManager.saveConfiguration();
332 | if (isSave) {
333 | return networkId;
334 | }
335 | }
336 | }
337 | return -1;
338 | }
339 |
340 | /**
341 | * 断开指定 WIFI
342 | *
343 | * @param netId netId
344 | * @return 是否断开
345 | */
346 | public boolean disconnectWifi(int netId) {
347 | if (null != mWifiManager) {
348 | boolean isDisable = mWifiManager.disableNetwork(netId);
349 | boolean isDisconnect = mWifiManager.disconnect();
350 | return isDisable && isDisconnect;
351 | }
352 | return false;
353 | }
354 |
355 | /**
356 | * 断开当前的WIFI
357 | *
358 | * @return 是否断开成功
359 | */
360 | public boolean disconnectCurrentWifi() {
361 | WifiInfo wifiInfo = getConnectionInfo();
362 | if (null != wifiInfo) {
363 | int networkId = wifiInfo.getNetworkId();
364 | return disconnectWifi(networkId);
365 | } else {
366 | // 断开状态
367 | return true;
368 | }
369 | }
370 |
371 | /**
372 | * 删除配置
373 | *
374 | * @param netId netId
375 | * @return 是否删除成功
376 | */
377 | public boolean deleteConfig(int netId) {
378 | if (null != mWifiManager) {
379 | boolean isDisable = mWifiManager.disableNetwork(netId);
380 | boolean isRemove = mWifiManager.removeNetwork(netId);
381 | boolean isSave = mWifiManager.saveConfiguration();
382 | return (isDisable && isRemove && isSave);
383 | }
384 | return false;
385 | }
386 |
387 | /**
388 | * 计算WIFI信号强度
389 | *
390 | * @param rssi WIFI信号
391 | * @return 强度
392 | */
393 | public int calculateSignalLevel(int rssi) {
394 | return WifiManager.calculateSignalLevel(rssi, 5);
395 | }
396 |
397 | /**
398 | * 获取WIFI的加密方式
399 | *
400 | * @param scanResult WIFI信息
401 | * @return 加密方式
402 | */
403 | public SecurityModeEnum getSecurityMode(@NonNull ScanResult scanResult) {
404 | //获取wifi加密类型
405 | String capabilities = scanResult.capabilities;
406 |
407 | if (capabilities.contains("WEP")) {
408 | return SecurityModeEnum.WEP;
409 | } else if (capabilities.contains("WPA")) {
410 | return SecurityModeEnum.WPA;
411 | } else if (capabilities.contains("WPA2")) {
412 | return SecurityModeEnum.WPA2;
413 | } else {
414 | // 没有加密
415 | return SecurityModeEnum.OPEN;
416 | }
417 | }
418 |
419 | /**
420 | * 添加双引号
421 | *
422 | * @param text 待处理字符串
423 | * @return 处理后字符串
424 | */
425 | public String addDoubleQuotation(String text) {
426 | if (TextUtils.isEmpty(text)) {
427 | return "";
428 | }
429 | return "\"" + text + "\"";
430 | }
431 | }
432 |
--------------------------------------------------------------------------------
/WiFiLibrary/src/main/java/com/kongqw/wifilibrary/SecurityModeEnum.java:
--------------------------------------------------------------------------------
1 | package com.kongqw.wifilibrary;
2 |
3 | /**
4 | * @Author: zhangyan
5 | * @Date: 2019/4/10 10:00
6 | * OPEN, WEP, WPA, WPA2
7 | * WIFI的四种安全性状态,枚举类型
8 | */
9 |
10 | public enum SecurityModeEnum {
11 | OPEN, WEP, WPA, WPA2
12 | }
13 |
--------------------------------------------------------------------------------
/WiFiLibrary/src/main/java/com/kongqw/wifilibrary/WiFiManager.java:
--------------------------------------------------------------------------------
1 | package com.kongqw.wifilibrary;
2 |
3 | import android.content.BroadcastReceiver;
4 | import android.content.Context;
5 | import android.content.Intent;
6 | import android.net.ConnectivityManager;
7 | import android.net.Uri;
8 | import android.net.wifi.ScanResult;
9 | import android.net.wifi.SupplicantState;
10 | import android.net.wifi.WifiConfiguration;
11 | import android.net.wifi.WifiInfo;
12 | import android.net.wifi.WifiManager;
13 | import android.os.Build;
14 | import android.os.Handler;
15 | import android.os.Message;
16 | import android.os.ResultReceiver;
17 | import android.provider.Settings;
18 | import android.support.annotation.NonNull;
19 | import android.util.Log;
20 | import android.widget.Toast;
21 |
22 | import com.kongqw.wifilibrary.listener.OnWifiConnectListener;
23 | import com.kongqw.wifilibrary.listener.OnWifiEnabledListener;
24 | import com.kongqw.wifilibrary.listener.OnWifiScanResultsListener;
25 |
26 | import java.lang.reflect.Field;
27 | import java.lang.reflect.InvocationTargetException;
28 | import java.lang.reflect.Method;
29 | import java.util.List;
30 |
31 |
32 | /**
33 | * /**
34 | *
35 | * @Author: zhangyan
36 | * @Date: 2019/4/10 9:32
37 | * WifiManager : https://developer.android.com/reference/android/net/wifi/WifiManager.html
38 | * WifiConfiguration : https://developer.android.com/reference/android/net/wifi/WifiConfiguration.html
39 | * ScanResult : https://developer.android.com/reference/android/net/wifi/ScanResult.html
40 | * WifiInfo : https://developer.android.com/reference/android/net/wifi/WifiInfo.html
41 | * Wifi管理
42 | */
43 | public class WiFiManager extends BaseWiFiManager {
44 |
45 | private static final String TAG = "WiFiManager";
46 | private static WiFiManager mWiFiManager;
47 | private static CallBackHandler mCallBackHandler = new CallBackHandler();
48 | private static final int WIFI_STATE_ENABLED = 0;
49 | private static final int WIFI_STATE_DISABLED = 1;
50 | private static final int SCAN_RESULTS_UPDATED = 3;
51 | private static final int WIFI_CONNECT_LOG = 4;
52 | private static final int WIFI_CONNECT_SUCCESS = 5;
53 | private static final int WIFI_CONNECT_FAILURE = 6;
54 | private static final String DEFAULT_AP_PASSWORD = "12345678";
55 |
56 | private WiFiManager(Context context) {
57 | super(context);
58 | }
59 |
60 | public static WiFiManager getInstance(Context context) {
61 | if (null == mWiFiManager) {
62 | synchronized (WiFiManager.class) {
63 | if (null == mWiFiManager) {
64 | mWiFiManager = new WiFiManager(context);
65 | }
66 | }
67 | }
68 | return mWiFiManager;
69 | }
70 |
71 | /**
72 | * 打开Wifi
73 | */
74 | public void openWiFi() {
75 | if (!isWifiEnabled() && null != mWifiManager) {
76 | mWifiManager.setWifiEnabled(true);
77 | }
78 | }
79 |
80 | /**
81 | * 关闭Wifi
82 | */
83 | public void closeWiFi() {
84 | if (isWifiEnabled() && null != mWifiManager) {
85 | mWifiManager.setWifiEnabled(false);
86 | }
87 | }
88 |
89 | /**
90 | * 创建热点,这里只能是7.0或7.0之前的版本
91 | * 手动设置热点名和密码
92 | */
93 | public void createWifiHotspot7() {
94 |
95 | WifiConfiguration config = new WifiConfiguration();
96 | config.SSID = "性感荷官在线发脾气";
97 | config.preSharedKey = "123456789";
98 | config.hiddenSSID = true;
99 | config.allowedAuthAlgorithms
100 | .set(WifiConfiguration.AuthAlgorithm.OPEN);//开放系统认证
101 | config.allowedGroupCiphers.set(WifiConfiguration.GroupCipher.TKIP);
102 |
103 | //设置加密的方式,这个对应小米手机MIUI
104 | int indexOfWPA2_PSK = 4;
105 | //从WifiConfiguration.KeyMgmt数组中查找WPA2_PSK的值
106 | for (int i = 0; i < WifiConfiguration.KeyMgmt.strings.length; i++) {
107 | if (WifiConfiguration.KeyMgmt.strings[i].equals("WPA2_PSK")) {
108 | indexOfWPA2_PSK = i;
109 | break;
110 | }
111 | }
112 | config.allowedKeyManagement.set(indexOfWPA2_PSK);
113 |
114 | config.allowedPairwiseCiphers
115 | .set(WifiConfiguration.PairwiseCipher.TKIP);
116 | config.allowedGroupCiphers.set(WifiConfiguration.GroupCipher.CCMP);
117 | config.allowedPairwiseCiphers
118 | .set(WifiConfiguration.PairwiseCipher.CCMP);
119 | config.status = WifiConfiguration.Status.ENABLED;
120 |
121 | //通过反射调用设置热点
122 | try {
123 | Method method = mWifiManager.getClass().getMethod(
124 | "setWifiApEnabled", WifiConfiguration.class, Boolean.TYPE);
125 | boolean enable = (Boolean) method.invoke(mWifiManager, config, true);
126 | if (enable) {
127 | Log.i(TAG, "热点已经开启##################################");
128 | } else {
129 | Log.i(TAG, "热点开启失败##################################");
130 | }
131 | } catch (Exception e) {
132 | e.printStackTrace();
133 | }
134 | }
135 |
136 | /**
137 | * 8.0 开启热点方法
138 | * 这里使用WPA2加密
139 | *
140 | * @param ssid
141 | * @param password
142 | */
143 | public void createWifiHotspot8(String ssid, String password) {
144 |
145 | WifiConfiguration wifiConfig = new WifiConfiguration();
146 | Log.i(TAG, "热点准备开启##################################");
147 |
148 | // 清理配置
149 | wifiConfig.SSID = new String(ssid);
150 | wifiConfig.allowedAuthAlgorithms.clear();
151 | wifiConfig.allowedGroupCiphers.clear();
152 | wifiConfig.allowedKeyManagement.clear();
153 | wifiConfig.allowedPairwiseCiphers.clear();
154 | wifiConfig.allowedProtocols.clear();
155 |
156 | // 如果密码为空或者小于8位数,则使用默认的密码
157 | if (null != password && password.length() >= 8) {
158 | wifiConfig.preSharedKey = password;
159 | } else {
160 | wifiConfig.preSharedKey = DEFAULT_AP_PASSWORD;
161 | }
162 | wifiConfig.hiddenSSID = false;
163 | wifiConfig.allowedAuthAlgorithms.set(WifiConfiguration.AuthAlgorithm.OPEN);
164 | wifiConfig.allowedKeyManagement.set(4);
165 | wifiConfig.allowedPairwiseCiphers.set(WifiConfiguration.PairwiseCipher.CCMP);
166 | wifiConfig.allowedPairwiseCiphers.set(WifiConfiguration.PairwiseCipher.TKIP);
167 | wifiConfig.allowedProtocols.set(WifiConfiguration.Protocol.RSN);
168 | wifiConfig.allowedProtocols.set(WifiConfiguration.Protocol.WPA);
169 | wifiConfig.allowedGroupCiphers.set(WifiConfiguration.GroupCipher.CCMP);
170 | wifiConfig.allowedGroupCiphers.set(WifiConfiguration.GroupCipher.TKIP);
171 | wifiConfig.status = WifiConfiguration.Status.ENABLED;
172 |
173 | }
174 |
175 | /**
176 | * 关闭热点
177 | */
178 | public void closeWifiHotspot8() {
179 | try {
180 | Method method = mWifiManager.getClass().getMethod("setWifiApEnabled", WifiConfiguration.class, boolean.class);
181 | method.invoke(mWifiManager, null, false);
182 | } catch (Exception e) {
183 | e.printStackTrace();
184 | }
185 | }
186 |
187 |
188 | /**
189 | * 连接到开放网络
190 | *
191 | * @param ssid 热点名
192 | * @return 配置是否成功
193 | */
194 | public boolean connectOpenNetwork(@NonNull String ssid) {
195 | // 获取networkId
196 | int networkId = setOpenNetwork(ssid);
197 | if (-1 != networkId) {
198 | // 保存配置
199 | boolean isSave = saveConfiguration();
200 | // 连接网络
201 | boolean isEnable = enableNetwork(networkId);
202 |
203 | return isSave && isEnable;
204 | }
205 | return false;
206 |
207 | }
208 |
209 | /**
210 | * 连接到WEP网络
211 | *
212 | * @param ssid 热点名
213 | * @param password 密码
214 | * @return 配置是否成功
215 | */
216 | public boolean connectWEPNetwork(@NonNull String ssid, @NonNull String password) {
217 | // 获取networkId
218 | int networkId = setWEPNetwork(ssid, password);
219 | if (-1 != networkId) {
220 | // 保存配置
221 | boolean isSave = saveConfiguration();
222 | // 连接网络
223 | boolean isEnable = enableNetwork(networkId);
224 |
225 | return isSave && isEnable;
226 | }
227 | return false;
228 | }
229 |
230 | /**
231 | * 连接到WPA2网络
232 | *
233 | * @param ssid 热点名
234 | * @param password 密码
235 | * @return 配置是否成功
236 | */
237 | public boolean connectWPA2Network(@NonNull String ssid, @NonNull String password) {
238 | // 获取networkId
239 | int networkId = setWPA2Network(ssid, password);
240 | if (-1 != networkId) {
241 | // 保存配置
242 | boolean isSave = saveConfiguration();
243 | // 连接网络
244 | boolean isEnable = enableNetwork(networkId);
245 |
246 | return isSave && isEnable;
247 | }
248 | return false;
249 | }
250 |
251 | /* *******************************************************************************************/
252 |
253 |
254 | /**
255 | * 广播接收者
256 | */
257 | public static class NetworkBroadcastReceiver extends BroadcastReceiver {
258 | @Override
259 | public void onReceive(Context context, Intent intent) {
260 | //获得WifiManager的实例对象
261 | WifiManager wifiManager = (WifiManager) context.getApplicationContext().getSystemService(Context.WIFI_SERVICE);
262 | switch (intent.getAction()) {
263 | //WIFI状态发生变化
264 | case WifiManager.WIFI_STATE_CHANGED_ACTION:
265 | switch (intent.getIntExtra(WifiManager.EXTRA_WIFI_STATE, WifiManager.WIFI_STATE_UNKNOWN)) {
266 | case WifiManager.WIFI_STATE_ENABLING:
267 | Log.i(TAG, "onReceive: 正在打开 WIFI...");
268 | break;
269 | case WifiManager.WIFI_STATE_ENABLED:
270 | Log.i(TAG, "onReceive: WIFI 已打开");
271 | mCallBackHandler.sendEmptyMessage(WIFI_STATE_ENABLED);
272 | break;
273 | case WifiManager.WIFI_STATE_DISABLING:
274 | Log.i(TAG, "onReceive: 正在关闭 WIFI...");
275 | break;
276 | case WifiManager.WIFI_STATE_DISABLED:
277 | Log.i(TAG, "onReceive: WIFI 已关闭");
278 | mCallBackHandler.sendEmptyMessage(WIFI_STATE_DISABLED);
279 | break;
280 | case WifiManager.WIFI_STATE_UNKNOWN:
281 | default:
282 | Log.i(TAG, "onReceive: WIFI 状态未知!");
283 | break;
284 | }
285 | break;
286 | // WIFI扫描完成
287 | case WifiManager.SCAN_RESULTS_AVAILABLE_ACTION:
288 | if (android.os.Build.VERSION.SDK_INT >= android.os.Build.VERSION_CODES.M) {
289 | boolean isUpdated = intent.getBooleanExtra(WifiManager.EXTRA_RESULTS_UPDATED, false);
290 | Log.i(TAG, "onReceive: WIFI扫描 " + (isUpdated ? "完成" : "未完成"));
291 | } else {
292 | Log.i(TAG, "onReceive: WIFI扫描完成");
293 | }
294 |
295 | Message scanResultsMessage = Message.obtain();
296 | scanResultsMessage.what = SCAN_RESULTS_UPDATED;
297 | scanResultsMessage.obj = wifiManager.getScanResults();
298 | mCallBackHandler.sendMessage(scanResultsMessage);
299 | break;
300 | //WIFI网络状态变化通知
301 | case WifiManager.NETWORK_STATE_CHANGED_ACTION:
302 | WifiInfo wifiInfo = intent.getParcelableExtra(WifiManager.EXTRA_WIFI_INFO);
303 | if (null != wifiInfo && wifiInfo.getSupplicantState() == SupplicantState.COMPLETED) {
304 | String ssid = wifiInfo.getSSID();
305 | Log.i(TAG, "onReceive: 网络连接成功 ssid = " + ssid);
306 | }
307 | break;
308 | //WIFI连接状态变化的时候
309 | case WifiManager.SUPPLICANT_CONNECTION_CHANGE_ACTION:
310 | boolean isConnected = intent.getBooleanExtra(WifiManager.EXTRA_SUPPLICANT_CONNECTED, false);
311 | Log.i(TAG, "onReceive: SUPPLICANT_CONNECTION_CHANGE_ACTION isConnected = " + isConnected);
312 | break;
313 | //wifi连接结果通知 WIFI连接请求状态发生改变
314 | case WifiManager.SUPPLICANT_STATE_CHANGED_ACTION:
315 | // 获取连接状态
316 | SupplicantState supplicantState = intent.getParcelableExtra(WifiManager.EXTRA_NEW_STATE);
317 |
318 | Message logMessage = Message.obtain();
319 | logMessage.what = WIFI_CONNECT_LOG;
320 | logMessage.obj = supplicantState.toString();
321 | logMessage.obj = supplicantState.toString();
322 | mCallBackHandler.sendMessage(logMessage);
323 |
324 | switch (supplicantState) {
325 | case INTERFACE_DISABLED: // 接口禁用
326 | Log.i(TAG, "onReceive: INTERFACE_DISABLED 接口禁用");
327 | break;
328 | case DISCONNECTED:// 断开连接
329 | // Log.i(TAG, "onReceive: DISCONNECTED:// 断开连接");
330 | // break;
331 | case INACTIVE: // 不活跃的
332 | WifiInfo connectFailureInfo = wifiManager.getConnectionInfo();
333 | Log.i(TAG, "onReceive: INACTIVE 不活跃的 connectFailureInfo = " + connectFailureInfo);
334 | if (null != connectFailureInfo) {
335 | Message wifiConnectFailureMessage = Message.obtain();
336 | wifiConnectFailureMessage.what = WIFI_CONNECT_FAILURE;
337 | wifiConnectFailureMessage.obj = connectFailureInfo.getSSID();
338 | mCallBackHandler.sendMessage(wifiConnectFailureMessage);
339 | // 断开连接
340 | int networkId = connectFailureInfo.getNetworkId();
341 | boolean isDisable = wifiManager.disableNetwork(networkId);
342 | boolean isDisconnect = wifiManager.disconnect();
343 | Log.i(TAG, "onReceive: 断开连接 = " + (isDisable && isDisconnect));
344 | }
345 | break;
346 | case SCANNING: // 正在扫描
347 | Log.i(TAG, "onReceive: SCANNING 正在扫描");
348 | break;
349 | case AUTHENTICATING: // 正在验证
350 | Log.i(TAG, "onReceive: AUTHENTICATING: // 正在验证");
351 | break;
352 | case ASSOCIATING: // 正在关联
353 | Log.i(TAG, "onReceive: ASSOCIATING: // 正在关联");
354 | break;
355 | case ASSOCIATED: // 已经关联
356 | Log.i(TAG, "onReceive: ASSOCIATED: // 已经关联");
357 | break;
358 | case FOUR_WAY_HANDSHAKE: // 四次握手
359 | Log.i(TAG, "onReceive: FOUR_WAY_HANDSHAKE:");
360 | break;
361 | case GROUP_HANDSHAKE: // 组握手
362 | Log.i(TAG, "onReceive: GROUP_HANDSHAKE:");
363 | break;
364 | case COMPLETED: // 完成
365 | Log.i(TAG, "onReceive: WIFI_CONNECT_SUCCESS: // 完成");
366 | WifiInfo connectSuccessInfo = wifiManager.getConnectionInfo();
367 | if (null != connectSuccessInfo) {
368 | Message wifiConnectSuccessMessage = Message.obtain();
369 | wifiConnectSuccessMessage.what = WIFI_CONNECT_SUCCESS;
370 | wifiConnectSuccessMessage.obj = connectSuccessInfo.getSSID();
371 | mCallBackHandler.sendMessage(wifiConnectSuccessMessage);
372 | }
373 | break;
374 | case DORMANT: // 休眠
375 | Log.i(TAG, "onReceive: DORMANT:");
376 | break;
377 | case UNINITIALIZED: // 未初始化
378 | Log.i(TAG, "onReceive: UNINITIALIZED: // 未初始化");
379 | break;
380 | case INVALID: // 无效的
381 | Log.i(TAG, "onReceive: INVALID: // 无效的");
382 | break;
383 | default:
384 | break;
385 | }
386 | break;
387 | default:
388 | break;
389 | }
390 | }
391 | }
392 |
393 |
394 | private static class CallBackHandler extends Handler {
395 |
396 | @Override
397 | public void handleMessage(Message msg) {
398 | super.handleMessage(msg);
399 | switch (msg.what) {
400 | case WIFI_STATE_ENABLED: // WIFI已经打开
401 | if (null != mOnWifiEnabledListener) {
402 | mOnWifiEnabledListener.onWifiEnabled(true);
403 | }
404 | break;
405 | case WIFI_STATE_DISABLED: // WIFI已经关闭
406 | if (null != mOnWifiEnabledListener) {
407 | mOnWifiEnabledListener.onWifiEnabled(false);
408 | }
409 | break;
410 | case SCAN_RESULTS_UPDATED: // WIFI扫描完成
411 | if (null != mOnWifiScanResultsListener) {
412 | @SuppressWarnings("unchecked")
413 | List scanResults = (List) msg.obj;
414 | mOnWifiScanResultsListener.onScanResults(scanResults);
415 | }
416 | break;
417 | case WIFI_CONNECT_LOG: // WIFI连接完成
418 | if (null != mOnWifiConnectListener) {
419 | String log = (String) msg.obj;
420 | mOnWifiConnectListener.onWiFiConnectLog(log);
421 | }
422 | break;
423 | case WIFI_CONNECT_SUCCESS: // WIFI连接完成
424 | if (null != mOnWifiConnectListener) {
425 | String ssid = (String) msg.obj;
426 | mOnWifiConnectListener.onWiFiConnectSuccess(ssid);
427 | }
428 | break;
429 | case WIFI_CONNECT_FAILURE: // WIFI连接完成
430 | if (null != mOnWifiConnectListener) {
431 | String ssid = (String) msg.obj;
432 | mOnWifiConnectListener.onWiFiConnectFailure(ssid);
433 | }
434 | break;
435 | default:
436 | break;
437 | }
438 | }
439 | }
440 |
441 | private static OnWifiEnabledListener mOnWifiEnabledListener;
442 |
443 | private static OnWifiScanResultsListener mOnWifiScanResultsListener;
444 |
445 | private static OnWifiConnectListener mOnWifiConnectListener;
446 |
447 | public void setOnWifiEnabledListener(OnWifiEnabledListener listener) {
448 | mOnWifiEnabledListener = listener;
449 | }
450 |
451 | public void removeOnWifiEnabledListener() {
452 | mOnWifiEnabledListener = null;
453 | }
454 |
455 | public void setOnWifiScanResultsListener(OnWifiScanResultsListener listener) {
456 | mOnWifiScanResultsListener = listener;
457 | }
458 |
459 | public void removeOnWifiScanResultsListener() {
460 | mOnWifiScanResultsListener = null;
461 | }
462 |
463 | public void setOnWifiConnectListener(OnWifiConnectListener listener) {
464 | mOnWifiConnectListener = listener;
465 | }
466 |
467 | public void removeOnWifiConnectListener() {
468 | mOnWifiConnectListener = null;
469 | }
470 | }
471 |
--------------------------------------------------------------------------------
/WiFiLibrary/src/main/java/com/kongqw/wifilibrary/listener/OnWifiConnectListener.java:
--------------------------------------------------------------------------------
1 | package com.kongqw.wifilibrary.listener;
2 |
3 | /**
4 | * @Author: zhangyan
5 | * @Date: 2019/4/10 10:25
6 | * WIFI连接的回调接口
7 | */
8 | public interface OnWifiConnectListener {
9 |
10 | /**
11 | * WIFI连接信息的回调
12 | *
13 | * @param log log
14 | */
15 | void onWiFiConnectLog(String log);
16 |
17 | /**
18 | * WIFI连接成功的回调
19 | *
20 | * @param SSID 热点名
21 | */
22 | void onWiFiConnectSuccess(String SSID);
23 |
24 | /**
25 | * WIFI连接失败的回调
26 | *
27 | * @param SSID 热点名
28 | */
29 | void onWiFiConnectFailure(String SSID);
30 | }
31 |
--------------------------------------------------------------------------------
/WiFiLibrary/src/main/java/com/kongqw/wifilibrary/listener/OnWifiEnabledListener.java:
--------------------------------------------------------------------------------
1 | package com.kongqw.wifilibrary.listener;
2 |
3 | /**
4 | * @Author: zhangyan
5 | * @Date: 2019/4/10 10:19
6 | * WIFI打开关闭的回调接口
7 | */
8 | public interface OnWifiEnabledListener {
9 |
10 | /**
11 | * WIFI开关的回调
12 | *
13 | * @param enabled true 可用 false 不可用
14 | */
15 | void onWifiEnabled(boolean enabled);
16 | }
17 |
--------------------------------------------------------------------------------
/WiFiLibrary/src/main/java/com/kongqw/wifilibrary/listener/OnWifiScanResultsListener.java:
--------------------------------------------------------------------------------
1 | package com.kongqw.wifilibrary.listener;
2 |
3 | import android.net.wifi.ScanResult;
4 |
5 | import java.util.List;
6 |
7 | /**
8 | * @Author: zhangyan
9 | * @Date: 2019/4/10 10:17
10 | * WIFI扫描结果的回调接口
11 | */
12 | public interface OnWifiScanResultsListener {
13 |
14 | /**
15 | * 扫描结果的回调
16 | *
17 | * @param scanResults 扫描结果
18 | */
19 | void onScanResults(List scanResults);
20 | }
21 |
--------------------------------------------------------------------------------
/WiFiLibrary/src/main/res/values/strings.xml:
--------------------------------------------------------------------------------
1 |
2 | WiFiLibrary
3 |
4 |
--------------------------------------------------------------------------------
/app/.gitignore:
--------------------------------------------------------------------------------
1 | /build
2 |
--------------------------------------------------------------------------------
/app/build.gradle:
--------------------------------------------------------------------------------
1 | apply plugin: 'com.android.application'
2 |
3 | android {
4 | compileSdkVersion 25
5 | buildToolsVersion "25.0.2"
6 |
7 | defaultConfig {
8 | applicationId "kong.qingwei.kqwwifimanagerdemo"
9 | minSdkVersion 15
10 | targetSdkVersion 22
11 | versionCode 1
12 | versionName "1.0"
13 | vectorDrawables.useSupportLibrary = true
14 | }
15 | buildTypes {
16 | release {
17 | minifyEnabled false
18 | proguardFiles getDefaultProguardFile('proguard-android.txt'), 'proguard-rules.pro'
19 | }
20 | }
21 | }
22 |
23 | dependencies {
24 | compile fileTree(include: ['*.jar'], dir: 'libs')
25 | compile project(':WiFiLibrary')
26 | compile 'com.android.support:appcompat-v7:25.2.0'
27 | compile 'com.android.support:design:25.2.0'
28 | compile 'com.android.support:support-v4:25.2.0'
29 | compile 'com.android.support:support-vector-drawable:25.2.0'
30 | testCompile 'junit:junit:4.12'
31 |
32 | debugCompile 'com.squareup.leakcanary:leakcanary-android:1.5'
33 | releaseCompile 'com.squareup.leakcanary:leakcanary-android-no-op:1.5'
34 | testCompile 'com.squareup.leakcanary:leakcanary-android-no-op:1.5'
35 |
36 | compile 'com.github.kongqw:PermissionsManager:1.0.0'
37 | }
38 |
--------------------------------------------------------------------------------
/app/proguard-rules.pro:
--------------------------------------------------------------------------------
1 | # Add project specific ProGuard rules here.
2 | # By default, the flags in this file are appended to flags specified
3 | # in D:\Android\sdk/tools/proguard/proguard-android.txt
4 | # You can edit the include path and order by changing the proguardFiles
5 | # directive in build.gradle.
6 | #
7 | # For more details, see
8 | # http://developer.android.com/guide/developing/tools/proguard.html
9 |
10 | # Add any project specific keep options here:
11 |
12 | # If your project uses WebView with JS, uncomment the following
13 | # and specify the fully qualified class name to the JavaScript interface
14 | # class:
15 | #-keepclassmembers class fqcn.of.javascript.interface.for.webview {
16 | # public *;
17 | #}
18 |
--------------------------------------------------------------------------------
/app/src/main/AndroidManifest.xml:
--------------------------------------------------------------------------------
1 |
2 |
5 |
6 |
7 |
9 |
10 |
17 |
21 |
22 |
23 |
24 |
25 |
26 |
27 |
28 |
29 |
--------------------------------------------------------------------------------
/app/src/main/java/kong/qingwei/kqwwifimanagerdemo/MainActivity.java:
--------------------------------------------------------------------------------
1 | package kong.qingwei.kqwwifimanagerdemo;
2 |
3 | import android.Manifest;
4 | import android.content.DialogInterface;
5 | import android.net.wifi.ScanResult;
6 | import android.net.wifi.WifiConfiguration;
7 | import android.net.wifi.WifiInfo;
8 | import android.os.Bundle;
9 | import android.support.annotation.NonNull;
10 | import android.support.design.widget.Snackbar;
11 | import android.support.v4.widget.SwipeRefreshLayout;
12 | import android.support.v7.app.AlertDialog;
13 | import android.support.v7.app.AppCompatActivity;
14 | import android.support.v7.widget.SwitchCompat;
15 | import android.support.v7.widget.Toolbar;
16 | import android.util.Log;
17 | import android.view.View;
18 | import android.widget.AdapterView;
19 | import android.widget.CompoundButton;
20 | import android.widget.FrameLayout;
21 | import android.widget.ListView;
22 | import android.widget.Toast;
23 |
24 | import com.kongqw.permissionslibrary.PermissionsManager;
25 | import com.kongqw.wifilibrary.WiFiManager;
26 | import com.kongqw.wifilibrary.listener.OnWifiConnectListener;
27 | import com.kongqw.wifilibrary.listener.OnWifiEnabledListener;
28 | import com.kongqw.wifilibrary.listener.OnWifiScanResultsListener;
29 |
30 | import java.util.List;
31 |
32 | import kong.qingwei.kqwwifimanagerdemo.adapter.WifiListAdapter;
33 | import kong.qingwei.kqwwifimanagerdemo.view.ConnectWifiDialog;
34 |
35 | /**
36 | * @Author: zhangyan
37 | * @Date: 2019/4/10 10:30
38 | * 主活动
39 | */
40 | public class MainActivity extends AppCompatActivity implements SwipeRefreshLayout.OnRefreshListener, AdapterView.OnItemClickListener, AdapterView.OnItemLongClickListener, OnWifiScanResultsListener, OnWifiConnectListener, OnWifiEnabledListener {
41 |
42 | private static final String TAG = "MainActivity";
43 |
44 | private ListView mWifiList;
45 | private SwipeRefreshLayout mSwipeLayout;
46 | private PermissionsManager mPermissionsManager;
47 |
48 | // 所需的全部权限
49 | static final String[] PERMISSIONS = new String[]{
50 | Manifest.permission.ACCESS_FINE_LOCATION,
51 | Manifest.permission.ACCESS_COARSE_LOCATION
52 | };
53 | private final int GET_WIFI_LIST_REQUEST_CODE = 0;
54 | private WiFiManager mWiFiManager;
55 | private WifiListAdapter mWifiListAdapter;
56 | private SwitchCompat switchCompat;
57 | private SwitchCompat VLAN;
58 | private FrameLayout frameLayout;
59 |
60 | @Override
61 | protected void onCreate(Bundle savedInstanceState) {
62 | super.onCreate(savedInstanceState);
63 | setContentView(R.layout.activity_main);
64 | Toolbar toolbar = (Toolbar) findViewById(R.id.toolbar);
65 | setSupportActionBar(toolbar);
66 | // 加载View
67 | initView();
68 | // 添加WIFI开关的监听
69 | switchCompat.setOnCheckedChangeListener(new CompoundButton.OnCheckedChangeListener() {
70 | @Override
71 | public void onCheckedChanged(CompoundButton buttonView, boolean isChecked) {
72 | if (isChecked) {
73 | mWiFiManager.openWiFi();
74 | } else {
75 | mWiFiManager.closeWiFi();
76 | }
77 | }
78 | });
79 |
80 | //添加VLAN开关的监听
81 | VLAN.setOnCheckedChangeListener(new CompoundButton.OnCheckedChangeListener() {
82 | @Override
83 | public void onCheckedChanged(CompoundButton buttonView, boolean isChecked) {
84 | if (isChecked) {
85 | mWiFiManager.createWifiHotspot8("性感荷官在线发脾气", "123456789");
86 | } else {
87 | // mWiFiManager.closeWifiHotspot();
88 | }
89 | }
90 | });
91 |
92 |
93 | // 添加下拉刷新的监听
94 | mSwipeLayout.setOnRefreshListener(this);
95 | // 初始化WIFI列表
96 | mWifiList.setEmptyView(findViewById(R.id.empty_view));
97 | mWifiListAdapter = new WifiListAdapter(getApplicationContext());
98 | //加载适配器
99 | mWifiList.setAdapter(mWifiListAdapter);
100 | mWifiList.setOnItemClickListener(this);
101 | mWifiList.setOnItemLongClickListener(this);
102 | // WIFI管理器
103 | mWiFiManager = WiFiManager.getInstance(getApplicationContext());
104 | // 动态权限管理器
105 | mPermissionsManager = new PermissionsManager(this) {
106 | @Override
107 | public void authorized(int requestCode) {
108 | // 6.0 以上系统授权通过
109 | if (GET_WIFI_LIST_REQUEST_CODE == requestCode) {
110 | // 获取WIFI列表
111 | List scanResults = mWiFiManager.getScanResults();
112 | refreshData(scanResults);
113 | }
114 | }
115 |
116 | @Override
117 | public void noAuthorization(int requestCode, String[] lacksPermissions) {
118 | // 6.0 以上系统授权失败
119 | }
120 |
121 | @Override
122 | public void ignore() {
123 | // 6.0 以下系统 获取WIFI列表
124 | List scanResults = mWiFiManager.getScanResults();
125 | refreshData(scanResults);
126 | }
127 | };
128 | // 请求WIFI列表
129 | mPermissionsManager.checkPermissions(GET_WIFI_LIST_REQUEST_CODE, PERMISSIONS);
130 | }
131 |
132 | /**
133 | * 初始化界面
134 | */
135 | private void initView() {
136 | // WIFI 开关
137 | switchCompat = (SwitchCompat) findViewById(R.id.switch_wifi);
138 | //开启热点开关
139 | VLAN = (SwitchCompat) findViewById(R.id.switch_vlan);
140 | // 显示WIFI信息的布局
141 | frameLayout = (FrameLayout) findViewById(R.id.fl_wifi);
142 | // 下拉刷新
143 | mSwipeLayout = (SwipeRefreshLayout) findViewById(R.id.swipeRefreshLayout);
144 | // WIFI列表
145 | mWifiList = (ListView) findViewById(R.id.wifi_list);
146 | }
147 |
148 | @Override
149 | protected void onResume() {
150 | super.onResume();
151 | // 添加监听
152 | mWiFiManager.setOnWifiEnabledListener(this);
153 | mWiFiManager.setOnWifiScanResultsListener(this);
154 | mWiFiManager.setOnWifiConnectListener(this);
155 | // 更新WIFI开关状态
156 | switchCompat.setChecked(mWiFiManager.isWifiEnabled());
157 | }
158 |
159 | @Override
160 | protected void onPause() {
161 | super.onPause();
162 | // 移除监听
163 | mWiFiManager.removeOnWifiEnabledListener();
164 | mWiFiManager.removeOnWifiScanResultsListener();
165 | mWiFiManager.removeOnWifiConnectListener();
166 | }
167 |
168 | /**
169 | * 刷新页面
170 | *
171 | * @param scanResults WIFI数据
172 | */
173 | public void refreshData(List scanResults) {
174 | mSwipeLayout.setRefreshing(false);
175 | // 刷新界面
176 | mWifiListAdapter.refreshData(scanResults);
177 |
178 | Snackbar.make(mWifiList, "WIFI列表刷新成功", Snackbar.LENGTH_SHORT).show();
179 | }
180 |
181 | /**
182 | * Android 6.0 权限校验
183 | *
184 | * @param requestCode requestCode
185 | * @param permissions permissions
186 | * @param grantResults grantResults
187 | */
188 | @Override
189 | public void onRequestPermissionsResult(int requestCode, @NonNull String[] permissions, @NonNull int[] grantResults) {
190 | super.onRequestPermissionsResult(requestCode, permissions, grantResults);
191 | // 复查权限
192 | mPermissionsManager.recheckPermissions(requestCode, permissions, grantResults);
193 | }
194 |
195 | /**
196 | * WIFI列表单击监听
197 | * 三个安全性的排序为:WEP < WPA < WPA2
198 | *
199 | * @param parent parent
200 | * @param view view
201 | * @param position position
202 | * @param id id
203 | */
204 | @Override
205 | public void onItemClick(AdapterView> parent, View view, int position, long id) {
206 | final ScanResult scanResult = (ScanResult) mWifiListAdapter.getItem(position);
207 | switch (mWiFiManager.getSecurityMode(scanResult)) {
208 | case WEP:
209 | new ConnectWifiDialog(this) {
210 |
211 | @Override
212 | public void connect(String password) {
213 | mWiFiManager.connectWEPNetwork(scanResult.SSID, password);
214 | }
215 | }.setSsid(scanResult.SSID).show();
216 | break;
217 | case WPA:
218 | new ConnectWifiDialog(this) {
219 |
220 | @Override
221 | public void connect(String password) {
222 | mWiFiManager.connectWPA2Network(scanResult.SSID, password);
223 | }
224 | }.setSsid(scanResult.SSID).show();
225 | break;
226 | case WPA2:
227 | new ConnectWifiDialog(this) {
228 |
229 | @Override
230 | public void connect(String password) {
231 | mWiFiManager.connectWPA2Network(scanResult.SSID, password);
232 | }
233 | }.setSsid(scanResult.SSID).show();
234 | break;
235 | case OPEN:
236 | mWiFiManager.connectOpenNetwork(scanResult.SSID);
237 | break;
238 | }
239 | }
240 |
241 | /**
242 | * WIFI列表长按
243 | *
244 | * @param parent parent
245 | * @param view view
246 | * @param position position
247 | * @param id id
248 | * @return 是否拦截长按事件
249 | */
250 | @Override
251 | public boolean onItemLongClick(AdapterView> parent, View view, int position, long id) {
252 | ScanResult scanResult = (ScanResult) mWifiListAdapter.getItem(position);
253 | final String ssid = scanResult.SSID;
254 | new AlertDialog.Builder(this)
255 | .setTitle(ssid)
256 | .setItems(new String[]{"断开连接", "删除网络配置"}, new DialogInterface.OnClickListener() {
257 | @Override
258 | public void onClick(DialogInterface dialog, int which) {
259 | switch (which) {
260 | case 0: // 断开连接
261 | WifiInfo connectionInfo = mWiFiManager.getConnectionInfo();
262 | Log.i(TAG, "onClick: connectionInfo :" + connectionInfo.getSSID());
263 | if (mWiFiManager.addDoubleQuotation(ssid).equals(connectionInfo.getSSID())) {
264 | mWiFiManager.disconnectWifi(connectionInfo.getNetworkId());
265 | } else {
266 | Toast.makeText(getApplicationContext(), "当前没有连接 [ " + ssid + " ]", Toast.LENGTH_SHORT).show();
267 | }
268 | break;
269 | case 1: // 删除网络配置
270 | WifiConfiguration wifiConfiguration = mWiFiManager.getConfigFromConfiguredNetworksBySsid(ssid);
271 | if (null != wifiConfiguration) {
272 | boolean isDelete = mWiFiManager.deleteConfig(wifiConfiguration.networkId);
273 | Toast.makeText(getApplicationContext(), isDelete ? "删除成功!" : "其他应用配置的网络没有ROOT权限不能删除!", Toast.LENGTH_SHORT).show();
274 | } else {
275 | Toast.makeText(getApplicationContext(), "没有保存该网络!", Toast.LENGTH_SHORT).show();
276 | }
277 | break;
278 | default:
279 | break;
280 | }
281 | }
282 | })
283 | .show();
284 | return true;
285 | }
286 |
287 |
288 | /**
289 | * 下拉刷新的回调
290 | */
291 | @Override
292 | public void onRefresh() {
293 | // 下拉刷新
294 | mWiFiManager.startScan();
295 | }
296 |
297 | /**
298 | * WIFI列表刷新后的回调
299 | *
300 | * @param scanResults 扫描结果
301 | */
302 | @Override
303 | public void onScanResults(List scanResults) {
304 | refreshData(scanResults);
305 | }
306 |
307 | /**
308 | * WIFI连接的Log得回调
309 | *
310 | * @param log log
311 | */
312 | @Override
313 | public void onWiFiConnectLog(String log) {
314 | Log.i(TAG, "onWiFiConnectLog: " + log);
315 | Snackbar.make(mWifiList, "WIFI正在连接 : " + log, Snackbar.LENGTH_SHORT).show();
316 | }
317 |
318 | /**
319 | * WIFI连接成功的回调
320 | *
321 | * @param SSID 热点名
322 | */
323 | @Override
324 | public void onWiFiConnectSuccess(String SSID) {
325 | Log.i(TAG, "onWiFiConnectSuccess: [ " + SSID + " ] 连接成功");
326 | Toast.makeText(getApplicationContext(), SSID + " 连接成功", Toast.LENGTH_SHORT).show();
327 | }
328 |
329 | /**
330 | * WIFI连接失败的回调
331 | *
332 | * @param SSID 热点名
333 | */
334 | @Override
335 | public void onWiFiConnectFailure(String SSID) {
336 | Log.i(TAG, "onWiFiConnectFailure: [ " + SSID + " ] 连接失败");
337 | Toast.makeText(getApplicationContext(), SSID + " 连接失败!请重新连接!", Toast.LENGTH_SHORT).show();
338 | }
339 |
340 | /**
341 | * WIFI开关状态的回调
342 | *
343 | * @param enabled true 可用 false 不可用
344 | */
345 | @Override
346 | public void onWifiEnabled(boolean enabled) {
347 | switchCompat.setChecked(enabled);
348 | frameLayout.setVisibility(enabled ? View.VISIBLE : View.GONE);
349 | }
350 |
351 | }
352 |
--------------------------------------------------------------------------------
/app/src/main/java/kong/qingwei/kqwwifimanagerdemo/MyApplication.java:
--------------------------------------------------------------------------------
1 | package kong.qingwei.kqwwifimanagerdemo;
2 |
3 | import android.app.Application;
4 | import android.content.Context;
5 |
6 | import com.squareup.leakcanary.LeakCanary;
7 |
8 | /**
9 | * @Author: zhangyan
10 | * @Date: 2019/4/9 15:48
11 | * @Description: 全局Application
12 | * @Version: 1.0
13 | */
14 | public class MyApplication extends Application {
15 |
16 | @Override
17 | public void onCreate() {
18 | super.onCreate();
19 | context = getApplicationContext();
20 |
21 | if (LeakCanary.isInAnalyzerProcess(this)) {
22 | return;
23 | }
24 | LeakCanary.install(this);
25 | }
26 |
27 | public static Context getContext() {
28 | return context;
29 | }
30 |
31 | private static Context context;
32 |
33 | }
34 |
--------------------------------------------------------------------------------
/app/src/main/java/kong/qingwei/kqwwifimanagerdemo/adapter/WifiListAdapter.java:
--------------------------------------------------------------------------------
1 | package kong.qingwei.kqwwifimanagerdemo.adapter;
2 |
3 | import android.content.Context;
4 | import android.net.wifi.ScanResult;
5 | import android.net.wifi.WifiManager;
6 | import android.text.Layout;
7 | import android.util.Log;
8 | import android.view.LayoutInflater;
9 | import android.view.View;
10 | import android.view.ViewGroup;
11 | import android.widget.BaseAdapter;
12 | import android.widget.TextView;
13 |
14 | import com.kongqw.wifilibrary.WiFiManager;
15 |
16 | import java.util.ArrayList;
17 | import java.util.List;
18 |
19 | import kong.qingwei.kqwwifimanagerdemo.R;
20 |
21 | /**
22 | * @Author: zhangyan
23 | * @Date: 2019/4/10 10:46
24 | * Wifi列表ListView的数据适配器
25 | */
26 | public class WifiListAdapter extends BaseAdapter {
27 |
28 | private static final String TAG = "WifiListAdapter";
29 | private List scanResults;
30 | private Context mContext;
31 |
32 | /**
33 | * 构造函数
34 | *
35 | * @param context
36 | */
37 | public WifiListAdapter(Context context) {
38 | mContext = context.getApplicationContext();
39 | this.scanResults = new ArrayList<>();
40 | }
41 |
42 | /**
43 | * 更新数据
44 | *
45 | * @param scanResults
46 | */
47 | public void refreshData(List scanResults) {
48 | if (null != scanResults) {
49 | Log.i(TAG, "refreshData 1 : " + scanResults.size());
50 | // 去重
51 | scanResults = WiFiManager.excludeRepetition(scanResults);
52 | Log.i(TAG, "refreshData 2 : " + scanResults.size());
53 | // 清空数据
54 | this.scanResults.clear();
55 | // 更新数据
56 | this.scanResults.addAll(scanResults);
57 | }
58 | // 更新显示
59 | notifyDataSetChanged();
60 | }
61 |
62 | @Override
63 | public int getCount() {
64 | return scanResults.size();
65 | }
66 |
67 | @Override
68 | public Object getItem(int position) {
69 | return scanResults.get(position);
70 | }
71 |
72 | @Override
73 | public long getItemId(int position) {
74 | return position;
75 | }
76 |
77 | @Override
78 | public View getView(int position, View convertView, ViewGroup parent) {
79 | ViewHolder holder;
80 | ScanResult scanResult;
81 |
82 | if (convertView == null) {
83 | LayoutInflater layoutInflater = LayoutInflater.from(mContext);
84 | convertView = layoutInflater.inflate(R.layout.item_wifi, null);
85 | holder = new ViewHolder();
86 | holder.ssid = (TextView) (convertView).findViewById(R.id.ssid);
87 | convertView.setTag(holder);
88 |
89 | } else {
90 | holder = (ViewHolder) convertView.getTag();
91 | }
92 | scanResult = scanResults.get(position);
93 | holder.ssid.setText("热点名称:" + scanResult.SSID + "\n信号强度:" + WifiManager.calculateSignalLevel(scanResult.level, 5) + "/5\n加密方式:" + scanResult.capabilities);
94 | return convertView;
95 | }
96 |
97 | private class ViewHolder {
98 | private TextView ssid;
99 | }
100 | }
101 |
--------------------------------------------------------------------------------
/app/src/main/java/kong/qingwei/kqwwifimanagerdemo/util/VlanUtil.java:
--------------------------------------------------------------------------------
1 | package kong.qingwei.kqwwifimanagerdemo.util;
2 |
3 | /**
4 | * @Author: zhangyan
5 | * @Date: 2019/4/9 17:26
6 | * @Description:
7 | * @Version: 1.0
8 | */
9 | /**
10 | * 开启热点工具类
11 | */
12 | public class VlanUtil {
13 |
14 |
15 | }
16 |
17 |
--------------------------------------------------------------------------------
/app/src/main/java/kong/qingwei/kqwwifimanagerdemo/view/ConnectWifiDialog.java:
--------------------------------------------------------------------------------
1 | package kong.qingwei.kqwwifimanagerdemo.view;
2 |
3 | import android.app.Dialog;
4 | import android.content.Context;
5 | import android.text.TextUtils;
6 | import android.view.Gravity;
7 | import android.view.View;
8 | import android.view.Window;
9 | import android.view.WindowManager;
10 | import android.widget.Button;
11 | import android.widget.EditText;
12 | import android.widget.TextView;
13 | import android.widget.Toast;
14 |
15 | import kong.qingwei.kqwwifimanagerdemo.R;
16 |
17 | /**
18 | * @Author: zhangyan
19 | * @Date: 2019/4/10 10:17\
20 | * 连接wifi监听
21 | **/
22 |
23 | public abstract class ConnectWifiDialog extends Dialog implements View.OnClickListener {
24 |
25 | private EditText mEditTextPassword;
26 |
27 | public abstract void connect(String password);
28 |
29 | private TextView mTextViewSsid;
30 |
31 | public ConnectWifiDialog(Context context) {
32 | super(context, R.style.ShareDialog);
33 | initView();
34 | }
35 |
36 | private void initView() {
37 | // 布局这里考虑只有分享到微信还有和朋友圈 所以没有用RecyclerView
38 | View view = View.inflate(getContext().getApplicationContext(), R.layout.dialog_connect_wifi, null);
39 | mTextViewSsid = (TextView) view.findViewById(R.id.tv_ssid);
40 | mEditTextPassword = (EditText) view.findViewById(R.id.et_pwd);
41 | Button mButtonCancel = (Button) view.findViewById(R.id.btn_cancel);
42 | mButtonCancel.setOnClickListener(this);
43 | Button mButtonConnect = (Button) view.findViewById(R.id.btn_connect);
44 | mButtonConnect.setOnClickListener(this);
45 | // 加载布局
46 | setContentView(view);
47 | // 设置Dialog参数
48 | Window window = getWindow();
49 | WindowManager.LayoutParams params = window.getAttributes();
50 | params.width = WindowManager.LayoutParams.MATCH_PARENT;
51 | params.height = WindowManager.LayoutParams.WRAP_CONTENT;
52 | params.gravity = Gravity.CENTER;
53 | window.setAttributes(params);
54 | }
55 |
56 | public ConnectWifiDialog setSsid(String ssid) {
57 | mTextViewSsid.setText(ssid);
58 | return this;
59 | }
60 |
61 | @Override
62 | public void onClick(View v) {
63 | switch (v.getId()) {
64 | case R.id.btn_cancel:
65 |
66 | dismiss();
67 | break;
68 | case R.id.btn_connect:
69 | String pwd = mEditTextPassword.getText().toString();
70 | if (TextUtils.isEmpty(pwd)) {
71 | Toast.makeText(getContext(), "小老弟,密码不能为空 !", Toast.LENGTH_SHORT).show();
72 | } else {
73 | connect(pwd);
74 | dismiss();
75 | }
76 | break;
77 | }
78 | }
79 | }
80 |
--------------------------------------------------------------------------------
/app/src/main/res/anim/dialog_bottom_in.xml:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
8 |
--------------------------------------------------------------------------------
/app/src/main/res/anim/dialog_bottom_out.xml:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
8 |
--------------------------------------------------------------------------------
/app/src/main/res/layout/activity_main.xml:
--------------------------------------------------------------------------------
1 |
2 |
9 |
10 |
14 |
15 |
21 |
22 |
23 |
24 |
29 |
30 |
36 |
37 |
43 |
44 |
48 |
49 |
53 |
54 |
58 |
59 |
63 |
64 |
65 |
72 |
73 |
74 |
75 |
76 |
77 |
--------------------------------------------------------------------------------
/app/src/main/res/layout/dialog_connect_wifi.xml:
--------------------------------------------------------------------------------
1 |
2 |
11 |
12 |
18 |
19 |
26 |
27 |
31 |
32 |
38 |
39 |
45 |
46 |
--------------------------------------------------------------------------------
/app/src/main/res/layout/item_wifi.xml:
--------------------------------------------------------------------------------
1 |
2 |
9 |
10 |
17 |
18 |
19 |
--------------------------------------------------------------------------------
/app/src/main/res/mipmap-hdpi/alipay.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/YanInfo/WiFiManager/eb4268220db99ffa1778583acd4fa88252088f9f/app/src/main/res/mipmap-hdpi/alipay.png
--------------------------------------------------------------------------------
/app/src/main/res/mipmap-hdpi/ic_launcher.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/YanInfo/WiFiManager/eb4268220db99ffa1778583acd4fa88252088f9f/app/src/main/res/mipmap-hdpi/ic_launcher.png
--------------------------------------------------------------------------------
/app/src/main/res/mipmap-mdpi/ic_launcher.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/YanInfo/WiFiManager/eb4268220db99ffa1778583acd4fa88252088f9f/app/src/main/res/mipmap-mdpi/ic_launcher.png
--------------------------------------------------------------------------------
/app/src/main/res/mipmap-xhdpi/ic_launcher.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/YanInfo/WiFiManager/eb4268220db99ffa1778583acd4fa88252088f9f/app/src/main/res/mipmap-xhdpi/ic_launcher.png
--------------------------------------------------------------------------------
/app/src/main/res/mipmap-xxhdpi/ic_launcher.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/YanInfo/WiFiManager/eb4268220db99ffa1778583acd4fa88252088f9f/app/src/main/res/mipmap-xxhdpi/ic_launcher.png
--------------------------------------------------------------------------------
/app/src/main/res/mipmap-xxxhdpi/ic_launcher.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/YanInfo/WiFiManager/eb4268220db99ffa1778583acd4fa88252088f9f/app/src/main/res/mipmap-xxxhdpi/ic_launcher.png
--------------------------------------------------------------------------------
/app/src/main/res/values-v21/styles.xml:
--------------------------------------------------------------------------------
1 |
2 |
3 |
--------------------------------------------------------------------------------
/app/src/main/res/values-w820dp/dimens.xml:
--------------------------------------------------------------------------------
1 |
2 |
5 | 64dp
6 |
7 |
--------------------------------------------------------------------------------
/app/src/main/res/values/colors.xml:
--------------------------------------------------------------------------------
1 |
2 |
3 | #3F51B5
4 | #303F9F
5 | #FF4081
6 |
7 |
--------------------------------------------------------------------------------
/app/src/main/res/values/dimens.xml:
--------------------------------------------------------------------------------
1 |
2 |
3 | 16dp
4 | 16dp
5 | 16dp
6 |
7 |
--------------------------------------------------------------------------------
/app/src/main/res/values/strings.xml:
--------------------------------------------------------------------------------
1 |
2 | AndroidWiFiManager
3 | MainActivity
4 |
5 |
--------------------------------------------------------------------------------
/app/src/main/res/values/styles.xml:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
10 |
11 |
15 |
16 |
17 |
18 |
19 |
20 |
21 |
25 |
26 |
42 |
43 |
--------------------------------------------------------------------------------
/build.gradle:
--------------------------------------------------------------------------------
1 | // Top-level build file where you can add configuration options common to all sub-projects/modules.
2 |
3 | buildscript {
4 | repositories {
5 | jcenter()
6 | }
7 | dependencies {
8 | classpath 'com.android.tools.build:gradle:2.3.1'
9 |
10 | // NOTE: Do not place your application dependencies here; they belong
11 | // in the individual module build.gradle files
12 | }
13 | }
14 |
15 | allprojects {
16 | repositories {
17 | jcenter()
18 | maven { url 'https://jitpack.io' }
19 | }
20 | }
21 |
22 | task clean(type: Delete) {
23 | delete rootProject.buildDir
24 | }
25 |
--------------------------------------------------------------------------------
/gradle.properties:
--------------------------------------------------------------------------------
1 | # Project-wide Gradle settings.
2 |
3 | # IDE (e.g. Android Studio) users:
4 | # Gradle settings configured through the IDE *will override*
5 | # any settings specified in this file.
6 |
7 | # For more details on how to configure your build environment visit
8 | # http://www.gradle.org/docs/current/userguide/build_environment.html
9 |
10 | # Specifies the JVM arguments used for the daemon process.
11 | # The setting is particularly useful for tweaking memory settings.
12 | # Default value: -Xmx10248m -XX:MaxPermSize=256m
13 | # org.gradle.jvmargs=-Xmx2048m -XX:MaxPermSize=512m -XX:+HeapDumpOnOutOfMemoryError -Dfile.encoding=UTF-8
14 |
15 | # When configured, Gradle will run in incubating parallel mode.
16 | # This option should only be used with decoupled projects. More details, visit
17 | # http://www.gradle.org/docs/current/userguide/multi_project_builds.html#sec:decoupled_projects
18 | # org.gradle.parallel=true
--------------------------------------------------------------------------------
/gradle/wrapper/gradle-wrapper.jar:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/YanInfo/WiFiManager/eb4268220db99ffa1778583acd4fa88252088f9f/gradle/wrapper/gradle-wrapper.jar
--------------------------------------------------------------------------------
/gradle/wrapper/gradle-wrapper.properties:
--------------------------------------------------------------------------------
1 | #Wed Mar 08 14:00:33 CST 2017
2 | distributionBase=GRADLE_USER_HOME
3 | distributionPath=wrapper/dists
4 | zipStoreBase=GRADLE_USER_HOME
5 | zipStorePath=wrapper/dists
6 | distributionUrl=https\://services.gradle.org/distributions/gradle-3.3-all.zip
7 |
--------------------------------------------------------------------------------
/gradlew:
--------------------------------------------------------------------------------
1 | #!/usr/bin/env bash
2 |
3 | ##############################################################################
4 | ##
5 | ## Gradle start up script for UN*X
6 | ##
7 | ##############################################################################
8 |
9 | # Add default JVM options here. You can also use JAVA_OPTS and GRADLE_OPTS to pass JVM options to this script.
10 | DEFAULT_JVM_OPTS=""
11 |
12 | APP_NAME="Gradle"
13 | APP_BASE_NAME=`basename "$0"`
14 |
15 | # Use the maximum available, or set MAX_FD != -1 to use that value.
16 | MAX_FD="maximum"
17 |
18 | warn ( ) {
19 | echo "$*"
20 | }
21 |
22 | die ( ) {
23 | echo
24 | echo "$*"
25 | echo
26 | exit 1
27 | }
28 |
29 | # OS specific support (must be 'true' or 'false').
30 | cygwin=false
31 | msys=false
32 | darwin=false
33 | case "`uname`" in
34 | CYGWIN* )
35 | cygwin=true
36 | ;;
37 | Darwin* )
38 | darwin=true
39 | ;;
40 | MINGW* )
41 | msys=true
42 | ;;
43 | esac
44 |
45 | # Attempt to set APP_HOME
46 | # Resolve links: $0 may be a link
47 | PRG="$0"
48 | # Need this for relative symlinks.
49 | while [ -h "$PRG" ] ; do
50 | ls=`ls -ld "$PRG"`
51 | link=`expr "$ls" : '.*-> \(.*\)$'`
52 | if expr "$link" : '/.*' > /dev/null; then
53 | PRG="$link"
54 | else
55 | PRG=`dirname "$PRG"`"/$link"
56 | fi
57 | done
58 | SAVED="`pwd`"
59 | cd "`dirname \"$PRG\"`/" >/dev/null
60 | APP_HOME="`pwd -P`"
61 | cd "$SAVED" >/dev/null
62 |
63 | CLASSPATH=$APP_HOME/gradle/wrapper/gradle-wrapper.jar
64 |
65 | # Determine the Java command to use to start the JVM.
66 | if [ -n "$JAVA_HOME" ] ; then
67 | if [ -x "$JAVA_HOME/jre/sh/java" ] ; then
68 | # IBM's JDK on AIX uses strange locations for the executables
69 | JAVACMD="$JAVA_HOME/jre/sh/java"
70 | else
71 | JAVACMD="$JAVA_HOME/bin/java"
72 | fi
73 | if [ ! -x "$JAVACMD" ] ; then
74 | die "ERROR: JAVA_HOME is set to an invalid directory: $JAVA_HOME
75 |
76 | Please set the JAVA_HOME variable in your environment to match the
77 | location of your Java installation."
78 | fi
79 | else
80 | JAVACMD="java"
81 | which java >/dev/null 2>&1 || die "ERROR: JAVA_HOME is not set and no 'java' command could be found in your PATH.
82 |
83 | Please set the JAVA_HOME variable in your environment to match the
84 | location of your Java installation."
85 | fi
86 |
87 | # Increase the maximum file descriptors if we can.
88 | if [ "$cygwin" = "false" -a "$darwin" = "false" ] ; then
89 | MAX_FD_LIMIT=`ulimit -H -n`
90 | if [ $? -eq 0 ] ; then
91 | if [ "$MAX_FD" = "maximum" -o "$MAX_FD" = "max" ] ; then
92 | MAX_FD="$MAX_FD_LIMIT"
93 | fi
94 | ulimit -n $MAX_FD
95 | if [ $? -ne 0 ] ; then
96 | warn "Could not set maximum file descriptor limit: $MAX_FD"
97 | fi
98 | else
99 | warn "Could not query maximum file descriptor limit: $MAX_FD_LIMIT"
100 | fi
101 | fi
102 |
103 | # For Darwin, add options to specify how the application appears in the dock
104 | if $darwin; then
105 | GRADLE_OPTS="$GRADLE_OPTS \"-Xdock:name=$APP_NAME\" \"-Xdock:icon=$APP_HOME/media/gradle.icns\""
106 | fi
107 |
108 | # For Cygwin, switch paths to Windows format before running java
109 | if $cygwin ; then
110 | APP_HOME=`cygpath --path --mixed "$APP_HOME"`
111 | CLASSPATH=`cygpath --path --mixed "$CLASSPATH"`
112 | JAVACMD=`cygpath --unix "$JAVACMD"`
113 |
114 | # We build the pattern for arguments to be converted via cygpath
115 | ROOTDIRSRAW=`find -L / -maxdepth 1 -mindepth 1 -type d 2>/dev/null`
116 | SEP=""
117 | for dir in $ROOTDIRSRAW ; do
118 | ROOTDIRS="$ROOTDIRS$SEP$dir"
119 | SEP="|"
120 | done
121 | OURCYGPATTERN="(^($ROOTDIRS))"
122 | # Add a user-defined pattern to the cygpath arguments
123 | if [ "$GRADLE_CYGPATTERN" != "" ] ; then
124 | OURCYGPATTERN="$OURCYGPATTERN|($GRADLE_CYGPATTERN)"
125 | fi
126 | # Now convert the arguments - kludge to limit ourselves to /bin/sh
127 | i=0
128 | for arg in "$@" ; do
129 | CHECK=`echo "$arg"|egrep -c "$OURCYGPATTERN" -`
130 | CHECK2=`echo "$arg"|egrep -c "^-"` ### Determine if an option
131 |
132 | if [ $CHECK -ne 0 ] && [ $CHECK2 -eq 0 ] ; then ### Added a condition
133 | eval `echo args$i`=`cygpath --path --ignore --mixed "$arg"`
134 | else
135 | eval `echo args$i`="\"$arg\""
136 | fi
137 | i=$((i+1))
138 | done
139 | case $i in
140 | (0) set -- ;;
141 | (1) set -- "$args0" ;;
142 | (2) set -- "$args0" "$args1" ;;
143 | (3) set -- "$args0" "$args1" "$args2" ;;
144 | (4) set -- "$args0" "$args1" "$args2" "$args3" ;;
145 | (5) set -- "$args0" "$args1" "$args2" "$args3" "$args4" ;;
146 | (6) set -- "$args0" "$args1" "$args2" "$args3" "$args4" "$args5" ;;
147 | (7) set -- "$args0" "$args1" "$args2" "$args3" "$args4" "$args5" "$args6" ;;
148 | (8) set -- "$args0" "$args1" "$args2" "$args3" "$args4" "$args5" "$args6" "$args7" ;;
149 | (9) set -- "$args0" "$args1" "$args2" "$args3" "$args4" "$args5" "$args6" "$args7" "$args8" ;;
150 | esac
151 | fi
152 |
153 | # Split up the JVM_OPTS And GRADLE_OPTS values into an array, following the shell quoting and substitution rules
154 | function splitJvmOpts() {
155 | JVM_OPTS=("$@")
156 | }
157 | eval splitJvmOpts $DEFAULT_JVM_OPTS $JAVA_OPTS $GRADLE_OPTS
158 | JVM_OPTS[${#JVM_OPTS[*]}]="-Dorg.gradle.appname=$APP_BASE_NAME"
159 |
160 | exec "$JAVACMD" "${JVM_OPTS[@]}" -classpath "$CLASSPATH" org.gradle.wrapper.GradleWrapperMain "$@"
161 |
--------------------------------------------------------------------------------
/gradlew.bat:
--------------------------------------------------------------------------------
1 | @if "%DEBUG%" == "" @echo off
2 | @rem ##########################################################################
3 | @rem
4 | @rem Gradle startup script for Windows
5 | @rem
6 | @rem ##########################################################################
7 |
8 | @rem Set local scope for the variables with windows NT shell
9 | if "%OS%"=="Windows_NT" setlocal
10 |
11 | @rem Add default JVM options here. You can also use JAVA_OPTS and GRADLE_OPTS to pass JVM options to this script.
12 | set DEFAULT_JVM_OPTS=
13 |
14 | set DIRNAME=%~dp0
15 | if "%DIRNAME%" == "" set DIRNAME=.
16 | set APP_BASE_NAME=%~n0
17 | set APP_HOME=%DIRNAME%
18 |
19 | @rem Find java.exe
20 | if defined JAVA_HOME goto findJavaFromJavaHome
21 |
22 | set JAVA_EXE=java.exe
23 | %JAVA_EXE% -version >NUL 2>&1
24 | if "%ERRORLEVEL%" == "0" goto init
25 |
26 | echo.
27 | echo ERROR: JAVA_HOME is not set and no 'java' command could be found in your PATH.
28 | echo.
29 | echo Please set the JAVA_HOME variable in your environment to match the
30 | echo location of your Java installation.
31 |
32 | goto fail
33 |
34 | :findJavaFromJavaHome
35 | set JAVA_HOME=%JAVA_HOME:"=%
36 | set JAVA_EXE=%JAVA_HOME%/bin/java.exe
37 |
38 | if exist "%JAVA_EXE%" goto init
39 |
40 | echo.
41 | echo ERROR: JAVA_HOME is set to an invalid directory: %JAVA_HOME%
42 | echo.
43 | echo Please set the JAVA_HOME variable in your environment to match the
44 | echo location of your Java installation.
45 |
46 | goto fail
47 |
48 | :init
49 | @rem Get command-line arguments, handling Windowz variants
50 |
51 | if not "%OS%" == "Windows_NT" goto win9xME_args
52 | if "%@eval[2+2]" == "4" goto 4NT_args
53 |
54 | :win9xME_args
55 | @rem Slurp the command line arguments.
56 | set CMD_LINE_ARGS=
57 | set _SKIP=2
58 |
59 | :win9xME_args_slurp
60 | if "x%~1" == "x" goto execute
61 |
62 | set CMD_LINE_ARGS=%*
63 | goto execute
64 |
65 | :4NT_args
66 | @rem Get arguments from the 4NT Shell from JP Software
67 | set CMD_LINE_ARGS=%$
68 |
69 | :execute
70 | @rem Setup the command line
71 |
72 | set CLASSPATH=%APP_HOME%\gradle\wrapper\gradle-wrapper.jar
73 |
74 | @rem Execute Gradle
75 | "%JAVA_EXE%" %DEFAULT_JVM_OPTS% %JAVA_OPTS% %GRADLE_OPTS% "-Dorg.gradle.appname=%APP_BASE_NAME%" -classpath "%CLASSPATH%" org.gradle.wrapper.GradleWrapperMain %CMD_LINE_ARGS%
76 |
77 | :end
78 | @rem End local scope for the variables with windows NT shell
79 | if "%ERRORLEVEL%"=="0" goto mainEnd
80 |
81 | :fail
82 | rem Set variable GRADLE_EXIT_CONSOLE if you need the _script_ return code instead of
83 | rem the _cmd.exe /c_ return code!
84 | if not "" == "%GRADLE_EXIT_CONSOLE%" exit 1
85 | exit /b 1
86 |
87 | :mainEnd
88 | if "%OS%"=="Windows_NT" endlocal
89 |
90 | :omega
91 |
--------------------------------------------------------------------------------
/settings.gradle:
--------------------------------------------------------------------------------
1 | include ':app', ':WiFiLibrary'
2 |
--------------------------------------------------------------------------------