1 /*
2  * Copyright (C) 2022 The Android Open Source Project
3  *
4  * Licensed under the Apache License, Version 2.0 (the "License");
5  * you may not use this file except in compliance with the License.
6  * You may obtain a copy of the License at
7  *
8  *      http://www.apache.org/licenses/LICENSE-2.0
9  *
10  * Unless required by applicable law or agreed to in writing, software
11  * distributed under the License is distributed on an "AS IS" BASIS,
12  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13  * See the License for the specific language governing permissions and
14  * limitations under the License.
15  */
16 
17 package com.android.managedprovisioning.networkconnection;
18 
19 import android.annotation.Nullable;
20 import android.app.admin.DevicePolicyManager;
21 import android.content.Intent;
22 import android.os.Bundle;
23 
24 import androidx.lifecycle.ViewModelProvider;
25 
26 import com.android.managedprovisioning.R;
27 import com.android.managedprovisioning.common.ErrorDialogUtils;
28 import com.android.managedprovisioning.common.ErrorWrapper;
29 import com.android.managedprovisioning.common.ManagedProvisioningSharedPreferences;
30 import com.android.managedprovisioning.common.SettingsFacade;
31 import com.android.managedprovisioning.common.SetupGlifLayoutActivity;
32 import com.android.managedprovisioning.common.Utils;
33 import com.android.managedprovisioning.model.ProvisioningParams;
34 import com.android.managedprovisioning.networkconnection.EstablishNetworkConnectionViewModel.EstablishNetworkConnectionViewModelFactory;
35 
36 import com.google.android.setupcompat.util.WizardManagerHelper;
37 
38 /**
39  * Spinner which takes care of network connectivity.
40  *
41  * <p>For a list of possible extras see {@link
42  * DevicePolicyManager#ACTION_ESTABLISH_NETWORK_CONNECTION}. If relevant extras are supplied,
43  * it will try to connect to wifi or mobile data.
44  *
45  * <p>If no extras are supplied, then a network picker is shown to the end-user.
46  *
47  * <p>If successfully connected to network, {@link #RESULT_OK} is returned. Otherwise the result is
48  * {@link #RESULT_CANCELED}.
49  *
50  * <p>If the result is {@link #RESULT_CANCELED}, it may be accompanied by
51  * {@link ErrorDialogUtils#EXTRA_DIALOG_TITLE_ID}, {@link
52  * ErrorDialogUtils#EXTRA_ERROR_MESSAGE_RES} and {@link
53  * ErrorDialogUtils#EXTRA_FACTORY_RESET_REQUIRED} which can be used to display in a user-visible
54  * dialog.
55  */
56 public final class EstablishNetworkConnectionActivity extends SetupGlifLayoutActivity {
57 
58     private static final int WIFI_REQUEST_CODE = 1;
59     private EstablishNetworkConnectionViewModel mViewModel;
60 
61     @Override
onCreate(Bundle savedInstanceState)62     protected void onCreate(Bundle savedInstanceState) {
63         super.onCreate(savedInstanceState);
64         mViewModel = new ViewModelProvider(this,
65                 new EstablishNetworkConnectionViewModelFactory(
66                         new Utils(),
67                         new SettingsFacade(),
68                         new ManagedProvisioningSharedPreferences(this)))
69                 .get(EstablishNetworkConnectionViewModel.class);
70         mViewModel.observeState().observe(this, this::onStateChanged);
71     }
72 
onStateChanged(int state)73     private void onStateChanged(int state) {
74         switch (state) {
75             case EstablishNetworkConnectionViewModel.STATE_IDLE:
76                 ProvisioningParams params =
77                         mViewModel.parseExtras(getApplicationContext(), getIntent());
78                 mViewModel.connectToNetwork(getApplicationContext(), params);
79                 initializeUi();
80                 break;
81             case EstablishNetworkConnectionViewModel.STATE_CONNECTING:
82                 break;
83             case EstablishNetworkConnectionViewModel.STATE_CONNECTED:
84                 setResult(RESULT_OK);
85                 getTransitionHelper().finishActivity(this);
86                 break;
87             case EstablishNetworkConnectionViewModel.STATE_ERROR:
88                 ErrorWrapper error = mViewModel.getError();
89                 setResult(RESULT_CANCELED,
90                         ErrorDialogUtils.createResultIntent(error, getApplicationContext()));
91                 getTransitionHelper().finishActivity(this);
92                 break;
93             case EstablishNetworkConnectionViewModel.STATE_SHOW_NETWORK_PICKER:
94                 Intent wifiPickIntent = mUtils.getWifiPickIntent();
95                 if (canLaunchWifiPicker(wifiPickIntent)) {
96                     launchWifiPicker(wifiPickIntent);
97                 } else {
98                     setResult(RESULT_CANCELED);
99                     getTransitionHelper().finishActivity(this);
100                 }
101                 break;
102         }
103     }
104 
launchWifiPicker(Intent wifiPickIntent)105     private void launchWifiPicker(Intent wifiPickIntent) {
106         WizardManagerHelper.copyWizardManagerExtras(getIntent(), wifiPickIntent);
107         getTransitionHelper()
108                 .startActivityForResultWithTransition(
109                         this, wifiPickIntent, WIFI_REQUEST_CODE);
110     }
111 
canLaunchWifiPicker(Intent wifiPickIntent)112     private boolean canLaunchWifiPicker(Intent wifiPickIntent) {
113         return getPackageManager().resolveActivity(wifiPickIntent, 0) != null;
114     }
115 
116     @Override
onActivityResult(int requestCode, int resultCode, @Nullable Intent data)117     protected void onActivityResult(int requestCode, int resultCode, @Nullable Intent data) {
118         if (requestCode == WIFI_REQUEST_CODE) {
119             setResult(resultCode);
120             getTransitionHelper().finishActivity(this);
121         } else {
122             super.onActivityResult(requestCode, resultCode, data);
123         }
124     }
125 
initializeUi()126     private void initializeUi() {
127         final int headerResId = R.string.just_a_sec;
128         final int titleResId = R.string.just_a_sec;
129         initializeLayoutParams(R.layout.empty_loading_layout, headerResId);
130         setTitle(titleResId);
131     }
132 
133     @Override
isWaitingScreen()134     protected boolean isWaitingScreen() {
135         return true;
136     }
137 }
138