16e565ffab8916af6c991c4f189a7ec438bce6978Jeff Sharkey/* 26e565ffab8916af6c991c4f189a7ec438bce6978Jeff Sharkey * Copyright (C) 2014 The Android Open Source Project 36e565ffab8916af6c991c4f189a7ec438bce6978Jeff Sharkey * 46e565ffab8916af6c991c4f189a7ec438bce6978Jeff Sharkey * Licensed under the Apache License, Version 2.0 (the "License"); 56e565ffab8916af6c991c4f189a7ec438bce6978Jeff Sharkey * you may not use this file except in compliance with the License. 66e565ffab8916af6c991c4f189a7ec438bce6978Jeff Sharkey * You may obtain a copy of the License at 76e565ffab8916af6c991c4f189a7ec438bce6978Jeff Sharkey * 86e565ffab8916af6c991c4f189a7ec438bce6978Jeff Sharkey * http://www.apache.org/licenses/LICENSE-2.0 96e565ffab8916af6c991c4f189a7ec438bce6978Jeff Sharkey * 106e565ffab8916af6c991c4f189a7ec438bce6978Jeff Sharkey * Unless required by applicable law or agreed to in writing, software 116e565ffab8916af6c991c4f189a7ec438bce6978Jeff Sharkey * distributed under the License is distributed on an "AS IS" BASIS, 126e565ffab8916af6c991c4f189a7ec438bce6978Jeff Sharkey * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 136e565ffab8916af6c991c4f189a7ec438bce6978Jeff Sharkey * See the License for the specific language governing permissions and 146e565ffab8916af6c991c4f189a7ec438bce6978Jeff Sharkey * limitations under the License. 156e565ffab8916af6c991c4f189a7ec438bce6978Jeff Sharkey */ 166e565ffab8916af6c991c4f189a7ec438bce6978Jeff Sharkey 17d080506e3aa8547605cd4783eb660775d7d2b8eeSteve McKaypackage com.android.documentsui.picker; 186e565ffab8916af6c991c4f189a7ec438bce6978Jeff Sharkey 19c8bdc7f8c692c22afa3312bc5ff672449b0a58a5Steve McKayimport static com.android.documentsui.services.FileOperationService.OPERATION_DELETE; 20bc7eb5fc39b5555eedc7d7b3591687343ecda18dTomasz Mikolajewskiimport static com.android.documentsui.services.FileOperationService.OPERATION_COPY; 21bc7eb5fc39b5555eedc7d7b3591687343ecda18dTomasz Mikolajewskiimport static com.android.documentsui.services.FileOperationService.OPERATION_COMPRESS; 22bc7eb5fc39b5555eedc7d7b3591687343ecda18dTomasz Mikolajewskiimport static com.android.documentsui.services.FileOperationService.OPERATION_EXTRACT; 23f171934ad7a9d901e81a33bbd0ec74aa34a48787Steve McKayimport static com.android.documentsui.services.FileOperationService.OPERATION_MOVE; 24c8bdc7f8c692c22afa3312bc5ff672449b0a58a5Steve McKayimport static com.android.documentsui.services.FileOperationService.OPERATION_UNKNOWN; 25f171934ad7a9d901e81a33bbd0ec74aa34a48787Steve McKay 26676453ce79abc53cd2ec4d41cce3829e21697f49Daichi Hironoimport android.app.Activity; 276e565ffab8916af6c991c4f189a7ec438bce6978Jeff Sharkeyimport android.app.Fragment; 286e565ffab8916af6c991c4f189a7ec438bce6978Jeff Sharkeyimport android.app.FragmentManager; 296e565ffab8916af6c991c4f189a7ec438bce6978Jeff Sharkeyimport android.app.FragmentTransaction; 306e565ffab8916af6c991c4f189a7ec438bce6978Jeff Sharkeyimport android.os.Bundle; 316e565ffab8916af6c991c4f189a7ec438bce6978Jeff Sharkeyimport android.view.LayoutInflater; 326e565ffab8916af6c991c4f189a7ec438bce6978Jeff Sharkeyimport android.view.View; 336e565ffab8916af6c991c4f189a7ec438bce6978Jeff Sharkeyimport android.view.ViewGroup; 346e565ffab8916af6c991c4f189a7ec438bce6978Jeff Sharkeyimport android.widget.Button; 3510e77bf308e4a4e6c5ad28bcf25714d7ae33e35fGarfield Tanimport android.widget.TextView; 366e565ffab8916af6c991c4f189a7ec438bce6978Jeff Sharkey 37d080506e3aa8547605cd4783eb660775d7d2b8eeSteve McKayimport com.android.documentsui.BaseActivity; 3823ac60cd2b1beb59b6cd760b91c7e1b1f7e8fe49Garfield Tanimport com.android.documentsui.Injector; 39d080506e3aa8547605cd4783eb660775d7d2b8eeSteve McKayimport com.android.documentsui.R; 40d080506e3aa8547605cd4783eb660775d7d2b8eeSteve McKayimport com.android.documentsui.base.DocumentInfo; 41d9caa6ab53aa784acaf241c0ded3c4ae2d342bf8Steve McKayimport com.android.documentsui.base.State; 42f171934ad7a9d901e81a33bbd0ec74aa34a48787Steve McKayimport com.android.documentsui.services.FileOperationService.OpType; 436e565ffab8916af6c991c4f189a7ec438bce6978Jeff Sharkey 446e565ffab8916af6c991c4f189a7ec438bce6978Jeff Sharkey/** 456e565ffab8916af6c991c4f189a7ec438bce6978Jeff Sharkey * Display pick confirmation bar, usually for selecting a directory. 466e565ffab8916af6c991c4f189a7ec438bce6978Jeff Sharkey */ 476e565ffab8916af6c991c4f189a7ec438bce6978Jeff Sharkeypublic class PickFragment extends Fragment { 486e565ffab8916af6c991c4f189a7ec438bce6978Jeff Sharkey public static final String TAG = "PickFragment"; 496e565ffab8916af6c991c4f189a7ec438bce6978Jeff Sharkey 50242cb88857ccc197286181ce85cbf0859ae7d71dGarfield Tan private static final String ACTION_KEY = "action"; 51242cb88857ccc197286181ce85cbf0859ae7d71dGarfield Tan private static final String COPY_OPERATION_SUBTYPE_KEY = "copyOperationSubType"; 52242cb88857ccc197286181ce85cbf0859ae7d71dGarfield Tan private static final String PICK_TARGET_KEY = "pickTarget"; 53242cb88857ccc197286181ce85cbf0859ae7d71dGarfield Tan 54242cb88857ccc197286181ce85cbf0859ae7d71dGarfield Tan private final View.OnClickListener mPickListener = new View.OnClickListener() { 55242cb88857ccc197286181ce85cbf0859ae7d71dGarfield Tan @Override 56242cb88857ccc197286181ce85cbf0859ae7d71dGarfield Tan public void onClick(View v) { 5723ac60cd2b1beb59b6cd760b91c7e1b1f7e8fe49Garfield Tan mInjector.actions.pickDocument(mPickTarget); 58242cb88857ccc197286181ce85cbf0859ae7d71dGarfield Tan } 59242cb88857ccc197286181ce85cbf0859ae7d71dGarfield Tan }; 60242cb88857ccc197286181ce85cbf0859ae7d71dGarfield Tan 61242cb88857ccc197286181ce85cbf0859ae7d71dGarfield Tan private final View.OnClickListener mCancelListener = new View.OnClickListener() { 62242cb88857ccc197286181ce85cbf0859ae7d71dGarfield Tan @Override 63242cb88857ccc197286181ce85cbf0859ae7d71dGarfield Tan public void onClick(View v) { 64242cb88857ccc197286181ce85cbf0859ae7d71dGarfield Tan final BaseActivity activity = BaseActivity.get(PickFragment.this); 65242cb88857ccc197286181ce85cbf0859ae7d71dGarfield Tan activity.setResult(Activity.RESULT_CANCELED); 66242cb88857ccc197286181ce85cbf0859ae7d71dGarfield Tan activity.finish(); 67242cb88857ccc197286181ce85cbf0859ae7d71dGarfield Tan } 68242cb88857ccc197286181ce85cbf0859ae7d71dGarfield Tan }; 69242cb88857ccc197286181ce85cbf0859ae7d71dGarfield Tan 7023ac60cd2b1beb59b6cd760b91c7e1b1f7e8fe49Garfield Tan private Injector<ActionHandler<PickActivity>> mInjector; 714e2bb18dbb0ee7c24888e99e1cba386edbad1dc3Daichi Hirono private int mAction; 72bc7eb5fc39b5555eedc7d7b3591687343ecda18dTomasz Mikolajewski // Only legal values are OPERATION_COPY, OPERATION_COMPRESS, OPERATION_EXTRACT, 73bc7eb5fc39b5555eedc7d7b3591687343ecda18dTomasz Mikolajewski // OPERATION_MOVE, and unset (OPERATION_UNKNOWN). 74c8bdc7f8c692c22afa3312bc5ff672449b0a58a5Steve McKay private @OpType int mCopyOperationSubType = OPERATION_UNKNOWN; 756e565ffab8916af6c991c4f189a7ec438bce6978Jeff Sharkey private DocumentInfo mPickTarget; 766e565ffab8916af6c991c4f189a7ec438bce6978Jeff Sharkey private View mContainer; 7710e77bf308e4a4e6c5ad28bcf25714d7ae33e35fGarfield Tan private TextView mPick; 7810e77bf308e4a4e6c5ad28bcf25714d7ae33e35fGarfield Tan private TextView mCancel; 796e565ffab8916af6c991c4f189a7ec438bce6978Jeff Sharkey 806e565ffab8916af6c991c4f189a7ec438bce6978Jeff Sharkey public static void show(FragmentManager fm) { 814e2bb18dbb0ee7c24888e99e1cba386edbad1dc3Daichi Hirono // Fragment can be restored by FragmentManager automatically. 824e2bb18dbb0ee7c24888e99e1cba386edbad1dc3Daichi Hirono if (get(fm) != null) { 834e2bb18dbb0ee7c24888e99e1cba386edbad1dc3Daichi Hirono return; 844e2bb18dbb0ee7c24888e99e1cba386edbad1dc3Daichi Hirono } 856e565ffab8916af6c991c4f189a7ec438bce6978Jeff Sharkey 864e2bb18dbb0ee7c24888e99e1cba386edbad1dc3Daichi Hirono final PickFragment fragment = new PickFragment(); 876e565ffab8916af6c991c4f189a7ec438bce6978Jeff Sharkey final FragmentTransaction ft = fm.beginTransaction(); 886e565ffab8916af6c991c4f189a7ec438bce6978Jeff Sharkey ft.replace(R.id.container_save, fragment, TAG); 896e565ffab8916af6c991c4f189a7ec438bce6978Jeff Sharkey ft.commitAllowingStateLoss(); 906e565ffab8916af6c991c4f189a7ec438bce6978Jeff Sharkey } 916e565ffab8916af6c991c4f189a7ec438bce6978Jeff Sharkey 926e565ffab8916af6c991c4f189a7ec438bce6978Jeff Sharkey public static PickFragment get(FragmentManager fm) { 936e565ffab8916af6c991c4f189a7ec438bce6978Jeff Sharkey return (PickFragment) fm.findFragmentByTag(TAG); 946e565ffab8916af6c991c4f189a7ec438bce6978Jeff Sharkey } 956e565ffab8916af6c991c4f189a7ec438bce6978Jeff Sharkey 966e565ffab8916af6c991c4f189a7ec438bce6978Jeff Sharkey @Override 976e565ffab8916af6c991c4f189a7ec438bce6978Jeff Sharkey public View onCreateView( 986e565ffab8916af6c991c4f189a7ec438bce6978Jeff Sharkey LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState) { 996e565ffab8916af6c991c4f189a7ec438bce6978Jeff Sharkey mContainer = inflater.inflate(R.layout.fragment_pick, container, false); 1006e565ffab8916af6c991c4f189a7ec438bce6978Jeff Sharkey 10110e77bf308e4a4e6c5ad28bcf25714d7ae33e35fGarfield Tan mPick = (TextView) mContainer.findViewById(android.R.id.button1); 1026e565ffab8916af6c991c4f189a7ec438bce6978Jeff Sharkey mPick.setOnClickListener(mPickListener); 1036e565ffab8916af6c991c4f189a7ec438bce6978Jeff Sharkey 10410e77bf308e4a4e6c5ad28bcf25714d7ae33e35fGarfield Tan mCancel = (TextView) mContainer.findViewById(android.R.id.button2); 105676453ce79abc53cd2ec4d41cce3829e21697f49Daichi Hirono mCancel.setOnClickListener(mCancelListener); 106676453ce79abc53cd2ec4d41cce3829e21697f49Daichi Hirono 1074e2bb18dbb0ee7c24888e99e1cba386edbad1dc3Daichi Hirono updateView(); 1086e565ffab8916af6c991c4f189a7ec438bce6978Jeff Sharkey return mContainer; 1096e565ffab8916af6c991c4f189a7ec438bce6978Jeff Sharkey } 1106e565ffab8916af6c991c4f189a7ec438bce6978Jeff Sharkey 111242cb88857ccc197286181ce85cbf0859ae7d71dGarfield Tan @Override 112242cb88857ccc197286181ce85cbf0859ae7d71dGarfield Tan public void onActivityCreated(Bundle savedInstanceState) { 113242cb88857ccc197286181ce85cbf0859ae7d71dGarfield Tan super.onActivityCreated(savedInstanceState); 114242cb88857ccc197286181ce85cbf0859ae7d71dGarfield Tan if (savedInstanceState != null) { 115242cb88857ccc197286181ce85cbf0859ae7d71dGarfield Tan // Restore status 116242cb88857ccc197286181ce85cbf0859ae7d71dGarfield Tan mAction = savedInstanceState.getInt(ACTION_KEY); 117242cb88857ccc197286181ce85cbf0859ae7d71dGarfield Tan mCopyOperationSubType = 118242cb88857ccc197286181ce85cbf0859ae7d71dGarfield Tan savedInstanceState.getInt(COPY_OPERATION_SUBTYPE_KEY); 119242cb88857ccc197286181ce85cbf0859ae7d71dGarfield Tan mPickTarget = savedInstanceState.getParcelable(PICK_TARGET_KEY); 120242cb88857ccc197286181ce85cbf0859ae7d71dGarfield Tan updateView(); 1216e565ffab8916af6c991c4f189a7ec438bce6978Jeff Sharkey } 12223ac60cd2b1beb59b6cd760b91c7e1b1f7e8fe49Garfield Tan 12323ac60cd2b1beb59b6cd760b91c7e1b1f7e8fe49Garfield Tan mInjector = ((PickActivity) getActivity()).getInjector(); 124242cb88857ccc197286181ce85cbf0859ae7d71dGarfield Tan } 1256e565ffab8916af6c991c4f189a7ec438bce6978Jeff Sharkey 126242cb88857ccc197286181ce85cbf0859ae7d71dGarfield Tan @Override 127242cb88857ccc197286181ce85cbf0859ae7d71dGarfield Tan public void onSaveInstanceState(final Bundle outState) { 128242cb88857ccc197286181ce85cbf0859ae7d71dGarfield Tan super.onSaveInstanceState(outState); 129242cb88857ccc197286181ce85cbf0859ae7d71dGarfield Tan outState.putInt(ACTION_KEY, mAction); 130242cb88857ccc197286181ce85cbf0859ae7d71dGarfield Tan outState.putInt(COPY_OPERATION_SUBTYPE_KEY, mCopyOperationSubType); 131242cb88857ccc197286181ce85cbf0859ae7d71dGarfield Tan outState.putParcelable(PICK_TARGET_KEY, mPickTarget); 132242cb88857ccc197286181ce85cbf0859ae7d71dGarfield Tan } 1336e565ffab8916af6c991c4f189a7ec438bce6978Jeff Sharkey 134676453ce79abc53cd2ec4d41cce3829e21697f49Daichi Hirono /** 135f8a5e08bfb793e0b1ec7e3ac455a6158ff968afcSteve McKay * @param action Which action defined in State is the picker shown for. 136676453ce79abc53cd2ec4d41cce3829e21697f49Daichi Hirono */ 137c8bdc7f8c692c22afa3312bc5ff672449b0a58a5Steve McKay public void setPickTarget( 138c8bdc7f8c692c22afa3312bc5ff672449b0a58a5Steve McKay int action, @OpType int copyOperationSubType, DocumentInfo pickTarget) { 1390af8afd3309538dec784ed0c9c35b252a8213123Steve McKay assert(copyOperationSubType != OPERATION_DELETE); 1400af8afd3309538dec784ed0c9c35b252a8213123Steve McKay 1414e2bb18dbb0ee7c24888e99e1cba386edbad1dc3Daichi Hirono mAction = action; 142c8bdc7f8c692c22afa3312bc5ff672449b0a58a5Steve McKay mCopyOperationSubType = copyOperationSubType; 1434e2bb18dbb0ee7c24888e99e1cba386edbad1dc3Daichi Hirono mPickTarget = pickTarget; 144f4943e16a80a7ae37ee19e9301017c15061df378Jeff Sharkey if (mContainer != null) { 1454e2bb18dbb0ee7c24888e99e1cba386edbad1dc3Daichi Hirono updateView(); 1464e2bb18dbb0ee7c24888e99e1cba386edbad1dc3Daichi Hirono } 1474e2bb18dbb0ee7c24888e99e1cba386edbad1dc3Daichi Hirono } 1484e2bb18dbb0ee7c24888e99e1cba386edbad1dc3Daichi Hirono 1494e2bb18dbb0ee7c24888e99e1cba386edbad1dc3Daichi Hirono /** 1504e2bb18dbb0ee7c24888e99e1cba386edbad1dc3Daichi Hirono * Applies the state of fragment to the view components. 1514e2bb18dbb0ee7c24888e99e1cba386edbad1dc3Daichi Hirono */ 1524e2bb18dbb0ee7c24888e99e1cba386edbad1dc3Daichi Hirono private void updateView() { 1534e2bb18dbb0ee7c24888e99e1cba386edbad1dc3Daichi Hirono switch (mAction) { 154f8a5e08bfb793e0b1ec7e3ac455a6158ff968afcSteve McKay case State.ACTION_OPEN_TREE: 1554e2bb18dbb0ee7c24888e99e1cba386edbad1dc3Daichi Hirono mPick.setText(R.string.button_select); 1564e2bb18dbb0ee7c24888e99e1cba386edbad1dc3Daichi Hirono mCancel.setVisibility(View.GONE); 1574e2bb18dbb0ee7c24888e99e1cba386edbad1dc3Daichi Hirono break; 158ae96780a8909476dca709b88dbae5ec9a2f0632cBen Kwa case State.ACTION_PICK_COPY_DESTINATION: 159bc7eb5fc39b5555eedc7d7b3591687343ecda18dTomasz Mikolajewski int titleId; 160bc7eb5fc39b5555eedc7d7b3591687343ecda18dTomasz Mikolajewski switch (mCopyOperationSubType) { 161bc7eb5fc39b5555eedc7d7b3591687343ecda18dTomasz Mikolajewski case OPERATION_COPY: 162bc7eb5fc39b5555eedc7d7b3591687343ecda18dTomasz Mikolajewski titleId = R.string.button_copy; 163bc7eb5fc39b5555eedc7d7b3591687343ecda18dTomasz Mikolajewski break; 164bc7eb5fc39b5555eedc7d7b3591687343ecda18dTomasz Mikolajewski case OPERATION_COMPRESS: 165bc7eb5fc39b5555eedc7d7b3591687343ecda18dTomasz Mikolajewski titleId = R.string.button_compress; 166bc7eb5fc39b5555eedc7d7b3591687343ecda18dTomasz Mikolajewski break; 167bc7eb5fc39b5555eedc7d7b3591687343ecda18dTomasz Mikolajewski case OPERATION_EXTRACT: 168bc7eb5fc39b5555eedc7d7b3591687343ecda18dTomasz Mikolajewski titleId = R.string.button_extract; 169bc7eb5fc39b5555eedc7d7b3591687343ecda18dTomasz Mikolajewski break; 170bc7eb5fc39b5555eedc7d7b3591687343ecda18dTomasz Mikolajewski case OPERATION_MOVE: 171bc7eb5fc39b5555eedc7d7b3591687343ecda18dTomasz Mikolajewski titleId = R.string.button_move; 172bc7eb5fc39b5555eedc7d7b3591687343ecda18dTomasz Mikolajewski break; 173bc7eb5fc39b5555eedc7d7b3591687343ecda18dTomasz Mikolajewski default: 174bc7eb5fc39b5555eedc7d7b3591687343ecda18dTomasz Mikolajewski throw new UnsupportedOperationException(); 175bc7eb5fc39b5555eedc7d7b3591687343ecda18dTomasz Mikolajewski } 176bc7eb5fc39b5555eedc7d7b3591687343ecda18dTomasz Mikolajewski mPick.setText(titleId); 1774e2bb18dbb0ee7c24888e99e1cba386edbad1dc3Daichi Hirono mCancel.setVisibility(View.VISIBLE); 1784e2bb18dbb0ee7c24888e99e1cba386edbad1dc3Daichi Hirono break; 1794e2bb18dbb0ee7c24888e99e1cba386edbad1dc3Daichi Hirono default: 180f4943e16a80a7ae37ee19e9301017c15061df378Jeff Sharkey mContainer.setVisibility(View.GONE); 1814e2bb18dbb0ee7c24888e99e1cba386edbad1dc3Daichi Hirono return; 1824e2bb18dbb0ee7c24888e99e1cba386edbad1dc3Daichi Hirono } 1834e2bb18dbb0ee7c24888e99e1cba386edbad1dc3Daichi Hirono 1844e2bb18dbb0ee7c24888e99e1cba386edbad1dc3Daichi Hirono if (mPickTarget != null && ( 185f8a5e08bfb793e0b1ec7e3ac455a6158ff968afcSteve McKay mAction == State.ACTION_OPEN_TREE || 1864e2bb18dbb0ee7c24888e99e1cba386edbad1dc3Daichi Hirono mPickTarget.isCreateSupported())) { 1874e2bb18dbb0ee7c24888e99e1cba386edbad1dc3Daichi Hirono mContainer.setVisibility(View.VISIBLE); 1884e2bb18dbb0ee7c24888e99e1cba386edbad1dc3Daichi Hirono } else { 1894e2bb18dbb0ee7c24888e99e1cba386edbad1dc3Daichi Hirono mContainer.setVisibility(View.GONE); 1906e565ffab8916af6c991c4f189a7ec438bce6978Jeff Sharkey } 1916e565ffab8916af6c991c4f189a7ec438bce6978Jeff Sharkey } 1926e565ffab8916af6c991c4f189a7ec438bce6978Jeff Sharkey} 193