Skip to content

Commit 0b357be

Browse files
ashishkumar468maskaravivek
authored andcommitted
Bugfix/uploads (#3002)
* merged with master * BugFix IllegalStateException * setRetainState(true), not required with FragmentStatePagerAdapter * Increase the ViewPager's Offscreen Limit, we want all the fragments to be active * BugFix, clear selected categoris for previous upload session * Clear Selected Categories * Addded JavaDocs for CategoriesModel * Code Formatting in app/src/main/java/fr/free/nrw/commons/upload/UploadModel.java * Added class level JavaDoc UploadRemoteDataSource * Added class level JavaDoc for UploadRepository * Added JavaDocs for ThumbnailsAdapter * Added JavaDocs for MediaLicensePresenter, CategoriesPresenter * Removed null check on category query * Show default catgeories based on image title and gps location when category text empty * Allow search for empty category search * Attached image scale listener to upload media image * Bug fix, reduced the add description edit text clickable bound * Added tooltip in Title in UploadMediaFragment * BugFix recent categories * Updated test methods
1 parent 7dd42c3 commit 0b357be

12 files changed

+94
-124
lines changed

app/src/main/java/fr/free/nrw/commons/category/CategoriesModel.java

+12-45
Original file line numberDiff line numberDiff line change
@@ -1,22 +1,19 @@
11
package fr.free.nrw.commons.category;
22

33
import android.text.TextUtils;
4-
4+
import fr.free.nrw.commons.kvstore.JsonKvStore;
5+
import fr.free.nrw.commons.mwapi.MediaWikiApi;
6+
import fr.free.nrw.commons.upload.GpsCategoryModel;
7+
import fr.free.nrw.commons.utils.StringSortingUtils;
8+
import io.reactivex.Observable;
59
import java.util.ArrayList;
610
import java.util.Calendar;
711
import java.util.Comparator;
812
import java.util.Date;
913
import java.util.HashMap;
1014
import java.util.List;
11-
1215
import javax.inject.Inject;
1316
import javax.inject.Named;
14-
15-
import fr.free.nrw.commons.kvstore.JsonKvStore;
16-
import fr.free.nrw.commons.mwapi.MediaWikiApi;
17-
import fr.free.nrw.commons.upload.GpsCategoryModel;
18-
import fr.free.nrw.commons.utils.StringSortingUtils;
19-
import io.reactivex.Observable;
2017
import timber.log.Timber;
2118

2219
/**
@@ -107,11 +104,14 @@ boolean cacheContainsKey(String term) {
107104
* @return
108105
*/
109106
public Observable<CategoryItem> searchAll(String term, List<String> imageTitleList) {
110-
//If user hasn't typed anything in yet, get GPS and recent items
107+
//If query text is empty, show him category based on gps and title and recent searches
111108
if (TextUtils.isEmpty(term)) {
112-
return gpsCategories()
113-
.concatWith(titleCategories(imageTitleList))
114-
.concatWith(recentCategories());
109+
Observable<CategoryItem> categoryItemObservable = gpsCategories()
110+
.concatWith(titleCategories(imageTitleList));
111+
if (hasDirectCategories()) {
112+
categoryItemObservable.concatWith(directCategories().concatWith(recentCategories()));
113+
}
114+
return categoryItemObservable;
115115
}
116116

117117
//if user types in something that is in cache, return cached category
@@ -126,18 +126,6 @@ public Observable<CategoryItem> searchAll(String term, List<String> imageTitleLi
126126
.map(name -> new CategoryItem(name, false));
127127
}
128128

129-
public Observable<CategoryItem> searchCategories(String term, List<String> imageTitleList) {
130-
//If user hasn't typed anything in yet, get GPS and recent items
131-
if (TextUtils.isEmpty(term)) {
132-
return gpsCategories()
133-
.concatWith(titleCategories(imageTitleList))
134-
.concatWith(recentCategories());
135-
}
136-
137-
return mwApi
138-
.searchCategories(term, SEARCH_CATS_LIMIT)
139-
.map(s -> new CategoryItem(s, false));
140-
}
141129

142130
/**
143131
* Returns cached categories
@@ -148,27 +136,6 @@ private ArrayList<String> getCachedCategories(String term) {
148136
return categoriesCache.get(term);
149137
}
150138

151-
/**
152-
* Returns default categories
153-
* @param titleList
154-
* @return
155-
*/
156-
public Observable<CategoryItem> defaultCategories(List<String> titleList) {
157-
Observable<CategoryItem> directCat = directCategories();
158-
if (hasDirectCategories()) {
159-
Timber.d("Image has direct Cat");
160-
return directCat
161-
.concatWith(gpsCategories())
162-
.concatWith(titleCategories(titleList))
163-
.concatWith(recentCategories());
164-
} else {
165-
Timber.d("Image has no direct Cat");
166-
return gpsCategories()
167-
.concatWith(titleCategories(titleList))
168-
.concatWith(recentCategories());
169-
}
170-
}
171-
172139
/**
173140
* Returns if we have a category in DirectKV Store
174141
* @return

app/src/main/java/fr/free/nrw/commons/repository/UploadRemoteDataSource.java

-21
Original file line numberDiff line numberDiff line change
@@ -105,27 +105,6 @@ public Observable<CategoryItem> searchAll(String query, List<String> imageTitleL
105105
return categoriesModel.searchAll(query, imageTitleList);
106106
}
107107

108-
/**
109-
* searchCategories from MWApi
110-
*
111-
* @param query
112-
* @param imageTitleList
113-
* @return
114-
*/
115-
public Observable<CategoryItem> searchCategories(String query, List<String> imageTitleList) {
116-
return categoriesModel.searchCategories(query, imageTitleList);
117-
}
118-
119-
/**
120-
* returns the list of default categoies
121-
*
122-
* @param imageTitleList
123-
* @return
124-
*/
125-
public Observable<CategoryItem> defaultCategories(List<String> imageTitleList) {
126-
return categoriesModel.defaultCategories(imageTitleList);
127-
}
128-
129108
/**
130109
* returns the string list of categories
131110
*

app/src/main/java/fr/free/nrw/commons/repository/UploadRepository.java

-21
Original file line numberDiff line numberDiff line change
@@ -93,27 +93,6 @@ public Observable<CategoryItem> searchAll(String query, List<String> imageTitleL
9393
return remoteDataSource.searchAll(query, imageTitleList);
9494
}
9595

96-
/**
97-
* searchCategories from MWApi
98-
*
99-
* @param query
100-
* @param imageTitleList
101-
* @return
102-
*/
103-
public Observable<CategoryItem> searchCategories(String query, List<String> imageTitleList) {
104-
return remoteDataSource.searchCategories(query, imageTitleList);
105-
}
106-
107-
/**
108-
* returns the default categorories for the list of images based on their titles
109-
*
110-
* @param imageTitleList
111-
* @return
112-
*/
113-
public Observable<CategoryItem> defaultCategories(List<String> imageTitleList) {
114-
return remoteDataSource.defaultCategories(imageTitleList);
115-
}
116-
11796
/**
11897
* returns the string list of categories
11998
*

app/src/main/java/fr/free/nrw/commons/upload/UploadActivity.java

-1
Original file line numberDiff line numberDiff line change
@@ -331,7 +331,6 @@ public int getTotalNumberOfSteps() {
331331
}
332332

333333
uploadCategoriesFragment = new UploadCategoriesFragment();
334-
uploadCategoriesFragment.setMediaTitleList(presenter.getImageTitleList());
335334
uploadCategoriesFragment.setCallback(this);
336335

337336
mediaLicenseFragment = new MediaLicenseFragment();

app/src/main/java/fr/free/nrw/commons/upload/UploadContract.java

-2
Original file line numberDiff line numberDiff line change
@@ -35,8 +35,6 @@ public interface UserActionListener extends BasePresenter<View> {
3535

3636
void handleSubmit();
3737

38-
List<String> getImageTitleList();
39-
4038
void deletePictureAtIndex(int index);
4139
}
4240
}

app/src/main/java/fr/free/nrw/commons/upload/UploadPresenter.java

-10
Original file line numberDiff line numberDiff line change
@@ -86,16 +86,6 @@ public void onComplete() {
8686
}
8787
}
8888

89-
public List<String> getImageTitleList() {
90-
List<String> titleList = new ArrayList<>();
91-
for (UploadItem item : repository.getUploads()) {
92-
if (item.getTitle().isSet()) {
93-
titleList.add(item.getTitle().toString());
94-
}
95-
}
96-
return titleList;
97-
}
98-
9989
@Override
10090
public void deletePictureAtIndex(int index) {
10191
List<UploadableFile> uploadableFiles = view.getUploadableFiles();

app/src/main/java/fr/free/nrw/commons/upload/categories/CategoriesContract.java

+1-2
Original file line numberDiff line numberDiff line change
@@ -1,7 +1,6 @@
11
package fr.free.nrw.commons.upload.categories;
22

33
import fr.free.nrw.commons.BasePresenter;
4-
import fr.free.nrw.commons.category.CategoryClickedListener;
54
import fr.free.nrw.commons.category.CategoryItem;
65

76
import java.util.List;
@@ -32,7 +31,7 @@ public interface View {
3231

3332
public interface UserActionListener extends BasePresenter<View> {
3433

35-
void searchForCategories(String query, List<String> imageTitleList);
34+
void searchForCategories(String query);
3635

3736
void verifyCategories();
3837

app/src/main/java/fr/free/nrw/commons/upload/categories/CategoriesPresenter.java

+24-14
Original file line numberDiff line numberDiff line change
@@ -4,23 +4,20 @@
44
import static fr.free.nrw.commons.di.CommonsApplicationModule.MAIN_THREAD;
55

66
import android.text.TextUtils;
7-
87
import fr.free.nrw.commons.R;
98
import fr.free.nrw.commons.category.CategoryItem;
109
import fr.free.nrw.commons.repository.UploadRepository;
10+
import fr.free.nrw.commons.upload.UploadModel.UploadItem;
1111
import io.reactivex.Observable;
1212
import io.reactivex.Scheduler;
1313
import io.reactivex.disposables.CompositeDisposable;
1414
import io.reactivex.disposables.Disposable;
15-
1615
import java.lang.reflect.Proxy;
1716
import java.util.ArrayList;
1817
import java.util.List;
19-
2018
import javax.inject.Inject;
2119
import javax.inject.Named;
2220
import javax.inject.Singleton;
23-
2421
import timber.log.Timber;
2522

2623
/**
@@ -64,14 +61,14 @@ public void onDetachView() {
6461

6562
/**
6663
* asks the repository to fetch categories for the query
64+
* @param query
6765
*
68-
* @param query
69-
* @param imageTitleList
7066
*/
7167
@Override
72-
public void searchForCategories(String query, List<String> imageTitleList) {
68+
public void searchForCategories(String query) {
7369
List<CategoryItem> categoryItems = new ArrayList<>();
74-
Disposable searchCategoriesDisposable = Observable
70+
List<String> imageTitleList = getImageTitleList();
71+
Observable<CategoryItem> distinctCategoriesObservable = Observable
7572
.fromIterable(repository.getSelectedCategories())
7673
.subscribeOn(ioScheduler)
7774
.observeOn(mainThreadScheduler)
@@ -83,14 +80,13 @@ public void searchForCategories(String query, List<String> imageTitleList) {
8380
.observeOn(ioScheduler)
8481
.concatWith(
8582
repository.searchAll(query, imageTitleList)
86-
.mergeWith(repository.searchCategories(query, imageTitleList))
87-
.concatWith(TextUtils.isEmpty(query)
88-
? repository.defaultCategories(imageTitleList)
89-
: Observable.empty())
9083
)
9184
.filter(categoryItem -> !repository.containsYear(categoryItem.getName()))
92-
.distinct()
93-
.sorted(repository.sortBySimilarity(query))
85+
.distinct();
86+
if(!TextUtils.isEmpty(query)) {
87+
distinctCategoriesObservable=distinctCategoriesObservable.sorted(repository.sortBySimilarity(query));
88+
}
89+
Disposable searchCategoriesDisposable = distinctCategoriesObservable
9490
.observeOn(mainThreadScheduler)
9591
.subscribe(
9692
s -> categoryItems.add(s),
@@ -108,6 +104,20 @@ public void searchForCategories(String query, List<String> imageTitleList) {
108104
compositeDisposable.add(searchCategoriesDisposable);
109105
}
110106

107+
/**
108+
* Returns image title list from UploadItem
109+
* @return
110+
*/
111+
private List<String> getImageTitleList() {
112+
List<String> titleList = new ArrayList<>();
113+
for (UploadItem item : repository.getUploads()) {
114+
if (item.getTitle().isSet()) {
115+
titleList.add(item.getTitle().toString());
116+
}
117+
}
118+
return titleList;
119+
}
120+
111121
/**
112122
* Verifies the number of categories selected, prompts the user if none selected
113123
*/

app/src/main/java/fr/free/nrw/commons/upload/categories/UploadCategoriesFragment.java

+24-5
Original file line numberDiff line numberDiff line change
@@ -49,8 +49,10 @@ public class UploadCategoriesFragment extends UploadBaseFragment implements Cate
4949
@Inject
5050
CategoriesContract.UserActionListener presenter;
5151
private RVRendererAdapter<CategoryItem> adapter;
52-
private List<String> mediaTitleList;
52+
private List<String> mediaTitleList=new ArrayList<>();
5353
private Disposable subscribe;
54+
private List<CategoryItem> categories;
55+
private boolean isVisible;
5456

5557
@Override
5658
public void onCreate(@Nullable Bundle savedInstanceState) {
@@ -82,7 +84,14 @@ private void init() {
8284
initRecyclerView();
8385
addTextChangeListenerToEtSearch();
8486
//get default categories for empty query
85-
presenter.searchForCategories(null,mediaTitleList);
87+
}
88+
89+
@Override
90+
public void onResume() {
91+
super.onResume();
92+
if (presenter != null && isVisible && (categories == null || categories.isEmpty())) {
93+
presenter.searchForCategories(null);
94+
}
8695
}
8796

8897
private void addTextChangeListenerToEtSearch() {
@@ -95,7 +104,7 @@ private void addTextChangeListenerToEtSearch() {
95104
}
96105

97106
private void searchForCategory(String query) {
98-
presenter.searchForCategories(query, mediaTitleList);
107+
presenter.searchForCategories(query);
99108
}
100109

101110
private void initRecyclerView() {
@@ -130,8 +139,8 @@ public void showError(int stringResourceId) {
130139
@Override
131140
public void setCategories(List<CategoryItem> categories) {
132141
adapter.clear();
133-
if (categories == null) {
134-
} else {
142+
if (categories != null) {
143+
this.categories = categories;
135144
adapter.addAll(categories);
136145
adapter.notifyDataSetChanged();
137146
}
@@ -178,4 +187,14 @@ public void onPreviousButtonClicked() {
178187
public void categoryClicked(CategoryItem item) {
179188
presenter.onCategoryItemClicked(item);
180189
}
190+
191+
@Override
192+
public void setUserVisibleHint(boolean isVisibleToUser) {
193+
super.setUserVisibleHint(isVisibleToUser);
194+
isVisible = isVisibleToUser;
195+
196+
if (presenter != null && isResumed() && (categories == null || categories.isEmpty())) {
197+
presenter.searchForCategories(null);
198+
}
199+
}
181200
}

app/src/main/java/fr/free/nrw/commons/upload/mediaDetails/UploadMediaDetailFragment.java

+31
Original file line numberDiff line numberDiff line change
@@ -1,9 +1,13 @@
11
package fr.free.nrw.commons.upload.mediaDetails;
22

3+
import android.content.Context;
34
import android.os.Bundle;
45
import android.text.TextUtils;
6+
import android.util.DisplayMetrics;
7+
import android.util.Log;
58
import android.util.Log;
69
import android.view.LayoutInflater;
10+
import android.view.MotionEvent;
711
import android.view.View;
812
import android.view.ViewGroup;
913
import android.widget.EditText;
@@ -159,6 +163,33 @@ private void init() {
159163
}
160164

161165
attachImageViewScaleChangeListener();
166+
167+
addEtTitleTouchListener();
168+
}
169+
170+
/**
171+
* Handles the drawable click listener for Edit Text
172+
*/
173+
private void addEtTitleTouchListener() {
174+
etTitle.setOnTouchListener((v, event) -> {
175+
//2 is for drawable right
176+
float twelveDpInPixels = convertDpToPixel(12, getContext());
177+
if (event.getAction() == MotionEvent.ACTION_UP && etTitle.getCompoundDrawables()[2].getBounds().contains((int)(etTitle.getWidth()-(event.getX()+twelveDpInPixels)),(int)(event.getY()-twelveDpInPixels))){
178+
showInfoAlert(R.string.media_detail_title,R.string.title_info);
179+
return true;
180+
}
181+
return false;
182+
});
183+
}
184+
185+
/**
186+
* converts dp to pixel
187+
* @param dp
188+
* @param context
189+
* @return
190+
*/
191+
private float convertDpToPixel(float dp, Context context) {
192+
return dp * ((float) context.getResources().getDisplayMetrics().densityDpi / DisplayMetrics.DENSITY_DEFAULT);
162193
}
163194

164195
/**

0 commit comments

Comments
 (0)