1 /* 2 * Copyright (C) 2016 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 17 package com.android.bips.ui; 18 19 import android.app.Activity; 20 import android.app.AlertDialog; 21 import android.content.ComponentName; 22 import android.content.Context; 23 import android.content.Intent; 24 import android.content.ServiceConnection; 25 import android.os.Bundle; 26 import android.os.IBinder; 27 import android.preference.Preference; 28 import android.preference.PreferenceCategory; 29 import android.preference.PreferenceFragment; 30 import android.preference.SwitchPreference; 31 import android.util.Log; 32 33 import com.android.bips.BuiltInPrintService; 34 import com.android.bips.P2pPermissionManager; 35 import com.android.bips.R; 36 import com.android.bips.discovery.DiscoveredPrinter; 37 import com.android.bips.p2p.P2pUtils; 38 39 /** 40 * Presents a list of printers and the ability to add a new one 41 */ 42 public class AddPrintersFragment extends PreferenceFragment implements ServiceConnection { 43 private static final String TAG = AddPrintersFragment.class.getSimpleName(); 44 private static final boolean DEBUG = false; 45 46 private static final String KEY_ADD_BY_IP = "add_by_ip"; 47 private static final String KEY_FIND_WIFI_DIRECT = "find_wifi_direct"; 48 private static final String KEY_WIFI_DIRECT_PRINTING = "wifi_direct_printing"; 49 private static final String KEY_SAVED_PRINTERS = "saved_printers"; 50 public static final String EXTRA_FIX_P2P_PERMISSION = "fix_p2p_permission"; 51 52 private static final int ORDER_SAVED = 2; 53 54 private PreferenceCategory mSavedPrintersCategory; 55 private Preference mAddPrinterByIpPreference; 56 private Preference mFindP2pPrintersPreference; 57 private SwitchPreference mP2pEnablePreference; 58 private BuiltInPrintService mPrintService; 59 private P2pPermissionManager mP2pPermissionManager; 60 61 @Override onCreate(Bundle in)62 public void onCreate(Bundle in) { 63 if (DEBUG) Log.d(TAG, "onCreate"); 64 super.onCreate(in); 65 addPreferencesFromResource(R.xml.add_printers_prefs); 66 mAddPrinterByIpPreference = getPreferenceScreen().findPreference(KEY_ADD_BY_IP); 67 68 mFindP2pPrintersPreference = getPreferenceScreen().findPreference( 69 KEY_FIND_WIFI_DIRECT); 70 mFindP2pPrintersPreference.setOnPreferenceClickListener(preference -> { 71 getFragmentManager().beginTransaction() 72 .replace(android.R.id.content, new FindP2pPrintersFragment()) 73 .addToBackStack(null) 74 .commit(); 75 return true; 76 }); 77 mP2pEnablePreference = (SwitchPreference) getPreferenceScreen() 78 .findPreference(KEY_WIFI_DIRECT_PRINTING); 79 mSavedPrintersCategory = (PreferenceCategory) getPreferenceScreen() 80 .findPreference(KEY_SAVED_PRINTERS); 81 } 82 83 @Override onStart()84 public void onStart() { 85 super.onStart(); 86 if (DEBUG) Log.d(TAG, "onStart"); 87 88 getActivity().setTitle(R.string.title_activity_add_printer); 89 getContext().bindService(new Intent(getContext(), BuiltInPrintService.class), this, 90 Context.BIND_AUTO_CREATE); 91 92 mP2pPermissionManager = new P2pPermissionManager(getActivity()); 93 updateP2pPreferences(); 94 95 if (getActivity().getIntent().getBooleanExtra(EXTRA_FIX_P2P_PERMISSION, false)) { 96 // Additional explanation is redundant, since the user saw it in notification. 97 mP2pPermissionManager.request(false, approve -> { 98 updateP2pPreferences(); 99 if (!approve) { 100 // Try again next time 101 mP2pPermissionManager.setState(P2pPermissionManager.State.TEMPORARILY_DISABLED); 102 } 103 }); 104 } 105 106 mP2pEnablePreference.setOnPreferenceClickListener(preference -> { 107 if (mP2pEnablePreference.isChecked()) { 108 mP2pEnablePreference.setChecked(false); 109 if (mP2pPermissionManager.getState() == P2pPermissionManager.State.DISABLED) { 110 // We're no longer disabled, just denied 111 mP2pPermissionManager.setState(P2pPermissionManager.State.DENIED); 112 } 113 mP2pPermissionManager.reset(); 114 mP2pPermissionManager.request(true, approve -> updateP2pPreferences()); 115 } else { 116 // User disabled P2P 117 mP2pPermissionManager.setState(P2pPermissionManager.State.DISABLED); 118 updateP2pPreferences(); 119 } 120 return true; 121 }); 122 } 123 124 @Override onStop()125 public void onStop() { 126 super.onStop(); 127 if (DEBUG) Log.d(TAG, "onStop"); 128 129 getContext().unbindService(this); 130 } 131 132 @Override onServiceConnected(ComponentName componentName, IBinder iBinder)133 public void onServiceConnected(ComponentName componentName, IBinder iBinder) { 134 if (DEBUG) Log.d(TAG, "onServiceConnected"); 135 mPrintService = BuiltInPrintService.getInstance(); 136 137 mAddPrinterByIpPreference.setOnPreferenceClickListener(preference -> { 138 AlertDialog dialog = new AddManualPrinterDialog(getActivity(), 139 mPrintService.getManualDiscovery()); 140 dialog.setOnDismissListener(d -> updateSavedPrinters()); 141 dialog.show(); 142 return true; 143 }); 144 145 updateSavedPrinters(); 146 } 147 updateP2pPreferences()148 private void updateP2pPreferences() { 149 // Only allow the user to find new P2P printers when enabled 150 if (mP2pPermissionManager.isP2pEnabled()) { 151 mP2pEnablePreference.setChecked(true); 152 getPreferenceScreen().addPreference(mFindP2pPrintersPreference); 153 Activity activity = getActivity(); 154 if (activity != null && activity.getIntent().getBooleanExtra(EXTRA_FIX_P2P_PERMISSION, 155 false)) { 156 // If we were only here to enable P2P permissions, go back to the print now. 157 activity.finish(); 158 } 159 } else { 160 mP2pEnablePreference.setChecked(false); 161 getPreferenceScreen().removePreference(mFindP2pPrintersPreference); 162 } 163 164 updateSavedPrinters(); 165 } 166 167 @Override onServiceDisconnected(ComponentName componentName)168 public void onServiceDisconnected(ComponentName componentName) { 169 mPrintService = null; 170 } 171 updateSavedPrinters()172 private void updateSavedPrinters() { 173 int savedCount = mPrintService == null ? 0 : mPrintService.getDiscovery() 174 .getSavedPrinters().size(); 175 176 if (savedCount == 0) { 177 if (getPreferenceScreen().findPreference(mSavedPrintersCategory.getKey()) != null) { 178 getPreferenceScreen().removePreference(mSavedPrintersCategory); 179 } 180 } else { 181 if (getPreferenceScreen().findPreference(mSavedPrintersCategory.getKey()) == null) { 182 getPreferenceScreen().addPreference(mSavedPrintersCategory); 183 } 184 185 mSavedPrintersCategory.removeAll(); 186 187 // With the service enumerate all saved printers 188 boolean p2pEnabled = mP2pPermissionManager.isP2pEnabled(); 189 for (DiscoveredPrinter printer : mPrintService.getDiscovery().getSavedPrinters()) { 190 // Don't show P2P printers while P2P is disabled. 191 if (P2pUtils.isP2p(printer) && !p2pEnabled) { 192 continue; 193 } 194 if (DEBUG) Log.d(TAG, "Adding saved printer " + printer); 195 PrinterPreference pref = new PrinterPreference(getContext(), mPrintService, 196 printer, false); 197 pref.setOrder(ORDER_SAVED); 198 pref.setOnPreferenceClickListener(preference -> { 199 showRemovalDialog(printer); 200 return true; 201 }); 202 mSavedPrintersCategory.addPreference(pref); 203 } 204 } 205 } 206 showRemovalDialog(DiscoveredPrinter printer)207 private void showRemovalDialog(DiscoveredPrinter printer) { 208 String message; 209 if (P2pUtils.isP2p(printer)) { 210 message = mPrintService.getString(R.string.connects_via_wifi_direct); 211 } else { 212 message = mPrintService.getString(R.string.connects_via_network, printer.path); 213 } 214 new AlertDialog.Builder(getContext()) 215 .setTitle(printer.name) 216 .setMessage(message) 217 .setNegativeButton(android.R.string.cancel, null) 218 .setPositiveButton(R.string.forget, (dialog, which) -> { 219 mPrintService.getDiscovery().removeSavedPrinter(printer.path); 220 updateSavedPrinters(); 221 }).show(); 222 } 223 } 224