diff --git a/android/AndroidManifest.xml b/android/AndroidManifest.xml index e1eb9c3975..57b4b43316 100644 --- a/android/AndroidManifest.xml +++ b/android/AndroidManifest.xml @@ -447,6 +447,7 @@ android:label="@string/ugc_route_tags_screen_label"> + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/android/res/layout/ugc_route_edit_settings_activity.xml b/android/res/layout/ugc_route_edit_settings_activity.xml new file mode 100644 index 0000000000..2717be4ebd --- /dev/null +++ b/android/res/layout/ugc_route_edit_settings_activity.xml @@ -0,0 +1,7 @@ + + + diff --git a/android/src/com/mapswithme/maps/base/DataObservable.java b/android/src/com/mapswithme/maps/base/DataObservable.java new file mode 100644 index 0000000000..231126732a --- /dev/null +++ b/android/src/com/mapswithme/maps/base/DataObservable.java @@ -0,0 +1,13 @@ +package com.mapswithme.maps.base; + +import android.database.Observable; +import android.support.v7.widget.RecyclerView; + +public class DataObservable extends Observable +{ + public void notifyChanged() { + for (int i = mObservers.size() - 1; i >= 0; i--) { + mObservers.get(i).onChanged(); + } + } +} diff --git a/android/src/com/mapswithme/maps/base/ObservableHost.java b/android/src/com/mapswithme/maps/base/ObservableHost.java new file mode 100644 index 0000000000..1fec5942e4 --- /dev/null +++ b/android/src/com/mapswithme/maps/base/ObservableHost.java @@ -0,0 +1,11 @@ +package com.mapswithme.maps.base; + +import android.database.Observable; +import android.support.annotation.NonNull; +import android.support.v7.widget.RecyclerView; + +public interface ObservableHost> +{ + @NonNull + T getObservable(); +} diff --git a/android/src/com/mapswithme/maps/bookmarks/data/AbstractCategoriesSnapshot.java b/android/src/com/mapswithme/maps/bookmarks/data/AbstractCategoriesSnapshot.java index faa4654cf0..4707b4d8e4 100644 --- a/android/src/com/mapswithme/maps/bookmarks/data/AbstractCategoriesSnapshot.java +++ b/android/src/com/mapswithme/maps/bookmarks/data/AbstractCategoriesSnapshot.java @@ -42,17 +42,31 @@ public abstract class AbstractCategoriesSnapshot public int indexOfOrThrow(@NonNull BookmarkCategory category) { - List items = getItems(); - int indexOf = items.indexOf(category); + return indexOfThrowInternal(getItems(), category); + } + + private static int indexOfThrowInternal(@NonNull List categories, + @NonNull BookmarkCategory category) + { + int indexOf = categories.indexOf(category); if (indexOf < 0) { - throw new UnsupportedOperationException(new StringBuilder("This category absent in current snapshot ") + throw new UnsupportedOperationException(new StringBuilder("This category absent in " + + "current snapshot ") .append(category) .append("all items : ") - .append(Arrays.toString(items.toArray())) + .append(Arrays.toString(categories.toArray())) .toString()); } return indexOf; } + + @NonNull + public BookmarkCategory refresh(@NonNull BookmarkCategory category) + { + List items = getItems(); + int index = indexOfThrowInternal(items, category); + return items.get(index); + } } } diff --git a/android/src/com/mapswithme/maps/bookmarks/data/BookmarkCategory.java b/android/src/com/mapswithme/maps/bookmarks/data/BookmarkCategory.java index be131a9db9..5eb0d2c324 100644 --- a/android/src/com/mapswithme/maps/bookmarks/data/BookmarkCategory.java +++ b/android/src/com/mapswithme/maps/bookmarks/data/BookmarkCategory.java @@ -7,11 +7,13 @@ import android.os.Parcelable; import android.support.annotation.NonNull; import android.support.annotation.Nullable; import android.support.annotation.PluralsRes; +import android.support.annotation.StringRes; import android.text.TextUtils; import com.mapswithme.maps.R; import com.mapswithme.maps.bookmarks.BookmarksPageFactory; import com.mapswithme.util.TypeConverter; +import com.mapswithme.util.UiUtils; public class BookmarkCategory implements Parcelable { @@ -27,13 +29,16 @@ public class BookmarkCategory implements Parcelable private final int mTracksCount; private final int mBookmarksCount; private final int mTypeIndex; + private final int mAccessRulesIndex; private final boolean mIsMyCategory; private final boolean mIsVisible; + public BookmarkCategory(long id, @NonNull String name, @NonNull String authorId, @NonNull String authorName, @NonNull String annotation, @NonNull String description, int tracksCount, int bookmarksCount, - boolean fromCatalog, boolean isMyCategory, boolean isVisible) + boolean fromCatalog, boolean isMyCategory, boolean isVisible, + int accessRulesIndex) { mId = id; mName = name; @@ -47,6 +52,7 @@ public class BookmarkCategory implements Parcelable mAuthor = TextUtils.isEmpty(authorId) || TextUtils.isEmpty(authorName) ? null : new Author(authorId, authorName); + mAccessRulesIndex = accessRulesIndex; } @Override @@ -91,11 +97,18 @@ public class BookmarkCategory implements Parcelable return mBookmarksCount; } + @NonNull public Type getType() { return Type.values()[mTypeIndex]; } + @NonNull + public AccessRules getAccessRules() + { + return AccessRules.values()[mAccessRulesIndex]; + } + public boolean isFromCatalog() { return Type.values()[mTypeIndex] == Type.CATALOG; @@ -270,6 +283,7 @@ public class BookmarkCategory implements Parcelable sb.append(", mType=").append(Type.values()[mTypeIndex]); sb.append(", mIsMyCategory=").append(mIsMyCategory); sb.append(", mIsVisible=").append(mIsVisible); + sb.append(", mAccessRules=").append(getAccessRules()); sb.append('}'); return sb.toString(); } @@ -331,6 +345,7 @@ public class BookmarkCategory implements Parcelable dest.writeInt(this.mTypeIndex); dest.writeByte(this.mIsMyCategory ? (byte) 1 : (byte) 0); dest.writeByte(this.mIsVisible ? (byte) 1 : (byte) 0); + dest.writeInt(this.mAccessRulesIndex); } protected BookmarkCategory(Parcel in) @@ -345,6 +360,7 @@ public class BookmarkCategory implements Parcelable this.mTypeIndex = in.readInt(); this.mIsMyCategory = in.readByte() != 0; this.mIsVisible = in.readByte() != 0; + this.mAccessRulesIndex = in.readInt(); } public static final Creator CREATOR = new Creator() @@ -361,4 +377,40 @@ public class BookmarkCategory implements Parcelable return new BookmarkCategory[size]; } }; + + public enum AccessRules + { + ACCESS_RULES_LOCAL(R.string.not_shared), + ACCESS_RULES_PUBLIC(R.string.public_access), + ACCESS_RULES_DIRECT_LINK(R.string.limited_access), + ACCESS_RULES_P2P(UiUtils.NO_ID) + { + @Override + public int getResId() + { + throw new IllegalStateException("Unsupported here"); + } + }, + ACCESS_RULES_PAID(UiUtils.NO_ID) + { + @Override + public int getResId() + { + throw new IllegalStateException("Unsupported here"); + } + }; + + private final int mResId; + + AccessRules(int resId) + { + mResId = resId; + } + + @StringRes + public int getResId() + { + return mResId; + } + } } diff --git a/android/src/com/mapswithme/maps/bookmarks/data/BookmarkManager.java b/android/src/com/mapswithme/maps/bookmarks/data/BookmarkManager.java index 16afe5830c..e994c57c8a 100644 --- a/android/src/com/mapswithme/maps/bookmarks/data/BookmarkManager.java +++ b/android/src/com/mapswithme/maps/bookmarks/data/BookmarkManager.java @@ -49,16 +49,6 @@ public enum BookmarkManager public static final List ICONS = new ArrayList<>(); - @Retention(RetentionPolicy.SOURCE) - @IntDef({ ACCESS_RULES_LOCAL, ACCESS_RULES_PUBLIC, ACCESS_RULES_DIRECT_LINK, - ACCESS_RULES_P2P, ACCESS_RULES_PAID }) - public @interface AccessRules {} - public static final int ACCESS_RULES_LOCAL = 0; - public static final int ACCESS_RULES_PUBLIC = 1; - public static final int ACCESS_RULES_DIRECT_LINK = 2; - public static final int ACCESS_RULES_P2P = 3; - public static final int ACCESS_RULES_PAID = 4; - @Retention(RetentionPolicy.SOURCE) @IntDef({ UPLOAD_RESULT_SUCCESS, UPLOAD_RESULT_NETWORK_ERROR, UPLOAD_RESULT_SERVER_ERROR, UPLOAD_RESULT_AUTH_ERROR, UPLOAD_RESULT_MALFORMED_DATA_ERROR, @@ -348,6 +338,21 @@ public enum BookmarkManager nativeSetCategoryName(catId, name); } + public void setCategoryDesc(long id, @NonNull String categoryDesc) + { + nativeSetCategoryDesc(id, categoryDesc); + } + + public void setAccessRules(long id, @NonNull BookmarkCategory.AccessRules rules) + { + nativeSetCategoryAccessRules(id, rules.ordinal()); + } + + public void uploadToCatalog(@NonNull BookmarkCategory.AccessRules rules, long id) + { + nativeUploadToCatalog(rules.ordinal(), id); + } + /** * @return total count - tracks + bookmarks * @param category @@ -653,18 +658,17 @@ public enum BookmarkManager private native void nativeSetCategoryName(long catId, @NonNull String n); + private native void nativeSetCategoryDesc(long catId, @NonNull String n); + private native void nativeSetCategoryTags(long catId, @NonNull String[] tagsIds); - private native void nativeSetCategoryAccessRules(long catId, @AccessRules int accessRules); + private native void nativeSetCategoryAccessRules(long catId, int accessRules); private native void nativeSetCategoryCustomProperty(long catId, String key, String value); @NonNull private native String nativeGetCategoryAuthor(long catId); - @AccessRules - private native int nativeGetCategoryAccessRules(long catId); - private static native void nativeLoadBookmarks(); private native boolean nativeDeleteCategory(long catId); @@ -733,7 +737,7 @@ public enum BookmarkManager private static native void nativeImportFromCatalog(@NonNull String serverId, @NonNull String filePath); - private static native void nativeUploadToCatalog(@AccessRules int accessRules, + private static native void nativeUploadToCatalog(int accessRules, long catId); @NonNull diff --git a/android/src/com/mapswithme/maps/ugc/routes/UgcRouteEditSettingsActivity.java b/android/src/com/mapswithme/maps/ugc/routes/UgcRouteEditSettingsActivity.java new file mode 100644 index 0000000000..18f5a2a54e --- /dev/null +++ b/android/src/com/mapswithme/maps/ugc/routes/UgcRouteEditSettingsActivity.java @@ -0,0 +1,57 @@ +package com.mapswithme.maps.ugc.routes; + +import android.os.Bundle; +import android.support.annotation.NonNull; +import android.support.annotation.Nullable; +import android.support.v4.app.Fragment; +import android.support.v4.app.FragmentManager; + +import com.mapswithme.maps.R; +import com.mapswithme.maps.base.BaseMwmFragmentActivity; +import com.mapswithme.maps.base.DataObservable; +import com.mapswithme.maps.base.ObservableHost; + +public class UgcRouteEditSettingsActivity extends BaseMwmFragmentActivity implements ObservableHost +{ + public static final String EXTRA_BOOKMARK_CATEGORY = "bookmark_category"; + + private static final String FRAGMENT_TAG = "edit_settings_fragment_tag"; + + @SuppressWarnings("NullableProblems") + @NonNull + private DataObservable mObservable; + + @Override + protected void safeOnCreate(@Nullable Bundle savedInstanceState) + { + super.safeOnCreate(savedInstanceState); + setContentView(R.layout.ugc_route_edit_settings_activity); + mObservable = new DataObservable(); + addSettingsFragmentIfAbsent(); + } + + private void addSettingsFragmentIfAbsent() + { + FragmentManager fm = getSupportFragmentManager(); + UgcRouteEditSettingsFragment fragment = (UgcRouteEditSettingsFragment) fm.findFragmentByTag(FRAGMENT_TAG); + + if (fragment == null) + { + fragment = UgcRouteEditSettingsFragment.makeInstance(getIntent().getExtras()); + fm.beginTransaction().add(R.id.fragment_container, fragment, FRAGMENT_TAG).commit(); + } + } + + @Override + protected Class getFragmentClass() + { + return null; + } + + @NonNull + @Override + public DataObservable getObservable() + { + return mObservable; + } +} diff --git a/android/src/com/mapswithme/maps/ugc/routes/UgcRouteEditSettingsFragment.java b/android/src/com/mapswithme/maps/ugc/routes/UgcRouteEditSettingsFragment.java new file mode 100644 index 0000000000..42e0b7b2d3 --- /dev/null +++ b/android/src/com/mapswithme/maps/ugc/routes/UgcRouteEditSettingsFragment.java @@ -0,0 +1,190 @@ +package com.mapswithme.maps.ugc.routes; + +import android.content.Context; +import android.os.Bundle; +import android.support.annotation.NonNull; +import android.support.annotation.Nullable; +import android.support.v4.app.Fragment; +import android.support.v7.widget.RecyclerView; +import android.text.TextUtils; +import android.view.LayoutInflater; +import android.view.MenuItem; +import android.view.View; +import android.view.ViewGroup; +import android.widget.EditText; +import android.widget.TextView; + +import com.mapswithme.maps.R; +import com.mapswithme.maps.base.BaseMwmToolbarFragment; +import com.mapswithme.maps.base.DataObservable; +import com.mapswithme.maps.base.ObservableHost; +import com.mapswithme.maps.bookmarks.data.BookmarkCategory; +import com.mapswithme.maps.bookmarks.data.BookmarkManager; +import com.mapswithme.maps.widget.ToolbarController; + +import java.util.Objects; + +public class UgcRouteEditSettingsFragment extends BaseMwmToolbarFragment +{ + private static final String SHARING_OPTIONS_FRAGMENT_TAG = "sharing_options_fragment"; + + @SuppressWarnings("NullableProblems") + @NonNull + private BookmarkCategory mCategory; + + @SuppressWarnings("NullableProblems") + @NonNull + private RecyclerView.AdapterDataObserver mObserver; + + @SuppressWarnings("NullableProblems") + @NonNull + private TextView mAccessRulesView; + + @SuppressWarnings("NullableProblems") + @NonNull + private ObservableHost mObserverHost; + + @SuppressWarnings("NullableProblems") + @NonNull + private EditText mEditDescView; + + @SuppressWarnings("NullableProblems") + @NonNull + private EditText mEditCategoryNameView; + + @Override + public void onAttach(Context context) + { + super.onAttach(context); + mObserverHost = (ObservableHost) context; + } + + @Override + public void onCreate(@Nullable Bundle savedInstanceState) + { + super.onCreate(savedInstanceState); + Bundle args = getArguments(); + if (args == null) + throw new IllegalArgumentException("Args must be not null"); + mCategory = Objects.requireNonNull(args.getParcelable(UgcRouteEditSettingsActivity.EXTRA_BOOKMARK_CATEGORY)); + } + + @Nullable + @Override + public View onCreateView(LayoutInflater inflater, @Nullable ViewGroup container, + @Nullable Bundle savedInstanceState) + { + View root = inflater.inflate(R.layout.fragment_ugc_route_edit, container, false); + initViews(root); + mObserver = new CategoryObserver(); + mObserverHost.getObservable().registerObserver(mObserver); + return root; + } + + private void initViews(@NonNull View root) + { + View sharingOptionsBtn = root.findViewById(R.id.open_sharing_options_screen_btn_container); + mEditCategoryNameView = root.findViewById(R.id.edit_category_name_view); + mEditCategoryNameView.setText(mCategory.getName()); + mEditCategoryNameView.requestFocus(); + mAccessRulesView = root.findViewById(R.id.sharing_options_desc); + mAccessRulesView.setText(mCategory.getAccessRules().getResId()); + mEditDescView = root.findViewById(R.id.edit_description); + mEditDescView.setText(mCategory.getDescription()); + View clearNameBtn = root.findViewById(R.id.edit_text_clear_btn); + clearNameBtn.setOnClickListener(v -> mEditCategoryNameView.getEditableText().clear()); + sharingOptionsBtn.setOnClickListener(v -> onSharingOptionsClicked()); + } + + @Override + public void onDestroyView() + { + super.onDestroyView(); + mObserverHost.getObservable().unregisterObserver(mObserver); + } + + private void onSharingOptionsClicked() + { + openSharingOptionsScreen(); + } + + private void openSharingOptionsScreen() + { + Fragment fragment = UgcSharingOptionsFragment.makeInstance(mCategory); + getFragmentManager() + .beginTransaction() + .replace(R.id.fragment_container, fragment, SHARING_OPTIONS_FRAGMENT_TAG) + .addToBackStack(null) + .commit(); + } + + @Override + public void onViewCreated(@NonNull View view, @Nullable Bundle savedInstanceState) + { + super.onViewCreated(view, savedInstanceState); + getToolbarController().setTitle(R.string.edit_list); + } + + @NonNull + @Override + protected ToolbarController onCreateToolbarController(@NonNull View root) + { + return new EditSettingsController(root); + } + + @Override + public boolean onOptionsItemSelected(MenuItem item) + { + if (item.getItemId() == R.id.done) + { + onEditDoneClicked(); + return true; + } + return super.onOptionsItemSelected(item); + } + + private void onEditDoneClicked() + { + String categoryName = mEditCategoryNameView.getEditableText().toString().trim(); + + if (!TextUtils.equals(categoryName, mCategory.getName())) + BookmarkManager.INSTANCE.setCategoryName(mCategory.getId(), categoryName); + + String categoryDesc = mEditDescView.getEditableText().toString().trim(); + if (!TextUtils.equals(mCategory.getDescription(), categoryDesc)) + BookmarkManager.INSTANCE.setCategoryDesc(mCategory.getId(), categoryDesc); + + } + + @NonNull + public static UgcRouteEditSettingsFragment makeInstance(@Nullable Bundle extras) + { + UgcRouteEditSettingsFragment fragment = new UgcRouteEditSettingsFragment(); + fragment.setArguments(extras); + return fragment; + } + + public class CategoryObserver extends RecyclerView.AdapterDataObserver + { + @Override + public void onChanged() + { + mCategory = BookmarkManager.INSTANCE.getAllCategoriesSnapshot().refresh(mCategory); + mAccessRulesView.setText(mCategory.getAccessRules().getResId()); + } + } + + private class EditSettingsController extends ToolbarController + { + EditSettingsController(@NonNull View root) + { + super(root, getActivity()); + } + + @Override + public void onUpClick() + { + getActivity().finish(); + } + } +} diff --git a/android/src/com/mapswithme/maps/ugc/routes/UgcSharingOptionsFragment.java b/android/src/com/mapswithme/maps/ugc/routes/UgcSharingOptionsFragment.java index eb60e78e68..308206f379 100644 --- a/android/src/com/mapswithme/maps/ugc/routes/UgcSharingOptionsFragment.java +++ b/android/src/com/mapswithme/maps/ugc/routes/UgcSharingOptionsFragment.java @@ -22,6 +22,7 @@ import com.mapswithme.maps.auth.BaseMwmAuthorizationFragment; import com.mapswithme.maps.bookmarks.data.BookmarkManager; import com.mapswithme.maps.bookmarks.data.CatalogCustomProperty; import com.mapswithme.maps.bookmarks.data.CatalogTagsGroup; +import com.mapswithme.maps.bookmarks.data.BookmarkCategory; import com.mapswithme.maps.dialog.AlertDialog; import com.mapswithme.maps.dialog.ProgressDialogFragment; import com.mapswithme.maps.widget.ToolbarController; @@ -29,9 +30,11 @@ import com.mapswithme.util.ConnectionState; import com.mapswithme.util.UiUtils; import java.util.List; +import java.util.Objects; public class UgcSharingOptionsFragment extends BaseMwmAuthorizationFragment implements BookmarkManager.BookmarksCatalogListener { + public static final String EXTRA_BOOKMARK_CATEGORY = "bookmark_category"; private static final String NO_NETWORK_CONNECTION_DIALOG_TAG = "no_network_connection_dialog"; private static final String UPLOADING_PROGRESS_DIALOG_TAG = "uploading_progress_dialog"; @@ -39,18 +42,16 @@ public class UgcSharingOptionsFragment extends BaseMwmAuthorizationFragment impl @NonNull private View mGetDirectLinkContainer; + @SuppressWarnings("NullableProblems") @NonNull + private BookmarkCategory mCategory; + @Override - protected ToolbarController onCreateToolbarController(@NonNull View root) + public void onCreate(@Nullable Bundle savedInstanceState) { - return new ToolbarController(root, getActivity()) - { - @Override - public void onUpClick() - { - getActivity().finish(); - } - }; + super.onCreate(savedInstanceState); + Bundle args = Objects.requireNonNull(getArguments()); + mCategory = Objects.requireNonNull(args.getParcelable(EXTRA_BOOKMARK_CATEGORY)); } @Nullable @@ -78,6 +79,13 @@ public class UgcSharingOptionsFragment extends BaseMwmAuthorizationFragment impl getToolbarController().setTitle(R.string.sharing_options); } + @NonNull + @Override + protected ToolbarController onCreateToolbarController(@NonNull View root) + { + return new SharingOptionsController(root); + } + private void initClickListeners(@NonNull View root) { View getDirectLinkView = root.findViewById(R.id.get_direct_link_text); @@ -287,4 +295,21 @@ public class UgcSharingOptionsFragment extends BaseMwmAuthorizationFragment impl { return true; } + + private class SharingOptionsController extends ToolbarController + { + SharingOptionsController(@NonNull View root) + { + super(root, getActivity()); + } + + @Override + public void onUpClick() + { + if (getFragmentManager().getBackStackEntryCount() == 0) + getActivity().finish(); + else + getFragmentManager().popBackStackImmediate(); + } + } } diff --git a/android/src/com/mapswithme/util/Utils.java b/android/src/com/mapswithme/util/Utils.java index 20b93461ad..b53e5ac20d 100644 --- a/android/src/com/mapswithme/util/Utils.java +++ b/android/src/com/mapswithme/util/Utils.java @@ -13,6 +13,7 @@ import android.net.Uri; import android.net.wifi.WifiInfo; import android.net.wifi.WifiManager; import android.os.Build; +import android.os.Bundle; import android.provider.Settings; import android.support.annotation.DimenRes; import android.support.annotation.NonNull;