Donate to e Foundation | Murena handsets with /e/OS | Own a part of Murena! Learn more

Commit d8ba12c5 authored by DvTonder's avatar DvTonder
Browse files

Framework: Quick Settings customization (Part 2 of 2) WIP!

This commit will alow loading the Quick Settings tiles layout from
a layout that is configured in Settings.

Patchset 3 - Restore Settings tile to AOSP location

Change-Id: Id4e4353dee68b8ca434dfa64d1f88737792a2e28
parent c90b2343
Loading
Loading
Loading
Loading
+35 −0
Original line number Diff line number Diff line
@@ -2575,6 +2575,41 @@ public final class Settings {
         */
        public static final String POINTER_SPEED = "pointer_speed";

        /**
         * Quick Settings Panel Tiles to Use
         *
         * @hide
         */
        public static final String QUICK_SETTINGS_TILES = "quick_settings_tiles";

        /**
         * Quick Settings Panel Dynamic Tiles
         *
         * @hide
         */
        public static final String QS_DYNAMIC_ALARM = "qs_dyanmic_alarm";

        /**
         * Quick Settings Panel Dynamic Tiles
         *
         * @hide
         */
        public static final String QS_DYNAMIC_BUGREPORT = "qs_dyanmic_bugreport";

        /**
         * Quick Settings Panel Dynamic Tiles
         *
         * @hide
         */
        public static final String QS_DYNAMIC_IME = "qs_dyanmic_ime";

        /**
         * Quick Settings Panel Dynamic Tiles
         *
         * @hide
         */
        public static final String QS_DYNAMIC_WIFI = "qs_dyanmic_wifi";

        /**
         * Use the Notification Power Widget? (Who wouldn't!)
         *
+214 −40
Original line number Diff line number Diff line
package com.android.systemui.quicksettings;

import android.content.BroadcastReceiver;
import android.content.ContentResolver;
import android.content.Context;
import android.content.Intent;
import android.content.IntentFilter;
import android.database.ContentObserver;
import android.media.AudioManager;
import android.os.Handler;
import android.os.Vibrator;
import android.provider.Settings;
import android.text.TextUtils;
import android.view.LayoutInflater;
import android.view.View;
import android.view.View.OnLongClickListener;
@@ -16,49 +21,58 @@ import com.android.systemui.statusbar.phone.QuickSettingsContainerView;

public class RingerVibrationModeTile extends QuickSettingsTile {

    private static final String SEPARATOR = "OV=I=XseparatorX=I=VO";

    // Define the available ringer modes
    private final Ringer mSilentRinger = new Ringer(false,
            AudioManager.VIBRATE_SETTING_OFF,
            AudioManager.RINGER_MODE_SILENT, false);
    private final Ringer mVibrateRinger = new Ringer(true,
            AudioManager.VIBRATE_SETTING_ONLY_SILENT,
            AudioManager.RINGER_MODE_VIBRATE, true);
    private final Ringer mSoundRinger = new Ringer(true,
            AudioManager.VIBRATE_SETTING_ONLY_SILENT,
            AudioManager.RINGER_MODE_NORMAL, false);
    private final Ringer mSoundVibrateRinger = new Ringer(true,
            AudioManager.VIBRATE_SETTING_ON,
            AudioManager.RINGER_MODE_NORMAL, true);
    private final Ringer[] mRingers = new Ringer[] {
            mSilentRinger, mVibrateRinger, mSoundRinger, mSoundVibrateRinger
    };

    private int mRingersIndex = 2;
    private int[] mRingerValues = new int[] {
            0, 1, 2, 3
    };
    private int mRingerValuesIndex = 2;

    private AudioManager mAudioManager;
    private Handler mHandler;
    private SoundModesChangedObserver mSoundModesChangedObserver;

    public RingerVibrationModeTile(Context context, LayoutInflater inflater,
            QuickSettingsContainerView container, QuickSettingsController qsc) {
        super(context, inflater, container, qsc);

        mAudioManager = (AudioManager) mContext.getSystemService(Context.AUDIO_SERVICE);
        mHandler = new Handler();

        onClick = new View.OnClickListener() {
        // Load the available ringer modes
        updateSettings(mContext.getContentResolver());

        // Start observing for changes
        mSoundModesChangedObserver = new SoundModesChangedObserver(mHandler);
        mSoundModesChangedObserver.startObserving();

        onClick = new View.OnClickListener() {
            @Override
            public void onClick(View v) {
                Vibrator vibrator = (Vibrator) mContext.getSystemService(Context.VIBRATOR_SERVICE);
                boolean vibrate = mAudioManager.getVibrateSetting(AudioManager.VIBRATE_TYPE_RINGER) == AudioManager.VIBRATE_SETTING_ON;
                if(mAudioManager.getRingerMode() == AudioManager.RINGER_MODE_NORMAL && vibrate){
                    // Switch to Silent
                    mAudioManager.setVibrateSetting(AudioManager.VIBRATE_TYPE_RINGER, AudioManager.VIBRATE_SETTING_OFF);
                    mAudioManager.setRingerMode(AudioManager.RINGER_MODE_SILENT);
                }else if(mAudioManager.getRingerMode() == AudioManager.RINGER_MODE_NORMAL){
                    // Switch to Sound + Vibration
                    vibrator.vibrate(300);
                    mAudioManager.setVibrateSetting(AudioManager.VIBRATE_TYPE_RINGER, AudioManager.VIBRATE_SETTING_ON);
                    mAudioManager.setRingerMode(AudioManager.RINGER_MODE_NORMAL);
                    Intent i = new Intent(VibrationModeTile.VIBRATION_STATE_CHANGED);
                    mContext.sendBroadcast(i);
                }else if(mAudioManager.getRingerMode() == AudioManager.RINGER_MODE_SILENT){
                    // Switch to Vibration
                    vibrator.vibrate(300);
                    mAudioManager.setRingerMode(AudioManager.RINGER_MODE_VIBRATE);
                    mAudioManager.setVibrateSetting(AudioManager.VIBRATE_TYPE_RINGER, AudioManager.VIBRATE_SETTING_ON);
                    Intent i = new Intent(VibrationModeTile.VIBRATION_STATE_CHANGED);
                    mContext.sendBroadcast(i);
                }else if(mAudioManager.getRingerMode() == AudioManager.RINGER_MODE_VIBRATE){
                    // Switch to Sound
                    mAudioManager.setVibrateSetting(AudioManager.VIBRATE_TYPE_RINGER, AudioManager.VIBRATE_SETTING_OFF);
                    mAudioManager.setRingerMode(AudioManager.RINGER_MODE_NORMAL);
                }
                toggleState();
                applyVibrationChanges();
            }
        };

        onLongClick = new OnLongClickListener() {

            @Override
            public boolean onLongClick(View v) {
                startSettingsActivity(android.provider.Settings.ACTION_SOUND_SETTINGS);
@@ -67,7 +81,6 @@ public class RingerVibrationModeTile extends QuickSettingsTile {
        };

        mBroadcastReceiver = new BroadcastReceiver() {

            @Override
            public void onReceive(Context context, Intent intent) {
                applyVibrationChanges();
@@ -80,20 +93,181 @@ public class RingerVibrationModeTile extends QuickSettingsTile {
    }

    private void applyVibrationChanges(){
        boolean vibrate = mAudioManager.getVibrateSetting(AudioManager.VIBRATE_TYPE_RINGER) == AudioManager.VIBRATE_SETTING_ON;
        updateState();
        updateQuickSettings();
    }

    protected void updateState() {
        // The title does not change
        mLabel = mContext.getString(R.string.quick_settings_ringer_normal);
        if(mAudioManager.getRingerMode() == AudioManager.RINGER_MODE_NORMAL && vibrate){
            //Sound + Vibrate
            mDrawable = R.drawable.ic_qs_ring_vibrate_on;
        }else if(mAudioManager.getRingerMode() == AudioManager.RINGER_MODE_NORMAL){
            //Sound
            mDrawable = R.drawable.ic_qs_ring_on;
        }else if(mAudioManager.getRingerMode() == AudioManager.RINGER_MODE_SILENT){

        // The icon will change depending on index
        findCurrentState();
        switch (mRingersIndex) {
            case 0:
                mDrawable = R.drawable.ic_qs_ring_off;
        }else{
                break;
            case 1:
                mDrawable = R.drawable.ic_qs_vibrate_on;
                break;
            case 2:
                mDrawable = R.drawable.ic_qs_ring_on;
                break;
            case 3:
                mDrawable = R.drawable.ic_qs_ring_vibrate_on;
                break;
        }
        updateQuickSettings();

        for (int i = 0; i < mRingerValues.length; i++) {
            if (mRingersIndex == mRingerValues[i]) {
                mRingerValuesIndex = i;
                break;
            }
        }
    }

    protected void toggleState() {
        mRingerValuesIndex++;
        if (mRingerValuesIndex > mRingerValues.length - 1) {
            mRingerValuesIndex = 0;
        }

        mRingersIndex = mRingerValues[mRingerValuesIndex];
        if (mRingersIndex > mRingers.length - 1) {
            mRingersIndex = 0;
        }

        Ringer ringer = mRingers[mRingersIndex];
        ringer.execute(mContext);
    }

    public String[] parseStoredValue(CharSequence val) {
        if (TextUtils.isEmpty(val)) {
          return null;
        } else {
          return val.toString().split(SEPARATOR);
        }
    }

    private void updateSettings(ContentResolver resolver) {
        String[] modes = parseStoredValue(Settings.System.getString(
                resolver, Settings.System.EXPANDED_RING_MODE));
        if (modes == null || modes.length == 0) {
            mRingerValues = new int[] {
                    0, 1, 2, 3
            };
        } else {
            mRingerValues = new int[modes.length];
            for (int i = 0; i < modes.length; i++) {
                mRingerValues[i] = Integer.valueOf(modes[i]);
            }
        }
    }

    private void findCurrentState() {
        boolean vibrateInSilent = Settings.System.getInt(mContext.getContentResolver(),
                Settings.System.VIBRATE_IN_SILENT, 0) == 1;
        int vibrateSetting = mAudioManager.getVibrateSetting(AudioManager.VIBRATE_TYPE_RINGER);
        int ringerMode = mAudioManager.getRingerMode();

        // Sometimes the setting don't quite match up to the states we've defined.
        // In that case, override the reported settings to get us "close" to the
        // defined settings. This bit is a little ugly but oh well.
        if (!vibrateInSilent && ringerMode == AudioManager.RINGER_MODE_SILENT) {
            vibrateSetting = AudioManager.VIBRATE_SETTING_OFF; // match Silent ringer
        } else if (!vibrateInSilent && ringerMode == AudioManager.RINGER_MODE_NORMAL) {
            vibrateInSilent = true; // match either Sound or SoundVibrate ringer
            if (vibrateSetting == AudioManager.VIBRATE_SETTING_OFF) {
                vibrateSetting = AudioManager.VIBRATE_SETTING_ONLY_SILENT; // match Sound ringer
            }
        } else if (vibrateInSilent && ringerMode == AudioManager.RINGER_MODE_VIBRATE) {
            vibrateSetting = AudioManager.VIBRATE_SETTING_ONLY_SILENT; // match Vibrate ringer 
        }

        Ringer ringer = new Ringer(vibrateInSilent, vibrateSetting, ringerMode, false);
        for (int i = 0; i < mRingers.length; i++) {
            if (mRingers[i].equals(ringer)) {
                mRingersIndex = i;
                break;
            }
        }
    }

    private class Ringer {
        final boolean mVibrateInSilent;
        final int mVibrateSetting;
        final int mRingerMode;

        Ringer(boolean vibrateInSilent, int vibrateSetting, int ringerMode, boolean doHapticFeedback) {
            mVibrateInSilent = vibrateInSilent;
            mVibrateSetting = vibrateSetting;
            mRingerMode = ringerMode;
        }

        void execute(Context context) {
            ContentResolver resolver = context.getContentResolver();
            Settings.System.putInt(resolver, Settings.System.VIBRATE_IN_SILENT,
                    (mVibrateInSilent ? 1 : 0));

            // If we are setting a vibrating state, vibrate to indicate it
            if (mVibrateSetting == AudioManager.VIBRATE_SETTING_ON
                    || mVibrateSetting == AudioManager.VIBRATE_SETTING_ONLY_SILENT) {
                Vibrator vibrator = (Vibrator) mContext.getSystemService(Context.VIBRATOR_SERVICE);
                vibrator.vibrate(250);
            }

            // Set the desired state
            mAudioManager.setVibrateSetting(AudioManager.VIBRATE_TYPE_RINGER, mVibrateSetting);
            mAudioManager.setRingerMode(mRingerMode);
        }

        @Override
        public boolean equals(Object o) {
            if (o == null) {
                return false;
            }
            if (o.getClass() != getClass()) {
                return false;
            }

            Ringer r = (Ringer) o;
            // Silent mode docs: "Ringer mode that will be silent and will not
            // vibrate. (This overrides the vibrate setting.)" If silent mode is
            // set, don't bother checking vibrate since silent overrides. This
            // fixes cases where silent mode is not detected because of "wrong"
            // vibrate state.
            if (mRingerMode == AudioManager.RINGER_MODE_SILENT
                    && (r.mRingerMode == mRingerMode)) {
                return true;
            }

            return r.mVibrateInSilent == mVibrateInSilent
                    && r.mVibrateSetting == mVibrateSetting
                    && r.mRingerMode == mRingerMode;
        }
    }

    /**
     *  ContentObserver to watch for Quick Settings tiles changes
     * @author dvtonder
     *
     */
    private class SoundModesChangedObserver extends ContentObserver {
        public SoundModesChangedObserver(Handler handler) {
            super(handler);
        }

        @Override
        public void onChange(boolean selfChange) {
            updateSettings(mContext.getContentResolver());
            applyVibrationChanges();
        }

        public void startObserving() {
            final ContentResolver cr = mContext.getContentResolver();
            cr.registerContentObserver(
                    Settings.System.getUriFor(Settings.System.EXPANDED_RING_MODE),
                    false, this);
        }
    }
}
+51 −0
Original line number Diff line number Diff line
@@ -201,6 +201,7 @@ public class PhoneStatusBar extends BaseStatusBar {
    View mFlipSettingsView;
    QuickSettingsContainerView mSettingsContainer;
    int mSettingsPanelGravity;
    private TilesChangedObserver mTilesChangedObserver;

    // top bar
    View mNotificationPanelHeader;
@@ -633,6 +634,11 @@ public class PhoneStatusBar extends BaseStatusBar {
                mQS.setService(this);
                mQS.setBar(mStatusBarView);
                mQS.setupQuickSettings();

                // Start observing for changes
                mTilesChangedObserver = new TilesChangedObserver(mHandler);
                mTilesChangedObserver.startObserving();

            } else {
                mQS = null; // fly away, be free
            }
@@ -2668,4 +2674,49 @@ public class PhoneStatusBar extends BaseStatusBar {
        public void setBounds(Rect bounds) {
        }
    }

    /**
     *  ContentObserver to watch for Quick Settings tiles changes
     * @author dvtonder
     *
     */
    private class TilesChangedObserver extends ContentObserver {
        public TilesChangedObserver(Handler handler) {
            super(handler);
        }

        @Override
        public void onChange(boolean selfChange) {
            if (mSettingsContainer != null) {
                // Refresh the container
                mSettingsContainer.removeAllViews();
                mQS.setupQuickSettings();
                mSettingsContainer.requestLayout();
            }
        }

        public void startObserving() {
            final ContentResolver cr = mContext.getContentResolver();
            cr.registerContentObserver(
                    Settings.System.getUriFor(Settings.System.QUICK_SETTINGS_TILES),
                    false, this);

            cr.registerContentObserver(
                    Settings.System.getUriFor(Settings.System.QS_DYNAMIC_ALARM),
                    false, this);

            cr.registerContentObserver(
                    Settings.System.getUriFor(Settings.System.QS_DYNAMIC_BUGREPORT),
                    false, this);

            cr.registerContentObserver(
                    Settings.System.getUriFor(Settings.System.QS_DYNAMIC_IME),
                    false, this);

            cr.registerContentObserver(
                    Settings.System.getUriFor(Settings.System.QS_DYNAMIC_WIFI),
                    false, this);
        }
    }

}
+205 −68

File changed.

Preview size limit exceeded, changes collapsed.

+3 −1
Original line number Diff line number Diff line
@@ -55,6 +55,7 @@ public class SettingsPanelView extends PanelView {
        mHandleView = findViewById(R.id.handle);

        setContentDescription(resources.getString(R.string.accessibility_desc_quick_settings));

    }

    public void setQuickSettings(QuickSettingsController qs) {
@@ -130,4 +131,5 @@ public class SettingsPanelView extends PanelView {
        mHandleBar.draw(canvas);
        canvas.translate(0, -off);
    }

}