| Index: chrome/android/java_staging/src/org/chromium/chrome/browser/bookmark/AddEditBookmarkFragment.java
|
| diff --git a/chrome/android/java_staging/src/org/chromium/chrome/browser/bookmark/AddEditBookmarkFragment.java b/chrome/android/java_staging/src/org/chromium/chrome/browser/bookmark/AddEditBookmarkFragment.java
|
| new file mode 100644
|
| index 0000000000000000000000000000000000000000..6e6dbba149cb753042223639e350e56f6849faa7
|
| --- /dev/null
|
| +++ b/chrome/android/java_staging/src/org/chromium/chrome/browser/bookmark/AddEditBookmarkFragment.java
|
| @@ -0,0 +1,738 @@
|
| +// Copyright 2015 The Chromium Authors. All rights reserved.
|
| +// Use of this source code is governed by a BSD-style license that can be
|
| +// found in the LICENSE file.
|
| +
|
| +package org.chromium.chrome.browser.bookmark;
|
| +
|
| +import static org.chromium.chrome.browser.ChromeBrowserProviderClient.INVALID_BOOKMARK_ID;
|
| +
|
| +import android.app.AlertDialog;
|
| +import android.content.ContentUris;
|
| +import android.content.ContentValues;
|
| +import android.content.Context;
|
| +import android.content.DialogInterface;
|
| +import android.content.res.Resources;
|
| +import android.net.Uri;
|
| +import android.os.Bundle;
|
| +import android.provider.Browser;
|
| +import android.text.Editable;
|
| +import android.text.TextUtils;
|
| +import android.text.TextWatcher;
|
| +import android.util.Log;
|
| +import android.view.LayoutInflater;
|
| +import android.view.View;
|
| +import android.view.View.OnClickListener;
|
| +import android.view.ViewGroup;
|
| +import android.view.inputmethod.InputMethodManager;
|
| +import android.widget.Button;
|
| +import android.widget.EditText;
|
| +import android.widget.TextView;
|
| +
|
| +import com.google.android.apps.chrome.R;
|
| +
|
| +import org.chromium.base.VisibleForTesting;
|
| +import org.chromium.chrome.browser.ChromeBrowserProvider;
|
| +import org.chromium.chrome.browser.ChromeBrowserProvider.BookmarkNode;
|
| +import org.chromium.chrome.browser.ChromeBrowserProviderClient;
|
| +
|
| +import javax.annotation.Nullable;
|
| +
|
| +/**
|
| + * UI container that manages adding or editing bookmark nodes.
|
| + */
|
| +public class AddEditBookmarkFragment extends AsyncTaskFragment implements OnClickListener {
|
| + private static final String TAG = "AddEditBookmarkFragment";
|
| +
|
| + /**
|
| + * Defines the constants used as arguments to this fragment.
|
| + * @see android.app.Fragment#setArguments(Bundle)
|
| + */
|
| + private static class Arguments {
|
| + private Arguments() {}
|
| +
|
| + public static final String MODE = "mode";
|
| + public static final String ID = "id";
|
| + public static final String NAME = "name";
|
| + public static final String URL = "url";
|
| + public static final String PARENT_FOLDER_ID = "parentId";
|
| + public static final String PARENT_FOLDER_NAME = "parentName";
|
| + }
|
| +
|
| + /**
|
| + * Determines the operating mode/UI of this fragment.
|
| + */
|
| + private enum Mode {
|
| + ADD_BOOKMARK,
|
| + EDIT_BOOKMARK,
|
| + ADD_FOLDER(true),
|
| + EDIT_FOLDER(true);
|
| +
|
| + private final boolean mIsFolder;
|
| +
|
| + private Mode() {
|
| + mIsFolder = false;
|
| + }
|
| +
|
| + private Mode(boolean isFolder) {
|
| + mIsFolder = isFolder;
|
| + }
|
| +
|
| + /** @return Whether this mode is operating on a folder (creation or editing). */
|
| + protected boolean isFolder() {
|
| + return mIsFolder;
|
| + }
|
| + }
|
| +
|
| + private Button mFolderInput;
|
| + private Button mRemoveButton;
|
| + private Button mOkButton;
|
| + private Button mCancelButton;
|
| +
|
| + private EditText mTitleInput;
|
| + private EditText mUrlInput;
|
| +
|
| + /** The initial name of a bookmark (will only be used if adding a new node). */
|
| + private String mInitialName;
|
| +
|
| + /** The initial URL of a bookmark (will only be used if adding a new non-folder node). */
|
| + private String mInitialUrl;
|
| +
|
| + private long mParentFolderId = INVALID_BOOKMARK_ID;
|
| +
|
| + /** The name of the parent folder to this bookmark. */
|
| + private String mParentFolderName;
|
| +
|
| + /** The mode of the current activity to distinguish between adding vs editing. */
|
| + private Mode mActivityMode = Mode.ADD_BOOKMARK;
|
| +
|
| + /**
|
| + * The ID of the current bookmark being edited (if adding a new bookmark then this will
|
| + * be null).
|
| + */
|
| + private Long mBookmarkId;
|
| +
|
| + /** The listener that will be notified when the actions of this fragment are completed. */
|
| + private OnActionListener mActionListener;
|
| +
|
| + /** Lock for synchronizing calls to the loaded status checks. */
|
| + private final Object mLoadedLock = new Object();
|
| + private boolean mBookmarkNodeLoaded = false;
|
| + private boolean mDefaultFolderLoaded = false;
|
| +
|
| + /**
|
| + * Creates a new add bookmark folder fragment.
|
| + *
|
| + * @param parentFolderId The ID of the default parent folder for the new folder.
|
| + * @param parentFolderName The name of the default parent folder for the new folder.
|
| + * @return An initialized add new bookmark folder fragment.
|
| + */
|
| + public static AddEditBookmarkFragment newAddNewFolderInstance(
|
| + long parentFolderId, String parentFolderName) {
|
| + AddEditBookmarkFragment fragment = new AddEditBookmarkFragment();
|
| + Bundle arguments = new Bundle();
|
| + arguments.putSerializable(Arguments.MODE, Mode.ADD_FOLDER);
|
| + arguments.putLong(Arguments.PARENT_FOLDER_ID, parentFolderId);
|
| + arguments.putString(Arguments.PARENT_FOLDER_NAME, parentFolderName);
|
| + fragment.setArguments(arguments);
|
| + return fragment;
|
| + }
|
| +
|
| + /**
|
| + * Creates a new editing bookmark fragment where all the details of the bookmark node are to
|
| + * be loaded from the model.
|
| + *
|
| + * @param isFolder Whether the node being edited is a folder.
|
| + * @param bookmarkId The ID of the node being edited.
|
| + * @return An initialized edit bookmark fragment.
|
| + */
|
| + public static AddEditBookmarkFragment newEditInstance(boolean isFolder, long bookmarkId) {
|
| + AddEditBookmarkFragment fragment = new AddEditBookmarkFragment();
|
| + Bundle arguments = new Bundle();
|
| + arguments.putSerializable(Arguments.MODE, isFolder ? Mode.EDIT_FOLDER : Mode.EDIT_BOOKMARK);
|
| + arguments.putLong(Arguments.ID, bookmarkId);
|
| + fragment.setArguments(arguments);
|
| + return fragment;
|
| + }
|
| +
|
| + /**
|
| + * Creates a new add/edit bookmark fragment with the given details.
|
| + *
|
| + * @param isFolder Whether the node being edited is a folder.
|
| + * @param bookmarkId The ID of the node being edited (or null if adding a new bookmark node).
|
| + * @param name The name of the bookmark being added/edited.
|
| + * @param url The url of the bookmark being added/edited (not applicable if isFolder is set)
|
| + * @return An initialized add or edit bookmark fragment.
|
| + */
|
| + public static AddEditBookmarkFragment newInstance(
|
| + boolean isFolder,
|
| + @Nullable Long bookmarkId,
|
| + @Nullable String name,
|
| + @Nullable String url) {
|
| + AddEditBookmarkFragment fragment = new AddEditBookmarkFragment();
|
| + Bundle arguments = new Bundle();
|
| + if (bookmarkId == null || bookmarkId == INVALID_BOOKMARK_ID) {
|
| + arguments.putSerializable(
|
| + Arguments.MODE, isFolder ? Mode.ADD_FOLDER : Mode.ADD_BOOKMARK);
|
| + } else {
|
| + arguments.putSerializable(
|
| + Arguments.MODE, isFolder ? Mode.EDIT_FOLDER : Mode.EDIT_BOOKMARK);
|
| + arguments.putLong(Arguments.ID, bookmarkId);
|
| + }
|
| + if (name != null) arguments.putString(Arguments.NAME, name);
|
| + if (url != null) arguments.putString(Arguments.URL, url);
|
| + fragment.setArguments(arguments);
|
| + return fragment;
|
| + }
|
| +
|
| + /**
|
| + * Sets the action listener for this fragment.
|
| + * @param listener The listener to be set.
|
| + */
|
| + public void setOnActionListener(OnActionListener listener) {
|
| + mActionListener = listener;
|
| + }
|
| +
|
| + /**
|
| + * Retrieves the current action listener for this fragment.
|
| + * Used by testing to intercept calls as a proxy.
|
| + */
|
| + @VisibleForTesting
|
| + public OnActionListener getOnActionListenerForTest() {
|
| + return mActionListener;
|
| + }
|
| +
|
| + /**
|
| + * @return Whether the default bookmark folder has been loaded.
|
| + */
|
| + protected boolean isDefaultFolderLoaded() {
|
| + synchronized (mLoadedLock) {
|
| + return mDefaultFolderLoaded;
|
| + }
|
| + }
|
| +
|
| + /**
|
| + * @return Whether the bookmark node has been loaded from the backend model.
|
| + */
|
| + protected boolean isBookmarkNodeLoaded() {
|
| + synchronized (mLoadedLock) {
|
| + return mBookmarkNodeLoaded;
|
| + }
|
| + }
|
| +
|
| + @Override
|
| + public void onCreate(Bundle savedInstanceState) {
|
| + super.onCreate(savedInstanceState);
|
| +
|
| + Bundle args = getArguments();
|
| + mActivityMode = (Mode) args.get(Arguments.MODE);
|
| + if (mActivityMode == null) {
|
| + Log.e(getClass().getName(), "Created new AddEditBookmarkFragment without a mode "
|
| + + "defined. Make sure arguments are correctly populated.");
|
| + mActivityMode = Mode.ADD_BOOKMARK;
|
| + return;
|
| + }
|
| + if (args.containsKey(Arguments.ID)) mBookmarkId = args.getLong(Arguments.ID);
|
| + mParentFolderId = args.getLong(Arguments.PARENT_FOLDER_ID, INVALID_BOOKMARK_ID);
|
| + mParentFolderName = args.getString(Arguments.PARENT_FOLDER_NAME, null);
|
| + mInitialName = args.getString(Arguments.NAME, null);
|
| + mInitialUrl = args.getString(Arguments.URL, null);
|
| + }
|
| +
|
| + @Override
|
| + public View onCreateView(
|
| + LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState) {
|
| + return inflater.inflate(R.layout.add_bookmark, container, false);
|
| + }
|
| +
|
| + @Override
|
| + public void onViewCreated(View view, Bundle savedInstanceState) {
|
| + super.onViewCreated(view, savedInstanceState);
|
| +
|
| + mRemoveButton = (Button) getView().findViewById(R.id.remove);
|
| + mRemoveButton.setOnClickListener(this);
|
| + mOkButton = (Button) getView().findViewById(R.id.ok);
|
| + mOkButton.setOnClickListener(this);
|
| + mCancelButton = (Button) getView().findViewById(R.id.cancel);
|
| + mCancelButton.setOnClickListener(this);
|
| + mTitleInput = (EditText) getView().findViewById(R.id.bookmark_title_input);
|
| + clearErrorWhenNonEmpty(mTitleInput);
|
| + mUrlInput = (EditText) getView().findViewById(R.id.bookmark_url_input);
|
| + clearErrorWhenNonEmpty(mUrlInput);
|
| + mFolderInput = (Button) getView().findViewById(R.id.bookmark_folder_select);
|
| + mFolderInput.setOnClickListener(this);
|
| + }
|
| +
|
| + @Override
|
| + public void onActivityCreated(Bundle savedInstanceState) {
|
| + super.onActivityCreated(savedInstanceState);
|
| +
|
| + int actionTitleTextResId = R.string.edit_bookmark;
|
| + int bookmarkInputDescResId = R.string.accessibility_bookmark_title_textbox;
|
| +
|
| + switch (mActivityMode) {
|
| + case ADD_BOOKMARK:
|
| + actionTitleTextResId = R.string.add_bookmark;
|
| + bookmarkInputDescResId = R.string.accessibility_bookmark_title_textbox;
|
| + break;
|
| + case EDIT_BOOKMARK:
|
| + actionTitleTextResId = R.string.edit_bookmark;
|
| + bookmarkInputDescResId = R.string.accessibility_bookmark_title_textbox;
|
| + break;
|
| + case ADD_FOLDER:
|
| + actionTitleTextResId = R.string.add_folder;
|
| + bookmarkInputDescResId = R.string.accessibility_bookmark_folder_name_textbox;
|
| + break;
|
| + case EDIT_FOLDER:
|
| + actionTitleTextResId = R.string.edit_folder;
|
| + bookmarkInputDescResId = R.string.accessibility_bookmark_folder_name_textbox;
|
| + break;
|
| + default:
|
| + assert false;
|
| + }
|
| +
|
| + TextView actionTitle = (TextView) getView().findViewById(R.id.bookmark_action_title);
|
| + EditText titleInput = (EditText) getView().findViewById(R.id.bookmark_title_input);
|
| + actionTitle.setText(actionTitleTextResId);
|
| + titleInput.setContentDescription(getResources().getString(bookmarkInputDescResId));
|
| +
|
| + if (mActivityMode == Mode.ADD_BOOKMARK || mActivityMode == Mode.ADD_FOLDER) {
|
| + mRemoveButton.setVisibility(View.GONE);
|
| + }
|
| + if (mActivityMode.isFolder()) {
|
| + hideUrlInputRow();
|
| + }
|
| +
|
| + initializeFolderInputContent(savedInstanceState);
|
| + initializeStateFromIntent(savedInstanceState);
|
| +
|
| + if (mActivityMode == Mode.ADD_FOLDER) {
|
| + mTitleInput.post(new Runnable() {
|
| + @Override
|
| + public void run() {
|
| + if (getActivity() == null) return;
|
| +
|
| + mTitleInput.requestFocus();
|
| + InputMethodManager imm = (InputMethodManager) getActivity().getSystemService(
|
| + Context.INPUT_METHOD_SERVICE);
|
| + imm.showSoftInput(mTitleInput, InputMethodManager.SHOW_IMPLICIT);
|
| + }
|
| + });
|
| + }
|
| + }
|
| +
|
| + private void hideUrlInputRow() {
|
| + getView().findViewById(R.id.bookmark_url_label).setVisibility(View.GONE);
|
| + getView().findViewById(R.id.bookmark_url_input).setVisibility(View.GONE);
|
| + }
|
| +
|
| + private void initializeStateFromIntent(Bundle savedInstanceState) {
|
| + // If restoring from a previous state, do not set the fields to their initial values
|
| + // (allow the individual views to reset their values correctly).
|
| + if (savedInstanceState != null) {
|
| + return;
|
| + }
|
| +
|
| + if (!TextUtils.isEmpty(mInitialName)) mTitleInput.setText(mInitialName);
|
| + if (!TextUtils.isEmpty(mTitleInput.getText())) {
|
| + mTitleInput.setSelection(mTitleInput.getText().length());
|
| + }
|
| + if (!TextUtils.isEmpty(mInitialUrl)) mUrlInput.setText(mInitialUrl);
|
| + }
|
| +
|
| + private void initializeFolderInputContent(Bundle savedInstanceState) {
|
| + if (savedInstanceState != null) {
|
| + long savedParentId = savedInstanceState.getLong(
|
| + Arguments.PARENT_FOLDER_ID, INVALID_BOOKMARK_ID);
|
| + if (savedParentId != INVALID_BOOKMARK_ID) {
|
| + mParentFolderId = savedParentId;
|
| + mFolderInput.setText(savedInstanceState.getString(Arguments.PARENT_FOLDER_NAME));
|
| + return;
|
| + }
|
| + } else if (mParentFolderId != INVALID_BOOKMARK_ID && mParentFolderName != null) {
|
| + mFolderInput.setText(mParentFolderName);
|
| + return;
|
| + }
|
| +
|
| + // Start a new asynchronous fragment task to read the bookmark folder data.
|
| + if (!isFragmentAsyncTaskRunning() && !isDefaultFolderLoaded() && !isBookmarkNodeLoaded()) {
|
| + runFragmentAsyncTask(new LoadBookmarkNodeTask(
|
| + (mActivityMode == Mode.ADD_BOOKMARK || mActivityMode == Mode.ADD_FOLDER)
|
| + ? null : mBookmarkId),
|
| + getActivity().getString(R.string.loading_bookmark));
|
| + }
|
| + }
|
| +
|
| + @Override
|
| + public void onSaveInstanceState(Bundle outState) {
|
| + super.onSaveInstanceState(outState);
|
| +
|
| + if (!isVisible()) return;
|
| +
|
| + outState.putString(Arguments.PARENT_FOLDER_NAME, mFolderInput.getText().toString());
|
| + outState.putLong(Arguments.PARENT_FOLDER_ID, mParentFolderId);
|
| + }
|
| +
|
| + @Override
|
| + public void onClick(View v) {
|
| + if (mActionListener == null) {
|
| + Log.d(getClass().getName(), "No OnResultListener specified -- onClick == NoOp");
|
| + return;
|
| + }
|
| + String title = mTitleInput.getText().toString().trim();
|
| + String url = mUrlInput.getText().toString().trim();
|
| + if (v == mOkButton) {
|
| + if (!checkValidInputs(title, url)) return;
|
| + if (isFragmentAsyncTaskRunning()) {
|
| + Log.e(TAG, "Pending asynchronous task when trying to add/update bookmarks.");
|
| + return;
|
| + }
|
| +
|
| + ContentValues bookmarkValues = new ContentValues();
|
| + if (!mActivityMode.isFolder()) {
|
| + bookmarkValues.put(Browser.BookmarkColumns.URL, url);
|
| + }
|
| + bookmarkValues.put(Browser.BookmarkColumns.TITLE, title);
|
| + bookmarkValues.put(
|
| + ChromeBrowserProvider.BOOKMARK_PARENT_ID_PARAM, mParentFolderId);
|
| + bookmarkValues.put(
|
| + ChromeBrowserProvider.BOOKMARK_IS_FOLDER_PARAM, mActivityMode.isFolder());
|
| +
|
| + runFragmentAsyncTask(new InsertUpdateBookmarkTask(
|
| + bookmarkValues,
|
| + (mActivityMode == Mode.ADD_BOOKMARK || mActivityMode == Mode.ADD_FOLDER)
|
| + ? null : mBookmarkId),
|
| + getActivity().getString(R.string.saving_bookmark));
|
| +
|
| + } else if (v == mRemoveButton) {
|
| + if (mActivityMode == Mode.ADD_BOOKMARK) {
|
| + throw new AssertionError(
|
| + "The remove functionality should be disabled for new bookmarks.");
|
| + }
|
| +
|
| + if (isFragmentAsyncTaskRunning()) {
|
| + Log.e(TAG, "Pending asynchronous task when trying to delete bookmarks.");
|
| + return;
|
| + }
|
| +
|
| + runFragmentAsyncTask(new DeleteBookmarkTask(mBookmarkId),
|
| + getActivity().getString(R.string.removing_bookmark));
|
| +
|
| + } else if (v == mCancelButton) {
|
| + mActionListener.onCancel();
|
| + } else if (v == mFolderInput) {
|
| + mActionListener.triggerFolderSelection();
|
| + }
|
| + }
|
| +
|
| + /**
|
| + * Adds a listener to |textView| that will clear the TextView's error once the user types
|
| + * something.
|
| + * Note that we needed this function in EnhancedBookmarkAddEditFolderDialog.java and just
|
| + * duplicated there instead of sharing, because the old bookmark UI is supposed go away anyways.
|
| + * If you have found this message in the latest repository in 2016, you can come by Kibeom's
|
| + * desk and punch him.
|
| + */
|
| + private void clearErrorWhenNonEmpty(final TextView textView) {
|
| + textView.addTextChangedListener(new TextWatcher() {
|
| + @Override
|
| + public void afterTextChanged(Editable s) {
|
| + }
|
| +
|
| + @Override
|
| + public void beforeTextChanged(CharSequence s, int start, int count, int after) {
|
| + }
|
| +
|
| + @Override
|
| + public void onTextChanged(CharSequence s, int start, int before, int count) {
|
| + if (s.length() != 0) {
|
| + textView.setError(null);
|
| + }
|
| + }
|
| + });
|
| + }
|
| +
|
| + private boolean checkValidInputs(String title, String url) {
|
| + Resources resources = getResources();
|
| + boolean validInput = true;
|
| + if (!mActivityMode.isFolder() && url.isEmpty()) {
|
| + mUrlInput.setError(resources.getText(R.string.bookmark_missing_url));
|
| + mUrlInput.requestFocus();
|
| + validInput = false;
|
| + }
|
| + if (title.isEmpty()) {
|
| + mTitleInput.setError(resources.getText(R.string.bookmark_missing_title));
|
| + mTitleInput.requestFocus();
|
| + validInput = false;
|
| + }
|
| + return validInput;
|
| + }
|
| +
|
| + @VisibleForTesting
|
| + public boolean isLoadingBookmarks() {
|
| + return mCurrentTask instanceof LoadBookmarkNodeTask;
|
| + }
|
| +
|
| + /**
|
| + * Sets the parent folder information for this bookmark node (updating the view if present).
|
| + * @param id The ID of the parent folder.
|
| + * @param name The name of the parent folder.
|
| + */
|
| + protected void setParentFolderInfo(long id, String name) {
|
| + mParentFolderName = name;
|
| + mParentFolderId = id;
|
| + if (isVisible()) {
|
| + mFolderInput.setText(name);
|
| + }
|
| + }
|
| +
|
| + /**
|
| + * @return The ID of the parent node of this bookmark.
|
| + */
|
| + protected long getParentFolderId() {
|
| + return mParentFolderId;
|
| + }
|
| +
|
| + /**
|
| + * @return boolean Whether a folder or bookmark is being created/edited.
|
| + */
|
| + protected boolean isFolder() {
|
| + return mActivityMode.isFolder();
|
| + }
|
| +
|
| + private void handleGetBookmarkNode(BookmarkNode result) {
|
| + if (getActivity() == null || getActivity().isFinishing()) return;
|
| +
|
| + if (result == null) {
|
| + AlertDialog.Builder builder = new AlertDialog.Builder(getActivity())
|
| + .setMessage(getActivity().getResources().getText(R.string.invalid_bookmark))
|
| + .setPositiveButton(getActivity().getResources().getText(R.string.ok),
|
| + new DialogInterface.OnClickListener() {
|
| + @Override
|
| + public void onClick(DialogInterface dialog, int id) {
|
| + getActivity().finish();
|
| + }
|
| + }).setOnCancelListener(new DialogInterface.OnCancelListener() {
|
| + @Override
|
| + public void onCancel(DialogInterface dialog) {
|
| + getActivity().finish();
|
| + }
|
| + });
|
| + builder.create().show();
|
| + return;
|
| + }
|
| +
|
| + mTitleInput.setText(result.name());
|
| + if (result.isUrl()) mUrlInput.setText(result.url());
|
| + if (result.parent() != null) {
|
| + setParentFolderInfo(result.parent().id(), result.parent().name());
|
| + }
|
| +
|
| + synchronized (mLoadedLock) {
|
| + mBookmarkNodeLoaded = true;
|
| + }
|
| + }
|
| +
|
| + private void handleDefaultBookmarkNode(BookmarkNode result) {
|
| + if (getActivity() == null || getActivity().isFinishing()) return;
|
| +
|
| + if (result != null) {
|
| + setParentFolderInfo(result.id(), result.name());
|
| + } else {
|
| + mFolderInput.setError(getResources().getText(R.string.default_folder_error));
|
| + }
|
| +
|
| + synchronized (mLoadedLock) {
|
| + mDefaultFolderLoaded = true;
|
| + }
|
| + }
|
| +
|
| + /**
|
| + * Asynchronously retrieves the requested bookmark node showing a progress dialog if the task
|
| + * takes too long.
|
| + */
|
| + private class LoadBookmarkNodeTask extends FragmentAsyncTask {
|
| + private final Context mContext;
|
| + private final Long mBookmarkId;
|
| + private BookmarkNode mResult;
|
| +
|
| + /**
|
| + * @param bookmarkId Id of the bookmark node to retrieve. Will retrieve the default bookmark
|
| + * folder if null.
|
| + */
|
| + LoadBookmarkNodeTask(Long bookmarkId) {
|
| + // The activity might be temporarily detached during the background operation if the
|
| + // screen is rotated. Make sure to use a valid context even in that case.
|
| + mContext = getActivity().getApplicationContext();
|
| + mBookmarkId = bookmarkId;
|
| + }
|
| +
|
| + @Override
|
| + protected void runBackgroundTask() {
|
| + mResult = (mBookmarkId == null)
|
| + ? ChromeBrowserProviderClient.getDefaultBookmarkFolder(mContext)
|
| + : ChromeBrowserProviderClient.getBookmarkNode(mContext, mBookmarkId,
|
| + ChromeBrowserProviderClient.GET_PARENT);
|
| + }
|
| +
|
| + @Override
|
| + protected void onTaskFinished() {
|
| + if (mBookmarkId == null) {
|
| + handleDefaultBookmarkNode(mResult);
|
| + } else {
|
| + handleGetBookmarkNode(mResult);
|
| + }
|
| + }
|
| +
|
| + @Override
|
| + protected void setDependentUIEnabled(boolean enabled) {
|
| + mOkButton.setEnabled(enabled);
|
| + mFolderInput.setEnabled(enabled);
|
| +
|
| + switch (mActivityMode) {
|
| + case ADD_BOOKMARK:
|
| + case ADD_FOLDER:
|
| + break;
|
| + case EDIT_BOOKMARK:
|
| + case EDIT_FOLDER:
|
| + mTitleInput.setEnabled(enabled);
|
| + mUrlInput.setEnabled(enabled);
|
| + mRemoveButton.setEnabled(enabled);
|
| +
|
| + if (!enabled) {
|
| + mUrlInput.setText(R.string.loading_bookmark);
|
| + mTitleInput.setText(R.string.loading_bookmark);
|
| + }
|
| + break;
|
| + default:
|
| + assert false;
|
| + }
|
| + }
|
| + }
|
| +
|
| + /**
|
| + * Asynchronously inserts or updates a bookmark showing a progress dialog if the task takes
|
| + * too long.
|
| + */
|
| + private class InsertUpdateBookmarkTask extends FragmentAsyncTask {
|
| + private final Context mContext;
|
| + private final ContentValues mBookmarkValues;
|
| + private Long mBookmarkId;
|
| +
|
| + /**
|
| + * @param bookmarkValues Contents of the bookmark to be inserted or updated.
|
| + * @param bookmarkId Id of the bookmark node to update. If null the bookmark will be
|
| + * inserted.
|
| + */
|
| + InsertUpdateBookmarkTask(ContentValues bookmarkValues, Long bookmarkId) {
|
| + mContext = getActivity().getApplicationContext();
|
| + mBookmarkValues = bookmarkValues;
|
| + mBookmarkId = bookmarkId;
|
| + }
|
| +
|
| + @Override
|
| + protected void runBackgroundTask() {
|
| + Uri bookmarksUri = ChromeBrowserProvider.getBookmarksUri(mContext);
|
| + if (mBookmarkId == null) {
|
| + Uri response = mContext.getContentResolver().insert(
|
| + bookmarksUri, mBookmarkValues);
|
| + mBookmarkId = response != null ? ContentUris.parseId(response) :
|
| + INVALID_BOOKMARK_ID;
|
| + } else {
|
| + mContext.getContentResolver().update(
|
| + ContentUris.withAppendedId(bookmarksUri, mBookmarkId),
|
| + mBookmarkValues, null, null);
|
| + }
|
| + }
|
| +
|
| + @Override
|
| + protected void onTaskFinished() {
|
| + if (isFolder()) {
|
| + mActionListener.onFolderCreated(mBookmarkId, mTitleInput.getText().toString());
|
| + } else {
|
| + mActionListener.onNodeEdited(mBookmarkId);
|
| + }
|
| + }
|
| +
|
| + @Override
|
| + protected void setDependentUIEnabled(boolean enabled) {
|
| + mOkButton.setEnabled(enabled);
|
| + mRemoveButton.setEnabled(enabled);
|
| + mCancelButton.setEnabled(enabled);
|
| + mActionListener.setBackEnabled(enabled);
|
| + }
|
| + }
|
| +
|
| + /**
|
| + * Asynchronously deletes a bookmark showing a progress dialog if the task takes too long.
|
| + */
|
| + private class DeleteBookmarkTask extends FragmentAsyncTask {
|
| + private final Context mContext;
|
| + private final long mBookmarkId;
|
| +
|
| + DeleteBookmarkTask(long bookmarkId) {
|
| + mContext = getActivity().getApplicationContext();
|
| + mBookmarkId = bookmarkId;
|
| + }
|
| +
|
| + @Override
|
| + protected void runBackgroundTask() {
|
| + Uri bookmarksUri = ChromeBrowserProvider.getBookmarksUri(mContext);
|
| + mContext.getContentResolver().delete(
|
| + ContentUris.withAppendedId(bookmarksUri, mBookmarkId),
|
| + null, null);
|
| + }
|
| +
|
| + @Override
|
| + protected void onTaskFinished() {
|
| + mActionListener.onRemove();
|
| + }
|
| +
|
| + @Override
|
| + protected void setDependentUIEnabled(boolean enabled) {
|
| + mOkButton.setEnabled(enabled);
|
| + mRemoveButton.setEnabled(enabled);
|
| + mCancelButton.setEnabled(enabled);
|
| + mActionListener.setBackEnabled(enabled);
|
| + }
|
| + }
|
| +
|
| + /**
|
| + * Listener to handle actions triggered by this fragment.
|
| + */
|
| + public static interface OnActionListener {
|
| + /**
|
| + * Called when the addition/editing of this bookmark node has been canceled.
|
| + */
|
| + public void onCancel();
|
| +
|
| + /**
|
| + * The add/edit of this bookmark node was successful.
|
| + * @param id The ID of the newly added bookmark (or the ID of the existing
|
| + * bookmark being edited).
|
| + */
|
| + public void onNodeEdited(long id);
|
| +
|
| + /**
|
| + * The folder was succesfully created.
|
| + * @param id The ID of the newly added folder.
|
| + * @param name Name of the folder as well.
|
| + */
|
| + public void onFolderCreated(long id, String name);
|
| +
|
| + /**
|
| + * Triggered when the user asks select a different bookmark folder for this node.
|
| + */
|
| + public void triggerFolderSelection();
|
| +
|
| + /**
|
| + * Called when the bookmark node has been removed.
|
| + */
|
| + public void onRemove();
|
| +
|
| + /**
|
| + * Called when the fragment wants to temporarily disable the back button.
|
| + * Done only while performing an asynchronous task that changes the bookmark model.
|
| + */
|
| + public void setBackEnabled(boolean enabled);
|
| + }
|
| +}
|
|
|