diff options
Diffstat (limited to 'src/com')
17 files changed, 978 insertions, 52 deletions
diff --git a/src/com/android/settings/SecuritySettings.java b/src/com/android/settings/SecuritySettings.java index 057e5de..9a83311 100644 --- a/src/com/android/settings/SecuritySettings.java +++ b/src/com/android/settings/SecuritySettings.java @@ -237,7 +237,7 @@ public class SecuritySettings extends SettingsPreferenceFragment private void updateLockAfterPreferenceSummary() { // Update summary message with current value long currentTimeout = Settings.Secure.getLong(getContentResolver(), - Settings.Secure.LOCK_SCREEN_LOCK_AFTER_TIMEOUT, 0); + Settings.Secure.LOCK_SCREEN_LOCK_AFTER_TIMEOUT, 5000); final CharSequence[] entries = mLockAfter.getEntries(); final CharSequence[] values = mLockAfter.getEntryValues(); int best = 0; diff --git a/src/com/android/settings/Settings.java b/src/com/android/settings/Settings.java index eb0b40c..2b69c2a 100644 --- a/src/com/android/settings/Settings.java +++ b/src/com/android/settings/Settings.java @@ -559,8 +559,10 @@ public class Settings extends PreferenceActivity implements ButtonBarHandler { public static class DateTimeSettingsActivity extends Settings { /* empty */ } public static class StorageSettingsActivity extends Settings { /* empty */ } public static class WifiSettingsActivity extends Settings { /* empty */ } + public static class WifiP2pSettingsActivity extends Settings { /* empty */ } public static class InputMethodAndLanguageSettingsActivity extends Settings { /* empty */ } public static class InputMethodAndSubtypeEnablerActivity extends Settings { /* empty */ } + public static class SpellCheckersSettingsActivity extends Settings { /* empty */ } public static class LocalePickerActivity extends Settings { /* empty */ } public static class UserDictionarySettingsActivity extends Settings { /* empty */ } public static class SoundSettingsActivity extends Settings { /* empty */ } diff --git a/src/com/android/settings/TetherSettings.java b/src/com/android/settings/TetherSettings.java index 1513d43..9991725 100644 --- a/src/com/android/settings/TetherSettings.java +++ b/src/com/android/settings/TetherSettings.java @@ -31,6 +31,7 @@ import android.content.DialogInterface; import android.content.Intent; import android.content.IntentFilter; import android.content.res.AssetManager; +import android.hardware.usb.UsbManager; import android.net.ConnectivityManager; import android.net.wifi.WifiConfiguration; import android.net.wifi.WifiManager; @@ -95,6 +96,9 @@ public class TetherSettings extends SettingsPreferenceFragment private WifiManager mWifiManager; private WifiConfiguration mWifiConfig = null; + private boolean mUsbConnected; + private boolean mMassStorageActive; + private boolean mBluetoothEnableForTether; @Override @@ -253,8 +257,14 @@ public class TetherSettings extends SettingsPreferenceFragment updateState(available.toArray(new String[available.size()]), active.toArray(new String[active.size()]), errored.toArray(new String[errored.size()])); - } else if (action.equals(Intent.ACTION_MEDIA_SHARED) || - action.equals(Intent.ACTION_MEDIA_UNSHARED)) { + } else if (action.equals(Intent.ACTION_MEDIA_SHARED)) { + mMassStorageActive = true; + updateState(); + } else if (action.equals(Intent.ACTION_MEDIA_UNSHARED)) { + mMassStorageActive = false; + updateState(); + } else if (action.equals(UsbManager.ACTION_USB_STATE)) { + mUsbConnected = intent.getBooleanExtra(UsbManager.USB_CONNECTED, false); updateState(); } else if (action.equals(BluetoothAdapter.ACTION_STATE_CHANGED)) { if (mBluetoothEnableForTether) { @@ -285,11 +295,16 @@ public class TetherSettings extends SettingsPreferenceFragment final Activity activity = getActivity(); + mMassStorageActive = Environment.MEDIA_SHARED.equals(Environment.getExternalStorageState()); mTetherChangeReceiver = new TetherChangeReceiver(); IntentFilter filter = new IntentFilter(ConnectivityManager.ACTION_TETHER_STATE_CHANGED); Intent intent = activity.registerReceiver(mTetherChangeReceiver, filter); filter = new IntentFilter(); + filter.addAction(UsbManager.ACTION_USB_STATE); + activity.registerReceiver(mTetherChangeReceiver, filter); + + filter = new IntentFilter(); filter.addAction(Intent.ACTION_MEDIA_SHARED); filter.addAction(Intent.ACTION_MEDIA_UNSHARED); filter.addDataScheme("file"); @@ -334,14 +349,11 @@ public class TetherSettings extends SettingsPreferenceFragment String[] errored) { ConnectivityManager cm = (ConnectivityManager)getSystemService(Context.CONNECTIVITY_SERVICE); - boolean usbAvailable = false; + boolean usbAvailable = mUsbConnected && !mMassStorageActive; int usbError = ConnectivityManager.TETHER_ERROR_NO_ERROR; - boolean massStorageActive = - Environment.MEDIA_SHARED.equals(Environment.getExternalStorageState()); for (String s : available) { for (String regex : mUsbRegexs) { if (s.matches(regex)) { - usbAvailable = true; if (usbError == ConnectivityManager.TETHER_ERROR_NO_ERROR) { usbError = cm.getLastTetherError(s); } @@ -377,7 +389,7 @@ public class TetherSettings extends SettingsPreferenceFragment mUsbTether.setSummary(R.string.usb_tethering_errored_subtext); mUsbTether.setEnabled(false); mUsbTether.setChecked(false); - } else if (massStorageActive) { + } else if (mMassStorageActive) { mUsbTether.setSummary(R.string.usb_tethering_storage_active_subtext); mUsbTether.setEnabled(false); mUsbTether.setChecked(false); @@ -434,40 +446,18 @@ public class TetherSettings extends SettingsPreferenceFragment @Override public boolean onPreferenceTreeClick(PreferenceScreen screen, Preference preference) { + ConnectivityManager cm = + (ConnectivityManager)getSystemService(Context.CONNECTIVITY_SERVICE); + if (preference == mUsbTether) { boolean newState = mUsbTether.isChecked(); - ConnectivityManager cm = - (ConnectivityManager)getSystemService(Context.CONNECTIVITY_SERVICE); - - if (newState) { - String[] available = cm.getTetherableIfaces(); - - String usbIface = findIface(available, mUsbRegexs); - if (usbIface == null) { - updateState(); - return true; - } - if (cm.tether(usbIface) != ConnectivityManager.TETHER_ERROR_NO_ERROR) { - mUsbTether.setChecked(false); - mUsbTether.setSummary(R.string.usb_tethering_errored_subtext); - return true; - } - mUsbTether.setSummary(""); - } else { - String [] tethered = cm.getTetheredIfaces(); - - String usbIface = findIface(tethered, mUsbRegexs); - if (usbIface == null) { - updateState(); - return true; - } - if (cm.untether(usbIface) != ConnectivityManager.TETHER_ERROR_NO_ERROR) { - mUsbTether.setSummary(R.string.usb_tethering_errored_subtext); - return true; - } - mUsbTether.setSummary(""); + if (cm.setUsbTethering(newState) != ConnectivityManager.TETHER_ERROR_NO_ERROR) { + mUsbTether.setChecked(false); + mUsbTether.setSummary(R.string.usb_tethering_errored_subtext); + return true; } + mUsbTether.setSummary(""); } else if (preference == mBluetoothTether) { boolean bluetoothTetherState = mBluetoothTether.isChecked(); @@ -486,8 +476,6 @@ public class TetherSettings extends SettingsPreferenceFragment } else { boolean errored = false; - ConnectivityManager cm = - (ConnectivityManager)getSystemService(Context.CONNECTIVITY_SERVICE); String [] tethered = cm.getTetheredIfaces(); String bluetoothIface = findIface(tethered, mBluetoothRegexs); if (bluetoothIface != null && diff --git a/src/com/android/settings/WirelessSettings.java b/src/com/android/settings/WirelessSettings.java index c07388e..beab491 100644 --- a/src/com/android/settings/WirelessSettings.java +++ b/src/com/android/settings/WirelessSettings.java @@ -21,6 +21,7 @@ import android.app.admin.DevicePolicyManager; import android.content.Context; import android.content.Intent; import android.net.ConnectivityManager; +import android.net.wifi.p2p.WifiP2pManager; import android.nfc.NfcAdapter; import android.os.Bundle; import android.os.SystemProperties; @@ -28,6 +29,9 @@ import android.preference.CheckBoxPreference; import android.preference.Preference; import android.preference.PreferenceScreen; import android.provider.Settings; +import android.view.LayoutInflater; +import android.view.View; +import android.widget.Switch; import com.android.internal.telephony.TelephonyIntents; import com.android.internal.telephony.TelephonyProperties; @@ -39,6 +43,7 @@ public class WirelessSettings extends SettingsPreferenceFragment { private static final String KEY_TOGGLE_NFC = "toggle_nfc"; private static final String KEY_ZEROCLICK_SETTINGS = "zeroclick_settings"; private static final String KEY_VPN_SETTINGS = "vpn_settings"; + private static final String KEY_WIFI_P2P_SETTINGS = "wifi_p2p_settings"; private static final String KEY_TETHER_SETTINGS = "tether_settings"; private static final String KEY_PROXY_SETTINGS = "proxy_settings"; private static final String KEY_MOBILE_NETWORK_SETTINGS = "mobile_network_settings"; @@ -118,6 +123,11 @@ public class WirelessSettings extends SettingsPreferenceFragment { getPreferenceScreen().removePreference(findPreference(KEY_MOBILE_NETWORK_SETTINGS)); } + WifiP2pManager wifiP2p = (WifiP2pManager) getSystemService(Context.WIFI_P2P_SERVICE); + if (!wifiP2p.isP2pSupported()) { + getPreferenceScreen().removePreference(findPreference(KEY_WIFI_P2P_SETTINGS)); + } + // Enable Proxy selector settings if allowed. Preference mGlobalProxy = findPreference(KEY_PROXY_SETTINGS); DevicePolicyManager mDPM = (DevicePolicyManager) diff --git a/src/com/android/settings/inputmethod/CheckBoxAndSettingsPreference.java b/src/com/android/settings/inputmethod/CheckBoxAndSettingsPreference.java new file mode 100644 index 0000000..f983f59 --- /dev/null +++ b/src/com/android/settings/inputmethod/CheckBoxAndSettingsPreference.java @@ -0,0 +1,118 @@ +/* + * Copyright (C) 2011 The Android Open Source Project + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +package com.android.settings.inputmethod; + +import com.android.settings.R; +import com.android.settings.SettingsPreferenceFragment; + +import android.content.Context; +import android.content.Intent; +import android.preference.CheckBoxPreference; +import android.util.AttributeSet; +import android.view.View; +import android.view.View.OnClickListener; +import android.widget.ImageView; +import android.widget.TextView; + +public class CheckBoxAndSettingsPreference extends CheckBoxPreference { + private static final float DISABLED_ALPHA = 0.4f; + + private SettingsPreferenceFragment mFragment; + private TextView mTitleText; + private TextView mSummaryText; + private View mCheckBox; + private ImageView mSetingsButton; + private Intent mSettingsIntent; + + public CheckBoxAndSettingsPreference(Context context, AttributeSet attrs) { + super(context, attrs); + setLayoutResource(R.layout.preference_inputmethod); + setWidgetLayoutResource(R.layout.preference_inputmethod_widget); + } + + @Override + protected void onBindView(View view) { + super.onBindView(view); + mCheckBox = view.findViewById(R.id.inputmethod_pref); + mCheckBox.setOnClickListener( + new OnClickListener() { + @Override + public void onClick(View arg0) { + onCheckBoxClicked(arg0); + } + }); + mSetingsButton = (ImageView)view.findViewById(R.id.inputmethod_settings); + mTitleText = (TextView)view.findViewById(android.R.id.title); + mSummaryText = (TextView)view.findViewById(android.R.id.summary); + mSetingsButton.setOnClickListener( + new OnClickListener() { + @Override + public void onClick(View arg0) { + onSettingsButtonClicked(arg0); + } + }); + enableSettingsButton(); + } + + + @Override + public void setEnabled(boolean enabled) { + super.setEnabled(enabled); + enableSettingsButton(); + } + + public void setFragmentIntent(SettingsPreferenceFragment fragment, Intent intent) { + mFragment = fragment; + mSettingsIntent = intent; + } + + protected void onCheckBoxClicked(View view) { + if (isChecked()) { + setChecked(false); + } else { + setChecked(true); + } + } + + protected void onSettingsButtonClicked(View arg0) { + if (mFragment != null && mSettingsIntent != null) { + mFragment.startActivity(mSettingsIntent); + } + } + + private void enableSettingsButton() { + if (mSetingsButton != null) { + if (mSettingsIntent == null) { + mSetingsButton.setVisibility(View.GONE); + } else { + final boolean checked = isChecked(); + mSetingsButton.setEnabled(checked); + mSetingsButton.setClickable(checked); + mSetingsButton.setFocusable(checked); + if (!checked) { + mSetingsButton.setAlpha(DISABLED_ALPHA); + } + } + } + if (mTitleText != null) { + mTitleText.setEnabled(true); + } + if (mSummaryText != null) { + mSummaryText.setEnabled(true); + } + } +} diff --git a/src/com/android/settings/inputmethod/InputMethodAndLanguageSettings.java b/src/com/android/settings/inputmethod/InputMethodAndLanguageSettings.java index e966ec7..d0ff2a0 100644 --- a/src/com/android/settings/inputmethod/InputMethodAndLanguageSettings.java +++ b/src/com/android/settings/inputmethod/InputMethodAndLanguageSettings.java @@ -17,6 +17,7 @@ package com.android.settings.inputmethod; import com.android.settings.R; +import com.android.settings.Settings.SpellCheckersSettingsActivity; import com.android.settings.SettingsPreferenceFragment; import com.android.settings.UserDictionarySettings; import com.android.settings.Utils; @@ -112,6 +113,11 @@ public class InputMethodAndLanguageSettings extends SettingsPreferenceFragment mImm = (InputMethodManager) getSystemService(Context.INPUT_METHOD_SERVICE); mImis = mImm.getInputMethodList(); createImePreferenceHierarchy((PreferenceGroup)findPreference("keyboard_settings_category")); + + final Intent intent = new Intent(Intent.ACTION_MAIN); + intent.setClass(getActivity(), SpellCheckersSettingsActivity.class); + ((SpellCheckersPreference)findPreference("spellcheckers_settings")).setFragmentIntent( + this, intent); } private void updateInputMethodSelectorSummary(int value) { diff --git a/src/com/android/settings/inputmethod/InputMethodAndSubtypeEnabler.java b/src/com/android/settings/inputmethod/InputMethodAndSubtypeEnabler.java index 43d54a2..efed823 100644 --- a/src/com/android/settings/inputmethod/InputMethodAndSubtypeEnabler.java +++ b/src/com/android/settings/inputmethod/InputMethodAndSubtypeEnabler.java @@ -22,6 +22,7 @@ import com.android.settings.SettingsPreferenceFragment; import android.app.AlertDialog; import android.content.Context; import android.content.DialogInterface; +import android.content.Intent; import android.content.pm.PackageManager; import android.content.res.Configuration; import android.os.Bundle; @@ -56,19 +57,29 @@ public class InputMethodAndSubtypeEnabler extends SettingsPreferenceFragment { Configuration config = getResources().getConfiguration(); mHaveHardKeyboard = (config.keyboard == Configuration.KEYBOARD_QWERTY); + final Bundle arguments = getArguments(); // Input method id should be available from an Intent when this preference is launched as a // single Activity (see InputMethodAndSubtypeEnablerActivity). It should be available // from a preference argument when the preference is launched as a part of the other // Activity (like a right pane of 2-pane Settings app) mInputMethodId = getActivity().getIntent().getStringExtra( android.provider.Settings.EXTRA_INPUT_METHOD_ID); - if (mInputMethodId == null && (getArguments() != null)) { + if (mInputMethodId == null && (arguments != null)) { final String inputMethodId = - getArguments().getString(android.provider.Settings.EXTRA_INPUT_METHOD_ID); + arguments.getString(android.provider.Settings.EXTRA_INPUT_METHOD_ID); if (inputMethodId != null) { mInputMethodId = inputMethodId; } } + CharSequence title = getActivity().getIntent().getStringExtra( + Intent.EXTRA_TITLE); + if (title == null && (arguments != null)) { + title = arguments.getString(Intent.EXTRA_TITLE); + } + + if (!TextUtils.isEmpty(title)) { + getActivity().setTitle(title); + } onCreateIMM(); setPreferenceScreen(createPreferenceHierarchy()); @@ -136,6 +147,7 @@ public class InputMethodAndSubtypeEnabler extends SettingsPreferenceFragment { .setCancelable(true) .setPositiveButton(android.R.string.ok, new DialogInterface.OnClickListener() { + @Override public void onClick(DialogInterface dialog, int which) { chkPref.setChecked(true); InputMethodAndSubtypeUtil.setSubtypesPreferenceEnabled( @@ -146,6 +158,7 @@ public class InputMethodAndSubtypeEnabler extends SettingsPreferenceFragment { }) .setNegativeButton(android.R.string.cancel, new DialogInterface.OnClickListener() { + @Override public void onClick(DialogInterface dialog, int which) { } diff --git a/src/com/android/settings/inputmethod/SpellCheckerUtils.java b/src/com/android/settings/inputmethod/SpellCheckerUtils.java new file mode 100644 index 0000000..3cc256f --- /dev/null +++ b/src/com/android/settings/inputmethod/SpellCheckerUtils.java @@ -0,0 +1,35 @@ +/* + * Copyright (C) 2011 The Android Open Source Project + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +package com.android.settings.inputmethod; + +import android.view.textservice.SpellCheckerInfo; + +public class SpellCheckerUtils { + public static void setSpellCheckersEnabled(boolean enable) { + } + public static boolean getSpellCheckersEnabled() { + return true; + } + public static void setCurrentSpellChecker(SpellCheckerInfo info) { + } + public static SpellCheckerInfo getCurrentSpellChecker() { + return null; + } + public static SpellCheckerInfo[] getEnabledSpellCheckers() { + return null; + } +} diff --git a/src/com/android/settings/inputmethod/SpellCheckersPreference.java b/src/com/android/settings/inputmethod/SpellCheckersPreference.java new file mode 100644 index 0000000..7d2eec8 --- /dev/null +++ b/src/com/android/settings/inputmethod/SpellCheckersPreference.java @@ -0,0 +1,27 @@ +/* + * Copyright (C) 2011 The Android Open Source Project + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +package com.android.settings.inputmethod; + +import android.content.Context; +import android.util.AttributeSet; + +public class SpellCheckersPreference extends CheckBoxAndSettingsPreference { + + public SpellCheckersPreference(Context context, AttributeSet attrs) { + super(context, attrs); + } +} diff --git a/src/com/android/settings/inputmethod/SpellCheckersSettings.java b/src/com/android/settings/inputmethod/SpellCheckersSettings.java new file mode 100644 index 0000000..a36491f --- /dev/null +++ b/src/com/android/settings/inputmethod/SpellCheckersSettings.java @@ -0,0 +1,84 @@ +/* + * Copyright (C) 2011 The Android Open Source Project + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +package com.android.settings.inputmethod; + +import com.android.settings.R; +import com.android.settings.SettingsPreferenceFragment; + +import android.os.Bundle; +import android.preference.Preference; +import android.preference.PreferenceScreen; +import android.view.textservice.SpellCheckerInfo; + +public class SpellCheckersSettings extends SettingsPreferenceFragment + implements Preference.OnPreferenceChangeListener { + + private SpellCheckerInfo mCurrentSci; + private SpellCheckerInfo[] mEnabledScis; + + @Override + public void onCreate(Bundle icicle) { + super.onCreate(icicle); + addPreferencesFromResource(R.xml.spellchecker_prefs); + updateScreen(); + } + + @Override + public boolean onPreferenceChange(Preference arg0, Object arg1) { + return false; + } + + @Override + public boolean onPreferenceTreeClick(PreferenceScreen screen, Preference preference) { + return false; + } + + @Override + public void onResume() { + updateScreen(); + } + + @Override + public void onPause() { + saveState(); + } + + private void saveState() { + SpellCheckerUtils.setCurrentSpellChecker(mCurrentSci); + } + + private void updateScreen() { + getPreferenceScreen().removeAll(); + updateEnabledSpellCheckers(); + } + + private void updateEnabledSpellCheckers() { + mCurrentSci = SpellCheckerUtils.getCurrentSpellChecker(); + mEnabledScis = SpellCheckerUtils.getEnabledSpellCheckers(); + if (mCurrentSci == null || mEnabledScis == null) { + return; + } + // TODO: implement here + for (int i = 0; i < mEnabledScis.length; ++i) { + final SpellCheckerInfo sci = mEnabledScis[i]; + final PreferenceScreen scs = new PreferenceScreen(getActivity(), null); + scs.setTitle(sci.getId()); + getPreferenceScreen().addPreference(scs); + + } + } +} diff --git a/src/com/android/settings/inputmethod/UserDictionaryList.java b/src/com/android/settings/inputmethod/UserDictionaryList.java index e0afe48..232a6db 100644 --- a/src/com/android/settings/inputmethod/UserDictionaryList.java +++ b/src/com/android/settings/inputmethod/UserDictionaryList.java @@ -45,6 +45,7 @@ public class UserDictionaryList extends SettingsPreferenceFragment { } static Set<String> getUserDictionaryLocalesList(Activity activity) { + @SuppressWarnings("deprecation") final Cursor cursor = activity.managedQuery(UserDictionary.Words.CONTENT_URI, new String[] { UserDictionary.Words.LOCALE }, null, null, null); diff --git a/src/com/android/settings/wifi/WifiConfigController.java b/src/com/android/settings/wifi/WifiConfigController.java index a8ce94f..897280f 100644 --- a/src/com/android/settings/wifi/WifiConfigController.java +++ b/src/com/android/settings/wifi/WifiConfigController.java @@ -90,8 +90,8 @@ public class WifiConfigController implements TextWatcher, /* These values come from "wifi_network_setup" resource array */ public static final int MANUAL = 0; public static final int WPS_PBC = 1; - public static final int WPS_PIN_FROM_ACCESS_POINT = 2; - public static final int WPS_PIN_FROM_DEVICE = 3; + public static final int WPS_KEYPAD = 2; + public static final int WPS_DISPLAY = 3; /* These values come from "wifi_proxy_settings" resource array */ public static final int PROXY_NONE = 0; @@ -473,11 +473,11 @@ public class WifiConfigController implements TextWatcher, case WPS_PBC: config.setup = Setup.PBC; break; - case WPS_PIN_FROM_ACCESS_POINT: - config.setup = Setup.PIN_FROM_ACCESS_POINT; + case WPS_KEYPAD: + config.setup = Setup.KEYPAD; break; - case WPS_PIN_FROM_DEVICE: - config.setup = Setup.PIN_FROM_DEVICE; + case WPS_DISPLAY: + config.setup = Setup.DISPLAY; break; default: config.setup = Setup.INVALID; @@ -559,14 +559,14 @@ public class WifiConfigController implements TextWatcher, int pos = mNetworkSetupSpinner.getSelectedItemPosition(); /* Show pin text input if needed */ - if (pos == WPS_PIN_FROM_ACCESS_POINT) { + if (pos == WPS_DISPLAY) { mView.findViewById(R.id.wps_fields).setVisibility(View.VISIBLE); } else { mView.findViewById(R.id.wps_fields).setVisibility(View.GONE); } /* show/hide manual security fields appropriately */ - if ((pos == WPS_PIN_FROM_ACCESS_POINT) || (pos == WPS_PIN_FROM_DEVICE) + if ((pos == WPS_DISPLAY) || (pos == WPS_KEYPAD) || (pos == WPS_PBC)) { mView.findViewById(R.id.security_fields).setVisibility(View.GONE); } else { diff --git a/src/com/android/settings/wifi/WifiSettings.java b/src/com/android/settings/wifi/WifiSettings.java index 74400d4..ba8e440 100644 --- a/src/com/android/settings/wifi/WifiSettings.java +++ b/src/com/android/settings/wifi/WifiSettings.java @@ -683,8 +683,8 @@ public class WifiSettings extends SettingsPreferenceFragment int networkSetup = configController.chosenNetworkSetupMethod(); switch(networkSetup) { case WifiConfigController.WPS_PBC: - case WifiConfigController.WPS_PIN_FROM_ACCESS_POINT: - case WifiConfigController.WPS_PIN_FROM_DEVICE: + case WifiConfigController.WPS_DISPLAY: + case WifiConfigController.WPS_KEYPAD: mWifiManager.startWps(configController.getWpsConfig()); break; case WifiConfigController.MANUAL: diff --git a/src/com/android/settings/wifi/p2p/WifiP2pDialog.java b/src/com/android/settings/wifi/p2p/WifiP2pDialog.java new file mode 100644 index 0000000..380fa13 --- /dev/null +++ b/src/com/android/settings/wifi/p2p/WifiP2pDialog.java @@ -0,0 +1,137 @@ +/* + * Copyright (C) 2011 The Android Open Source Project + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +package com.android.settings.wifi.p2p; + +import android.app.AlertDialog; +import android.content.Context; +import android.content.DialogInterface; +import android.net.wifi.WpsConfiguration; +import android.net.wifi.WpsConfiguration.Setup; +import android.net.wifi.p2p.WifiP2pConfig; +import android.net.wifi.p2p.WifiP2pDevice; +import android.os.Bundle; +import android.view.View; +import android.widget.AdapterView; +import android.widget.CheckBox; +import android.widget.Spinner; +import android.widget.TextView; + +import com.android.settings.R; + +/** + * Dialog to setup a p2p connection + */ +public class WifiP2pDialog extends AlertDialog implements AdapterView.OnItemSelectedListener { + + static final int BUTTON_SUBMIT = DialogInterface.BUTTON_POSITIVE; + + private final DialogInterface.OnClickListener mListener; + + private View mView; + private TextView mDeviceName; + private TextView mDeviceAddress; + + /* These values come from "wifi_p2p_wps_setup" resource array */ + private static final int WPS_PBC = 0; + private static final int WPS_KEYPAD = 1; + private static final int WPS_DISPLAY = 2; + + private int mWpsSetupIndex = WPS_PBC; //default is pbc + + WifiP2pDevice mDevice; + + public WifiP2pDialog(Context context, DialogInterface.OnClickListener listener, + WifiP2pDevice device) { + super(context); + mListener = listener; + mDevice = device; + } + + public WifiP2pConfig getConfig() { + WifiP2pConfig config = new WifiP2pConfig(); + config.deviceAddress = mDeviceAddress.getText().toString(); + config.deviceName = mDeviceName.getText().toString(); + config.wpsConfig = new WpsConfiguration(); + switch (mWpsSetupIndex) { + case WPS_PBC: + config.wpsConfig.setup = Setup.PBC; + break; + case WPS_KEYPAD: + config.wpsConfig.setup = Setup.KEYPAD; + config.wpsConfig.pin = ((TextView) mView.findViewById(R.id.wps_pin)). + getText().toString(); + break; + case WPS_DISPLAY: + config.wpsConfig.setup = Setup.DISPLAY; + break; + default: + config.wpsConfig.setup = Setup.PBC; + break; + } + if (mDevice.isGroupOwner()) { + config.joinExistingGroup = true; + } + return config; + } + + @Override + protected void onCreate(Bundle savedInstanceState) { + + mView = getLayoutInflater().inflate(R.layout.wifi_p2p_dialog, null); + Spinner mWpsSetup = ((Spinner) mView.findViewById(R.id.wps_setup)); + + setView(mView); + setInverseBackgroundForced(true); + + Context context = getContext(); + + setTitle(R.string.wifi_p2p_settings_title); + mDeviceName = (TextView) mView.findViewById(R.id.device_name); + mDeviceAddress = (TextView) mView.findViewById(R.id.device_address); + + setButton(BUTTON_SUBMIT, context.getString(R.string.wifi_connect), mListener); + setButton(DialogInterface.BUTTON_NEGATIVE, + context.getString(R.string.wifi_cancel), mListener); + + if (mDevice != null) { + mDeviceName.setText(mDevice.deviceName); + mDeviceAddress.setText(mDevice.deviceAddress); + mWpsSetup.setSelection(mWpsSetupIndex); //keep pbc as default + } + + mWpsSetup.setOnItemSelectedListener(this); + + super.onCreate(savedInstanceState); + } + + @Override + public void onItemSelected(AdapterView<?> parent, View view, int position, long id) { + mWpsSetupIndex = position; + + if (mWpsSetupIndex == WPS_KEYPAD) { + mView.findViewById(R.id.wps_pin_entry).setVisibility(View.VISIBLE); + } else { + mView.findViewById(R.id.wps_pin_entry).setVisibility(View.GONE); + } + return; + } + + @Override + public void onNothingSelected(AdapterView<?> parent) { + } + +} diff --git a/src/com/android/settings/wifi/p2p/WifiP2pEnabler.java b/src/com/android/settings/wifi/p2p/WifiP2pEnabler.java new file mode 100644 index 0000000..fd79a58 --- /dev/null +++ b/src/com/android/settings/wifi/p2p/WifiP2pEnabler.java @@ -0,0 +1,144 @@ +/* + * Copyright (C) 2011 The Android Open Source Project + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +package com.android.settings.wifi.p2p; + +import com.android.settings.R; + +import android.content.BroadcastReceiver; +import android.content.Context; +import android.content.Intent; +import android.content.IntentFilter; +import android.net.wifi.p2p.WifiP2pManager; +import android.os.Handler; +import android.os.Message; +import android.preference.Preference; +import android.provider.Settings; +import android.util.Log; +import android.widget.CompoundButton; +import android.widget.Switch; + +/** + * WifiP2pEnabler is a helper to manage the Wifi p2p on/off + */ +public class WifiP2pEnabler implements CompoundButton.OnCheckedChangeListener { + private static final String TAG = "WifiP2pEnabler"; + + private final Context mContext; + private Switch mSwitch; + private int mWifiP2pState; + private final IntentFilter mIntentFilter; + private final Handler mHandler = new WifiP2pHandler(); + private WifiP2pManager mWifiP2pManager; + + private final BroadcastReceiver mReceiver = new BroadcastReceiver() { + @Override + public void onReceive(Context context, Intent intent) { + String action = intent.getAction(); + + if (WifiP2pManager.WIFI_P2P_STATE_CHANGED_ACTION.equals(action)) { + handleP2pStateChanged(intent.getIntExtra( + WifiP2pManager.EXTRA_WIFI_STATE, WifiP2pManager.WIFI_P2P_STATE_DISABLED)); + } + } + }; + + public WifiP2pEnabler(Context context, Switch switch_) { + mContext = context; + mSwitch = switch_; + + mWifiP2pManager = (WifiP2pManager) context.getSystemService(Context.WIFI_P2P_SERVICE); + if (!mWifiP2pManager.connectHandler(mContext, mHandler)) { + //Failure to set up connection + Log.e(TAG, "Failed to set up connection with wifi p2p service"); + mWifiP2pManager = null; + mSwitch.setEnabled(false); + } + mIntentFilter = new IntentFilter(WifiP2pManager.WIFI_P2P_STATE_CHANGED_ACTION); + + } + + public void resume() { + if (mWifiP2pManager == null) return; + mContext.registerReceiver(mReceiver, mIntentFilter); + mSwitch.setOnCheckedChangeListener(this); + } + + public void pause() { + if (mWifiP2pManager == null) return; + mContext.unregisterReceiver(mReceiver); + mSwitch.setOnCheckedChangeListener(null); + } + + public void setSwitch(Switch switch_) { + if (mSwitch == switch_) return; + mSwitch.setOnCheckedChangeListener(null); + mSwitch = switch_; + mSwitch.setOnCheckedChangeListener(this); + + mSwitch.setChecked(mWifiP2pState == WifiP2pManager.WIFI_P2P_STATE_ENABLED); + } + + public void onCheckedChanged(CompoundButton buttonView, boolean isChecked) { + + if (mWifiP2pManager == null) return; + + if (isChecked) { + mWifiP2pManager.enableP2p(); + } else { + mWifiP2pManager.disableP2p(); + } + } + + private void handleP2pStateChanged(int state) { + mSwitch.setEnabled(true); + switch (state) { + case WifiP2pManager.WIFI_P2P_STATE_ENABLED: + mWifiP2pState = WifiP2pManager.WIFI_P2P_STATE_ENABLED; + mSwitch.setChecked(true); + break; + case WifiP2pManager.WIFI_P2P_STATE_DISABLED: + mWifiP2pState = WifiP2pManager.WIFI_P2P_STATE_DISABLED; + mSwitch.setChecked(false); + break; + default: + mWifiP2pState = WifiP2pManager.WIFI_P2P_STATE_DISABLED; + Log.e(TAG,"Unhandled wifi state " + state); + break; + } + } + + private class WifiP2pHandler extends Handler { + @Override + public void handleMessage(Message msg) { + switch (msg.what) { + case WifiP2pManager.HANDLER_DISCONNECTION: + //Failure to set up connection + Log.e(TAG, "Lost connection with wifi p2p service"); + mWifiP2pManager = null; + mSwitch.setEnabled(false); + break; + case WifiP2pManager.ENABLE_P2P_FAILED: + mSwitch.setEnabled(true); + break; + default: + //Ignore + break; + } + } + } + +} diff --git a/src/com/android/settings/wifi/p2p/WifiP2pPeer.java b/src/com/android/settings/wifi/p2p/WifiP2pPeer.java new file mode 100644 index 0000000..35ae15a --- /dev/null +++ b/src/com/android/settings/wifi/p2p/WifiP2pPeer.java @@ -0,0 +1,104 @@ +/* + * Copyright (C) 2011 The Android Open Source Project + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +package com.android.settings.wifi.p2p; + +import com.android.settings.R; + +import android.content.Context; +import android.net.wifi.WifiManager; +import android.net.wifi.p2p.WifiP2pManager; +import android.net.wifi.p2p.WifiP2pDevice; +import android.net.wifi.p2p.WifiP2pDevice.Status; +import android.preference.Preference; +import android.text.TextUtils; +import android.view.View; +import android.widget.ImageView; + +import java.util.Comparator; + +public class WifiP2pPeer extends Preference { + + private static final int[] STATE_SECURED = {R.attr.state_encrypted}; + public WifiP2pDevice device; + + private int mRssi; + private ImageView mSignal; + + private static final int SIGNAL_LEVELS = 4; + + public WifiP2pPeer(Context context, WifiP2pDevice dev) { + super(context); + device = dev; + setWidgetLayoutResource(R.layout.preference_widget_wifi_signal); + mRssi = 60; //TODO: fix + } + + @Override + protected void onBindView(View view) { + if (TextUtils.isEmpty(device.deviceName)) { + setTitle(device.deviceAddress); + } else { + setTitle(device.deviceName); + } + mSignal = (ImageView) view.findViewById(R.id.signal); + if (mRssi == Integer.MAX_VALUE) { + mSignal.setImageDrawable(null); + } else { + mSignal.setImageResource(R.drawable.wifi_signal); + mSignal.setImageState(STATE_SECURED, true); + } + refresh(); + super.onBindView(view); + } + + @Override + public int compareTo(Preference preference) { + if (!(preference instanceof WifiP2pPeer)) { + return 1; + } + WifiP2pPeer other = (WifiP2pPeer) preference; + + // devices go in the order of the status + if (device.status != other.device.status) { + return device.status.ordinal() < other.device.status.ordinal() ? -1 : 1; + } + + // Sort by name/address + if (device.deviceName != null) { + return device.deviceName.compareToIgnoreCase(other.device.deviceName); + } + + return device.deviceAddress.compareToIgnoreCase(other.device.deviceAddress); + } + + int getLevel() { + if (mRssi == Integer.MAX_VALUE) { + return -1; + } + return WifiManager.calculateSignalLevel(mRssi, SIGNAL_LEVELS); + } + + private void refresh() { + if (mSignal == null) { + return; + } + Context context = getContext(); + mSignal.setImageLevel(getLevel()); + String[] statusArray = context.getResources().getStringArray(R.array.wifi_p2p_status); + setSummary(statusArray[device.status.ordinal()]); + } +} diff --git a/src/com/android/settings/wifi/p2p/WifiP2pSettings.java b/src/com/android/settings/wifi/p2p/WifiP2pSettings.java new file mode 100644 index 0000000..2e05595 --- /dev/null +++ b/src/com/android/settings/wifi/p2p/WifiP2pSettings.java @@ -0,0 +1,257 @@ +/* + * Copyright (C) 2011 The Android Open Source Project + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +package com.android.settings; + +import android.app.ActionBar; +import android.app.Activity; +import android.app.AlertDialog; +import android.app.Dialog; +import android.content.BroadcastReceiver; +import android.content.Context; +import android.content.DialogInterface; +import android.content.DialogInterface.OnClickListener; +import android.content.Intent; +import android.content.IntentFilter; +import android.net.wifi.p2p.WifiP2pConfig; +import android.net.wifi.p2p.WifiP2pDevice; +import android.net.wifi.p2p.WifiP2pDeviceList; +import android.net.wifi.p2p.WifiP2pManager; +import android.os.Bundle; +import android.os.Handler; +import android.os.Message; +import android.preference.Preference; +import android.preference.PreferenceActivity; +import android.preference.PreferenceScreen; +import android.util.Log; +import android.view.Gravity; +import android.view.Menu; +import android.view.MenuInflater; +import android.view.MenuItem; +import android.widget.Switch; + +import com.android.settings.wifi.p2p.WifiP2pDialog; +import com.android.settings.wifi.p2p.WifiP2pEnabler; +import com.android.settings.wifi.p2p.WifiP2pPeer; + +import java.util.Arrays; +import java.util.List; +import java.util.Collection; + +/* + * Displays Wi-fi p2p settings UI + */ +public class WifiP2pSettings extends SettingsPreferenceFragment { + + private static final String TAG = "WifiP2pSettings"; + private static final int MENU_ID_SEARCH = Menu.FIRST; + private static final int MENU_ID_CREATE_GROUP = Menu.FIRST + 1; + private static final int MENU_ID_ADVANCED = Menu.FIRST +2; + + + private final IntentFilter mIntentFilter = new IntentFilter(); + private final Handler mHandler = new WifiP2pHandler(); + private WifiP2pManager mWifiP2pManager; + private WifiP2pEnabler mWifiP2pEnabler; + private WifiP2pDialog mConnectDialog; + private OnClickListener mConnectListener; + private OnClickListener mDisconnectListener; + private WifiP2pPeer mSelectedWifiPeer; + + private static final int DIALOG_CONNECT = 1; + private static final int DIALOG_DISCONNECT = 2; + + private final BroadcastReceiver mReceiver = new BroadcastReceiver() { + @Override + public void onReceive(Context context, Intent intent) { + String action = intent.getAction(); + + if (WifiP2pManager.WIFI_P2P_STATE_CHANGED_ACTION.equals(action)) { + //TODO: nothing right now + } else if (WifiP2pManager.WIFI_P2P_PEERS_CHANGED_ACTION.equals(action)) { + if (mWifiP2pManager != null) mWifiP2pManager.requestPeers(); + } + } + }; + + @Override + public void onCreate(Bundle icicle) { + super.onCreate(icicle); + addPreferencesFromResource(R.xml.wifi_p2p_settings); + + mIntentFilter.addAction(WifiP2pManager.WIFI_P2P_STATE_CHANGED_ACTION); + mIntentFilter.addAction(WifiP2pManager.WIFI_P2P_PEERS_CHANGED_ACTION); + + final Activity activity = getActivity(); + mWifiP2pManager = (WifiP2pManager) getSystemService(Context.WIFI_P2P_SERVICE); + if (!mWifiP2pManager.connectHandler(activity, mHandler)) { + //Failure to set up connection + Log.e(TAG, "Failed to set up connection with wifi p2p service"); + mWifiP2pManager = null; + } + + Switch actionBarSwitch = new Switch(activity); + + if (activity instanceof PreferenceActivity) { + PreferenceActivity preferenceActivity = (PreferenceActivity) activity; + if (preferenceActivity.onIsHidingHeaders() || !preferenceActivity.onIsMultiPane()) { + final int padding = activity.getResources().getDimensionPixelSize( + R.dimen.action_bar_switch_padding); + actionBarSwitch.setPadding(0, 0, padding, 0); + activity.getActionBar().setDisplayOptions(ActionBar.DISPLAY_SHOW_CUSTOM, + ActionBar.DISPLAY_SHOW_CUSTOM); + activity.getActionBar().setCustomView(actionBarSwitch, new ActionBar.LayoutParams( + ActionBar.LayoutParams.WRAP_CONTENT, + ActionBar.LayoutParams.WRAP_CONTENT, + Gravity.CENTER_VERTICAL | Gravity.RIGHT)); + } + } + + mWifiP2pEnabler = new WifiP2pEnabler(activity, actionBarSwitch); + + //connect dialog listener + mConnectListener = new OnClickListener() { + @Override + public void onClick(DialogInterface dialog, int which) { + if (which == DialogInterface.BUTTON_POSITIVE) { + WifiP2pConfig config = mConnectDialog.getConfig(); + if (mWifiP2pManager != null) { + mWifiP2pManager.connect(config); + } + } + } + }; + + //disconnect dialog listener + mDisconnectListener = new OnClickListener() { + @Override + public void onClick(DialogInterface dialog, int which) { + if (which == DialogInterface.BUTTON_POSITIVE) { + if (mWifiP2pManager != null) { + mWifiP2pManager.disconnect(); + } + } + } + }; + setHasOptionsMenu(true); + } + + @Override + public void onResume() { + super.onResume(); + getActivity().registerReceiver(mReceiver, mIntentFilter); + if (mWifiP2pEnabler != null) { + mWifiP2pEnabler.resume(); + } + if (mWifiP2pManager != null) mWifiP2pManager.discoverPeers(); + } + + @Override + public void onPause() { + super.onPause(); + if (mWifiP2pEnabler != null) { + mWifiP2pEnabler.pause(); + } + getActivity().unregisterReceiver(mReceiver); + } + + @Override + public void onCreateOptionsMenu(Menu menu, MenuInflater inflater) { + menu.add(Menu.NONE, MENU_ID_SEARCH, 0, R.string.wifi_p2p_menu_search) + .setShowAsAction(MenuItem.SHOW_AS_ACTION_IF_ROOM); + menu.add(Menu.NONE, MENU_ID_CREATE_GROUP, 0, R.string.wifi_p2p_menu_create_group) + .setShowAsAction(MenuItem.SHOW_AS_ACTION_IF_ROOM); + menu.add(Menu.NONE, MENU_ID_ADVANCED, 0, R.string.wifi_p2p_menu_advanced) + .setShowAsAction(MenuItem.SHOW_AS_ACTION_IF_ROOM); + super.onCreateOptionsMenu(menu, inflater); + } + + @Override + public boolean onOptionsItemSelected(MenuItem item) { + switch (item.getItemId()) { + case MENU_ID_SEARCH: + mWifiP2pManager.discoverPeers(); + return true; + case MENU_ID_CREATE_GROUP: + mWifiP2pManager.createGroup(); + return true; + case MENU_ID_ADVANCED: + //TODO: add advanced settings for p2p + return true; + } + return super.onOptionsItemSelected(item); + } + + @Override + public boolean onPreferenceTreeClick(PreferenceScreen screen, Preference preference) { + if (preference instanceof WifiP2pPeer) { + mSelectedWifiPeer = (WifiP2pPeer) preference; + if (mSelectedWifiPeer.device.status == WifiP2pDevice.Status.CONNECTED) { + showDialog(DIALOG_DISCONNECT); + } else { + showDialog(DIALOG_CONNECT); + } + } + return super.onPreferenceTreeClick(screen, preference); + } + + @Override + public Dialog onCreateDialog(int id) { + if (id == DIALOG_CONNECT) { + mConnectDialog = new WifiP2pDialog(getActivity(), mConnectListener, + mSelectedWifiPeer.device); + return mConnectDialog; + } else if (id == DIALOG_DISCONNECT) { + AlertDialog dialog = new AlertDialog.Builder(getActivity()) + .setTitle("Disconnect ?") + .setMessage("Do you want to disconnect ?") + .setPositiveButton(getActivity().getString(R.string.dlg_ok), mDisconnectListener) + .setNegativeButton(getActivity().getString(R.string.dlg_cancel), null) + .create(); + return dialog; + } + return null; + } + + private void updatePeers(WifiP2pDeviceList peers) { + final PreferenceScreen preferenceScreen = getPreferenceScreen(); + preferenceScreen.removeAll(); + + for (WifiP2pDevice peer: peers.getDeviceList()) { + preferenceScreen.addPreference(new WifiP2pPeer(getActivity(), peer)); + } + } + + private class WifiP2pHandler extends Handler { + @Override + public void handleMessage(Message message) { + switch (message.what) { + case WifiP2pManager.HANDLER_DISCONNECTION: + //Failure to set up connection + Log.e(TAG, "Lost connection with wifi p2p service"); + mWifiP2pManager = null; + break; + case WifiP2pManager.RESPONSE_PEERS: + updatePeers(mWifiP2pManager.peersInResponse(message)); + break; + default: + //Ignore + break; + } + } + } + +} |