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

Commit b12ba933 authored by David Christie's avatar David Christie
Browse files

Make location QuickSettings multi-user compatible (b/10563313)

Change-Id: I8ae5238e66fa2d6890ffe5697d3e6d5f50413c3e
parent 4c92f7ce
Loading
Loading
Loading
Loading
+12 −1
Original line number Original line Diff line number Diff line
@@ -357,7 +357,18 @@ public class UserManager {
     * @param restrictionKey the string key representing the restriction
     * @param restrictionKey the string key representing the restriction
     */
     */
    public boolean hasUserRestriction(String restrictionKey) {
    public boolean hasUserRestriction(String restrictionKey) {
        return getUserRestrictions().getBoolean(restrictionKey, false);
        return hasUserRestriction(restrictionKey, Process.myUserHandle());
    }

    /**
     * @hide
     * Returns whether the given user has been disallowed from performing certain actions
     * or setting certain settings.
     * @param restrictionKey the string key representing the restriction
     * @param userHandle the UserHandle of the user for whom to retrieve the restrictions.
     */
    public boolean hasUserRestriction(String restrictionKey, UserHandle userHandle) {
        return getUserRestrictions(userHandle).getBoolean(restrictionKey, false);
    }
    }


    /**
    /**
+4 −4
Original line number Original line Diff line number Diff line
@@ -640,10 +640,10 @@ class QuickSettings {
                @Override
                @Override
                public boolean onLongClick(View v) {
                public boolean onLongClick(View v) {
                    boolean newLocationEnabledState = !mLocationController.isLocationEnabled();
                    boolean newLocationEnabledState = !mLocationController.isLocationEnabled();
                    mLocationController.setLocationEnabled(newLocationEnabledState);
                    if (mLocationController.setLocationEnabled(newLocationEnabledState)
                    if (newLocationEnabledState) {
                            && newLocationEnabledState) {
                        // Close the notifications tray so that the network location provider
                        // If we've successfully switched from location off to on, close the
                        // consent dialog can be shown.
                        // notifications tray to show the network location provider consent dialog.
                        Intent closeDialog = new Intent(Intent.ACTION_CLOSE_SYSTEM_DIALOGS);
                        Intent closeDialog = new Intent(Intent.ACTION_CLOSE_SYSTEM_DIALOGS);
                        mContext.sendBroadcast(closeDialog);
                        mContext.sendBroadcast(closeDialog);
                    }
                    }
+46 −19
Original line number Original line Diff line number Diff line
@@ -16,6 +16,7 @@


package com.android.systemui.statusbar.policy;
package com.android.systemui.statusbar.policy;


import android.app.ActivityManager;
import android.app.AppOpsManager;
import android.app.AppOpsManager;
import android.app.StatusBarManager;
import android.app.StatusBarManager;
import android.content.BroadcastReceiver;
import android.content.BroadcastReceiver;
@@ -26,6 +27,7 @@ import android.content.IntentFilter;
import android.database.ContentObserver;
import android.database.ContentObserver;
import android.location.LocationManager;
import android.location.LocationManager;
import android.os.Handler;
import android.os.Handler;
import android.os.UserHandle;
import android.os.UserManager;
import android.os.UserManager;
import android.provider.Settings;
import android.provider.Settings;


@@ -81,18 +83,18 @@ public class LocationController extends BroadcastReceiver {
        mStatusBarManager
        mStatusBarManager
                = (StatusBarManager) context.getSystemService(Context.STATUS_BAR_SERVICE);
                = (StatusBarManager) context.getSystemService(Context.STATUS_BAR_SERVICE);


        // Register to listen for changes to the location settings
        // Register to listen for changes in location settings.
        context.getContentResolver().registerContentObserver(
        IntentFilter intentFilter = new IntentFilter();
                Settings.Secure.getUriFor(Settings.Secure.LOCATION_PROVIDERS_ALLOWED), true,
        intentFilter.addAction(LocationManager.MODE_CHANGED_ACTION);
                new ContentObserver(new Handler()) {
        context.registerReceiverAsUser(new BroadcastReceiver() {
            @Override
            @Override
                    public void onChange(boolean selfChange) {
            public void onReceive(Context context, Intent intent) {
                        boolean isEnabled = isLocationEnabled();
                String action = intent.getAction();
                        for (LocationSettingsChangeCallback cb : mSettingsChangeCallbacks) {
                if (LocationManager.MODE_CHANGED_ACTION.equals(action)) {
                            cb.onLocationSettingsChanged(isEnabled);
                    locationSettingsChanged();
                }
                }
            }
            }
                });
        }, UserHandle.ALL, intentFilter, null, new Handler());


        // Examine the current location state and initialize the status view.
        // Examine the current location state and initialize the status view.
        updateActiveLocationRequests();
        updateActiveLocationRequests();
@@ -114,30 +116,48 @@ public class LocationController extends BroadcastReceiver {
     *
     *
     * <p>If enabling, a user consent dialog will pop up prompting the user to accept.
     * <p>If enabling, a user consent dialog will pop up prompting the user to accept.
     * If the user doesn't accept, network location won't be enabled.
     * If the user doesn't accept, network location won't be enabled.
     *
     * @return true if attempt to change setting was successful.
     */
     */
    public void setLocationEnabled(boolean enabled) {
    public boolean setLocationEnabled(boolean enabled) {
        final UserManager um = (UserManager) mContext.getSystemService(Context.USER_SERVICE);
        int currentUserId = ActivityManager.getCurrentUser();
        if (um.hasUserRestriction(UserManager.DISALLOW_SHARE_LOCATION)) {
        if (isUserLocationRestricted(currentUserId)) {
            return;
            return false;
        }
        }
        final ContentResolver cr = mContext.getContentResolver();
        final ContentResolver cr = mContext.getContentResolver();
        // When enabling location, a user consent dialog will pop up, and the
        // When enabling location, a user consent dialog will pop up, and the
        // setting won't be fully enabled until the user accepts the agreement.
        // setting won't be fully enabled until the user accepts the agreement.
        int mode = enabled
        int mode = enabled
                ? Settings.Secure.LOCATION_MODE_HIGH_ACCURACY : Settings.Secure.LOCATION_MODE_OFF;
                ? Settings.Secure.LOCATION_MODE_HIGH_ACCURACY : Settings.Secure.LOCATION_MODE_OFF;
        Settings.Secure.putInt(cr, Settings.Secure.LOCATION_MODE, mode);
        return Settings.Secure
                .putIntForUser(cr, Settings.Secure.LOCATION_MODE, mode, currentUserId);
    }
    }


    /**
    /**
     * Returns true if location isn't disabled in settings.
     * Returns true if location isn't disabled in settings.
     */
     */
    public boolean isLocationEnabled() {
    public boolean isLocationEnabled() {
        int currentUserId = ActivityManager.getCurrentUser();
        if (isUserLocationRestricted(currentUserId)) {
            return false;
        }

        ContentResolver resolver = mContext.getContentResolver();
        ContentResolver resolver = mContext.getContentResolver();
        int mode = Settings.Secure.getInt(resolver, Settings.Secure.LOCATION_MODE,
        int mode = Settings.Secure.getIntForUser(resolver, Settings.Secure.LOCATION_MODE,
                Settings.Secure.LOCATION_MODE_OFF);
                Settings.Secure.LOCATION_MODE_OFF, currentUserId);
        return mode != Settings.Secure.LOCATION_MODE_OFF;
        return mode != Settings.Secure.LOCATION_MODE_OFF;
    }
    }


    /**
     * Returns true if the current user is restricted from using location.
     */
    private boolean isUserLocationRestricted(int userId) {
        final UserManager um = (UserManager) mContext.getSystemService(Context.USER_SERVICE);
        return um.hasUserRestriction(
                UserManager.DISALLOW_SHARE_LOCATION,
                new UserHandle(userId));
    }

    /**
    /**
     * Returns true if there currently exist active high power location requests.
     * Returns true if there currently exist active high power location requests.
     */
     */
@@ -188,6 +208,13 @@ public class LocationController extends BroadcastReceiver {
        }
        }
    }
    }


    private void locationSettingsChanged() {
        boolean isEnabled = isLocationEnabled();
        for (LocationSettingsChangeCallback cb : mSettingsChangeCallbacks) {
            cb.onLocationSettingsChanged(isEnabled);
        }
    }

    @Override
    @Override
    public void onReceive(Context context, Intent intent) {
    public void onReceive(Context context, Intent intent) {
        final String action = intent.getAction();
        final String action = intent.getAction();