diff --git a/res/drawable/ring_notif.xml b/res/drawable/ring_notif.xml new file mode 100644 index 00000000000..414a83d0ba3 --- /dev/null +++ b/res/drawable/ring_notif.xml @@ -0,0 +1,24 @@ + + + + diff --git a/res/drawable/ring_notif_mute.xml b/res/drawable/ring_notif_mute.xml new file mode 100644 index 00000000000..afb835c3009 --- /dev/null +++ b/res/drawable/ring_notif_mute.xml @@ -0,0 +1,23 @@ + + + diff --git a/res/drawable/ring_notif_vibrate.xml b/res/drawable/ring_notif_vibrate.xml new file mode 100644 index 00000000000..4f19e01f7f4 --- /dev/null +++ b/res/drawable/ring_notif_vibrate.xml @@ -0,0 +1,23 @@ + + + diff --git a/res/xml/notification_settings.xml b/res/xml/notification_settings.xml index e5dda19080e..e9a499260c5 100644 --- a/res/xml/notification_settings.xml +++ b/res/xml/notification_settings.xml @@ -39,13 +39,13 @@ diff --git a/src/com/android/settings/notification/NotificationSettings.java b/src/com/android/settings/notification/NotificationSettings.java index a523a759122..30940325d7e 100644 --- a/src/com/android/settings/notification/NotificationSettings.java +++ b/src/com/android/settings/notification/NotificationSettings.java @@ -30,6 +30,7 @@ import android.os.Bundle; import android.os.Handler; import android.os.Looper; import android.os.Message; +import android.os.Vibrator; import android.preference.Preference; import android.preference.Preference.OnPreferenceChangeListener; import android.preference.PreferenceCategory; @@ -40,6 +41,7 @@ import android.provider.SearchIndexableResource; import android.provider.Settings; import android.util.Log; +import android.widget.SeekBar; import com.android.internal.widget.LockPatternUtils; import com.android.settings.R; import com.android.settings.SettingsPreferenceFragment; @@ -76,6 +78,8 @@ public class NotificationSettings extends SettingsPreferenceFragment implements private Context mContext; private PackageManager mPM; private boolean mVoiceCapable; + private Vibrator mVibrator; + private VolumeSeekBarPreference mRingOrNotificationPreference; private Preference mPhoneRingtonePreference; private Preference mNotificationRingtonePreference; @@ -93,16 +97,24 @@ public class NotificationSettings extends SettingsPreferenceFragment implements mPM = mContext.getPackageManager(); mVoiceCapable = Utils.isVoiceCapable(mContext); mSecure = new LockPatternUtils(getActivity()).isSecure(); + + mVibrator = (Vibrator) getActivity().getSystemService(Context.VIBRATOR_SERVICE); + if (mVibrator != null && !mVibrator.hasVibrator()) { + mVibrator = null; + } + addPreferencesFromResource(R.xml.notification_settings); final PreferenceCategory sound = (PreferenceCategory) findPreference(KEY_SOUND); initVolumePreference(KEY_MEDIA_VOLUME, AudioManager.STREAM_MUSIC); initVolumePreference(KEY_ALARM_VOLUME, AudioManager.STREAM_ALARM); if (mVoiceCapable) { - initVolumePreference(KEY_RING_VOLUME, AudioManager.STREAM_RING); + mRingOrNotificationPreference = + initVolumePreference(KEY_RING_VOLUME, AudioManager.STREAM_RING); sound.removePreference(sound.findPreference(KEY_NOTIFICATION_VOLUME)); } else { - initVolumePreference(KEY_NOTIFICATION_VOLUME, AudioManager.STREAM_NOTIFICATION); + mRingOrNotificationPreference = + initVolumePreference(KEY_NOTIFICATION_VOLUME, AudioManager.STREAM_NOTIFICATION); sound.removePreference(sound.findPreference(KEY_RING_VOLUME)); } initRingtones(sound); @@ -134,10 +146,19 @@ public class NotificationSettings extends SettingsPreferenceFragment implements // === Volumes === - private void initVolumePreference(String key, int stream) { + private VolumeSeekBarPreference initVolumePreference(String key, int stream) { final VolumeSeekBarPreference volumePref = (VolumeSeekBarPreference) findPreference(key); - volumePref.setStream(stream); volumePref.setCallback(mVolumeCallback); + volumePref.setStream(stream); + return volumePref; + } + + private void updateRingOrNotificationIcon(int progress) { + mRingOrNotificationPreference.showIcon(progress > 0 + ? R.drawable.ring_notif + : (mVibrator == null + ? R.drawable.ring_notif_mute + : R.drawable.ring_notif_vibrate)); } private final class VolumePreferenceCallback implements VolumeSeekBarPreference.Callback { @@ -155,6 +176,14 @@ public class NotificationSettings extends SettingsPreferenceFragment implements } } + @Override + public void onStreamValueChanged(int stream, int progress) { + if (stream == AudioManager.STREAM_RING) { + mHandler.removeMessages(H.UPDATE_RINGER_ICON); + mHandler.obtainMessage(H.UPDATE_RINGER_ICON, progress, 0).sendToTarget(); + } + } + public void stopSample() { if (mCurrent != null) { mCurrent.stopSample(); @@ -426,6 +455,7 @@ public class NotificationSettings extends SettingsPreferenceFragment implements private static final int UPDATE_PHONE_RINGTONE = 1; private static final int UPDATE_NOTIFICATION_RINGTONE = 2; private static final int STOP_SAMPLE = 3; + private static final int UPDATE_RINGER_ICON = 4; private H() { super(Looper.getMainLooper()); @@ -443,6 +473,9 @@ public class NotificationSettings extends SettingsPreferenceFragment implements case STOP_SAMPLE: mVolumeCallback.stopSample(); break; + case UPDATE_RINGER_ICON: + updateRingOrNotificationIcon(msg.arg1); + break; } } } diff --git a/src/com/android/settings/notification/VolumeSeekBarPreference.java b/src/com/android/settings/notification/VolumeSeekBarPreference.java index 11a83a759dc..f94e6a132be 100644 --- a/src/com/android/settings/notification/VolumeSeekBarPreference.java +++ b/src/com/android/settings/notification/VolumeSeekBarPreference.java @@ -26,6 +26,7 @@ import android.preference.SeekBarVolumizer; import android.util.AttributeSet; import android.util.Log; import android.view.View; +import android.widget.ImageView; import android.widget.SeekBar; import com.android.settings.R; @@ -39,6 +40,7 @@ public class VolumeSeekBarPreference extends SeekBarPreference private SeekBar mSeekBar; private SeekBarVolumizer mVolumizer; private Callback mCallback; + private ImageView mIconView; public VolumeSeekBarPreference(Context context, AttributeSet attrs, int defStyleAttr, int defStyleRes) { @@ -93,9 +95,35 @@ public class VolumeSeekBarPreference extends SeekBarPreference }; final Uri sampleUri = mStream == AudioManager.STREAM_MUSIC ? getMediaVolumeUri() : null; if (mVolumizer == null) { - mVolumizer = new SeekBarVolumizer(getContext(), mStream, sampleUri, sbvc); + mVolumizer = new SeekBarVolumizer(getContext(), mStream, sampleUri, sbvc) { + // we need to piggyback on SBV's SeekBar listener to update our icon + @Override + public void onProgressChanged(SeekBar seekBar, int progress, + boolean fromTouch) { + super.onProgressChanged(seekBar, progress, fromTouch); + mCallback.onStreamValueChanged(mStream, progress); + } + }; } mVolumizer.setSeekBar(mSeekBar); + mIconView = (ImageView) view.findViewById(com.android.internal.R.id.icon); + mCallback.onStreamValueChanged(mStream, mSeekBar.getProgress()); + } + + // during initialization, this preference is the SeekBar listener + @Override + public void onProgressChanged(SeekBar seekBar, int progress, + boolean fromTouch) { + super.onProgressChanged(seekBar, progress, fromTouch); + mCallback.onStreamValueChanged(mStream, progress); + } + + public void showIcon(int resId) { + // Instead of using setIcon, which will trigger listeners, this just decorates the + // preference temporarily with a new icon. + if (mIconView != null) { + mIconView.setImageResource(resId); + } } private Uri getMediaVolumeUri() { @@ -106,5 +134,6 @@ public class VolumeSeekBarPreference extends SeekBarPreference public interface Callback { void onSampleStarting(SeekBarVolumizer sbv); + void onStreamValueChanged(int stream, int progress); } }