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

Commit e5bba189 authored by crizmess's avatar crizmess Committed by DvTonder
Browse files

Bringing basic Pie controls to CyanogenMod. (2/2)

This is the settings part of the pie commit, for the real implementation
look in frameworks/base.

Patch Set 3:
* CyanogenMod Code Style

Patch Set 4:
* Strings cleanup
* Better integration into CyanogenMod system settings UX
* Some related cleanup in SysteSettings.java

Patch Set 5 and 6:
* Rename feature to Quick controls to match AOSP terminology

Patch Set 7:
* Remove WIP

Patch Set 8:
* Revert name to Pie controls

Patch Set 11:
* Fix broken revert
* Fix spelling of search

Change-Id: I47599316273d8e46017f49ba62a02cc55a785678
parent 5814f085
Loading
Loading
Loading
Loading
+13 −0
Original line number Diff line number Diff line
@@ -5202,5 +5202,18 @@
    <string name="navring_action_google_now">Google Now</string>
    <string name="navring_choose_action_title">Choose action</string>

    <!-- Quick/Pie Control #CM -->
    <string name="pie_control_title">Pie controls</string>
    <string name="pie_control_enabled">Enabled when Expanded desktop is active</string>
    <string name="pie_control_disabled">Disabled</string>
    <string name="pie_control_search_title">Show search button</string>
    <string name="pie_control_size">Navigation key size</string>
    <string name="pie_control_trigger_positions">Trigger positions</string>
    <string name="pie_control_trigger_left">Left screen border</string>
    <string name="pie_control_trigger_bottom">Bottom screen border</string>
    <string name="pie_control_trigger_right">Right screen border</string>
    <string name="pie_control_trigger_top">Top screen border</string>
    <string name="pie_control_trigger_top_summary">Only navigation will be displayed at top</string>

    <!-- **** CYANOGENMOD ADDITIONS END **** -->
</resources>
+60 −0
Original line number Diff line number Diff line
<?xml version="1.0" encoding="utf-8"?>
<!-- Copyright (C) 2013 The CyanogenMod 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.
-->

<PreferenceScreen xmlns:android="http://schemas.android.com/apk/res/android"
    android:title="@string/pie_control_title"
    xmlns:settings="http://schemas.android.com/apk/res/com.android.settings">

    <CheckBoxPreference
        android:key="pie_control_checkbox"
        android:title="@string/pie_control_title"
        android:defaultValue="false" />

    <CheckBoxPreference
        android:key="pie_control_search"
        android:title="@string/pie_control_search_title"
        android:defaultValue="false" />

    <com.android.settings.cyanogenmod.PieSizePreference
        android:key="pie_control_size"
        android:title="@string/pie_control_size"
        android:dialogTitle="@string/pie_control_size" />

    <PreferenceCategory
        android:title="@string/pie_control_trigger_positions">

        <CheckBoxPreference
            android:key="pie_control_trigger_left"
            android:title="@string/pie_control_trigger_left"
            android:defaultValue="false" />

        <CheckBoxPreference
            android:key="pie_control_trigger_bottom"
            android:title="@string/pie_control_trigger_bottom"
            android:defaultValue="false" />

        <CheckBoxPreference
            android:key="pie_control_trigger_right"
            android:title="@string/pie_control_trigger_right"
            android:defaultValue="false" />

        <CheckBoxPreference
            android:key="pie_control_trigger_top"
            android:title="@string/pie_control_trigger_top"
            android:summary="@string/pie_control_trigger_top_summary"
            android:defaultValue="false" />
   </PreferenceCategory>
</PreferenceScreen>
+5 −0
Original line number Diff line number Diff line
@@ -64,6 +64,11 @@
        android:fragment="com.android.settings.cyanogenmod.HardwareKeys"
        android:title="@string/hardware_keys_title" />

    <PreferenceScreen
        android:key="pie_control"
        android:fragment="com.android.settings.cyanogenmod.PieControl"
        android:title="@string/pie_control_title" />

    <PreferenceCategory
        android:key="navigation_bar_category"
        android:title="@string/navigation_bar_category" >
+135 −0
Original line number Diff line number Diff line
package com.android.settings.cyanogenmod;

