165a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Lane/* 265a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Lane * Copyright (C) 2014 The Android Open Source Project 365a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Lane * 465a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Lane * Licensed under the Apache License, Version 2.0 (the "License"); 565a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Lane * you may not use this file except in compliance with the License. 665a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Lane * You may obtain a copy of the License at 765a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Lane * 865a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Lane * http://www.apache.org/licenses/LICENSE-2.0 965a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Lane * 1065a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Lane * Unless required by applicable law or agreed to in writing, software 1165a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Lane * distributed under the License is distributed on an "AS IS" BASIS, 1265a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Lane * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 1365a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Lane * See the License for the specific language governing permissions and 1465a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Lane * limitations under the License. 1565a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Lane */ 1665a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Lane 1765a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Lanepackage com.android.tv.settings.connectivity; 1865a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Lane 1965a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Laneimport com.android.tv.settings.R; 2065a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Laneimport com.android.tv.settings.connectivity.setup.MessageWizardFragment; 2165a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Laneimport com.android.tv.settings.connectivity.setup.SelectFromListWizardFragment; 2265a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Laneimport com.android.tv.settings.util.ThemeHelper; 2365a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Lane 2465a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Laneimport com.android.tv.settings.dialog.old.DialogActivity; 2565a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Lane 2665a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Laneimport android.app.Fragment; 2765a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Laneimport android.app.FragmentTransaction; 2865a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Laneimport android.content.Context; 2965a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Laneimport android.content.Intent; 3065a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Laneimport android.net.wifi.WifiManager; 3165a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Laneimport android.net.wifi.WifiManager.WpsCallback; 3265a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Laneimport android.net.wifi.WpsInfo; 3365a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Laneimport android.os.Bundle; 3465a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Laneimport android.os.Handler; 3565a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Laneimport android.os.Message; 3665a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Lane 3765a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Laneimport java.util.ArrayList; 3865a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Lane 3965a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Lanepublic class WpsConnectionActivity extends DialogActivity 4065a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Lane implements SelectFromListWizardFragment.Listener, TimedMessageWizardFragment.Listener { 4165a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Lane 4265a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Lane public static final String EXTRA_WPS_SETUP = "wps_setup"; 4365a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Lane 4465a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Lane public static Intent createIntent(Context context, int wpsSetup) { 4565a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Lane return new Intent(context, WpsConnectionActivity.class).putExtra(EXTRA_WPS_SETUP, wpsSetup); 4665a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Lane } 4765a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Lane 4865a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Lane private static final String WPS_FRAGMENT_TAG = "wps_fragment_tag"; 4965a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Lane private static final String KEY_CANCEL = "cancel"; 5065a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Lane private static final String KEY_RETRY = "retry"; 5165a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Lane 5265a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Lane private WifiManager mWifiManager; 5365a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Lane private int mWpsSetup; 5465a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Lane private boolean mWpsComplete; 5565a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Lane private final WpsCallback mWpsCallback = new WpsCallback() { 5665a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Lane @Override 5765a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Lane public void onStarted(String pin) { 5865a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Lane if (pin != null) { 5965a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Lane displayFragment(createEnterPinFragment(pin), true); 6065a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Lane } 6165a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Lane } 6265a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Lane 6365a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Lane @Override 6465a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Lane public void onSucceeded() { 6565a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Lane mWpsComplete = true; 6665a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Lane displayFragment(createSuccessFragment(), true); 6765a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Lane } 6865a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Lane 6965a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Lane @Override 7065a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Lane public void onFailed(int reason) { 7165a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Lane mWpsComplete = true; 7265a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Lane String errorMessage; 7365a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Lane switch (reason) { 7465a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Lane case WifiManager.WPS_OVERLAP_ERROR: 7565a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Lane errorMessage = getString(R.string.wifi_wps_failed_overlap); 7665a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Lane break; 7765a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Lane case WifiManager.WPS_WEP_PROHIBITED: 7865a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Lane errorMessage = getString(R.string.wifi_wps_failed_wep); 7965a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Lane break; 8065a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Lane case WifiManager.WPS_TKIP_ONLY_PROHIBITED: 8165a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Lane errorMessage = getString(R.string.wifi_wps_failed_tkip); 8265a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Lane break; 8365a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Lane case WifiManager.IN_PROGRESS: 8465a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Lane mWifiManager.cancelWps(null); 8565a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Lane startWps(); 8665a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Lane return; 8765a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Lane case WifiManager.WPS_TIMED_OUT: 8865a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Lane startWps(); 8965a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Lane return; 9065a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Lane default: 9165a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Lane errorMessage = getString(R.string.wifi_wps_failed_generic); 9265a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Lane break; 9365a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Lane } 9465a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Lane displayFragment(createErrorFragment(errorMessage), true); 9565a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Lane } 9665a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Lane }; 9765a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Lane 9865a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Lane @Override 9965a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Lane protected void onCreate(Bundle savedInstanceState) { 10065a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Lane setTheme(ThemeHelper.getThemeResource(getIntent())); 10165a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Lane setLayoutProperties(R.layout.setup_auth_activity, R.id.description, R.id.action); 10265a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Lane super.onCreate(savedInstanceState); 10365a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Lane Bundle extras = getIntent().getExtras(); 10465a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Lane mWpsSetup = getIntent().getIntExtra(EXTRA_WPS_SETUP, 0); 10565a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Lane mWifiManager = (WifiManager) getSystemService(Context.WIFI_SERVICE); 10665a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Lane } 10765a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Lane 10865a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Lane @Override 10965a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Lane protected void onStart() { 11065a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Lane super.onStart(); 11165a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Lane startWps(); 11265a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Lane } 11365a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Lane 11465a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Lane @Override 11565a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Lane protected void onStop() { 11665a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Lane super.onStop(); 11765a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Lane if (!mWpsComplete) { 11865a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Lane mWifiManager.cancelWps(null); 11965a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Lane } 12065a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Lane } 12165a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Lane 12265a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Lane @Override 12365a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Lane public void onTimedMessageCompleted() { 12465a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Lane setResult(RESULT_OK); 12565a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Lane finish(); 12665a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Lane } 12765a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Lane 12865a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Lane @Override 12965a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Lane public void onListSelectionComplete(SelectFromListWizardFragment.ListItem listItem) { 13065a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Lane startWps(); 13165a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Lane } 13265a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Lane 13365a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Lane @Override 13465a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Lane public void onListFocusChanged(SelectFromListWizardFragment.ListItem listItem) { 13565a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Lane // Do nothing. 13665a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Lane } 13765a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Lane 13865a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Lane private void startWps() { 13965a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Lane Fragment currentFragment = getFragmentManager().findFragmentByTag(WPS_FRAGMENT_TAG); 14065a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Lane if (!(currentFragment instanceof WpsScanningFragment)) { 14165a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Lane displayFragment(createWpsScanningFragment(), true); 14265a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Lane } 14365a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Lane mWpsComplete = false; 14465a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Lane WpsInfo wpsConfig = new WpsInfo(); 14565a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Lane wpsConfig.setup = mWpsSetup; 14665a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Lane if (!mWpsComplete) { 14765a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Lane mWifiManager.startWps(wpsConfig, mWpsCallback); 14865a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Lane } 14965a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Lane } 15065a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Lane 15165a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Lane private Fragment createWpsScanningFragment() { 15265a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Lane return WpsScanningFragment.newInstance(); 15365a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Lane } 15465a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Lane 15565a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Lane private Fragment createEnterPinFragment(String pin) { 15665a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Lane return WpsPinFragment.newInstance(pin); 15765a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Lane } 15865a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Lane 15965a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Lane private Fragment createErrorFragment(String errorMessage) { 16065a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Lane SelectFromListWizardFragment.ListItem retryListItem = 16165a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Lane new SelectFromListWizardFragment.ListItem( 16265a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Lane getString(R.string.wifi_wps_retry_scan).toUpperCase(), 0); 16365a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Lane ArrayList<SelectFromListWizardFragment.ListItem> listItems = new ArrayList< 16465a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Lane SelectFromListWizardFragment.ListItem>(); 16565a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Lane listItems.add(retryListItem); 16665a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Lane return SelectFromListWizardFragment.newInstance(errorMessage, null, listItems, 16765a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Lane retryListItem); 16865a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Lane } 16965a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Lane 17065a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Lane private Fragment createSuccessFragment() { 17165a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Lane return TimedMessageWizardFragment.newInstance( 17265a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Lane getString(R.string.wifi_setup_connection_success)); 17365a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Lane } 17465a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Lane 17565a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Lane private void displayFragment(Fragment fragment, boolean forward) { 17665a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Lane FragmentTransaction transaction = getFragmentManager().beginTransaction(); 17765a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Lane if (forward) { 17865a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Lane transaction.setTransition(FragmentTransaction.TRANSIT_FRAGMENT_OPEN); 17965a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Lane } else { 18065a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Lane transaction.setTransition(FragmentTransaction.TRANSIT_FRAGMENT_CLOSE); 18165a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Lane } 18265a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Lane transaction.replace(R.id.content, fragment, WPS_FRAGMENT_TAG).commit(); 18365a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Lane } 18465a5a7d84ad9b5324ae53eda526e39e513473af7Christopher Lane} 185