Implement Wi-Fi DPP flow
1. Wi-Fi DPP hanshake fail UI 2. Show Wi-Fi DPP QR code information field on WifiDppAddDeviceFragment if it's available. 3. Click 'Choose Different Network' button will show WifiDppChooseSavedWifiNetworkFragment 4. After QR code scanner scans success, WifiDppConfiguratorActivity caches WifiQrCode instead of just a QR code string Bug: 122429170 Test: manual test Change-Id: I1ce1b014ff86903b5a7a8f3575cc98eb1079583c
This commit is contained in:
@@ -2104,6 +2104,12 @@
|
||||
<string name="wifi_dpp_add_another_device">Add another device</string>
|
||||
<!-- Button label to choose different Wi-Fi network [CHAR LIMIT=80] -->
|
||||
<string name="wifi_dpp_choose_different_network">Choose different network</string>
|
||||
<!-- Hint for QR code detection [CHAR LIMIT=50] -->
|
||||
<string name="wifi_dpp_could_not_add_device">Couldn\u2019t add device</string>
|
||||
<!-- Title for the fragment to show that device found but naming known [CHAR LIMIT=50] -->
|
||||
<string name="wifi_dpp_device_found">Device found</string>
|
||||
<!-- Label for the try again button [CHAR LIMIT=20]-->
|
||||
<string name="retry">Retry</string>
|
||||
<!-- Label for the check box to share a network with other users on the same device -->
|
||||
<string name="wifi_shared">Share with other device users</string>
|
||||
<!-- Hint for unchanged fields -->
|
||||
|
@@ -21,6 +21,7 @@ import android.app.Activity;
|
||||
import android.content.Context;
|
||||
import android.net.wifi.WifiManager;
|
||||
import android.os.Bundle;
|
||||
import android.text.TextUtils;
|
||||
import android.util.Log;
|
||||
import android.view.LayoutInflater;
|
||||
import android.view.View;
|
||||
@@ -55,6 +56,7 @@ public class WifiDppAddDeviceFragment extends WifiDppQrCodeBaseFragment {
|
||||
// Update success UI.
|
||||
mTitle.setText(R.string.wifi_dpp_wifi_shared_with_device);
|
||||
mSummary.setVisibility(View.INVISIBLE);
|
||||
mChooseDifferentNetwork.setVisibility(View.INVISIBLE);
|
||||
mButtonLeft.setText(R.string.wifi_dpp_add_another_device);
|
||||
mButtonLeft.setOnClickListener(v -> getFragmentManager().popBackStack());
|
||||
mButtonRight.setText(R.string.done);
|
||||
@@ -63,8 +65,13 @@ public class WifiDppAddDeviceFragment extends WifiDppQrCodeBaseFragment {
|
||||
|
||||
@Override
|
||||
public void onFailure(int code) {
|
||||
//TODO(b/122429170): Show DPP configuration error state UI
|
||||
Log.d(TAG, "DppStatusCallback.onFailure " + code);
|
||||
|
||||
// Update fail UI.
|
||||
mTitle.setText(R.string.wifi_dpp_could_not_add_device);
|
||||
mSummary.setVisibility(View.INVISIBLE);
|
||||
mChooseDifferentNetwork.setVisibility(View.INVISIBLE);
|
||||
mButtonRight.setText(R.string.retry);
|
||||
}
|
||||
|
||||
@Override
|
||||
@@ -99,6 +106,15 @@ public class WifiDppAddDeviceFragment extends WifiDppQrCodeBaseFragment {
|
||||
public void onViewCreated(View view, Bundle savedInstanceState) {
|
||||
super.onViewCreated(view, savedInstanceState);
|
||||
|
||||
final WifiQrCode wifiQrCode = ((WifiDppConfiguratorActivity) getActivity())
|
||||
.getWifiDppQrCode();
|
||||
final String information = wifiQrCode.getInformation();
|
||||
if (TextUtils.isEmpty(information)) {
|
||||
mTitle.setText(R.string.wifi_dpp_device_found);
|
||||
} else {
|
||||
mTitle.setText(information);
|
||||
}
|
||||
|
||||
final WifiNetworkConfig wifiNetworkConfig = ((WifiDppConfiguratorActivity) getActivity())
|
||||
.getWifiNetworkConfig();
|
||||
if (!WifiNetworkConfig.isValidConfig(wifiNetworkConfig)) {
|
||||
@@ -110,7 +126,8 @@ public class WifiDppAddDeviceFragment extends WifiDppQrCodeBaseFragment {
|
||||
mWifiApPictureView = view.findViewById(R.id.wifi_ap_picture_view);
|
||||
|
||||
mChooseDifferentNetwork = view.findViewById(R.id.choose_different_network);
|
||||
mChooseDifferentNetwork.setOnClickListener(v -> getFragmentManager().popBackStack());
|
||||
mChooseDifferentNetwork.setOnClickListener(v ->
|
||||
mClickChooseDifferentNetworkListener.onClickChooseDifferentNetwork());
|
||||
|
||||
mButtonLeft = view.findViewById(R.id.button_left);
|
||||
mButtonLeft.setText(R.string.cancel);
|
||||
@@ -125,11 +142,34 @@ public class WifiDppAddDeviceFragment extends WifiDppQrCodeBaseFragment {
|
||||
}
|
||||
|
||||
private void startWifiDppInitiator() {
|
||||
final String enrolleeUri = ((WifiDppConfiguratorActivity) getActivity()).getDppUri();
|
||||
final WifiQrCode wifiQrCode = ((WifiDppConfiguratorActivity) getActivity())
|
||||
.getWifiDppQrCode();
|
||||
final String qrCode = wifiQrCode.getQrCode();
|
||||
final int networkId =
|
||||
((WifiDppConfiguratorActivity) getActivity()).getWifiNetworkConfig().getNetworkId();
|
||||
final WifiManager wifiManager = getContext().getSystemService(WifiManager.class);
|
||||
wifiManager.startDppAsConfiguratorInitiator(enrolleeUri, networkId,
|
||||
|
||||
wifiManager.startDppAsConfiguratorInitiator(qrCode, networkId,
|
||||
WifiManager.DPP_NETWORK_ROLE_STA, /* handler */ null, new DppStatusCallback());
|
||||
}
|
||||
|
||||
// Container Activity must implement this interface
|
||||
public interface OnClickChooseDifferentNetworkListener {
|
||||
public void onClickChooseDifferentNetwork();
|
||||
}
|
||||
OnClickChooseDifferentNetworkListener mClickChooseDifferentNetworkListener;
|
||||
|
||||
@Override
|
||||
public void onAttach(Context context) {
|
||||
super.onAttach(context);
|
||||
|
||||
mClickChooseDifferentNetworkListener = (OnClickChooseDifferentNetworkListener) context;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onDetach() {
|
||||
mClickChooseDifferentNetworkListener = null;
|
||||
|
||||
super.onDetach();
|
||||
}
|
||||
}
|
||||
|
@@ -51,7 +51,8 @@ public class WifiDppConfiguratorActivity extends InstrumentedActivity implements
|
||||
WifiNetworkConfig.Retriever,
|
||||
WifiDppQrCodeGeneratorFragment.OnQrCodeGeneratorFragmentAddButtonClickedListener,
|
||||
WifiDppQrCodeScannerFragment.OnScanWifiDppSuccessListener,
|
||||
WifiDppQrCodeScannerFragment.OnScanZxingWifiFormatSuccessListener {
|
||||
WifiDppQrCodeScannerFragment.OnScanZxingWifiFormatSuccessListener,
|
||||
WifiDppAddDeviceFragment.OnClickChooseDifferentNetworkListener {
|
||||
private static final String TAG = "WifiDppConfiguratorActivity";
|
||||
|
||||
public static final String ACTION_CONFIGURATOR_QR_CODE_SCANNER =
|
||||
@@ -66,9 +67,6 @@ public class WifiDppConfiguratorActivity extends InstrumentedActivity implements
|
||||
/** The Wi-Fi network which will be configured */
|
||||
private WifiNetworkConfig mWifiNetworkConfig;
|
||||
|
||||
/** The uri from Wi-Fi DPP QR code */
|
||||
private String mDppUri;
|
||||
|
||||
/** The Wi-Fi DPP QR code from intent ACTION_PROCESS_WIFI_DPP_QR_CODE */
|
||||
private WifiQrCode mWifiDppQrCode;
|
||||
|
||||
@@ -117,7 +115,7 @@ public class WifiDppConfiguratorActivity extends InstrumentedActivity implements
|
||||
break;
|
||||
case ACTION_PROCESS_WIFI_DPP_QR_CODE:
|
||||
String qrCode = intent.getStringExtra(WifiDppUtils.EXTRA_QR_CODE);
|
||||
mWifiDppQrCode = getValidWiFiDppQrCodeOrNull(qrCode);
|
||||
mWifiDppQrCode = getValidWifiDppQrCodeOrNull(qrCode);
|
||||
if (mWifiDppQrCode == null) {
|
||||
cancelActivity = true;
|
||||
} else {
|
||||
@@ -205,7 +203,7 @@ public class WifiDppConfiguratorActivity extends InstrumentedActivity implements
|
||||
fragmentTransaction.commit();
|
||||
}
|
||||
|
||||
private WifiQrCode getValidWiFiDppQrCodeOrNull(String qrCode) {
|
||||
private WifiQrCode getValidWifiDppQrCodeOrNull(String qrCode) {
|
||||
WifiQrCode wifiQrCode;
|
||||
try {
|
||||
wifiQrCode = new WifiQrCode(qrCode);
|
||||
@@ -225,10 +223,6 @@ public class WifiDppConfiguratorActivity extends InstrumentedActivity implements
|
||||
return mWifiNetworkConfig;
|
||||
}
|
||||
|
||||
public String getDppUri() {
|
||||
return mDppUri;
|
||||
}
|
||||
|
||||
public WifiQrCode getWifiDppQrCode() {
|
||||
return mWifiDppQrCode;
|
||||
}
|
||||
@@ -263,17 +257,21 @@ public class WifiDppConfiguratorActivity extends InstrumentedActivity implements
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onScanWifiDppSuccess(String uri) {
|
||||
mDppUri = uri;
|
||||
public void onScanWifiDppSuccess(WifiQrCode wifiQrCode) {
|
||||
mWifiDppQrCode = wifiQrCode;
|
||||
|
||||
showAddDeviceFragment(/* addToBackStack */ true);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onScanZxingWifiFormatSuccess(WifiNetworkConfig wifiNetworkConfig) {
|
||||
mDppUri = null;
|
||||
mWifiNetworkConfig = new WifiNetworkConfig(wifiNetworkConfig);
|
||||
// Do nothing, it's impossible to be a configurator without a Wi-Fi DPP QR code
|
||||
}
|
||||
|
||||
showAddDeviceFragment(/* addToBackStack */ true);
|
||||
@Override
|
||||
public void onClickChooseDifferentNetwork() {
|
||||
mWifiNetworkConfig = null;
|
||||
|
||||
showChooseSavedWifiNetworkFragment(/* addToBackStack */ true);
|
||||
}
|
||||
}
|
||||
|
@@ -145,9 +145,10 @@ public class WifiDppEnrolleeActivity extends InstrumentedActivity implements
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onScanWifiDppSuccess(String uri) {
|
||||
public void onScanWifiDppSuccess(WifiQrCode wifiQrCode) {
|
||||
final WifiManager wifiManager = (WifiManager) getSystemService(Context.WIFI_SERVICE);
|
||||
wifiManager.startDppAsEnrolleeInitiator(uri, /* handler */ null, new DppStatusCallback());
|
||||
wifiManager.startDppAsEnrolleeInitiator(wifiQrCode.getQrCode(), /* handler */ null,
|
||||
new DppStatusCallback());
|
||||
}
|
||||
|
||||
@Override
|
||||
|
@@ -100,7 +100,7 @@ public class WifiDppQrCodeScannerFragment extends WifiDppQrCodeBaseFragment impl
|
||||
|
||||
// Container Activity must implement this interface
|
||||
public interface OnScanWifiDppSuccessListener {
|
||||
public void onScanWifiDppSuccess(String uri);
|
||||
public void onScanWifiDppSuccess(WifiQrCode wifiQrCode);
|
||||
}
|
||||
OnScanWifiDppSuccessListener mScanWifiDppSuccessListener;
|
||||
|
||||
@@ -108,7 +108,7 @@ public class WifiDppQrCodeScannerFragment extends WifiDppQrCodeBaseFragment impl
|
||||
public interface OnScanZxingWifiFormatSuccessListener {
|
||||
public void onScanZxingWifiFormatSuccess(WifiNetworkConfig wifiNetworkConfig);
|
||||
}
|
||||
OnScanZxingWifiFormatSuccessListener mScanScanZxingWifiFormatSuccessListener;
|
||||
OnScanZxingWifiFormatSuccessListener mScanZxingWifiFormatSuccessListener;
|
||||
|
||||
/**
|
||||
* Configurator container activity of the fragment should create instance with this constructor.
|
||||
@@ -146,13 +146,13 @@ public class WifiDppQrCodeScannerFragment extends WifiDppQrCodeBaseFragment impl
|
||||
super.onAttach(context);
|
||||
|
||||
mScanWifiDppSuccessListener = (OnScanWifiDppSuccessListener) context;
|
||||
mScanScanZxingWifiFormatSuccessListener = (OnScanZxingWifiFormatSuccessListener) context;
|
||||
mScanZxingWifiFormatSuccessListener = (OnScanZxingWifiFormatSuccessListener) context;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onDetach() {
|
||||
mScanWifiDppSuccessListener = null;
|
||||
mScanScanZxingWifiFormatSuccessListener = null;
|
||||
mScanZxingWifiFormatSuccessListener = null;
|
||||
|
||||
super.onDetach();
|
||||
}
|
||||
@@ -278,11 +278,11 @@ public class WifiDppQrCodeScannerFragment extends WifiDppQrCodeBaseFragment impl
|
||||
public void handleSuccessfulResult(String qrCode) {
|
||||
switch (mWifiQrCode.getScheme()) {
|
||||
case WifiQrCode.SCHEME_DPP:
|
||||
handleWifiDpp(qrCode);
|
||||
handleWifiDpp();
|
||||
break;
|
||||
|
||||
case WifiQrCode.SCHEME_ZXING_WIFI_NETWORK_CONFIG:
|
||||
handleZxingWifiFormat(mWifiQrCode.getWifiNetworkConfig());
|
||||
handleZxingWifiFormat();
|
||||
break;
|
||||
|
||||
default:
|
||||
@@ -290,25 +290,22 @@ public class WifiDppQrCodeScannerFragment extends WifiDppQrCodeBaseFragment impl
|
||||
}
|
||||
}
|
||||
|
||||
private void handleWifiDpp(String uri) {
|
||||
private void handleWifiDpp() {
|
||||
destroyCamera();
|
||||
mDecorateView.setFocused(true);
|
||||
|
||||
final Bundle bundle = new Bundle();
|
||||
bundle.putString(KEY_PUBLIC_URI, uri);
|
||||
|
||||
Message message = mHandler.obtainMessage(MESSAGE_SCAN_WIFI_DPP_SUCCESS);
|
||||
message.setData(bundle);
|
||||
message.obj = new WifiQrCode(mWifiQrCode.getQrCode());
|
||||
|
||||
mHandler.sendMessageDelayed(message, SHOW_SUCCESS_SQUARE_INTERVAL);
|
||||
}
|
||||
|
||||
private void handleZxingWifiFormat(WifiNetworkConfig wifiNetworkConfig) {
|
||||
private void handleZxingWifiFormat() {
|
||||
destroyCamera();
|
||||
mDecorateView.setFocused(true);
|
||||
|
||||
Message message = mHandler.obtainMessage(MESSAGE_SCAN_ZXING_WIFI_FORMAT_SUCCESS);
|
||||
message.obj = wifiNetworkConfig;
|
||||
message.obj = new WifiQrCode(mWifiQrCode.getQrCode()).getWifiNetworkConfig();
|
||||
|
||||
mHandler.sendMessageDelayed(message, SHOW_SUCCESS_SQUARE_INTERVAL);
|
||||
}
|
||||
@@ -359,17 +356,14 @@ public class WifiDppQrCodeScannerFragment extends WifiDppQrCodeBaseFragment impl
|
||||
if (mScanWifiDppSuccessListener == null) {
|
||||
return;
|
||||
}
|
||||
final Bundle bundle = msg.getData();
|
||||
final String uri = bundle.getString(KEY_PUBLIC_URI);
|
||||
|
||||
mScanWifiDppSuccessListener.onScanWifiDppSuccess(uri);
|
||||
mScanWifiDppSuccessListener.onScanWifiDppSuccess((WifiQrCode)msg.obj);
|
||||
break;
|
||||
|
||||
case MESSAGE_SCAN_ZXING_WIFI_FORMAT_SUCCESS:
|
||||
if (mScanScanZxingWifiFormatSuccessListener == null) {
|
||||
if (mScanZxingWifiFormatSuccessListener == null) {
|
||||
return;
|
||||
}
|
||||
mScanScanZxingWifiFormatSuccessListener.onScanZxingWifiFormatSuccess(
|
||||
mScanZxingWifiFormatSuccessListener.onScanZxingWifiFormatSuccess(
|
||||
(WifiNetworkConfig)msg.obj);
|
||||
break;
|
||||
|
||||
|
@@ -20,7 +20,6 @@ import android.content.Intent;
|
||||
import android.net.wifi.WifiConfiguration;
|
||||
import android.text.TextUtils;
|
||||
|
||||
import androidx.annotation.Keep;
|
||||
import androidx.annotation.VisibleForTesting;
|
||||
|
||||
import java.util.Arrays;
|
||||
@@ -49,7 +48,6 @@ import java.util.regex.Pattern;
|
||||
* H true Optional. True if the network SSID is hidden.
|
||||
*
|
||||
*/
|
||||
@Keep
|
||||
public class WifiQrCode {
|
||||
public static final String SCHEME_DPP = "DPP";
|
||||
public static final String SCHEME_ZXING_WIFI_NETWORK_CONFIG = "WIFI";
|
||||
@@ -86,7 +84,6 @@ public class WifiQrCode {
|
||||
// Data from parsed ZXing reader library's Wi-Fi Network config format
|
||||
private WifiNetworkConfig mWifiNetworkConfig;
|
||||
|
||||
@Keep
|
||||
public WifiQrCode(String qrCode) throws IllegalArgumentException {
|
||||
if (TextUtils.isEmpty(qrCode)) {
|
||||
throw new IllegalArgumentException("Empty QR code");
|
||||
@@ -172,7 +169,6 @@ public class WifiQrCode {
|
||||
return null;
|
||||
}
|
||||
|
||||
@Keep
|
||||
@VisibleForTesting(otherwise = VisibleForTesting.PRIVATE)
|
||||
protected String removeBackSlash(String input) {
|
||||
if (input == null) {
|
||||
@@ -199,7 +195,6 @@ public class WifiQrCode {
|
||||
return sb.toString();
|
||||
}
|
||||
|
||||
@Keep
|
||||
public String getQrCode() {
|
||||
return mQrCode;
|
||||
}
|
||||
@@ -210,25 +205,22 @@ public class WifiQrCode {
|
||||
* SCHEME_DPP for standard Wi-Fi device provision protocol; SCHEME_ZXING_WIFI_NETWORK_CONFIG
|
||||
* for ZXing reader library' Wi-Fi Network config format
|
||||
*/
|
||||
@Keep
|
||||
public String getScheme() {
|
||||
return mScheme;
|
||||
}
|
||||
|
||||
/** Available when {@code getScheme()} returns SCHEME_DPP */
|
||||
@Keep
|
||||
public String getPublicKey() {
|
||||
@VisibleForTesting(otherwise = VisibleForTesting.PRIVATE)
|
||||
protected String getPublicKey() {
|
||||
return mPublicKey;
|
||||
}
|
||||
|
||||
/** May be available when {@code getScheme()} returns SCHEME_DPP */
|
||||
@Keep
|
||||
public String getInformation() {
|
||||
return mInformation;
|
||||
}
|
||||
|
||||
/** Available when {@code getScheme()} returns SCHEME_ZXING_WIFI_NETWORK_CONFIG */
|
||||
@Keep
|
||||
public WifiNetworkConfig getWifiNetworkConfig() {
|
||||
if (mWifiNetworkConfig == null) {
|
||||
return null;
|
||||
|
@@ -101,4 +101,12 @@ public class WifiDppConfiguratorActivityTest {
|
||||
assertThat(activity instanceof WifiDppQrCodeScannerFragment
|
||||
.OnScanZxingWifiFormatSuccessListener).isEqualTo(true);
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testActivity_shouldImplementsOnClickChooseDifferentNetworkCallback() {
|
||||
WifiDppConfiguratorActivity activity = mActivityRule.getActivity();
|
||||
|
||||
assertThat(activity instanceof WifiDppAddDeviceFragment
|
||||
.OnClickChooseDifferentNetworkListener).isEqualTo(true);
|
||||
}
|
||||
}
|
||||
|
Reference in New Issue
Block a user