import android.content.ContentResolver;
import android.database.ContentObserver;
import android.os.Bundle;
import android.os.Handler;
import android.preference.CheckBoxPreference;
import android.preference.Preference;
import android.preference.PreferenceScreen;
import android.preference.SeekBarDialogPreference;
import android.provider.Settings;

import com.android.settings.R;
import com.android.settings.SettingsPreferenceFragment;

public class PieControl extends SettingsPreferenceFragment
                        implements Preference.OnPreferenceChangeListener {

    private static final int DEFAULT_POSITION = 1 << 1; // this equals Position.BOTTOM.FLAG

    private static final String PIE_CONTROL = "pie_control_checkbox";
    private static final String SEARCH_BUTTON = "pie_control_search";
    private static final String PIE_SIZE = "pie_control_size";
    private static final String[] TRIGGER = {
        "pie_control_trigger_left",
        "pie_control_trigger_bottom",
        "pie_control_trigger_right",
        "pie_control_trigger_top"
    };

    private CheckBoxPreference mPieControl;
    private CheckBoxPreference mSearchButton;
    private SeekBarDialogPreference mPieSize;
    private CheckBoxPreference[] mTrigger = new CheckBoxPreference[4];

    private ContentObserver mPieTriggerObserver = new ContentObserver(new Handler()) {
        @Override
        public void onChange(boolean selfChange) {
            updatePieTriggers();
        }
    };

    @Override
    public void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);

        addPreferencesFromResource(R.xml.pie_control);

        PreferenceScreen prefSet = getPreferenceScreen();
        mPieControl = (CheckBoxPreference) prefSet.findPreference(PIE_CONTROL);
        mPieControl.setOnPreferenceChangeListener(this);
        mSearchButton = (CheckBoxPreference) prefSet.findPreference(SEARCH_BUTTON);
        mSearchButton.setOnPreferenceChangeListener(this);
        mPieSize = (SeekBarDialogPreference) prefSet.findPreference(PIE_SIZE);

        for (int i = 0; i < TRIGGER.length; i++) {
            mTrigger[i] = (CheckBoxPreference) prefSet.findPreference(TRIGGER[i]);
            mTrigger[i].setOnPreferenceChangeListener(this);
        }
    }

    @Override
    public boolean onPreferenceChange(Preference preference, Object newValue) {
        if (preference == mPieControl) {
            boolean newState = (Boolean) newValue;

            Settings.System.putInt(getContentResolver(),
                    Settings.System.PIE_CONTROLS, newState ? 1 : 0);
            propagatePieControl(newState);

        } else if (preference == mSearchButton) {
            Settings.System.putInt(getContentResolver(),
                    Settings.System.PIE_SEARCH, (Boolean) newValue ? 1 : 0);

        } else {
            int triggerSlots = 0;
            for (int i = 0; i < mTrigger.length; i++) {
                boolean checked = preference == mTrigger[i]
                        ? (Boolean) newValue : mTrigger[i].isChecked();
                if (checked) {
                    triggerSlots |= 1 << i;
                }
            }
            Settings.System.putInt(getContentResolver(),
                    Settings.System.PIE_GRAVITY, triggerSlots);
        }
        return true;
    }

    @Override
    public void onResume() {
        super.onResume();

        mPieControl.setChecked(Settings.System.getInt(getContentResolver(),
                Settings.System.PIE_CONTROLS, 0) == 1);
        propagatePieControl(mPieControl.isChecked());

        mSearchButton.setChecked(Settings.System.getInt(getContentResolver(),
                Settings.System.PIE_SEARCH, 0) == 1);

        getContentResolver().registerContentObserver(
                Settings.System.getUriFor(Settings.System.PIE_GRAVITY), true,
                mPieTriggerObserver);

        updatePieTriggers();
    }

    @Override
    public void onPause() {
        super.onPause();
        getContentResolver().unregisterContentObserver(mPieTriggerObserver);
    }

    private void propagatePieControl(boolean value) {
        mSearchButton.setEnabled(value);
        for (int i = 0; i < mTrigger.length; i++) {
            mTrigger[i].setEnabled(value);
        }
        mPieSize.setEnabled(value);
    }

    private void updatePieTriggers() {
        int triggerSlots = Settings.System.getInt(getContentResolver(),
                Settings.System.PIE_GRAVITY, DEFAULT_POSITION);

        for (int i = 0; i < mTrigger.length; i++) {
            if ((triggerSlots & (0x01 << i)) != 0) {
                mTrigger[i].setChecked(true);
            } else {
                mTrigger[i].setChecked(false);
            }
        }
    }

}
+148 −0
Original line number Diff line number Diff line
package com.android.settings.cyanogenmod;

