SyncedFolderPreferencesDialogFragment.java 26 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620
  1. /*
  2. * Nextcloud Android client application
  3. *
  4. * @author Andy Scherzinger
  5. * Copyright (C) 2016 Andy Scherzinger
  6. * Copyright (C) 2016 Nextcloud
  7. *
  8. * This program is free software; you can redistribute it and/or
  9. * modify it under the terms of the GNU AFFERO GENERAL PUBLIC LICENSE
  10. * License as published by the Free Software Foundation; either
  11. * version 3 of the License, or any later version.
  12. *
  13. * This program is distributed in the hope that it will be useful,
  14. * but WITHOUT ANY WARRANTY; without even the implied warranty of
  15. * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
  16. * GNU AFFERO GENERAL PUBLIC LICENSE for more details.
  17. *
  18. * You should have received a copy of the GNU Affero General Public
  19. * License along with this program. If not, see <http://www.gnu.org/licenses/>.
  20. */
  21. package com.owncloud.android.ui.dialog;
  22. import android.app.Activity;
  23. import android.app.Dialog;
  24. import android.content.DialogInterface;
  25. import android.content.Intent;
  26. import android.graphics.Color;
  27. import android.graphics.Typeface;
  28. import android.os.Bundle;
  29. import android.text.TextUtils;
  30. import android.text.style.StyleSpan;
  31. import android.view.LayoutInflater;
  32. import android.view.View;
  33. import android.view.View.OnClickListener;
  34. import android.view.ViewGroup;
  35. import android.widget.TextView;
  36. import com.google.android.material.button.MaterialButton;
  37. import com.owncloud.android.R;
  38. import com.owncloud.android.datamodel.MediaFolderType;
  39. import com.owncloud.android.datamodel.SyncedFolderDisplayItem;
  40. import com.owncloud.android.files.services.FileUploader;
  41. import com.owncloud.android.lib.common.utils.Log_OC;
  42. import com.owncloud.android.ui.activity.FolderPickerActivity;
  43. import com.owncloud.android.ui.activity.UploadFilesActivity;
  44. import com.owncloud.android.ui.dialog.parcel.SyncedFolderParcelable;
  45. import com.owncloud.android.utils.DisplayUtils;
  46. import com.owncloud.android.utils.FileStorageUtils;
  47. import com.owncloud.android.utils.ThemeUtils;
  48. import java.io.File;
  49. import androidx.annotation.NonNull;
  50. import androidx.annotation.Nullable;
  51. import androidx.appcompat.app.AlertDialog;
  52. import androidx.appcompat.widget.AppCompatCheckBox;
  53. import androidx.appcompat.widget.SwitchCompat;
  54. import androidx.fragment.app.DialogFragment;
  55. import static com.owncloud.android.datamodel.SyncedFolderDisplayItem.UNPERSISTED_ID;
  56. import static com.owncloud.android.ui.activity.UploadFilesActivity.REQUEST_CODE_KEY;
  57. /**
  58. * Dialog to show the preferences/configuration of a synced folder allowing the user to change the different parameters.
  59. */
  60. public class SyncedFolderPreferencesDialogFragment extends DialogFragment {
  61. public static final String SYNCED_FOLDER_PARCELABLE = "SyncedFolderParcelable";
  62. public static final int REQUEST_CODE__SELECT_REMOTE_FOLDER = 0;
  63. public static final int REQUEST_CODE__SELECT_LOCAL_FOLDER = 1;
  64. private final static String TAG = SyncedFolderPreferencesDialogFragment.class.getSimpleName();
  65. private static final String BEHAVIOUR_DIALOG_STATE = "BEHAVIOUR_DIALOG_STATE";
  66. private static final String NAME_COLLISION_POLICY_DIALOG_STATE = "NAME_COLLISION_POLICY_DIALOG_STATE";
  67. private final static float alphaEnabled = 1.0f;
  68. private final static float alphaDisabled = 0.7f;
  69. protected View mView;
  70. private CharSequence[] mUploadBehaviorItemStrings;
  71. private CharSequence[] mNameCollisionPolicyItemStrings;
  72. private SwitchCompat mEnabledSwitch;
  73. private AppCompatCheckBox mUploadOnWifiCheckbox;
  74. private AppCompatCheckBox mUploadOnChargingCheckbox;
  75. private AppCompatCheckBox mUploadExistingCheckbox;
  76. private AppCompatCheckBox mUploadUseSubfoldersCheckbox;
  77. private TextView mUploadBehaviorSummary;
  78. private TextView mNameCollisionPolicySummary;
  79. private TextView mLocalFolderPath;
  80. private TextView mLocalFolderSummary;
  81. private TextView mRemoteFolderSummary;
  82. private SyncedFolderParcelable mSyncedFolder;
  83. private MaterialButton mCancel;
  84. private MaterialButton mSave;
  85. private boolean behaviourDialogShown;
  86. private boolean nameCollisionPolicyDialogShown;
  87. private AlertDialog behaviourDialog;
  88. public static SyncedFolderPreferencesDialogFragment newInstance(SyncedFolderDisplayItem syncedFolder, int section) {
  89. if (syncedFolder == null) {
  90. throw new IllegalArgumentException("SyncedFolder is mandatory but NULL!");
  91. }
  92. Bundle args = new Bundle();
  93. args.putParcelable(SYNCED_FOLDER_PARCELABLE, new SyncedFolderParcelable(syncedFolder, section));
  94. SyncedFolderPreferencesDialogFragment dialogFragment = new SyncedFolderPreferencesDialogFragment();
  95. dialogFragment.setArguments(args);
  96. dialogFragment.setStyle(STYLE_NORMAL, R.style.Theme_ownCloud_Dialog);
  97. return dialogFragment;
  98. }
  99. @Override
  100. public void onAttach(@NonNull Activity activity) {
  101. super.onAttach(activity);
  102. if (!(activity instanceof OnSyncedFolderPreferenceListener)) {
  103. throw new IllegalArgumentException("The host activity must implement "
  104. + OnSyncedFolderPreferenceListener.class.getCanonicalName());
  105. }
  106. }
  107. @Override
  108. public void onCreate(Bundle savedInstanceState) {
  109. super.onCreate(savedInstanceState);
  110. // keep the state of the fragment on configuration changes
  111. setRetainInstance(true);
  112. mView = null;
  113. mSyncedFolder = getArguments().getParcelable(SYNCED_FOLDER_PARCELABLE);
  114. mUploadBehaviorItemStrings = getResources().getTextArray(R.array.pref_behaviour_entries);
  115. mNameCollisionPolicyItemStrings = getResources().getTextArray(R.array.pref_name_collision_policy_entries);
  116. }
  117. @Override
  118. public View onCreateView(@NonNull LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState) {
  119. Log_OC.d(TAG, "onCreateView, savedInstanceState is " + savedInstanceState);
  120. mView = inflater.inflate(R.layout.synced_folders_settings_layout, container, false);
  121. setupDialogElements(mView);
  122. setupListeners(mView);
  123. return mView;
  124. }
  125. /**
  126. * find all relevant UI elements and set their values.
  127. *
  128. * @param view the parent view
  129. */
  130. private void setupDialogElements(View view) {
  131. int accentColor = ThemeUtils.primaryAccentColor(getContext());
  132. if (mSyncedFolder.getType().getId() > MediaFolderType.CUSTOM.getId()) {
  133. // hide local folder chooser and delete for non-custom folders
  134. view.findViewById(R.id.local_folder_container).setVisibility(View.GONE);
  135. view.findViewById(R.id.delete).setVisibility(View.GONE);
  136. } else if (mSyncedFolder.getId() <= UNPERSISTED_ID) {
  137. // Hide delete/enabled for unpersisted custom folders
  138. view.findViewById(R.id.delete).setVisibility(View.GONE);
  139. view.findViewById(R.id.sync_enabled).setVisibility(View.GONE);
  140. // auto set custom folder to enabled
  141. mSyncedFolder.setEnabled(true);
  142. // switch text to create headline
  143. ((TextView) view.findViewById(R.id.synced_folders_settings_title))
  144. .setText(R.string.autoupload_create_new_custom_folder);
  145. // disable save button
  146. view.findViewById(R.id.save).setEnabled(false);
  147. } else {
  148. view.findViewById(R.id.local_folder_container).setVisibility(View.GONE);
  149. }
  150. // find/saves UI elements
  151. mEnabledSwitch = view.findViewById(R.id.sync_enabled);
  152. ThemeUtils.tintSwitch(mEnabledSwitch, accentColor);
  153. mLocalFolderPath = view.findViewById(R.id.synced_folders_settings_local_folder_path);
  154. mLocalFolderSummary = view.findViewById(R.id.local_folder_summary);
  155. mRemoteFolderSummary = view.findViewById(R.id.remote_folder_summary);
  156. mUploadOnWifiCheckbox = view.findViewById(R.id.setting_instant_upload_on_wifi_checkbox);
  157. ThemeUtils.tintCheckbox(mUploadOnWifiCheckbox, accentColor);
  158. mUploadOnChargingCheckbox = view.findViewById(R.id.setting_instant_upload_on_charging_checkbox);
  159. ThemeUtils.tintCheckbox(mUploadOnChargingCheckbox, accentColor);
  160. mUploadExistingCheckbox = view.findViewById(R.id.setting_instant_upload_existing_checkbox);
  161. ThemeUtils.tintCheckbox(mUploadExistingCheckbox, accentColor);
  162. mUploadUseSubfoldersCheckbox = view.findViewById(
  163. R.id.setting_instant_upload_path_use_subfolders_checkbox);
  164. ThemeUtils.tintCheckbox(mUploadUseSubfoldersCheckbox, accentColor);
  165. mUploadBehaviorSummary = view.findViewById(R.id.setting_instant_behaviour_summary);
  166. mNameCollisionPolicySummary = view.findViewById(R.id.setting_instant_name_collision_policy_summary);
  167. mCancel = view.findViewById(R.id.cancel);
  168. ThemeUtils.themeBorderlessButton(mCancel, accentColor);
  169. mSave = view.findViewById(R.id.save);
  170. ThemeUtils.themeBorderlessButton(mSave, accentColor);
  171. // Set values
  172. setEnabled(mSyncedFolder.isEnabled());
  173. if (!TextUtils.isEmpty(mSyncedFolder.getLocalPath())) {
  174. mLocalFolderPath.setText(
  175. DisplayUtils.createTextWithSpan(
  176. String.format(
  177. getString(R.string.synced_folders_preferences_folder_path),
  178. mSyncedFolder.getLocalPath()),
  179. mSyncedFolder.getFolderName(),
  180. new StyleSpan(Typeface.BOLD)));
  181. mLocalFolderSummary.setText(FileStorageUtils.pathToUserFriendlyDisplay(
  182. mSyncedFolder.getLocalPath(),
  183. getActivity(),
  184. getResources()));
  185. } else {
  186. mLocalFolderSummary.setText(R.string.choose_local_folder);
  187. }
  188. if (!TextUtils.isEmpty(mSyncedFolder.getLocalPath())) {
  189. mRemoteFolderSummary.setText(mSyncedFolder.getRemotePath());
  190. } else {
  191. mRemoteFolderSummary.setText(R.string.choose_remote_folder);
  192. }
  193. mUploadOnWifiCheckbox.setChecked(mSyncedFolder.isWifiOnly());
  194. mUploadOnChargingCheckbox.setChecked(mSyncedFolder.isChargingOnly());
  195. mUploadExistingCheckbox.setChecked(mSyncedFolder.isExisting());
  196. mUploadUseSubfoldersCheckbox.setChecked(mSyncedFolder.isSubfolderByDate());
  197. mUploadBehaviorSummary.setText(mUploadBehaviorItemStrings[mSyncedFolder.getUploadActionInteger()]);
  198. final int nameCollisionPolicyIndex =
  199. getSelectionIndexForNameCollisionPolicy(mSyncedFolder.getNameCollisionPolicy());
  200. mNameCollisionPolicySummary.setText(mNameCollisionPolicyItemStrings[nameCollisionPolicyIndex]);
  201. }
  202. /**
  203. * set correct icon/flag.
  204. *
  205. * @param enabled if enabled or disabled
  206. */
  207. private void setEnabled(boolean enabled) {
  208. mSyncedFolder.setEnabled(enabled);
  209. mEnabledSwitch.setChecked(enabled);
  210. setupViews(mView, enabled);
  211. }
  212. /**
  213. * set (new) remote path on activity result of the folder picker activity. The result gets originally propagated
  214. * to the underlying activity since the picker is an activity and the result can't get passed to the dialog
  215. * fragment directly.
  216. *
  217. * @param path the remote path to be set
  218. */
  219. public void setRemoteFolderSummary(String path) {
  220. mSyncedFolder.setRemotePath(path);
  221. mRemoteFolderSummary.setText(path);
  222. checkAndUpdateSaveButtonState();
  223. }
  224. /**
  225. * set (new) local path on activity result of the folder picker activity. The result gets originally propagated
  226. * to the underlying activity since the picker is an activity and the result can't get passed to the dialog
  227. * fragment directly.
  228. *
  229. * @param path the local path to be set
  230. */
  231. public void setLocalFolderSummary(String path) {
  232. mSyncedFolder.setLocalPath(path);
  233. mLocalFolderSummary.setText(FileStorageUtils.pathToUserFriendlyDisplay(path, getActivity(), getResources()));
  234. mLocalFolderPath.setText(
  235. DisplayUtils.createTextWithSpan(
  236. String.format(
  237. getString(R.string.synced_folders_preferences_folder_path),
  238. mSyncedFolder.getLocalPath()),
  239. new File(mSyncedFolder.getLocalPath()).getName(),
  240. new StyleSpan(Typeface.BOLD)));
  241. checkAndUpdateSaveButtonState();
  242. }
  243. private void checkAndUpdateSaveButtonState() {
  244. if (mSyncedFolder.getLocalPath() != null && mSyncedFolder.getRemotePath() != null) {
  245. mView.findViewById(R.id.save).setEnabled(true);
  246. } else {
  247. mView.findViewById(R.id.save).setEnabled(false);
  248. }
  249. checkWritableFolder();
  250. }
  251. private void checkWritableFolder() {
  252. if (!mSyncedFolder.isEnabled()) {
  253. mView.findViewById(R.id.setting_instant_behaviour_container).setEnabled(false);
  254. mView.findViewById(R.id.setting_instant_behaviour_container).setAlpha(alphaDisabled);
  255. return;
  256. }
  257. if (mSyncedFolder.getLocalPath() != null && new File(mSyncedFolder.getLocalPath()).canWrite()) {
  258. mView.findViewById(R.id.setting_instant_behaviour_container).setEnabled(true);
  259. mView.findViewById(R.id.setting_instant_behaviour_container).setAlpha(alphaEnabled);
  260. mUploadBehaviorSummary.setText(mUploadBehaviorItemStrings[mSyncedFolder.getUploadActionInteger()]);
  261. } else {
  262. mView.findViewById(R.id.setting_instant_behaviour_container).setEnabled(false);
  263. mView.findViewById(R.id.setting_instant_behaviour_container).setAlpha(alphaDisabled);
  264. mSyncedFolder.setUploadAction(
  265. getResources().getTextArray(R.array.pref_behaviour_entryValues)[0].toString());
  266. mUploadBehaviorSummary.setText(R.string.auto_upload_file_behaviour_kept_in_folder);
  267. }
  268. }
  269. private void setupViews(View view, boolean enable) {
  270. float alpha;
  271. if (enable) {
  272. alpha = alphaEnabled;
  273. } else {
  274. alpha = alphaDisabled;
  275. }
  276. view.findViewById(R.id.setting_instant_upload_on_wifi_container).setEnabled(enable);
  277. view.findViewById(R.id.setting_instant_upload_on_wifi_container).setAlpha(alpha);
  278. view.findViewById(R.id.setting_instant_upload_on_charging_container).setEnabled(enable);
  279. view.findViewById(R.id.setting_instant_upload_on_charging_container).setAlpha(alpha);
  280. view.findViewById(R.id.setting_instant_upload_existing_container).setEnabled(enable);
  281. view.findViewById(R.id.setting_instant_upload_existing_container).setAlpha(alpha);
  282. view.findViewById(R.id.setting_instant_upload_path_use_subfolders_container).setEnabled(enable);
  283. view.findViewById(R.id.setting_instant_upload_path_use_subfolders_container).setAlpha(alpha);
  284. view.findViewById(R.id.remote_folder_container).setEnabled(enable);
  285. view.findViewById(R.id.remote_folder_container).setAlpha(alpha);
  286. view.findViewById(R.id.local_folder_container).setEnabled(enable);
  287. view.findViewById(R.id.local_folder_container).setAlpha(alpha);
  288. view.findViewById(R.id.setting_instant_name_collision_policy_container).setEnabled(enable);
  289. view.findViewById(R.id.setting_instant_name_collision_policy_container).setAlpha(alpha);
  290. if (enable) {
  291. int accentColor = ThemeUtils.primaryAccentColor(getContext());
  292. ThemeUtils.tintCheckbox(mUploadOnWifiCheckbox, accentColor);
  293. ThemeUtils.tintCheckbox(mUploadOnChargingCheckbox, accentColor);
  294. ThemeUtils.tintCheckbox(mUploadExistingCheckbox, accentColor);
  295. ThemeUtils.tintCheckbox(mUploadUseSubfoldersCheckbox, accentColor);
  296. } else {
  297. ThemeUtils.tintCheckbox(mUploadOnWifiCheckbox, Color.GRAY);
  298. ThemeUtils.tintCheckbox(mUploadOnChargingCheckbox, Color.GRAY);
  299. ThemeUtils.tintCheckbox(mUploadExistingCheckbox, Color.GRAY);
  300. ThemeUtils.tintCheckbox(mUploadUseSubfoldersCheckbox, Color.GRAY);
  301. }
  302. checkWritableFolder();
  303. }
  304. /**
  305. * setup all listeners.
  306. *
  307. * @param view the parent view
  308. */
  309. private void setupListeners(View view) {
  310. mSave.setOnClickListener(new OnSyncedFolderSaveClickListener());
  311. mCancel.setOnClickListener(new OnSyncedFolderCancelClickListener());
  312. view.findViewById(R.id.delete).setOnClickListener(new OnSyncedFolderDeleteClickListener());
  313. view.findViewById(R.id.setting_instant_upload_on_wifi_container).setOnClickListener(
  314. new OnClickListener() {
  315. @Override
  316. public void onClick(View v) {
  317. mSyncedFolder.setWifiOnly(!mSyncedFolder.isWifiOnly());
  318. mUploadOnWifiCheckbox.toggle();
  319. }
  320. });
  321. view.findViewById(R.id.setting_instant_upload_on_charging_container).setOnClickListener(
  322. new OnClickListener() {
  323. @Override
  324. public void onClick(View v) {
  325. mSyncedFolder.setChargingOnly(!mSyncedFolder.isChargingOnly());
  326. mUploadOnChargingCheckbox.toggle();
  327. }
  328. });
  329. view.findViewById(R.id.setting_instant_upload_existing_container).setOnClickListener(
  330. new OnClickListener() {
  331. @Override
  332. public void onClick(View v) {
  333. mSyncedFolder.setExisting(!mSyncedFolder.isExisting());
  334. mUploadExistingCheckbox.toggle();
  335. }
  336. });
  337. view.findViewById(R.id.setting_instant_upload_path_use_subfolders_container).setOnClickListener(
  338. new OnClickListener() {
  339. @Override
  340. public void onClick(View v) {
  341. mSyncedFolder.setSubfolderByDate(!mSyncedFolder.isSubfolderByDate());
  342. mUploadUseSubfoldersCheckbox.toggle();
  343. }
  344. });
  345. view.findViewById(R.id.remote_folder_container).setOnClickListener(v -> {
  346. Intent action = new Intent(getActivity(), FolderPickerActivity.class);
  347. getActivity().startActivityForResult(action, REQUEST_CODE__SELECT_REMOTE_FOLDER);
  348. });
  349. view.findViewById(R.id.local_folder_container).setOnClickListener(v -> {
  350. Intent action = new Intent(getActivity(), UploadFilesActivity.class);
  351. action.putExtra(UploadFilesActivity.KEY_LOCAL_FOLDER_PICKER_MODE, true);
  352. action.putExtra(REQUEST_CODE_KEY, REQUEST_CODE__SELECT_LOCAL_FOLDER);
  353. getActivity().startActivityForResult(action, REQUEST_CODE__SELECT_LOCAL_FOLDER);
  354. });
  355. view.findViewById(R.id.sync_enabled).setOnClickListener(new OnClickListener() {
  356. @Override
  357. public void onClick(View v) {
  358. setEnabled(!mSyncedFolder.isEnabled());
  359. }
  360. });
  361. view.findViewById(R.id.setting_instant_behaviour_container).setOnClickListener(
  362. new OnClickListener() {
  363. @Override
  364. public void onClick(View v) {
  365. showBehaviourDialog();
  366. }
  367. });
  368. view.findViewById(R.id.setting_instant_name_collision_policy_container).setOnClickListener(
  369. new OnClickListener() {
  370. @Override
  371. public void onClick(View v) {
  372. showNameCollisionPolicyDialog();
  373. }
  374. });
  375. }
  376. private void showBehaviourDialog() {
  377. AlertDialog.Builder builder = new AlertDialog.Builder(getActivity());
  378. builder.setTitle(R.string.prefs_instant_behaviour_dialogTitle)
  379. .setSingleChoiceItems(getResources().getTextArray(R.array.pref_behaviour_entries),
  380. mSyncedFolder.getUploadActionInteger(),
  381. new
  382. DialogInterface.OnClickListener() {
  383. public void onClick(DialogInterface dialog, int which) {
  384. mSyncedFolder.setUploadAction(
  385. getResources().getTextArray(
  386. R.array.pref_behaviour_entryValues)[which].toString());
  387. mUploadBehaviorSummary.setText(SyncedFolderPreferencesDialogFragment
  388. .this.mUploadBehaviorItemStrings[which]);
  389. behaviourDialogShown = false;
  390. dialog.dismiss();
  391. }
  392. })
  393. .setOnCancelListener(new DialogInterface.OnCancelListener() {
  394. @Override
  395. public void onCancel(DialogInterface dialog) {
  396. behaviourDialogShown = false;
  397. }
  398. });
  399. behaviourDialogShown = true;
  400. behaviourDialog = builder.create();
  401. behaviourDialog.show();
  402. }
  403. private void showNameCollisionPolicyDialog() {
  404. AlertDialog.Builder builder = new AlertDialog.Builder(getActivity());
  405. builder.setTitle(R.string.pref_instant_name_collision_policy_dialogTitle)
  406. .setSingleChoiceItems(getResources().getTextArray(R.array.pref_name_collision_policy_entries),
  407. getSelectionIndexForNameCollisionPolicy(mSyncedFolder.getNameCollisionPolicy()),
  408. new OnNameCollisionDialogClickListener())
  409. .setOnCancelListener(dialog -> nameCollisionPolicyDialogShown = false);
  410. nameCollisionPolicyDialogShown = true;
  411. behaviourDialog = builder.create();
  412. behaviourDialog.show();
  413. }
  414. @Override
  415. @NonNull
  416. public Dialog onCreateDialog(Bundle savedInstanceState) {
  417. final Dialog dialog = super.onCreateDialog(savedInstanceState);
  418. dialog.setTitle(null);
  419. return dialog;
  420. }
  421. @Override
  422. public void onDestroyView() {
  423. Log_OC.d(TAG, "destroy SyncedFolderPreferencesDialogFragment view");
  424. if (getDialog() != null && getRetainInstance()) {
  425. getDialog().setDismissMessage(null);
  426. }
  427. if (behaviourDialog != null && behaviourDialog.isShowing()) {
  428. behaviourDialog.dismiss();
  429. }
  430. super.onDestroyView();
  431. }
  432. @Override
  433. public void onSaveInstanceState(@NonNull Bundle outState) {
  434. outState.putBoolean(BEHAVIOUR_DIALOG_STATE, behaviourDialogShown);
  435. outState.putBoolean(NAME_COLLISION_POLICY_DIALOG_STATE, nameCollisionPolicyDialogShown);
  436. super.onSaveInstanceState(outState);
  437. }
  438. @Override
  439. public void onViewStateRestored(@Nullable Bundle savedInstanceState) {
  440. behaviourDialogShown = savedInstanceState != null &&
  441. savedInstanceState.getBoolean(BEHAVIOUR_DIALOG_STATE, false);
  442. nameCollisionPolicyDialogShown = savedInstanceState != null &&
  443. savedInstanceState.getBoolean(NAME_COLLISION_POLICY_DIALOG_STATE, false);
  444. if (behaviourDialogShown) {
  445. showBehaviourDialog();
  446. }
  447. if (nameCollisionPolicyDialogShown){
  448. showNameCollisionPolicyDialog();
  449. }
  450. super.onViewStateRestored(savedInstanceState);
  451. }
  452. public interface OnSyncedFolderPreferenceListener {
  453. void onSaveSyncedFolderPreference(SyncedFolderParcelable syncedFolder);
  454. void onCancelSyncedFolderPreference();
  455. void onDeleteSyncedFolderPreference(SyncedFolderParcelable syncedFolder);
  456. }
  457. private class OnSyncedFolderSaveClickListener implements OnClickListener {
  458. @Override
  459. public void onClick(View v) {
  460. dismiss();
  461. ((OnSyncedFolderPreferenceListener) getActivity()).onSaveSyncedFolderPreference(mSyncedFolder);
  462. }
  463. }
  464. private class OnSyncedFolderCancelClickListener implements OnClickListener {
  465. @Override
  466. public void onClick(View v) {
  467. dismiss();
  468. ((OnSyncedFolderPreferenceListener) getActivity()).onCancelSyncedFolderPreference();
  469. }
  470. }
  471. private class OnSyncedFolderDeleteClickListener implements OnClickListener {
  472. @Override
  473. public void onClick(View v) {
  474. dismiss();
  475. ((OnSyncedFolderPreferenceListener) getActivity()).onDeleteSyncedFolderPreference(mSyncedFolder);
  476. }
  477. }
  478. private class OnNameCollisionDialogClickListener implements DialogInterface.OnClickListener {
  479. @Override
  480. public void onClick(DialogInterface dialog, int which) {
  481. mSyncedFolder.setNameCollisionPolicy(getNameCollisionPolicyForSelectionIndex(which));
  482. mNameCollisionPolicySummary.setText(
  483. SyncedFolderPreferencesDialogFragment.this.mNameCollisionPolicyItemStrings[which]);
  484. nameCollisionPolicyDialogShown = false;
  485. dialog.dismiss();
  486. }
  487. }
  488. /**
  489. * Get index for name collision selection dialog.
  490. * @return 0 if ASK_USER, 1 if OVERWRITE, 2 if RENAME, 3 if SKIP, Otherwise: 0
  491. */
  492. static private Integer getSelectionIndexForNameCollisionPolicy(FileUploader.NameCollisionPolicy nameCollisionPolicy) {
  493. switch (nameCollisionPolicy) {
  494. case OVERWRITE:
  495. return 1;
  496. case RENAME:
  497. return 2;
  498. case CANCEL:
  499. return 3;
  500. case ASK_USER:
  501. default:
  502. return 0;
  503. }
  504. }
  505. /**
  506. * Get index for name collision selection dialog. Inverse of getSelectionIndexForNameCollisionPolicy.
  507. *
  508. * @return ASK_USER if 0, OVERWRITE if 1, RENAME if 2, SKIP if 3. Otherwise: ASK_USER
  509. */
  510. static private FileUploader.NameCollisionPolicy getNameCollisionPolicyForSelectionIndex(int index) {
  511. switch (index) {
  512. case 1:
  513. return FileUploader.NameCollisionPolicy.OVERWRITE;
  514. case 2:
  515. return FileUploader.NameCollisionPolicy.RENAME;
  516. case 3:
  517. return FileUploader.NameCollisionPolicy.CANCEL;
  518. case 0:
  519. default:
  520. return FileUploader.NameCollisionPolicy.ASK_USER;
  521. }
  522. }
  523. }