mirror of
https://github.com/commons-app/apps-android-commons.git
synced 2025-10-26 20:33:53 +01:00
Add contributin list fragment
This commit is contained in:
parent
738db8306f
commit
095082248c
3 changed files with 168 additions and 251 deletions
|
|
@ -22,7 +22,7 @@ import fr.free.nrw.commons.upload.UploadService;
|
||||||
|
|
||||||
import static android.content.ContentResolver.requestSync;
|
import static android.content.ContentResolver.requestSync;
|
||||||
|
|
||||||
public class ContributionsActivity extends AuthenticatedActivity {
|
public class ContributionsActivity extends AuthenticatedActivity implements FragmentManager.OnBackStackChangedListener {
|
||||||
|
|
||||||
@Inject
|
@Inject
|
||||||
SessionManager sessionManager;
|
SessionManager sessionManager;
|
||||||
|
|
@ -178,6 +178,11 @@ public class ContributionsActivity extends AuthenticatedActivity {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void onBackStackChanged() {
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
public class ContributionsActivityPagerAdapter extends FragmentPagerAdapter {
|
public class ContributionsActivityPagerAdapter extends FragmentPagerAdapter {
|
||||||
FragmentManager fragmentManager;
|
FragmentManager fragmentManager;
|
||||||
private boolean isContributionsListFragment = true; // to know what to put in first tab, Contributions of Media Details
|
private boolean isContributionsListFragment = true; // to know what to put in first tab, Contributions of Media Details
|
||||||
|
|
|
||||||
|
|
@ -1,6 +1,5 @@
|
||||||
package fr.free.nrw.commons.contributions;
|
package fr.free.nrw.commons.contributions;
|
||||||
|
|
||||||
import android.app.FragmentManager;
|
|
||||||
import android.content.ComponentName;
|
import android.content.ComponentName;
|
||||||
import android.content.Context;
|
import android.content.Context;
|
||||||
import android.content.Intent;
|
import android.content.Intent;
|
||||||
|
|
@ -12,6 +11,7 @@ import android.graphics.PorterDuff;
|
||||||
import android.os.Bundle;
|
import android.os.Bundle;
|
||||||
import android.os.IBinder;
|
import android.os.IBinder;
|
||||||
import android.support.annotation.Nullable;
|
import android.support.annotation.Nullable;
|
||||||
|
import android.support.v4.app.FragmentManager;
|
||||||
import android.support.v4.app.FragmentTransaction;
|
import android.support.v4.app.FragmentTransaction;
|
||||||
|
|
||||||
import android.support.v4.content.ContextCompat;
|
import android.support.v4.content.ContextCompat;
|
||||||
|
|
@ -30,6 +30,7 @@ import android.widget.TextView;
|
||||||
|
|
||||||
import java.util.ArrayList;
|
import java.util.ArrayList;
|
||||||
import java.util.List;
|
import java.util.List;
|
||||||
|
import java.util.concurrent.CountDownLatch;
|
||||||
|
|
||||||
import javax.inject.Inject;
|
import javax.inject.Inject;
|
||||||
import javax.inject.Named;
|
import javax.inject.Named;
|
||||||
|
|
@ -44,8 +45,10 @@ import fr.free.nrw.commons.mwapi.MediaWikiApi;
|
||||||
import fr.free.nrw.commons.nearby.NearbyPlaces;
|
import fr.free.nrw.commons.nearby.NearbyPlaces;
|
||||||
import fr.free.nrw.commons.notification.Notification;
|
import fr.free.nrw.commons.notification.Notification;
|
||||||
import fr.free.nrw.commons.notification.NotificationController;
|
import fr.free.nrw.commons.notification.NotificationController;
|
||||||
|
import fr.free.nrw.commons.settings.Prefs;
|
||||||
import fr.free.nrw.commons.upload.UploadService;
|
import fr.free.nrw.commons.upload.UploadService;
|
||||||
import io.reactivex.android.schedulers.AndroidSchedulers;
|
import io.reactivex.android.schedulers.AndroidSchedulers;
|
||||||
|
import io.reactivex.disposables.CompositeDisposable;
|
||||||
import io.reactivex.schedulers.Schedulers;
|
import io.reactivex.schedulers.Schedulers;
|
||||||
import timber.log.Timber;
|
import timber.log.Timber;
|
||||||
|
|
||||||
|
|
@ -75,7 +78,8 @@ public class ContributionsFragment
|
||||||
private Cursor allContributions;
|
private Cursor allContributions;
|
||||||
private UploadService uploadService;
|
private UploadService uploadService;
|
||||||
private boolean isUploadServiceConnected;
|
private boolean isUploadServiceConnected;
|
||||||
|
private CompositeDisposable compositeDisposable = new CompositeDisposable();
|
||||||
|
CountDownLatch waitForContributionsListFragment = new CountDownLatch(1);
|
||||||
public TextView numberOfUploads;
|
public TextView numberOfUploads;
|
||||||
public ProgressBar numberOfUploadsProgressBar;
|
public ProgressBar numberOfUploadsProgressBar;
|
||||||
|
|
||||||
|
|
@ -332,6 +336,11 @@ public class ContributionsFragment
|
||||||
return contributionsListFragment.getAdapter().getCount();
|
return contributionsListFragment.getAdapter().getCount();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void notifyDatasetChanged() {
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void registerDataSetObserver(DataSetObserver observer) {
|
public void registerDataSetObserver(DataSetObserver observer) {
|
||||||
Adapter adapter = contributionsListFragment.getAdapter();
|
Adapter adapter = contributionsListFragment.getAdapter();
|
||||||
|
|
@ -354,12 +363,41 @@ public class ContributionsFragment
|
||||||
|
|
||||||
@SuppressWarnings("ConstantConditions")
|
@SuppressWarnings("ConstantConditions")
|
||||||
private void setUploadCount() {
|
private void setUploadCount() {
|
||||||
|
if (getChildFragmentManager().findFragmentByTag(MEDIA_DETAIL_PAGER_FRAGMENT_TAG) != null) {
|
||||||
|
// Means Media Details Fragment is active
|
||||||
|
// TODO: Neslihan ContributionListViewUtils.setIndicatorVisibility(numberOfUploads, numberOfUploadsProgressBar,false, true);
|
||||||
|
|
||||||
|
} else {
|
||||||
|
// Means Contribution List Fragment is visible to user
|
||||||
|
// TODO: Neslihan ContributionListViewUtils.setIndicatorVisibility(numberOfUploads, numberOfUploadsProgressBar,false, false);
|
||||||
|
}
|
||||||
|
compositeDisposable.add(mediaWikiApi
|
||||||
|
.getUploadCount(((ContributionsActivity)getActivity()).sessionManager.getCurrentAccount().name)
|
||||||
|
.subscribeOn(Schedulers.io())
|
||||||
|
.observeOn(AndroidSchedulers.mainThread())
|
||||||
|
.subscribe(this::displayUploadCount,
|
||||||
|
t -> Timber.e(t, "Fetching upload count failed")
|
||||||
|
));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
private void displayUploadCount(Integer uploadCount) {
|
private void displayUploadCount(Integer uploadCount) {
|
||||||
|
if (getActivity().isFinishing()
|
||||||
|
|| numberOfUploads == null
|
||||||
|
|| getResources() == null) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
numberOfUploads.setText(getResources()
|
||||||
|
.getQuantityString(R.plurals.contributions_subtitle,
|
||||||
|
uploadCount, uploadCount));
|
||||||
|
if (getChildFragmentManager().findFragmentByTag(MEDIA_DETAIL_PAGER_FRAGMENT_TAG) != null) {
|
||||||
|
// Means Media Details Fragment is active
|
||||||
|
// TODO: Neslihan ContributionListViewUtils.setIndicatorVisibility(numberOfUploads, numberOfUploadsProgressBar,false, true);
|
||||||
|
|
||||||
|
} else {
|
||||||
|
// Means Contribution List Fragment is visible to user
|
||||||
|
// TODO: Neslihan ContributionListViewUtils.setIndicatorVisibility(numberOfUploads, numberOfUploadsProgressBar,true, false);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
public void betaSetUploadCount(int betaUploadCount) {
|
public void betaSetUploadCount(int betaUploadCount) {
|
||||||
|
|
@ -381,5 +419,35 @@ public class ContributionsFragment
|
||||||
public void updateNearbyNotification(List<NearbyPlaces> nearbyPlaces) {
|
public void updateNearbyNotification(List<NearbyPlaces> nearbyPlaces) {
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void onSaveInstanceState(Bundle outState) {
|
||||||
|
super.onSaveInstanceState(outState);
|
||||||
|
boolean mediaDetailsVisible = mediaDetailPagerFragment != null && mediaDetailPagerFragment.isVisible();
|
||||||
|
outState.putBoolean("mediaDetailsVisible", mediaDetailsVisible);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void onResume() {
|
||||||
|
super.onResume();
|
||||||
|
boolean isSettingsChanged = prefs.getBoolean(Prefs.IS_CONTRIBUTION_COUNT_CHANGED, false);
|
||||||
|
prefs.edit().putBoolean(Prefs.IS_CONTRIBUTION_COUNT_CHANGED, false).apply();
|
||||||
|
if (isSettingsChanged) {
|
||||||
|
refreshSource();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void onDestroy() {
|
||||||
|
compositeDisposable.clear();
|
||||||
|
getChildFragmentManager().removeOnBackStackChangedListener(this);
|
||||||
|
super.onDestroy();
|
||||||
|
|
||||||
|
if (isUploadServiceConnected) {
|
||||||
|
if (getActivity() != null) {
|
||||||
|
getActivity().unbindService(uploadServiceConnection);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -1,44 +1,32 @@
|
||||||
package fr.free.nrw.commons.contributions;
|
package fr.free.nrw.commons.contributions;
|
||||||
|
|
||||||
import android.content.Intent;
|
import android.content.Context;
|
||||||
import android.content.SharedPreferences;
|
|
||||||
import android.content.pm.PackageManager;
|
|
||||||
import android.os.Build;
|
|
||||||
import android.os.Bundle;
|
import android.os.Bundle;
|
||||||
import android.support.annotation.NonNull;
|
import android.support.annotation.Nullable;
|
||||||
import android.support.v4.content.ContextCompat;
|
import android.support.design.widget.FloatingActionButton;
|
||||||
import android.support.v7.app.AlertDialog;
|
|
||||||
import android.view.LayoutInflater;
|
import android.view.LayoutInflater;
|
||||||
import android.view.Menu;
|
|
||||||
import android.view.MenuInflater;
|
|
||||||
import android.view.MenuItem;
|
|
||||||
import android.view.View;
|
import android.view.View;
|
||||||
import android.view.ViewGroup;
|
import android.view.ViewGroup;
|
||||||
|
import android.view.animation.Animation;
|
||||||
|
import android.view.animation.AnimationUtils;
|
||||||
import android.widget.AdapterView;
|
import android.widget.AdapterView;
|
||||||
import android.widget.GridView;
|
import android.widget.GridView;
|
||||||
import android.widget.ListAdapter;
|
import android.widget.ListAdapter;
|
||||||
import android.widget.ProgressBar;
|
import android.widget.ProgressBar;
|
||||||
import android.widget.TextView;
|
import android.widget.TextView;
|
||||||
|
|
||||||
import java.util.Arrays;
|
|
||||||
|
|
||||||
import javax.inject.Inject;
|
|
||||||
import javax.inject.Named;
|
|
||||||
|
|
||||||
import butterknife.BindView;
|
import butterknife.BindView;
|
||||||
import butterknife.ButterKnife;
|
import butterknife.ButterKnife;
|
||||||
import fr.free.nrw.commons.BuildConfig;
|
import fr.free.nrw.commons.BuildConfig;
|
||||||
import fr.free.nrw.commons.R;
|
import fr.free.nrw.commons.R;
|
||||||
import fr.free.nrw.commons.di.CommonsDaggerSupportFragment;
|
import fr.free.nrw.commons.di.CommonsDaggerSupportFragment;
|
||||||
import fr.free.nrw.commons.nearby.NearbyActivity;
|
|
||||||
import timber.log.Timber;
|
|
||||||
|
|
||||||
import static android.Manifest.permission.READ_EXTERNAL_STORAGE;
|
|
||||||
import static android.Manifest.permission.WRITE_EXTERNAL_STORAGE;
|
|
||||||
import static android.app.Activity.RESULT_OK;
|
|
||||||
import static android.content.pm.PackageManager.PERMISSION_GRANTED;
|
|
||||||
import static android.view.View.GONE;
|
import static android.view.View.GONE;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Created by root on 01.06.2018.
|
||||||
|
*/
|
||||||
|
|
||||||
public class ContributionsListFragment extends CommonsDaggerSupportFragment {
|
public class ContributionsListFragment extends CommonsDaggerSupportFragment {
|
||||||
|
|
||||||
@BindView(R.id.contributionsList)
|
@BindView(R.id.contributionsList)
|
||||||
|
|
@ -47,252 +35,108 @@ public class ContributionsListFragment extends CommonsDaggerSupportFragment {
|
||||||
TextView waitingMessage;
|
TextView waitingMessage;
|
||||||
@BindView(R.id.loadingContributionsProgressBar)
|
@BindView(R.id.loadingContributionsProgressBar)
|
||||||
ProgressBar progressBar;
|
ProgressBar progressBar;
|
||||||
|
@BindView(R.id.fab_plus)
|
||||||
|
FloatingActionButton fabPlus;
|
||||||
|
@BindView(R.id.fab_camera)
|
||||||
|
FloatingActionButton fabCamera;
|
||||||
|
@BindView(R.id.fab_galery)
|
||||||
|
FloatingActionButton fabGalery;
|
||||||
|
|
||||||
@Inject
|
private Animation fab_close;
|
||||||
@Named("prefs")
|
private Animation fab_open;
|
||||||
SharedPreferences prefs;
|
private Animation rotate_forward;
|
||||||
@Inject
|
private Animation rotate_backward;
|
||||||
@Named("default_preferences")
|
|
||||||
SharedPreferences defaultPrefs;
|
|
||||||
|
|
||||||
private ContributionController controller;
|
|
||||||
|
|
||||||
|
|
||||||
@Override
|
private boolean isFabOpen = false;
|
||||||
public View onCreateView(LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState) {
|
|
||||||
View v = inflater.inflate(R.layout.fragment_contributions_list, container, false);
|
|
||||||
ButterKnife.bind(this, v);
|
|
||||||
|
|
||||||
contributionsList.setOnItemClickListener((AdapterView.OnItemClickListener) getActivity());
|
public View onCreateView(LayoutInflater inflater, @Nullable ViewGroup container, @Nullable Bundle savedInstanceState) {
|
||||||
if (savedInstanceState != null) {
|
View view = inflater.inflate(R.layout.fragment_contributions_list, container, false);
|
||||||
Timber.d("Scrolling to %d", savedInstanceState.getInt("grid-position"));
|
ButterKnife.bind(this, view);
|
||||||
contributionsList.setSelection(savedInstanceState.getInt("grid-position"));
|
|
||||||
}
|
|
||||||
|
|
||||||
//TODO: Should this be in onResume?
|
contributionsList.setOnItemClickListener((AdapterView.OnItemClickListener) getParentFragment());
|
||||||
String lastModified = prefs.getString("lastSyncTimestamp", "");
|
|
||||||
Timber.d("Last Sync Timestamp: %s", lastModified);
|
|
||||||
|
|
||||||
if (lastModified.equals("")) {
|
|
||||||
waitingMessage.setVisibility(View.VISIBLE);
|
|
||||||
} else {
|
|
||||||
waitingMessage.setVisibility(GONE);
|
|
||||||
}
|
|
||||||
|
|
||||||
changeProgressBarVisibility(true);
|
changeProgressBarVisibility(true);
|
||||||
return v;
|
return view;
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void onViewCreated(View view, @Nullable Bundle savedInstanceState) {
|
||||||
|
super.onViewCreated(view, savedInstanceState);
|
||||||
|
initializeAnimations();
|
||||||
|
setListeners();
|
||||||
|
}
|
||||||
|
|
||||||
|
private void initializeAnimations() {
|
||||||
|
fab_open = AnimationUtils.loadAnimation(getActivity(), R.anim.fab_open);
|
||||||
|
fab_close = AnimationUtils.loadAnimation(getActivity(), R.anim.fab_close);
|
||||||
|
rotate_forward = AnimationUtils.loadAnimation(getActivity(), R.anim.rotate_forward);
|
||||||
|
rotate_backward = AnimationUtils.loadAnimation(getActivity(), R.anim.rotate_backward);
|
||||||
|
}
|
||||||
|
|
||||||
|
private void setListeners() {
|
||||||
|
fabPlus.setOnClickListener(view -> animateFAB(isFabOpen));
|
||||||
|
}
|
||||||
|
|
||||||
|
private void animateFAB(boolean isFabOpen) {
|
||||||
|
this.isFabOpen = !isFabOpen;
|
||||||
|
if (fabPlus.isShown()){
|
||||||
|
if (isFabOpen) {
|
||||||
|
fabPlus.startAnimation(rotate_backward);
|
||||||
|
fabCamera.startAnimation(fab_close);
|
||||||
|
fabGalery.startAnimation(fab_close);
|
||||||
|
fabCamera.hide();
|
||||||
|
fabGalery.hide();
|
||||||
|
} else {
|
||||||
|
fabPlus.startAnimation(rotate_forward);
|
||||||
|
fabCamera.startAnimation(fab_open);
|
||||||
|
fabGalery.startAnimation(fab_open);
|
||||||
|
fabCamera.show();
|
||||||
|
fabGalery.show();
|
||||||
|
}
|
||||||
|
this.isFabOpen=!isFabOpen;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void onAttach(Context context) {
|
||||||
|
super.onAttach(context);
|
||||||
|
ContributionsFragment parentFragment = (ContributionsFragment)getParentFragment();
|
||||||
|
parentFragment.waitForContributionsListFragment.countDown();
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Responsible to set progress bar invisible and visible
|
||||||
|
* @param isVisible True when contributions list should be hidden.
|
||||||
|
*/
|
||||||
|
public void changeProgressBarVisibility(boolean isVisible) {
|
||||||
|
this.progressBar.setVisibility(isVisible ? View.VISIBLE : View.GONE);
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Clears sync message displayed with progress bar before contributions list became visible
|
||||||
|
*/
|
||||||
|
protected void clearSyncMessage() {
|
||||||
|
waitingMessage.setVisibility(GONE);
|
||||||
}
|
}
|
||||||
|
|
||||||
public ListAdapter getAdapter() {
|
public ListAdapter getAdapter() {
|
||||||
return contributionsList.getAdapter();
|
return contributionsList.getAdapter();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Sets adapter to contributions list. If beta mode, sets upload count for beta explicitly.
|
||||||
|
* @param adapter List adapter for uploads of contributor
|
||||||
|
*/
|
||||||
public void setAdapter(ListAdapter adapter) {
|
public void setAdapter(ListAdapter adapter) {
|
||||||
this.contributionsList.setAdapter(adapter);
|
this.contributionsList.setAdapter(adapter);
|
||||||
|
|
||||||
if(BuildConfig.FLAVOR.equalsIgnoreCase("beta")){
|
if(BuildConfig.FLAVOR.equalsIgnoreCase("beta")){
|
||||||
// TODO: Neslihan open later ((ContributionsActivity) getActivity()).betaSetUploadCount(adapter.getCount());
|
//TODO: add betaSetUploadCount method
|
||||||
|
((ContributionsFragment) getParentFragment()).betaSetUploadCount(adapter.getCount());
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
public void changeProgressBarVisibility(boolean isVisible) {
|
|
||||||
this.progressBar.setVisibility(isVisible ? View.VISIBLE : View.GONE);
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public void onSaveInstanceState(Bundle outState) {
|
|
||||||
if (outState == null) {
|
|
||||||
outState = new Bundle();
|
|
||||||
}
|
|
||||||
super.onSaveInstanceState(outState);
|
|
||||||
controller.saveState(outState);
|
|
||||||
outState.putInt("grid-position", contributionsList.getFirstVisiblePosition());
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public void onActivityResult(int requestCode, int resultCode, Intent data) {
|
|
||||||
//FIXME: must get the file data for Google Photos when receive the intent answer, in the onActivityResult method
|
|
||||||
super.onActivityResult(requestCode, resultCode, data);
|
|
||||||
|
|
||||||
if (resultCode == RESULT_OK) {
|
|
||||||
Timber.d("OnActivityResult() parameters: Req code: %d Result code: %d Data: %s",
|
|
||||||
requestCode, resultCode, data);
|
|
||||||
if (requestCode == ContributionController.SELECT_FROM_CAMERA) {
|
|
||||||
// If coming from camera, pass null as uri. Because camera photos get saved to a
|
|
||||||
// fixed directory
|
|
||||||
controller.handleImagePicked(requestCode, null, false, null);
|
|
||||||
} else {
|
|
||||||
controller.handleImagePicked(requestCode, data.getData(), false, null);
|
|
||||||
}
|
|
||||||
} else {
|
|
||||||
Timber.e("OnActivityResult() parameters: Req code: %d Result code: %d Data: %s",
|
|
||||||
requestCode, resultCode, data);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public boolean onOptionsItemSelected(MenuItem item) {
|
|
||||||
switch (item.getItemId()) {
|
|
||||||
case R.id.menu_from_gallery:
|
|
||||||
//Gallery crashes before reach ShareActivity screen so must implement permissions check here
|
|
||||||
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.M) {
|
|
||||||
|
|
||||||
// Here, thisActivity is the current activity
|
|
||||||
if (ContextCompat.checkSelfPermission(getActivity(),
|
|
||||||
READ_EXTERNAL_STORAGE)
|
|
||||||
!= PERMISSION_GRANTED) {
|
|
||||||
|
|
||||||
// Should we show an explanation?
|
|
||||||
if (shouldShowRequestPermissionRationale(READ_EXTERNAL_STORAGE)) {
|
|
||||||
|
|
||||||
// Show an explanation to the user *asynchronously* -- don't block
|
|
||||||
// this thread waiting for the user's response! After the user
|
|
||||||
// sees the explanation, try again to request the permission.
|
|
||||||
|
|
||||||
new AlertDialog.Builder(getActivity())
|
|
||||||
.setMessage(getString(R.string.read_storage_permission_rationale))
|
|
||||||
.setPositiveButton(android.R.string.ok, (dialog, which) -> {
|
|
||||||
requestPermissions(new String[]{READ_EXTERNAL_STORAGE}, 1);
|
|
||||||
dialog.dismiss();
|
|
||||||
})
|
|
||||||
.setNegativeButton(android.R.string.cancel, null)
|
|
||||||
.create()
|
|
||||||
.show();
|
|
||||||
|
|
||||||
} else {
|
|
||||||
|
|
||||||
// No explanation needed, we can request the permission.
|
|
||||||
|
|
||||||
requestPermissions(new String[]{READ_EXTERNAL_STORAGE},
|
|
||||||
1);
|
|
||||||
|
|
||||||
// MY_PERMISSIONS_REQUEST_READ_CONTACTS is an
|
|
||||||
// app-defined int constant. The callback method gets the
|
|
||||||
// result of the request.
|
|
||||||
}
|
|
||||||
} else {
|
|
||||||
controller.startGalleryPick();
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
|
|
||||||
} else {
|
|
||||||
controller.startGalleryPick();
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
|
|
||||||
return true;
|
|
||||||
case R.id.menu_from_camera:
|
|
||||||
boolean useExtStorage = defaultPrefs.getBoolean("useExternalStorage", true);
|
|
||||||
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.M && useExtStorage) {
|
|
||||||
// Here, thisActivity is the current activity
|
|
||||||
if (ContextCompat.checkSelfPermission(getActivity(), WRITE_EXTERNAL_STORAGE)
|
|
||||||
!= PackageManager.PERMISSION_GRANTED) {
|
|
||||||
if (shouldShowRequestPermissionRationale(WRITE_EXTERNAL_STORAGE)) {
|
|
||||||
// Show an explanation to the user *asynchronously* -- don't block
|
|
||||||
// this thread waiting for the user's response! After the user
|
|
||||||
// sees the explanation, try again to request the permission.
|
|
||||||
new AlertDialog.Builder(getActivity())
|
|
||||||
.setMessage(getString(R.string.write_storage_permission_rationale))
|
|
||||||
.setPositiveButton(android.R.string.ok, (dialog, which) -> {
|
|
||||||
requestPermissions(new String[]{WRITE_EXTERNAL_STORAGE}, 3);
|
|
||||||
dialog.dismiss();
|
|
||||||
})
|
|
||||||
.setNegativeButton(android.R.string.cancel, null)
|
|
||||||
.create()
|
|
||||||
.show();
|
|
||||||
} else {
|
|
||||||
// No explanation needed, we can request the permission.
|
|
||||||
requestPermissions(new String[]{WRITE_EXTERNAL_STORAGE},
|
|
||||||
3);
|
|
||||||
// MY_PERMISSIONS_WRITE_EXTERNAL_STORAGE is an
|
|
||||||
// app-defined int constant. The callback method gets the
|
|
||||||
// result of the request.
|
|
||||||
}
|
|
||||||
} else {
|
|
||||||
controller.startCameraCapture();
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
} else {
|
|
||||||
controller.startCameraCapture();
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
return true;
|
|
||||||
default:
|
|
||||||
return super.onOptionsItemSelected(item);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public void onRequestPermissionsResult(int requestCode, @NonNull String[] permissions,
|
|
||||||
@NonNull int[] grantResults) {
|
|
||||||
Timber.d("onRequestPermissionsResult: req code = " + " perm = "
|
|
||||||
+ Arrays.toString(permissions) + " grant =" + Arrays.toString(grantResults));
|
|
||||||
|
|
||||||
switch (requestCode) {
|
|
||||||
// 1 = Storage allowed when gallery selected
|
|
||||||
case 1: {
|
|
||||||
if (grantResults.length > 0 && grantResults[0] == PERMISSION_GRANTED) {
|
|
||||||
Timber.d("Call controller.startGalleryPick()");
|
|
||||||
controller.startGalleryPick();
|
|
||||||
}
|
|
||||||
}
|
|
||||||
break;
|
|
||||||
// 2 = Location allowed when 'nearby places' selected
|
|
||||||
case 2: {
|
|
||||||
if (grantResults.length > 0 && grantResults[0] == PERMISSION_GRANTED) {
|
|
||||||
Timber.d("Location permission granted");
|
|
||||||
Intent nearbyIntent = new Intent(getActivity(), NearbyActivity.class);
|
|
||||||
startActivity(nearbyIntent);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
break;
|
|
||||||
case 3: {
|
|
||||||
if (grantResults.length > 0 && grantResults[0] == PackageManager.PERMISSION_GRANTED) {
|
|
||||||
Timber.d("Call controller.startCameraCapture()");
|
|
||||||
controller.startCameraCapture();
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public void onCreateOptionsMenu(Menu menu, MenuInflater inflater) {
|
|
||||||
menu.clear(); // See http://stackoverflow.com/a/8495697/17865
|
|
||||||
inflater.inflate(R.menu.fragment_contributions_list, menu);
|
|
||||||
|
|
||||||
if (!deviceHasCamera()) {
|
|
||||||
menu.findItem(R.id.menu_from_camera).setEnabled(false);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
public boolean deviceHasCamera() {
|
|
||||||
PackageManager pm = getContext().getPackageManager();
|
|
||||||
return pm.hasSystemFeature(PackageManager.FEATURE_CAMERA) ||
|
|
||||||
pm.hasSystemFeature(PackageManager.FEATURE_CAMERA_FRONT);
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public void onCreate(Bundle savedInstanceState) {
|
|
||||||
super.onCreate(savedInstanceState);
|
|
||||||
controller = new ContributionController(this);
|
|
||||||
setHasOptionsMenu(true);
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public void onDestroy() {
|
|
||||||
super.onDestroy();
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public void onActivityCreated(Bundle savedInstanceState) {
|
|
||||||
super.onActivityCreated(savedInstanceState);
|
|
||||||
controller.loadState(savedInstanceState);
|
|
||||||
}
|
|
||||||
|
|
||||||
protected void clearSyncMessage() {
|
|
||||||
waitingMessage.setVisibility(GONE);
|
|
||||||
}
|
|
||||||
|
|
||||||
public interface SourceRefresher {
|
public interface SourceRefresher {
|
||||||
void refreshSource();
|
void refreshSource();
|
||||||
}
|
}
|
||||||
|
|
|
||||||
Loading…
Add table
Add a link
Reference in a new issue