Home | History | Annotate | Download | only in ui
      1 /*
      2  * Copyright (C) 2015 The Android Open Source Project
      3  *
      4  * Licensed under the Apache License, Version 2.0 (the "License");
      5  * you may not use this file except in compliance with the License.
      6  * You may obtain a copy of the License at
      7  *
      8  *      http://www.apache.org/licenses/LICENSE-2.0
      9  *
     10  * Unless required by applicable law or agreed to in writing, software
     11  * distributed under the License is distributed on an "AS IS" BASIS,
     12  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
     13  * See the License for the specific language governing permissions and
     14  * limitations under the License.
     15  */
     16 package com.android.packageinstaller.permission.ui;
     17 
     18 import android.annotation.Nullable;
     19 import android.app.ActionBar;
     20 import android.app.FragmentTransaction;
     21 import android.content.ActivityNotFoundException;
     22 import android.content.Context;
     23 import android.content.Intent;
     24 import android.graphics.drawable.Drawable;
     25 import android.os.Bundle;
     26 import android.support.v7.preference.Preference;
     27 import android.support.v7.preference.Preference.OnPreferenceClickListener;
     28 import android.support.v7.preference.PreferenceScreen;
     29 import android.util.ArraySet;
     30 import android.util.Log;
     31 import android.view.MenuItem;
     32 import android.view.View;
     33 import android.widget.ImageView;
     34 import android.widget.TextView;
     35 
     36 import com.android.packageinstaller.R;
     37 import com.android.packageinstaller.permission.model.PermissionApps;
     38 import com.android.packageinstaller.permission.model.PermissionApps.PmCache;
     39 import com.android.packageinstaller.permission.model.PermissionGroup;
     40 import com.android.packageinstaller.permission.model.PermissionGroups;
     41 import com.android.packageinstaller.permission.utils.Utils;
     42 
     43 import java.util.List;
     44 
     45 public final class ManagePermissionsFragment extends PermissionsFrameFragment
     46         implements PermissionGroups.PermissionsGroupsChangeCallback, OnPreferenceClickListener {
     47     private static final String LOG_TAG = "ManagePermissionsFragment";
     48 
     49     private static final String OS_PKG = "android";
     50 
     51     private static final String EXTRA_PREFS_KEY = "extra_prefs_key";
     52 
     53     private ArraySet<String> mLauncherPkgs;
     54 
     55     private PermissionGroups mPermissions;
     56 
     57     private PreferenceScreen mExtraScreen;
     58 
     59     public static ManagePermissionsFragment newInstance() {
     60         return new ManagePermissionsFragment();
     61     }
     62 
     63     @Override
     64     public void onCreate(Bundle icicle) {
     65         super.onCreate(icicle);
     66         setLoading(true /* loading */, false /* animate */);
     67         setHasOptionsMenu(true);
     68         final ActionBar ab = getActivity().getActionBar();
     69         if (ab != null) {
     70             ab.setDisplayHomeAsUpEnabled(true);
     71         }
     72         mLauncherPkgs = Utils.getLauncherPackages(getContext());
     73         mPermissions = new PermissionGroups(getActivity(), getLoaderManager(), this);
     74     }
     75 
     76     @Override
     77     public void onResume() {
     78         super.onResume();
     79         mPermissions.refresh();
     80         updatePermissionsUi();
     81     }
     82 
     83     @Override
     84     public boolean onOptionsItemSelected(MenuItem item) {
     85         if (item.getItemId() == android.R.id.home) {
     86             getActivity().finish();
     87             return true;
     88         }
     89         return super.onOptionsItemSelected(item);
     90     }
     91 
     92     @Override
     93     public boolean onPreferenceClick(Preference preference) {
     94         String key = preference.getKey();
     95 
     96         PermissionGroup group = mPermissions.getGroup(key);
     97         if (group == null) {
     98             return false;
     99         }
    100 
    101         Intent intent = new Intent(Intent.ACTION_MANAGE_PERMISSION_APPS)
    102                 .putExtra(Intent.EXTRA_PERMISSION_NAME, key);
    103         try {
    104             getActivity().startActivity(intent);
    105         } catch (ActivityNotFoundException e) {
    106             Log.w(LOG_TAG, "No app to handle " + intent);
    107         }
    108 
    109         return true;
    110     }
    111 
    112     @Override
    113     public void onPermissionGroupsChanged() {
    114         updatePermissionsUi();
    115     }
    116 
    117     @Override
    118     public void onViewCreated(View view, @Nullable Bundle savedInstanceState) {
    119         super.onViewCreated(view, savedInstanceState);
    120         bindPermissionUi(getActivity(), getView());
    121     }
    122 
    123     private static void bindPermissionUi(@Nullable Context context, @Nullable View rootView) {
    124         if (context == null || rootView == null) {
    125             return;
    126         }
    127 
    128         ImageView iconView = (ImageView) rootView.findViewById(R.id.lb_icon);
    129         if (iconView != null) {
    130             // Set the icon as the background instead of the image because ImageView
    131             // doesn't properly scale vector drawables beyond their intrinsic size
    132             Drawable icon = context.getDrawable(R.drawable.ic_lock);
    133             icon.setTint(context.getColor(R.color.off_white));
    134             iconView.setBackground(icon);
    135         }
    136         TextView titleView = (TextView) rootView.findViewById(R.id.lb_title);
    137         if (titleView != null) {
    138             titleView.setText(R.string.app_permissions);
    139         }
    140         TextView breadcrumbView = (TextView) rootView.findViewById(R.id.lb_breadcrumb);
    141         if (breadcrumbView != null) {
    142             breadcrumbView.setText(R.string.app_permissions_breadcrumb);
    143         }
    144     }
    145 
    146     private void updatePermissionsUi() {
    147         Context context = getPreferenceManager().getContext();
    148         if (context == null) {
    149             return;
    150         }
    151 
    152         List<PermissionGroup> groups = mPermissions.getGroups();
    153         PreferenceScreen screen = getPreferenceScreen();
    154 
    155         // Use this to speed up getting the info for all of the PermissionApps below.
    156         // Create a new one for each refresh to make sure it has fresh data.
    157         PmCache cache = new PmCache(getContext().getPackageManager());
    158         for (PermissionGroup group : groups) {
    159             boolean isSystemPermission = group.getDeclaringPackage().equals(OS_PKG);
    160 
    161             Preference preference = findPreference(group.getName());
    162             if (preference == null && mExtraScreen != null) {
    163                 preference = mExtraScreen.findPreference(group.getName());
    164             }
    165             if (preference == null) {
    166                 preference = new Preference(context);
    167                 preference.setOnPreferenceClickListener(this);
    168                 preference.setKey(group.getName());
    169                 preference.setIcon(Utils.applyTint(context, group.getIcon(),
    170                         android.R.attr.colorControlNormal));
    171                 preference.setTitle(group.getLabel());
    172                 // Set blank summary so that no resizing/jumping happens when the summary is loaded.
    173                 preference.setSummary(" ");
    174                 preference.setPersistent(false);
    175                 if (isSystemPermission) {
    176                     screen.addPreference(preference);
    177                 } else {
    178                     if (mExtraScreen == null) {
    179                         mExtraScreen = getPreferenceManager().createPreferenceScreen(context);
    180                     }
    181                     mExtraScreen.addPreference(preference);
    182                 }
    183             }
    184             final Preference finalPref = preference;
    185 
    186             new PermissionApps(getContext(), group.getName(), new PermissionApps.Callback() {
    187                 @Override
    188                 public void onPermissionsLoaded(PermissionApps permissionApps) {
    189                     if (getActivity() == null) {
    190                         return;
    191                     }
    192                     int granted = permissionApps.getGrantedCount(mLauncherPkgs);
    193                     int total = permissionApps.getTotalCount(mLauncherPkgs);
    194                     finalPref.setSummary(getString(R.string.app_permissions_group_summary,
    195                             granted, total));
    196                 }
    197             }, cache).refresh(false);
    198         }
    199 
    200         if (mExtraScreen != null && mExtraScreen.getPreferenceCount() > 0
    201                 && screen.findPreference(EXTRA_PREFS_KEY) == null) {
    202             Preference extraScreenPreference = new Preference(context);
    203             extraScreenPreference.setKey(EXTRA_PREFS_KEY);
    204             extraScreenPreference.setIcon(Utils.applyTint(context,
    205                     com.android.internal.R.drawable.ic_more_items,
    206                     android.R.attr.colorControlNormal));
    207             extraScreenPreference.setTitle(R.string.additional_permissions);
    208             extraScreenPreference.setOnPreferenceClickListener(new OnPreferenceClickListener() {
    209                 @Override
    210                 public boolean onPreferenceClick(Preference preference) {
    211                     AdditionalPermissionsFragment frag = new AdditionalPermissionsFragment();
    212                     frag.setTargetFragment(ManagePermissionsFragment.this, 0);
    213                     FragmentTransaction ft = getFragmentManager().beginTransaction();
    214                     ft.replace(android.R.id.content, frag);
    215                     ft.addToBackStack(null);
    216                     ft.commit();
    217                     return true;
    218                 }
    219             });
    220             int count = mExtraScreen.getPreferenceCount();
    221             extraScreenPreference.setSummary(getResources().getQuantityString(
    222                     R.plurals.additional_permissions_more, count, count));
    223             screen.addPreference(extraScreenPreference);
    224         }
    225         if (screen.getPreferenceCount() != 0) {
    226             setLoading(false /* loading */, true /* animate */);
    227         }
    228     }
    229 
    230     public static class AdditionalPermissionsFragment extends PermissionsFrameFragment {
    231         @Override
    232         public void onCreate(Bundle icicle) {
    233             setLoading(true /* loading */, false /* animate */);
    234             super.onCreate(icicle);
    235             getActivity().setTitle(R.string.additional_permissions);
    236             setHasOptionsMenu(true);
    237         }
    238 
    239         @Override
    240         public void onDestroy() {
    241             getActivity().setTitle(R.string.app_permissions);
    242             super.onDestroy();
    243         }
    244 
    245         @Override
    246         public boolean onOptionsItemSelected(MenuItem item) {
    247             switch (item.getItemId()) {
    248                 case android.R.id.home:
    249                     getFragmentManager().popBackStack();
    250                     return true;
    251             }
    252             return super.onOptionsItemSelected(item);
    253         }
    254 
    255         @Override
    256         public void onViewCreated(View view, @Nullable Bundle savedInstanceState) {
    257             super.onViewCreated(view, savedInstanceState);
    258             bindPermissionUi(getActivity(), getView());
    259         }
    260 
    261         @Override
    262         public void onCreatePreferences(Bundle savedInstanceState, String rootKey) {
    263             setPreferenceScreen(((ManagePermissionsFragment) getTargetFragment()).mExtraScreen);
    264             setLoading(false /* loading */, true /* animate */);
    265         }
    266     }
    267 }
    268