blob: e87e53a643d66ec3389f904e991a57468e86c93e [file] [log] [blame]
Garfield Tan63bf8132016-10-11 11:00:49 -07001/*
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
17package com.android.documentsui;
18
19import android.app.Activity;
Garfield Tanbe1e0792017-02-24 17:14:53 -080020import android.content.BroadcastReceiver;
21import android.content.Context;
22import android.content.Intent;
23import android.content.IntentFilter;
Garfield Tan63bf8132016-10-11 11:00:49 -070024import android.net.Uri;
KOUSHIK PANUGANTI6ca7acc2018-04-17 16:00:10 -070025import androidx.localbroadcastmanager.content.LocalBroadcastManager;
Garfield Tan63bf8132016-10-11 11:00:49 -070026
27import com.android.documentsui.AbstractActionHandler.CommonAddons;
28import com.android.documentsui.base.DocumentInfo;
29import com.android.documentsui.base.PairedTask;
30import com.android.documentsui.base.RootInfo;
31import com.android.documentsui.base.State;
32import com.android.documentsui.dirlist.AnimationView;
Steve McKay3a268232016-10-19 11:15:47 -070033import com.android.documentsui.queries.SearchViewManager;
Jon Mann9bd40992017-03-24 12:34:34 -070034import com.android.documentsui.roots.ProvidersAccess;
Garfield Tan63bf8132016-10-11 11:00:49 -070035
36import java.util.Collection;
37
38/**
39 * Monitors roots change and refresh the page when necessary.
40 */
41final class RootsMonitor<T extends Activity & CommonAddons> {
42
Garfield Tanbe1e0792017-02-24 17:14:53 -080043 private final LocalBroadcastManager mManager;
44 private final BroadcastReceiver mReceiver;
Garfield Tan63bf8132016-10-11 11:00:49 -070045
46 RootsMonitor(
47 final T activity,
48 final ActionHandler actions,
Jon Mann9bd40992017-03-24 12:34:34 -070049 final ProvidersAccess providers,
Garfield Tan63bf8132016-10-11 11:00:49 -070050 final DocumentsAccess docs,
51 final State state,
Garfield Tan80b52b32017-04-25 15:50:52 -070052 final SearchViewManager searchMgr,
53 final Runnable actionModeFinisher) {
Garfield Tanbe1e0792017-02-24 17:14:53 -080054 mManager = LocalBroadcastManager.getInstance(activity);
Garfield Tan63bf8132016-10-11 11:00:49 -070055
Garfield Tanbe1e0792017-02-24 17:14:53 -080056 mReceiver = new BroadcastReceiver() {
Garfield Tan63bf8132016-10-11 11:00:49 -070057 @Override
Garfield Tanbe1e0792017-02-24 17:14:53 -080058 public void onReceive(Context context, Intent intent) {
Steve McKay2d19a692017-08-22 09:05:08 -070059 new HandleRootsChangedTask<>(
Garfield Tan63bf8132016-10-11 11:00:49 -070060 activity,
61 actions,
Jon Mann9bd40992017-03-24 12:34:34 -070062 providers,
Garfield Tan63bf8132016-10-11 11:00:49 -070063 docs,
64 state,
Garfield Tan80b52b32017-04-25 15:50:52 -070065 searchMgr,
66 actionModeFinisher).execute(activity.getCurrentRoot());
Garfield Tan63bf8132016-10-11 11:00:49 -070067 }
68 };
69 }
70
71 void start() {
Jon Mann9bd40992017-03-24 12:34:34 -070072 mManager.registerReceiver(mReceiver, new IntentFilter(ProvidersAccess.BROADCAST_ACTION));
Garfield Tan63bf8132016-10-11 11:00:49 -070073 }
74
75 void stop() {
Garfield Tanbe1e0792017-02-24 17:14:53 -080076 mManager.unregisterReceiver(mReceiver);
Garfield Tan63bf8132016-10-11 11:00:49 -070077 }
78
79 private static class HandleRootsChangedTask<T extends Activity & CommonAddons>
80 extends PairedTask<T, RootInfo, RootInfo> {
81 private final ActionHandler mActions;
Jon Mann9bd40992017-03-24 12:34:34 -070082 private final ProvidersAccess mProviders;
Garfield Tan63bf8132016-10-11 11:00:49 -070083 private final DocumentsAccess mDocs;
84 private final State mState;
85 private final SearchViewManager mSearchMgr;
Garfield Tan80b52b32017-04-25 15:50:52 -070086 private final Runnable mActionModeFinisher;
Garfield Tan63bf8132016-10-11 11:00:49 -070087
88 private RootInfo mCurrentRoot;
89 private DocumentInfo mDefaultRootDocument;
90
91 private HandleRootsChangedTask(
92 T activity,
93 ActionHandler actions,
Jon Mann9bd40992017-03-24 12:34:34 -070094 ProvidersAccess providers,
Garfield Tan63bf8132016-10-11 11:00:49 -070095 DocumentsAccess docs,
96 State state,
Garfield Tan80b52b32017-04-25 15:50:52 -070097 SearchViewManager searchMgr,
98 Runnable actionModeFinisher) {
Garfield Tan63bf8132016-10-11 11:00:49 -070099 super(activity);
100 mActions = actions;
Jon Mann9bd40992017-03-24 12:34:34 -0700101 mProviders = providers;
Garfield Tan63bf8132016-10-11 11:00:49 -0700102 mDocs = docs;
103 mState = state;
104 mSearchMgr = searchMgr;
Garfield Tan80b52b32017-04-25 15:50:52 -0700105 mActionModeFinisher = actionModeFinisher;
Garfield Tan63bf8132016-10-11 11:00:49 -0700106 }
107
108 @Override
109 protected RootInfo run(RootInfo... roots) {
110 assert (roots.length == 1);
111 mCurrentRoot = roots[0];
Jon Mann9bd40992017-03-24 12:34:34 -0700112 final Collection<RootInfo> cachedRoots = mProviders.getRootsBlocking();
Garfield Tan63bf8132016-10-11 11:00:49 -0700113 for (final RootInfo root : cachedRoots) {
114 if (root.getUri().equals(mCurrentRoot.getUri())) {
115 // We don't need to change the current root as the current root was not removed.
116 return null;
117 }
118 }
119
120 // Choose the default root.
Jon Mann9bd40992017-03-24 12:34:34 -0700121 final RootInfo defaultRoot = mProviders.getDefaultRootBlocking(mState);
Garfield Tan63bf8132016-10-11 11:00:49 -0700122 assert (defaultRoot != null);
123 if (!defaultRoot.isRecents()) {
124 mDefaultRootDocument = mDocs.getRootDocument(defaultRoot);
125 }
126 return defaultRoot;
127 }
128
129 @Override
130 protected void finish(RootInfo defaultRoot) {
131 if (defaultRoot == null) {
132 return;
133 }
134
135 // If the activity has been launched for the specific root and it is removed, finish the
136 // activity.
137 final Uri uri = mOwner.getIntent().getData();
138 if (uri != null && uri.equals(mCurrentRoot.getUri())) {
139 mOwner.finish();
140 return;
141 }
142
Garfield Tan80b52b32017-04-25 15:50:52 -0700143 // Clean action mode before changing root.
144 mActionModeFinisher.run();
145
Garfield Tan63bf8132016-10-11 11:00:49 -0700146 // Clear entire backstack and start in new root.
Garfield Tan2a837422016-10-19 11:50:45 -0700147 mState.stack.changeRoot(defaultRoot);
Tomasz Mikolajewski9e047852017-02-13 14:05:17 +0900148 mSearchMgr.update(mState.stack);
Garfield Tan63bf8132016-10-11 11:00:49 -0700149
150 if (defaultRoot.isRecents()) {
151 mOwner.refreshCurrentRootAndDirectory(AnimationView.ANIM_NONE);
152 } else {
153 mActions.openContainerDocument(mDefaultRootDocument);
154 }
155 }
156 }
157}