import android.content.Context;
import android.os.Bundle;
import android.os.Parcel;
import android.os.Parcelable;
import android.preference.SeekBarDialogPreference;
import android.provider.Settings;
import android.util.AttributeSet;
import android.view.View;
import android.widget.SeekBar;

public class PieSizePreference extends SeekBarDialogPreference
                               implements SeekBar.OnSeekBarChangeListener {

    private SeekBar mSeekBar;

    private float mOldSize;

    private boolean mRestoredOldState = true;

    private static final int SEEK_BAR_MIN = 500;
    private static final int SEEK_BAR_MAX = 1500;

    public PieSizePreference(Context context, AttributeSet attrs) {
        super(context, attrs);
    }

    @Override
    protected void showDialog(Bundle state) {
        super.showDialog(state);
        mRestoredOldState = false;
    }

    @Override
    protected void onBindDialogView(View view) {
        super.onBindDialogView(view);

        mSeekBar = getSeekBar(view);
        mSeekBar.setMax(SEEK_BAR_MAX);
        mOldSize = Settings.System.getFloat(getContext().getContentResolver(),
                Settings.System.PIE_SIZE, 1.0f);

        mSeekBar.setProgress((int) (mOldSize * 1000 - SEEK_BAR_MIN));
        mSeekBar.setEnabled(true);
        mSeekBar.setOnSeekBarChangeListener(this);
    }

    @Override
    public void onProgressChanged(SeekBar seekBar, int progress, boolean fromTouch) {
        Settings.System.putFloat(getContext().getContentResolver(),
                Settings.System.PIE_SIZE, (SEEK_BAR_MIN + progress) / 1000f);
    }

    @Override
    protected void onDialogClosed(boolean positiveResult) {
        super.onDialogClosed(positiveResult);

        if (positiveResult) {
            onProgressChanged(mSeekBar, mSeekBar.getProgress(), true);
        } else {
            restoreOldState();
        }
    }

    private void restoreOldState() {
        if (mRestoredOldState) {
            return;
        }

        Settings.System.putFloat(getContext().getContentResolver(),
                Settings.System.PIE_SIZE, mOldSize);

        mRestoredOldState = true;
    }

    @Override
    protected Parcelable onSaveInstanceState() {
        final Parcelable superState = super.onSaveInstanceState();
        if (getDialog() == null || !getDialog().isShowing()) {
            return superState;
        }

        // Save the dialog state
        final SavedState myState = new SavedState(superState);
        myState.oldSize = mOldSize;

        // Restore the old state when the activity or dialog is being paused
        restoreOldState();
        return myState;
    }

    @Override
    protected void onRestoreInstanceState(Parcelable state) {
        if (state == null || !state.getClass().equals(SavedState.class)) {
            // Didn't save state for us in onSaveInstanceState
            super.onRestoreInstanceState(state);
            return;
        }

        SavedState myState = (SavedState) state;
        super.onRestoreInstanceState(myState.getSuperState());
        mOldSize = myState.oldSize;
    }

    private static class SavedState extends BaseSavedState {

        float oldSize;

        public SavedState(Parcel source) {
            super(source);
            oldSize = source.readFloat();
        }

        @Override
        public void writeToParcel(Parcel dest, int flags) {
            super.writeToParcel(dest, flags);
            dest.writeFloat(oldSize);
        }

        public SavedState(Parcelable superState) {
            super(superState);
        }

        public static final Parcelable.Creator<SavedState> CREATOR =
                new Parcelable.Creator<SavedState>() {

            public SavedState createFromParcel(Parcel in) {
                return new SavedState(in);
            }

            public SavedState[] newArray(int size) {
                return new SavedState[size];
            }
        };
    }

    @Override
    public void onStartTrackingTouch(SeekBar seekBar) {
        // nothing to do
    }

    @Override
    public void onStopTrackingTouch(SeekBar seekBar) {
        // nothing to do
    }

}
Loading