--- /dev/null
+<?xml version="1.0" encoding="utf-8"?>
+<LinearLayout
+ xmlns:android="http://schemas.android.com/apk/res/android"
+ android:layout_width="fill_parent"
+ android:layout_height="fill_parent"
+ android:layout_margin="@dimen/standard_margin">
+
+ <ListView
+ android:id="@+id/file_actions_list"
+ android:layout_width="match_parent"
+ android:layout_height="match_parent" >
+ </ListView>
+
+</LinearLayout>
\ No newline at end of file
--- /dev/null
+<?xml version="1.0" encoding="utf-8"?>
+<TextView xmlns:android="http://schemas.android.com/apk/res/android"
+ android:id="@android:id/text1"
+ android:layout_width="match_parent"
+ android:layout_height="wrap_content"
+ android:textAppearance="?android:attr/textAppearanceListItemSmall"
+ android:textColor="@color/dialog_list_item"
+ android:textSize="16sp"
+ android:gravity="center_vertical"
+ android:paddingLeft="@dimen/standard_padding"
+ android:paddingRight="@dimen/standard_padding"
+ android:minHeight="48dp"/>
\ No newline at end of file
<!-- Colors -->
<color name="color_accent">@color/owncloud_blue_accent</color>
+ <color name="dialog_list_item">#1F1F1F</color>
<!-- standard material color definitions -->
<color name="primary">@color/owncloud_blue</color>
<item name="android:textColorPrimary">@color/primary</item>
</style>
- <style name="ownCloud.Dialog" parent="Theme.AppCompat.Light.Dialog">
-
- </style>
+ <style name="ownCloud.Dialog" parent="Theme.AppCompat.Light.Dialog" />
<style name="ownCloud.Button" parent="Widget.AppCompat.Button">
<item name="colorButtonNormal">@color/primary</item>
--- /dev/null
+package com.owncloud.android.ui.dialog;
+
+import android.support.v4.app.DialogFragment;
+import android.os.Bundle;
+import android.view.LayoutInflater;
+import android.view.Menu;
+import android.view.MenuItem;
+import android.view.View;
+import android.view.ViewGroup;
+import android.view.Window;
+import android.widget.AdapterView;
+import android.widget.AdapterView.OnItemClickListener;
+import android.widget.ArrayAdapter;
+import android.widget.ListView;
+
+import com.owncloud.android.R;
+import com.owncloud.android.ui.dialog.parcel.MenuItemParcelable;
+import com.owncloud.android.ui.dialog.parcel.MenuParcelable;
+
+import java.util.ArrayList;
+import java.util.List;
+
+/**
+ * Dialog for choosing a file action.
+ */
+public class FileActionsDialogFragment extends DialogFragment implements
+ OnItemClickListener {
+ private static final String ARG_ITEM_LIST = "ITEM_LIST";
+ private static final String ARG_FILE_POSITION = "FILE_POSITION";
+ public static final String FTAG_FILE_ACTIONS = "FILE_ACTIONS_FRAGMENT";
+
+ private List<MenuItemParcelable> menuItems;
+
+ private int filePosition;
+
+ private ListView mListView;
+
+ /**
+ * Listener interface for the file action fragment.
+ */
+ public interface FileActionsDialogFragmentListener {
+ public boolean onFileActionChosen(int menuId, int filePosition);
+ }
+
+ /**
+ * Public factory method to create new FileActionsDialogFragment instances.
+ *
+ * @param menu menu to be display.
+ * @return Dialog ready to show.
+ */
+ public static FileActionsDialogFragment newInstance(Menu menu, int filePosition) {
+ FileActionsDialogFragment fragment = new FileActionsDialogFragment();
+ Bundle args = new Bundle();
+
+ MenuParcelable menuParcelable = new MenuParcelable();
+ menuParcelable.setMenuItems(calculateMenuParcel(menu));
+
+ args.putParcelable(ARG_ITEM_LIST, menuParcelable);
+ args.putInt(ARG_FILE_POSITION, filePosition);
+
+ fragment.setArguments(args);
+ return fragment;
+ }
+
+ /**
+ * {@inheritDoc}
+ */
+ @Override
+ public void onCreate(Bundle savedInstanceState) {
+ super.onCreate(savedInstanceState);
+ setStyle(DialogFragment.STYLE_NORMAL, R.style.ownCloud_Dialog);
+ }
+
+ /**
+ * {@inheritDoc}
+ */
+ @Override
+ public View onCreateView(LayoutInflater inflater, ViewGroup container,
+ Bundle savedInstanceState) {
+ View view = inflater.inflate(R.layout.file_actions, null, false);
+ mListView = (ListView) view.findViewById(R.id.file_actions_list);
+
+ getDialog().getWindow().requestFeature(Window.FEATURE_NO_TITLE);
+ return view;
+ }
+
+
+ /**
+ * {@inheritDoc}
+ */
+ @Override
+ public void onActivityCreated(Bundle savedInstanceState) {
+ super.onActivityCreated(savedInstanceState);
+
+ filePosition = getArguments().getInt(ARG_FILE_POSITION);
+
+ MenuParcelable menu = getArguments().getParcelable(ARG_ITEM_LIST);
+ menuItems = menu.getMenuItems();
+ List<String> stringList = new ArrayList<String>();
+ for (int i = 0; i < menuItems.size(); i++) {
+ stringList.add(menuItems.get(i).getMenuText());
+ }
+
+ ArrayAdapter<String> adapter = new ArrayAdapter<String>(getActivity(),
+ R.layout.simple_dialog_list_item, stringList);
+
+ mListView.setAdapter(adapter);
+
+ mListView.setOnItemClickListener(this);
+ }
+
+ /**
+ * {@inheritDoc}
+ */
+ @Override
+ public void onItemClick(AdapterView<?> parent, View view, int position, long id) {
+ dismiss();
+ ((FileActionsDialogFragmentListener) getTargetFragment()).onFileActionChosen(menuItems.get(position).getMenuItemId(), filePosition);
+ }
+
+ /**
+ * calculates a parcelable list of MenuItemParcelable based on the given menu and the visibility of the menu items.
+ *
+ * @param menu the menu to be displayed
+ * @return a filtered List of parcelables based on the menu
+ */
+ private static List<MenuItemParcelable> calculateMenuParcel(Menu menu) {
+ int index = 0;
+ boolean hasNext = true;
+ List<MenuItemParcelable> itemList = new ArrayList<MenuItemParcelable>();
+ MenuParcelable menuParcelable = new MenuParcelable();
+ try {
+ while (hasNext) {
+ MenuItem item = menu.getItem(index);
+ if (item.isVisible()) {
+ itemList.add(new MenuItemParcelable(item));
+ }
+ index++;
+ }
+ } catch (IndexOutOfBoundsException iobe) {
+ // reach the end of the item list
+ }
+
+ return itemList;
+ }
+}
--- /dev/null
+package com.owncloud.android.ui.dialog.parcel;
+
+import android.os.Parcel;
+import android.os.Parcelable;
+import android.view.MenuItem;
+
+public class MenuItemParcelable implements Parcelable {
+ int menuItemId;
+
+ String menuText;
+
+ public MenuItemParcelable() {
+ }
+
+ public MenuItemParcelable(MenuItem menuItem) {
+ menuItemId = menuItem.getItemId();
+ menuText = menuItem.getTitle().toString();
+ menuItem.getMenuInfo();
+ }
+
+ public MenuItemParcelable(Parcel read) {
+ menuItemId = read.readInt();
+ }
+
+ public void setMenuItemId(int id) {
+ menuItemId = id;
+ }
+
+ public int getMenuItemId() {
+ return menuItemId;
+ }
+
+ public String getMenuText() {
+ return menuText;
+ }
+
+ public void setMenuText(String menuText) {
+ this.menuText = menuText;
+ }
+
+ public static final Parcelable.Creator<MenuItemParcelable> CREATOR =
+ new Parcelable.Creator<MenuItemParcelable>() {
+
+ @Override
+ public MenuItemParcelable createFromParcel(Parcel source) {
+ return new MenuItemParcelable(source);
+ }
+
+ @Override
+ public MenuItemParcelable[] newArray(int size) {
+ return new MenuItemParcelable[size];
+ }
+ };
+
+ @Override
+ public int describeContents() {
+ return 0;
+ }
+
+ @Override
+ public void writeToParcel(Parcel dest, int flags) {
+ dest.writeInt(menuItemId);
+ }
+}
--- /dev/null
+package com.owncloud.android.ui.dialog.parcel;
+
+import android.os.Parcel;
+import android.os.Parcelable;
+
+import java.util.ArrayList;
+import java.util.List;
+
+public class MenuParcelable implements Parcelable {
+
+ private List<MenuItemParcelable> menuItems = new ArrayList<MenuItemParcelable>();
+
+ public List<MenuItemParcelable> getMenuItems() {
+ return menuItems;
+ }
+
+ public void setMenuItems(List<MenuItemParcelable> menuItems) {
+ this.menuItems = menuItems;
+ }
+
+ public MenuParcelable() {
+ menuItems = new ArrayList<MenuItemParcelable>();
+ }
+
+ public MenuParcelable(Parcel in) {
+ in.readTypedList(menuItems, MenuItemParcelable.CREATOR);
+ }
+
+ public static final Parcelable.Creator<MenuParcelable> CREATOR = new Parcelable.Creator<MenuParcelable>() {
+
+ @Override
+ public MenuParcelable createFromParcel(Parcel in) {
+ return new MenuParcelable(in);
+ }
+
+ @Override
+ public MenuParcelable[] newArray(int size) {
+ return new MenuParcelable[size];
+ }
+ };
+
+ @Override
+ public int describeContents() {
+ return 0;
+ }
+
+ @Override
+ public void writeToParcel(Parcel outParcel, int flags) {
+ outParcel.writeTypedList(menuItems);
+ }
+}
import android.os.Bundle;
import android.support.v4.widget.SwipeRefreshLayout;
import android.view.ContextMenu;
+import android.view.Menu;
import android.view.MenuInflater;
import android.view.MenuItem;
import android.view.View;
import android.widget.AdapterView;
import android.widget.AdapterView.AdapterContextMenuInfo;
+import android.widget.PopupMenu;
import com.owncloud.android.R;
import com.owncloud.android.authentication.AccountUtils;
import com.owncloud.android.ui.activity.OnEnforceableRefreshListener;
import com.owncloud.android.ui.adapter.FileListListAdapter;
import com.owncloud.android.ui.dialog.ConfirmationDialogFragment;
+import com.owncloud.android.ui.dialog.FileActionsDialogFragment;
import com.owncloud.android.ui.dialog.RemoveFileDialogFragment;
import com.owncloud.android.ui.dialog.RenameFileDialogFragment;
import com.owncloud.android.ui.preview.PreviewImageFragment;
import com.owncloud.android.ui.preview.PreviewMediaFragment;
+import com.owncloud.android.utils.DialogMenuItem;
import com.owncloud.android.utils.FileStorageUtils;
/**
*
* TODO refactor to get rid of direct dependency on FileDisplayActivity
*/
-public class OCFileListFragment extends ExtendedListFragment {
+public class OCFileListFragment extends ExtendedListFragment implements FileActionsDialogFragment.FileActionsDialogFragmentListener {
private static final String TAG = OCFileListFragment.class.getSimpleName();
);
setListAdapter(mAdapter);
- registerForContextMenu();
+ registerLongClickListener();
}
+ private void registerLongClickListener() {
+ getListView().setOnItemLongClickListener(new AdapterView.OnItemLongClickListener() {
+ public boolean onItemLongClick(AdapterView<?> arg0, View v,
+ int index, long arg3) {
+ showFileAction(index);
+ return true;
+ }
+ });
+ }
+
+
+ private void showFileAction(int fileIndex) {
+ Bundle args = getArguments();
+ PopupMenu pm = new PopupMenu(getActivity(),null);
+ Menu menu = pm.getMenu();
+
+ boolean allowContextualActions =
+ (args == null) ? true : args.getBoolean(ARG_ALLOW_CONTEXTUAL_ACTIONS, true);
+
+ if (allowContextualActions) {
+ MenuInflater inflater = getActivity().getMenuInflater();
+
+ inflater.inflate(R.menu.file_actions_menu, menu);
+ OCFile targetFile = (OCFile) mAdapter.getItem(fileIndex);
+
+ if (mContainerActivity.getStorageManager() != null) {
+ FileMenuFilter mf = new FileMenuFilter(
+ targetFile,
+ mContainerActivity.getStorageManager().getAccount(),
+ mContainerActivity,
+ getActivity()
+ );
+ mf.filter(menu);
+ }
+
+ /// TODO break this direct dependency on FileDisplayActivity... if possible
+ MenuItem item = menu.findItem(R.id.action_open_file_with);
+ FileFragment frag = ((FileDisplayActivity)getActivity()).getSecondFragment();
+ if (frag != null && frag instanceof FileDetailFragment &&
+ frag.getFile().getFileId() == targetFile.getFileId()) {
+ item = menu.findItem(R.id.action_see_details);
+ if (item != null) {
+ item.setVisible(false);
+ item.setEnabled(false);
+ }
+ }
+
+ MenuItem menuItem = new DialogMenuItem(item.getItemId());
+ FileActionsDialogFragment dialog = FileActionsDialogFragment.newInstance(menu, fileIndex);
+ dialog.setTargetFragment(this, 0);
+ dialog.show(getFragmentManager(), FileActionsDialogFragment.FTAG_FILE_ACTIONS);
+ }
+ }
+
/**
* Saves the current listed folder.
*/
/**
* Call this, when the user presses the up button.
*
- * Tries to move up the current folder one level. If the parent folder was removed from the
+ * Tries to move up the current folder one level. If the parent folder was removed from the
* database, it continues browsing up until finding an existing folders.
*
* return Count of folder levels browsed up.
@Override
public void onCreateContextMenu (
ContextMenu menu, View v, ContextMenu.ContextMenuInfo menuInfo) {
- super.onCreateContextMenu(menu, v, menuInfo);
Bundle args = getArguments();
boolean allowContextualActions =
(args == null) ? true : args.getBoolean(ARG_ALLOW_CONTEXTUAL_ACTIONS, true);
}
}
}
-
-
- /**
- * {@inhericDoc}
- */
+
@Override
- public boolean onContextItemSelected (MenuItem item) {
- AdapterContextMenuInfo info = (AdapterContextMenuInfo) item.getMenuInfo();
- mTargetFile = (OCFile) mAdapter.getItem(info.position);
- switch (item.getItemId()) {
+ public boolean onFileActionChosen(int menuId, int filePosition) {
+ mTargetFile = (OCFile) mAdapter.getItem(filePosition);
+ switch (menuId) {
case R.id.action_share_file: {
mContainerActivity.getFileOperationsHelper().shareFileWithLink(mTargetFile);
return true;
dialog.show(getFragmentManager(), ConfirmationDialogFragment.FTAG_CONFIRMATION);
return true;
}
- case R.id.action_download_file:
+ case R.id.action_download_file:
case R.id.action_sync_file: {
mContainerActivity.getFileOperationsHelper().syncFile(mTargetFile);
return true;
}
case R.id.action_cancel_download:
case R.id.action_cancel_upload: {
- ((FileDisplayActivity)mContainerActivity).cancelTransference(mTargetFile);
+ ((FileDisplayActivity) mContainerActivity).cancelTransference(mTargetFile);
return true;
}
case R.id.action_see_details: {
// Obtain the file
if (!mTargetFile.isDown()) { // Download the file
Log_OC.d(TAG, mTargetFile.getRemotePath() + " : File must be downloaded");
- ((FileDisplayActivity)mContainerActivity).startDownloadForSending(mTargetFile);
-
+ ((FileDisplayActivity) mContainerActivity).startDownloadForSending(mTargetFile);
+
} else {
mContainerActivity.getFileOperationsHelper().sendDownloadedFile(mTargetFile);
}
getActivity().startActivityForResult(action, FileDisplayActivity.ACTION_MOVE_FILES);
return true;
}
- case R.id.action_favorite_file:{
+ case R.id.action_favorite_file: {
mContainerActivity.getFileOperationsHelper().toggleFavorite(mTargetFile, true);
return true;
}
- case R.id.action_unfavorite_file:{
+ case R.id.action_unfavorite_file: {
mContainerActivity.getFileOperationsHelper().toggleFavorite(mTargetFile, false);
return true;
}
default:
- return super.onContextItemSelected(item);
+ return false;
+ }
+ }
+
+ /**
+ * {@inhericDoc}
+ */
+ @Override
+ public boolean onContextItemSelected (MenuItem item) {
+ AdapterContextMenuInfo info = (AdapterContextMenuInfo) item.getMenuInfo();
+ boolean matched = onFileActionChosen(item.getItemId(), ((AdapterContextMenuInfo) item.getMenuInfo()).position);
+ if(!matched) {
+ return super.onContextItemSelected(item);
+ } else {
+ return matched;
}
}
if (version != null && version.supportsRemoteThumbnails() &&
imagesCount > 0 && imagesCount == filesCount) {
switchToGridView();
+ registerLongClickListener();
} else {
switchToListView();
}
return output;
}
-
public void sortByName(boolean descending) {
mAdapter.setSortOrder(FileStorageUtils.SORT_NAME, descending);
}
public void sortBySize(boolean descending) {
mAdapter.setSortOrder(FileStorageUtils.SORT_SIZE, descending);
}
-
-
}
--- /dev/null
+package com.owncloud.android.utils;
+
+import android.content.Intent;
+import android.graphics.drawable.Drawable;
+import android.view.ActionProvider;
+import android.view.ContextMenu;
+import android.view.MenuItem;
+import android.view.SubMenu;
+import android.view.View;
+
+/**
+ * Created by scherzia on 17.08.2015.
+ */
+public class DialogMenuItem implements MenuItem {
+ int itemId;
+ CharSequence title;
+
+ public DialogMenuItem(int itemId) {
+ this.itemId = itemId;
+ }
+
+ @Override
+ public int getItemId() {
+ return itemId;
+ }
+
+ @Override
+ public int getGroupId() {
+ return 0;
+ }
+
+ @Override
+ public int getOrder() {
+ return 0;
+ }
+
+ @Override
+ public MenuItem setTitle(CharSequence title) {
+ this.title = title;
+ return this;
+ }
+
+ @Override
+ public MenuItem setTitle(int title) {
+ return this;
+ }
+
+ @Override
+ public CharSequence getTitle() {
+ return this.title;
+ }
+
+ @Override
+ public MenuItem setTitleCondensed(CharSequence title) {
+ return null;
+ }
+
+ @Override
+ public CharSequence getTitleCondensed() {
+ return null;
+ }
+
+ @Override
+ public MenuItem setIcon(Drawable icon) {
+ return null;
+ }
+
+ @Override
+ public MenuItem setIcon(int iconRes) {
+ return null;
+ }
+
+ @Override
+ public Drawable getIcon() {
+ return null;
+ }
+
+ @Override
+ public MenuItem setIntent(Intent intent) {
+ return null;
+ }
+
+ @Override
+ public Intent getIntent() {
+ return null;
+ }
+
+ @Override
+ public MenuItem setShortcut(char numericChar, char alphaChar) {
+ return null;
+ }
+
+ @Override
+ public MenuItem setNumericShortcut(char numericChar) {
+ return null;
+ }
+
+ @Override
+ public char getNumericShortcut() {
+ return 0;
+ }
+
+ @Override
+ public MenuItem setAlphabeticShortcut(char alphaChar) {
+ return null;
+ }
+
+ @Override
+ public char getAlphabeticShortcut() {
+ return 0;
+ }
+
+ @Override
+ public MenuItem setCheckable(boolean checkable) {
+ return null;
+ }
+
+ @Override
+ public boolean isCheckable() {
+ return false;
+ }
+
+ @Override
+ public MenuItem setChecked(boolean checked) {
+ return null;
+ }
+
+ @Override
+ public boolean isChecked() {
+ return false;
+ }
+
+ @Override
+ public MenuItem setVisible(boolean visible) {
+ return null;
+ }
+
+ @Override
+ public boolean isVisible() {
+ return false;
+ }
+
+ @Override
+ public MenuItem setEnabled(boolean enabled) {
+ return null;
+ }
+
+ @Override
+ public boolean isEnabled() {
+ return false;
+ }
+
+ @Override
+ public boolean hasSubMenu() {
+ return false;
+ }
+
+ @Override
+ public SubMenu getSubMenu() {
+ return null;
+ }
+
+ @Override
+ public MenuItem setOnMenuItemClickListener(OnMenuItemClickListener menuItemClickListener) {
+ return null;
+ }
+
+ @Override
+ public ContextMenu.ContextMenuInfo getMenuInfo() {
+ return null;
+ }
+
+ @Override
+ public void setShowAsAction(int actionEnum) {
+
+ }
+
+ @Override
+ public MenuItem setShowAsActionFlags(int actionEnum) {
+ return null;
+ }
+
+ @Override
+ public MenuItem setActionView(View view) {
+ return null;
+ }
+
+ @Override
+ public MenuItem setActionView(int resId) {
+ return null;
+ }
+
+ @Override
+ public View getActionView() {
+ return null;
+ }
+
+ @Override
+ public MenuItem setActionProvider(ActionProvider actionProvider) {
+ return null;
+ }
+
+ @Override
+ public ActionProvider getActionProvider() {
+ return null;
+ }
+
+ @Override
+ public boolean expandActionView() {
+ return false;
+ }
+
+ @Override
+ public boolean collapseActionView() {
+ return false;
+ }
+
+ @Override
+ public boolean isActionViewExpanded() {
+ return false;
+ }
+
+ @Override
+ public MenuItem setOnActionExpandListener(OnActionExpandListener listener) {
+ return null;
+ }
+}