diff options
Diffstat (limited to 'src/com/android/settings/voice/VoiceInputPreference.java')
-rw-r--r-- | src/com/android/settings/voice/VoiceInputPreference.java | 233 |
1 files changed, 233 insertions, 0 deletions
diff --git a/src/com/android/settings/voice/VoiceInputPreference.java b/src/com/android/settings/voice/VoiceInputPreference.java new file mode 100644 index 0000000..0ebffbb --- /dev/null +++ b/src/com/android/settings/voice/VoiceInputPreference.java @@ -0,0 +1,233 @@ +/* + * Copyright (C) 2014 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.voice; + +import android.app.AlertDialog; +import android.content.ComponentName; +import android.content.Context; +import android.content.DialogInterface; +import android.content.Intent; +import android.preference.Preference; +import android.util.Log; +import android.view.View; +import android.view.ViewGroup; +import android.widget.Checkable; +import android.widget.CompoundButton; +import android.widget.RadioButton; + + +import com.android.settings.R; +import com.android.settings.Utils; + +public final class VoiceInputPreference extends Preference { + + private static final String TAG = "VoiceInputPreference"; + + private final CharSequence mLabel; + + private final CharSequence mAppLabel; + + private final CharSequence mAlertText; + + private final ComponentName mSettingsComponent; + + /** + * The shared radio button state, which button is checked etc. + */ + private final RadioButtonGroupState mSharedState; + + /** + * When true, the change callbacks on the radio button will not + * fire. + */ + private volatile boolean mPreventRadioButtonCallbacks; + + private View mSettingsIcon; + private RadioButton mRadioButton; + + private final CompoundButton.OnCheckedChangeListener mRadioChangeListener = + new CompoundButton.OnCheckedChangeListener() { + @Override + public void onCheckedChanged(CompoundButton buttonView, boolean isChecked) { + onRadioButtonClicked(buttonView, isChecked); + } + }; + + public VoiceInputPreference(Context context, VoiceInputHelper.BaseInfo info, + CharSequence summary, CharSequence alertText, RadioButtonGroupState state) { + super(context); + setLayoutResource(R.layout.preference_tts_engine); + + mSharedState = state; + mLabel = info.label; + mAppLabel = info.appLabel; + mAlertText = alertText; + mSettingsComponent = info.settings; + mPreventRadioButtonCallbacks = false; + + setKey(info.key); + setTitle(info.label); + setSummary(summary); + } + + @Override + public View getView(View convertView, ViewGroup parent) { + if (mSharedState == null) { + throw new IllegalStateException("Call to getView() before a call to" + + "setSharedState()"); + } + + View view = super.getView(convertView, parent); + final RadioButton rb = (RadioButton) view.findViewById(R.id.tts_engine_radiobutton); + rb.setOnCheckedChangeListener(mRadioChangeListener); + + boolean isChecked = getKey().equals(mSharedState.getCurrentKey()); + if (isChecked) { + mSharedState.setCurrentChecked(rb); + } + + mPreventRadioButtonCallbacks = true; + rb.setChecked(isChecked); + mPreventRadioButtonCallbacks = false; + + mRadioButton = rb; + + View textLayout = view.findViewById(R.id.tts_engine_pref_text); + textLayout.setOnClickListener(new View.OnClickListener() { + @Override + public void onClick(View v) { + onRadioButtonClicked(rb, !rb.isChecked()); + } + }); + + mSettingsIcon = view.findViewById(R.id.tts_engine_settings); + mSettingsIcon.setOnClickListener(new View.OnClickListener() { + @Override + public void onClick(View v) { + Intent intent = new Intent(Intent.ACTION_MAIN); + intent.setComponent(mSettingsComponent); + getContext().startActivity(new Intent(intent)); + } + }); + updateCheckedState(isChecked); + + return view; + } + + private boolean shouldDisplayAlert() { + return mAlertText != null; + } + + private void displayAlert( + final DialogInterface.OnClickListener positiveOnClickListener, + final DialogInterface.OnClickListener negativeOnClickListener) { + Log.i(TAG, "Displaying data alert for :" + getKey()); + + AlertDialog.Builder builder = new AlertDialog.Builder(getContext()); + String msg = String.format(getContext().getResources().getConfiguration().locale, + mAlertText.toString(), mAppLabel); + builder.setTitle(android.R.string.dialog_alert_title) + .setMessage(msg) + .setCancelable(true) + .setPositiveButton(android.R.string.ok, positiveOnClickListener) + .setNegativeButton(android.R.string.cancel, negativeOnClickListener) + .setOnCancelListener(new DialogInterface.OnCancelListener() { + @Override public void onCancel(DialogInterface dialog) { + negativeOnClickListener.onClick(dialog, DialogInterface.BUTTON_NEGATIVE); + } + }); + + AlertDialog dialog = builder.create(); + dialog.show(); + } + + public void doClick() { + mRadioButton.performClick(); + } + + void updateCheckedState(boolean isChecked) { + if (mSettingsComponent != null) { + mSettingsIcon.setVisibility(View.VISIBLE); + if (isChecked) { + mSettingsIcon.setEnabled(true); + mSettingsIcon.setAlpha(1); + } else { + mSettingsIcon.setEnabled(false); + mSettingsIcon.setAlpha(Utils.DISABLED_ALPHA); + } + } else { + mSettingsIcon.setVisibility(View.GONE); + } + } + + void onRadioButtonClicked(final CompoundButton buttonView, boolean isChecked) { + if (mPreventRadioButtonCallbacks) { + return; + } + if (mSharedState.getCurrentChecked() == buttonView) { + updateCheckedState(isChecked); + return; + } + + if (isChecked) { + // Should we alert user? if that's true, delay making engine current one. + if (shouldDisplayAlert()) { + displayAlert(new DialogInterface.OnClickListener() { + @Override + public void onClick(DialogInterface dialog, int which) { + makeCurrentChecked(buttonView); + } + }, new DialogInterface.OnClickListener() { + @Override + public void onClick(DialogInterface dialog, int which) { + // Undo the click. + buttonView.setChecked(false); + } + } + ); + } else { + // Privileged engine, set it current + makeCurrentChecked(buttonView); + } + } else { + updateCheckedState(isChecked); + } + } + + void makeCurrentChecked(Checkable current) { + if (mSharedState.getCurrentChecked() != null) { + mSharedState.getCurrentChecked().setChecked(false); + } + mSharedState.setCurrentChecked(current); + mSharedState.setCurrentKey(getKey()); + updateCheckedState(true); + callChangeListener(mSharedState.getCurrentKey()); + } + + /** + * Holds all state that is common to this group of radio buttons, such + * as the currently selected key and the currently checked compound button. + * (which corresponds to this key). + */ + public interface RadioButtonGroupState { + String getCurrentKey(); + Checkable getCurrentChecked(); + + void setCurrentKey(String key); + void setCurrentChecked(Checkable current); + } +} |