diff --git a/CHANGELOG.md b/CHANGELOG.md
index 035835839..7f3dfc30a 100644
--- a/CHANGELOG.md
+++ b/CHANGELOG.md
@@ -1,5 +1,15 @@
# Wikimedia Commons for Android
+## v2.7.0
+- New Nearby Places UI with direct uploads (and associated category suggestions)
+- Added two-factor authentication login
+- Added Notifications activity to display user talk messages
+- Added real-time location tracking in Nearby
+- Added "rate us", "translate", and FB link in About
+- Improvements to UI of navigation drawer, tutorial, media details view, login activity and Settings
+- Added option to nominate picture for deletion in media details view
+- Too many bug and crash fixes to mention!
+
## v2.6.7
- Added null checks to prevent frequent crashes in ModificationsSyncAdapter
diff --git a/CONTRIBUTING.md b/CONTRIBUTING.md
index ee7f42e06..0f1feeac7 100644
--- a/CONTRIBUTING.md
+++ b/CONTRIBUTING.md
@@ -1 +1,19 @@
-Please see our guidelines in the wiki: https://github.com/commons-app/apps-android-commons/wiki/Volunteers-welcome%21
+Thanks for considering to contribute to this project! A few guidelines for
+people who want to contribute their code to this software are documented in
+[this project's Wiki](https://github.com/commons-app/apps-android-commons/wiki/Contributing-Guidelines).
+If you're not sure where to start head on to [this wiki page](https://github.com/commons-app/apps-android-commons/wiki/Volunteers-welcome!).
+
+Here's a gist of the guidelines,
+
+# Make separate commits for logically separate changes
+
+# Describe your changes well in the commit message
+
+The first line of the commit message should be a short description of what has
+changed. It is also good to prefix the first line with "area: " where the "area"
+is a filename or identifier for the general area of the code being modified.
+The body should provide a meaningful commit message.
+
+# Write tests for your code (if possible)
+
+# Make sure the Wiki pages don't become stale by updating them (if needed)
diff --git a/CREDITS b/CREDITS
index a4a4ae0f5..6847ac9b6 100644
--- a/CREDITS
+++ b/CREDITS
@@ -30,6 +30,16 @@ their contribution to the product.
* Bruke Mekuria Mulugeta
* Paul Hawke
* Vishan Seru
+* Abhishek Poonia
+* Ayushi Negi
+* Harisanker Pradeep
+* Hassan Ismaeel
+* Jatin Rao
+* Meghna Gupta
+* S Balakrishnan
+* Suchit Kar
+* Tanvi Dadu
+* Ujjwal Agrawal
3rd party open source libraries used:
* Butterknife
diff --git a/app/build.gradle b/app/build.gradle
index 06996d5a6..46008d1c2 100644
--- a/app/build.gradle
+++ b/app/build.gradle
@@ -11,18 +11,19 @@ dependencies {
implementation 'fr.avianey.com.viewpagerindicator:library:2.4.1.1@aar'
implementation 'in.yuvi:http.fluent:1.3'
implementation 'com.android.volley:volley:1.0.0'
- implementation 'ch.acra:acra:4.7.0'
+ implementation 'ch.acra:acra:4.9.2'
implementation 'org.mediawiki:api:1.3'
implementation 'commons-codec:commons-codec:1.10'
implementation 'com.github.pedrovgs:renderers:3.3.3'
implementation 'com.google.code.gson:gson:2.8.1'
implementation 'com.jakewharton.timber:timber:4.5.1'
implementation 'info.debatty:java-string-similarity:0.24'
+ implementation 'com.borjabravo:readmoretextview:2.1.0'
+ implementation 'com.android.support.constraint:constraint-layout:1.0.2'
implementation ('com.mapbox.mapboxsdk:mapbox-android-sdk:5.4.1@aar'){
transitive=true
}
-
implementation "com.android.support:support-v4:$SUPPORT_LIB_VERSION"
implementation "com.android.support:appcompat-v7:$SUPPORT_LIB_VERSION"
implementation "com.android.support:design:$SUPPORT_LIB_VERSION"
@@ -41,8 +42,6 @@ dependencies {
// explicitly depend on RxJava's latest version for bug fixes and new features.
implementation 'com.android.support:multidex:1.0.3'
- testImplementation "org.robolectric:multidex:3.4.2"
-
implementation 'io.reactivex.rxjava2:rxjava:2.1.2'
implementation 'com.jakewharton.rxbinding2:rxbinding:2.0.0'
implementation 'com.jakewharton.rxbinding2:rxbinding-support-v4:2.0.0'
@@ -54,33 +53,25 @@ dependencies {
implementation "com.google.dagger:dagger:$DAGGER_VERSION"
implementation "com.google.dagger:dagger-android-support:$DAGGER_VERSION"
-
kapt "com.google.dagger:dagger-android-processor:$DAGGER_VERSION"
kapt "com.google.dagger:dagger-compiler:$DAGGER_VERSION"
+ testImplementation "org.robolectric:multidex:3.4.2"
testImplementation "org.jetbrains.kotlin:kotlin-stdlib-jre7:$kotlin_version"
- androidTestImplementation "org.jetbrains.kotlin:kotlin-stdlib-jre7:$kotlin_version"
-
+ testImplementation "org.jetbrains.kotlin:kotlin-reflect:$kotlin_version"
testImplementation 'junit:junit:4.12'
testImplementation 'org.robolectric:robolectric:3.7.1'
- testImplementation 'org.mockito:mockito-all:1.10.19'
-
+ testImplementation 'com.nhaarman:mockito-kotlin:1.5.0'
testImplementation 'com.squareup.okhttp3:mockwebserver:3.8.1'
+
+ androidTestImplementation "org.jetbrains.kotlin:kotlin-stdlib-jre7:$kotlin_version"
androidTestImplementation 'com.squareup.okhttp3:mockwebserver:3.8.1'
androidTestImplementation "com.android.support:support-annotations:$SUPPORT_LIB_VERSION"
- androidTestImplementation 'com.android.support.test.espresso:espresso-core:3.0.1'
+ androidTestImplementation 'com.android.support.test.espresso:espresso-core:3.0.2-alpha1'
debugImplementation "com.squareup.leakcanary:leakcanary-android:$LEAK_CANARY"
releaseImplementation "com.squareup.leakcanary:leakcanary-android-no-op:$LEAK_CANARY"
testImplementation "com.squareup.leakcanary:leakcanary-android-no-op:$LEAK_CANARY"
-
- implementation "com.google.dagger:dagger:$DAGGER_VERSION"
- implementation "com.google.dagger:dagger-android-support:$DAGGER_VERSION"
- kapt "com.google.dagger:dagger-compiler:$DAGGER_VERSION"
- kapt "com.google.dagger:dagger-android-processor:$DAGGER_VERSION"
-
- implementation 'com.borjabravo:readmoretextview:2.1.0'
- implementation 'com.android.support.constraint:constraint-layout:1.0.2'
}
android {
@@ -91,8 +82,8 @@ android {
defaultConfig {
applicationId 'fr.free.nrw.commons'
- versionCode 82
- versionName '2.6.7'
+ versionCode 83
+ versionName '2.7.0'
setProperty("archivesBaseName", "app-commons-v$versionName-" + getBranchName())
minSdkVersion project.minSdkVersion
diff --git a/app/src/main/AndroidManifest.xml b/app/src/main/AndroidManifest.xml
index 253bdaea8..6aab09b55 100644
--- a/app/src/main/AndroidManifest.xml
+++ b/app/src/main/AndroidManifest.xml
@@ -91,6 +91,10 @@
android:name=".notification.NotificationActivity"
android:label="@string/navigation_item_notification" />
+
+
languageAdapter = new ArrayAdapter(AboutActivity.this,
diff --git a/app/src/main/java/fr/free/nrw/commons/CommonsApplication.java b/app/src/main/java/fr/free/nrw/commons/CommonsApplication.java
index 5638db97e..57cb5fad1 100644
--- a/app/src/main/java/fr/free/nrw/commons/CommonsApplication.java
+++ b/app/src/main/java/fr/free/nrw/commons/CommonsApplication.java
@@ -54,9 +54,11 @@ public class CommonsApplication extends MultiDexApplication {
public static final String FEEDBACK_EMAIL = "commons-app-android@googlegroups.com";
+ public static final String FEEDBACK_EMAIL_SUBJECT = "Commons Android App (%s) Feedback";
+
public static final String LOGS_PRIVATE_EMAIL = "commons-app-android-private@googlegroups.com";
- public static final String FEEDBACK_EMAIL_SUBJECT = "Commons Android App (%s) Feedback";
+ public static final String LOGS_PRIVATE_EMAIL_SUBJECT = "Commons Android App (%s) Logs";
private RefWatcher refWatcher;
diff --git a/app/src/main/java/fr/free/nrw/commons/category/CategorizationFragment.java b/app/src/main/java/fr/free/nrw/commons/category/CategorizationFragment.java
index a873136fe..a41a52139 100644
--- a/app/src/main/java/fr/free/nrw/commons/category/CategorizationFragment.java
+++ b/app/src/main/java/fr/free/nrw/commons/category/CategorizationFragment.java
@@ -280,8 +280,11 @@ public class CategorizationFragment extends CommonsDaggerSupportFragment {
private Observable directCategories() {
String directCategory = directPrefs.getString("Category", "");
+ // Strip newlines to prevent blank categories, and to tidy existing categories
+ directCategory = directCategory.replace("\n", "");
+
List categoryList = new ArrayList<>();
- Timber.d("Direct category found: " + directCategory);
+ Timber.d("Direct category found: " + "'" + directCategory + "'");
if (!directCategory.equals("")) {
hasDirectCategories = true;
diff --git a/app/src/main/java/fr/free/nrw/commons/category/CategoryDao.java b/app/src/main/java/fr/free/nrw/commons/category/CategoryDao.java
index a5202046b..010e97095 100644
--- a/app/src/main/java/fr/free/nrw/commons/category/CategoryDao.java
+++ b/app/src/main/java/fr/free/nrw/commons/category/CategoryDao.java
@@ -105,6 +105,7 @@ public class CategoryDao {
return items;
}
+ @NonNull
Category fromCursor(Cursor cursor) {
// Hardcoding column positions!
return new Category(
diff --git a/app/src/main/java/fr/free/nrw/commons/di/ActivityBuilderModule.java b/app/src/main/java/fr/free/nrw/commons/di/ActivityBuilderModule.java
index e4fb13427..f88f3b34a 100644
--- a/app/src/main/java/fr/free/nrw/commons/di/ActivityBuilderModule.java
+++ b/app/src/main/java/fr/free/nrw/commons/di/ActivityBuilderModule.java
@@ -7,6 +7,7 @@ import fr.free.nrw.commons.WelcomeActivity;
import fr.free.nrw.commons.auth.LoginActivity;
import fr.free.nrw.commons.auth.SignupActivity;
import fr.free.nrw.commons.contributions.ContributionsActivity;
+import fr.free.nrw.commons.featured.FeaturedImagesActivity;
import fr.free.nrw.commons.nearby.NearbyActivity;
import fr.free.nrw.commons.notification.NotificationActivity;
import fr.free.nrw.commons.settings.SettingsActivity;
@@ -46,4 +47,7 @@ public abstract class ActivityBuilderModule {
@ContributesAndroidInjector
abstract NotificationActivity bindNotificationActivity();
+
+ @ContributesAndroidInjector
+ abstract FeaturedImagesActivity bindFeaturedImagesActivity();
}
diff --git a/app/src/main/java/fr/free/nrw/commons/di/FragmentBuilderModule.java b/app/src/main/java/fr/free/nrw/commons/di/FragmentBuilderModule.java
index a94f46ca9..c5cdcb5a7 100644
--- a/app/src/main/java/fr/free/nrw/commons/di/FragmentBuilderModule.java
+++ b/app/src/main/java/fr/free/nrw/commons/di/FragmentBuilderModule.java
@@ -4,6 +4,7 @@ import dagger.Module;
import dagger.android.ContributesAndroidInjector;
import fr.free.nrw.commons.category.CategorizationFragment;
import fr.free.nrw.commons.contributions.ContributionsListFragment;
+import fr.free.nrw.commons.featured.FeaturedImagesListFragment;
import fr.free.nrw.commons.media.MediaDetailFragment;
import fr.free.nrw.commons.media.MediaDetailPagerFragment;
import fr.free.nrw.commons.nearby.NearbyListFragment;
@@ -47,4 +48,7 @@ public abstract class FragmentBuilderModule {
@ContributesAndroidInjector
abstract SingleUploadFragment bindSingleUploadFragment();
+ @ContributesAndroidInjector
+ abstract FeaturedImagesListFragment bindFeaturedImagesListFragment();
+
}
diff --git a/app/src/main/java/fr/free/nrw/commons/featured/FeaturedImage.java b/app/src/main/java/fr/free/nrw/commons/featured/FeaturedImage.java
new file mode 100644
index 000000000..853fba29e
--- /dev/null
+++ b/app/src/main/java/fr/free/nrw/commons/featured/FeaturedImage.java
@@ -0,0 +1,44 @@
+package fr.free.nrw.commons.featured;
+
+
+import fr.free.nrw.commons.Media;
+
+/**
+ * Object to hold FeaturedImage
+ */
+
+public class FeaturedImage {
+ private Media image;
+ private String author;
+ private String fileName;
+
+ public FeaturedImage(Media image, String author, String fileName) {
+ this.image = image;
+ this.author = author;
+ this.fileName = fileName;
+ }
+
+ public Media getImage() {
+ return image;
+ }
+
+ public void setImage(Media image) {
+ this.image = image;
+ }
+
+ public String getAuthor() {
+ return author;
+ }
+
+ public void setAuthor(String author) {
+ this.author = author;
+ }
+
+ public String getFileName() {
+ return fileName;
+ }
+
+ public void setFileName(String fileName) {
+ this.fileName = fileName;
+ }
+}
diff --git a/app/src/main/java/fr/free/nrw/commons/featured/FeaturedImagesActivity.java b/app/src/main/java/fr/free/nrw/commons/featured/FeaturedImagesActivity.java
new file mode 100644
index 000000000..a2dc7b00b
--- /dev/null
+++ b/app/src/main/java/fr/free/nrw/commons/featured/FeaturedImagesActivity.java
@@ -0,0 +1,114 @@
+package fr.free.nrw.commons.featured;
+
+import android.database.DataSetObserver;
+import android.os.Bundle;
+import android.support.v4.app.FragmentManager;
+import android.view.View;
+import android.widget.AdapterView;
+
+import butterknife.ButterKnife;
+import fr.free.nrw.commons.Media;
+import fr.free.nrw.commons.R;
+import fr.free.nrw.commons.auth.AuthenticatedActivity;
+import fr.free.nrw.commons.media.MediaDetailPagerFragment;
+
+/**
+ * This activity displays pic of the days of last xx days
+ */
+
+public class FeaturedImagesActivity
+ extends AuthenticatedActivity
+ implements FragmentManager.OnBackStackChangedListener,
+ MediaDetailPagerFragment.MediaDetailProvider,
+ AdapterView.OnItemClickListener{
+
+ private FeaturedImagesListFragment featuredImagesListFragment;
+ private MediaDetailPagerFragment mediaDetails;
+
+ @Override
+ protected void onAuthCookieAcquired(String authCookie) {
+
+ }
+
+ @Override
+ protected void onAuthFailure() {
+
+ }
+
+ @Override
+ protected void onCreate(Bundle savedInstanceState) {
+ super.onCreate(savedInstanceState);
+ setContentView(R.layout.activity_featured_images);
+ ButterKnife.bind(this);
+
+ // Activity can call methods in the fragment by acquiring a
+ // reference to the Fragment from FragmentManager, using findFragmentById()
+ FragmentManager supportFragmentManager = getSupportFragmentManager();
+ featuredImagesListFragment = (FeaturedImagesListFragment)supportFragmentManager
+ .findFragmentById(R.id.featuedListFragment);
+
+ supportFragmentManager.addOnBackStackChangedListener(this);
+ if (savedInstanceState != null) {
+ mediaDetails = (MediaDetailPagerFragment)supportFragmentManager
+ .findFragmentById(R.id.featuredFragmentContainer);
+
+ }
+ requestAuthToken();
+ initDrawer();
+ setTitle(getString(R.string.title_activity_featured_images));
+ }
+
+ @Override
+ public void onBackStackChanged() {
+
+ }
+
+ @Override
+ public void onItemClick(AdapterView> adapterView, View view, int i, long l) {
+ if (mediaDetails == null || !mediaDetails.isVisible()) {
+ // set isFeaturedImage true for featured images, to include author field on media detail
+ mediaDetails = new MediaDetailPagerFragment(false, true);
+ FragmentManager supportFragmentManager = getSupportFragmentManager();
+ supportFragmentManager
+ .beginTransaction()
+ .replace(R.id.featuredFragmentContainer, mediaDetails)
+ .addToBackStack(null)
+ .commit();
+ supportFragmentManager.executePendingTransactions();
+ }
+ mediaDetails.showImage(i);
+ }
+
+ @Override
+ public Media getMediaAtPosition(int i) {
+ if (featuredImagesListFragment.getAdapter() == null) {
+ // not yet ready to return data
+ return null;
+ } else {
+ return ((FeaturedImage)featuredImagesListFragment.getAdapter().getItem(i)).getImage();
+ }
+ }
+
+ @Override
+ public int getTotalMediaCount() {
+ if (featuredImagesListFragment.getAdapter() == null) {
+ return 0;
+ }
+ return featuredImagesListFragment.getAdapter().getCount();
+ }
+
+ @Override
+ public void notifyDatasetChanged() {
+
+ }
+
+ @Override
+ public void registerDataSetObserver(DataSetObserver observer) {
+
+ }
+
+ @Override
+ public void unregisterDataSetObserver(DataSetObserver observer) {
+
+ }
+}
diff --git a/app/src/main/java/fr/free/nrw/commons/featured/FeaturedImagesListFragment.java b/app/src/main/java/fr/free/nrw/commons/featured/FeaturedImagesListFragment.java
new file mode 100644
index 000000000..3e5c37bd6
--- /dev/null
+++ b/app/src/main/java/fr/free/nrw/commons/featured/FeaturedImagesListFragment.java
@@ -0,0 +1,57 @@
+package fr.free.nrw.commons.featured;
+
+import android.os.Bundle;
+import android.support.annotation.Nullable;
+import android.view.LayoutInflater;
+import android.view.View;
+import android.view.ViewGroup;
+import android.widget.AdapterView;
+import android.widget.GridView;
+import android.widget.ListAdapter;
+
+import java.util.ArrayList;
+
+import butterknife.ButterKnife;
+import dagger.android.support.DaggerFragment;
+import fr.free.nrw.commons.Media;
+import fr.free.nrw.commons.R;
+
+
+/**
+ * Created by root on 09.01.2018.
+ */
+
+public class FeaturedImagesListFragment extends DaggerFragment {
+ private GridView gridView;
+ private MockGridViewAdapter gridAdapter;
+
+ @Override
+ public View onCreateView(LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState) {
+ View v = inflater.inflate(R.layout.fragment_featured_images, container, false);
+ ButterKnife.bind(this, v);
+ return v;
+ }
+
+ @Override
+ public void onViewCreated(View view, @Nullable Bundle savedInstanceState) {
+ super.onViewCreated(view, savedInstanceState);
+
+ gridView = getView().findViewById(R.id.featuredImagesList);
+ gridView.setOnItemClickListener((AdapterView.OnItemClickListener) getActivity());
+ gridAdapter = new MockGridViewAdapter(this.getContext(), R.layout.layout_featured_images, getMockFeaturedImages());
+ gridView.setAdapter(gridAdapter);
+
+ }
+
+ private ArrayList getMockFeaturedImages(){
+ ArrayList featuredImages = new ArrayList<>();
+ for (int i=0; i<10; i++){
+ featuredImages.add(new FeaturedImage(new Media("test.jpg"), "username: test", "test file name"));
+ }
+ return featuredImages;
+ }
+
+ public ListAdapter getAdapter() {
+ return gridView.getAdapter();
+ }
+}
diff --git a/app/src/main/java/fr/free/nrw/commons/featured/MockGridViewAdapter.java b/app/src/main/java/fr/free/nrw/commons/featured/MockGridViewAdapter.java
new file mode 100644
index 000000000..7aa2a8892
--- /dev/null
+++ b/app/src/main/java/fr/free/nrw/commons/featured/MockGridViewAdapter.java
@@ -0,0 +1,50 @@
+package fr.free.nrw.commons.featured;
+
+import android.app.Activity;
+import android.content.Context;
+import android.view.LayoutInflater;
+import android.view.View;
+import android.view.ViewGroup;
+import android.widget.ArrayAdapter;
+import android.widget.TextView;
+
+import java.util.ArrayList;
+
+import fr.free.nrw.commons.MediaWikiImageView;
+import fr.free.nrw.commons.R;
+
+/**
+ * This is created to only display UI implementation. Needs to be changed in real implementation
+ */
+
+public class MockGridViewAdapter extends ArrayAdapter {
+ private Context context;
+ private int layoutResourceId;
+ private ArrayList data = new ArrayList();
+
+ public MockGridViewAdapter(Context context, int layoutResourceId, ArrayList data) {
+ super(context, layoutResourceId, data);
+ this.layoutResourceId = layoutResourceId;
+ this.context = context;
+ this.data = data;
+ }
+
+ @Override
+ public View getView(int position, View convertView, ViewGroup parent) {
+
+ if (convertView == null) {
+ LayoutInflater inflater = ((Activity) context).getLayoutInflater();
+ convertView = inflater.inflate(R.layout.layout_featured_images, null);
+ }
+
+ FeaturedImage item = data.get(position);
+ MediaWikiImageView imageView = convertView.findViewById(R.id.featuredImageView);
+ TextView fileName = convertView.findViewById(R.id.featuredImageTitle);
+ TextView author = convertView.findViewById(R.id.featuredImageAuthor);
+ fileName.setText("Test file name");
+ author.setText("Uploaded by: Test user name");
+ imageView.setMedia(item.getImage());
+ return convertView;
+ }
+
+}
\ No newline at end of file
diff --git a/app/src/main/java/fr/free/nrw/commons/media/MediaDetailFragment.java b/app/src/main/java/fr/free/nrw/commons/media/MediaDetailFragment.java
index b06869e8d..5acfb218e 100644
--- a/app/src/main/java/fr/free/nrw/commons/media/MediaDetailFragment.java
+++ b/app/src/main/java/fr/free/nrw/commons/media/MediaDetailFragment.java
@@ -50,14 +50,16 @@ import static android.widget.Toast.LENGTH_SHORT;
public class MediaDetailFragment extends CommonsDaggerSupportFragment {
private boolean editable;
+ private boolean isFeaturedMedia;
private MediaDetailPagerFragment.MediaDetailProvider detailProvider;
private int index;
- public static MediaDetailFragment forMedia(int index, boolean editable) {
+ public static MediaDetailFragment forMedia(int index, boolean editable, boolean isFeaturedMedia) {
MediaDetailFragment mf = new MediaDetailFragment();
Bundle state = new Bundle();
state.putBoolean("editable", editable);
+ state.putBoolean("isFeaturedMedia", isFeaturedMedia);
state.putInt("index", index);
state.putInt("listIndex", 0);
state.putInt("listTop", 0);
@@ -79,12 +81,14 @@ public class MediaDetailFragment extends CommonsDaggerSupportFragment {
private TextView title;
private TextView desc;
+ private TextView author;
private TextView license;
private TextView coordinates;
private TextView uploadedDate;
private TextView seeMore;
private LinearLayout nominatedforDeletion;
private LinearLayout categoryContainer;
+ private LinearLayout authorLayout;
private Button delete;
private ScrollView scrollView;
private ArrayList categoryNames;
@@ -101,6 +105,7 @@ public class MediaDetailFragment extends CommonsDaggerSupportFragment {
super.onSaveInstanceState(outState);
outState.putInt("index", index);
outState.putBoolean("editable", editable);
+ outState.putBoolean("isFeaturedMedia", isFeaturedMedia);
getScrollPosition();
outState.putInt("listTop", initialListTop);
@@ -116,13 +121,16 @@ public class MediaDetailFragment extends CommonsDaggerSupportFragment {
if (savedInstanceState != null) {
editable = savedInstanceState.getBoolean("editable");
+ isFeaturedMedia = savedInstanceState.getBoolean("isFeaturedMedia");
index = savedInstanceState.getInt("index");
initialListTop = savedInstanceState.getInt("listTop");
} else {
editable = getArguments().getBoolean("editable");
+ isFeaturedMedia = getArguments().getBoolean("isFeaturedMedia");
index = getArguments().getInt("index");
initialListTop = 0;
}
+
categoryNames = new ArrayList<>();
categoryNames.add(getString(R.string.detail_panel_cats_loading));
@@ -135,6 +143,7 @@ public class MediaDetailFragment extends CommonsDaggerSupportFragment {
spacer = (MediaDetailSpacer) view.findViewById(R.id.mediaDetailSpacer);
title = (TextView) view.findViewById(R.id.mediaDetailTitle);
desc = (TextView) view.findViewById(R.id.mediaDetailDesc);
+ author = (TextView) view.findViewById(R.id.mediaDetailAuthor);
license = (TextView) view.findViewById(R.id.mediaDetailLicense);
coordinates = (TextView) view.findViewById(R.id.mediaDetailCoordinates);
uploadedDate = (TextView) view.findViewById(R.id.mediaDetailuploadeddate);
@@ -142,6 +151,13 @@ public class MediaDetailFragment extends CommonsDaggerSupportFragment {
nominatedforDeletion = (LinearLayout) view.findViewById(R.id.nominatedDeletionBanner);
delete = (Button) view.findViewById(R.id.nominateDeletion);
categoryContainer = (LinearLayout) view.findViewById(R.id.mediaDetailCategoryContainer);
+ authorLayout = (LinearLayout) view.findViewById(R.id.authorLinearLayout);
+
+ if (isFeaturedMedia){
+ authorLayout.setVisibility(View.VISIBLE);
+ } else {
+ authorLayout.setVisibility(View.GONE);
+ }
licenseList = new LicenseList(getActivity());
@@ -304,9 +320,10 @@ public class MediaDetailFragment extends CommonsDaggerSupportFragment {
coordinates.setOnClickListener(v -> openMap(media.getCoordinates()));
}
if (delete.getVisibility() == View.VISIBLE) {
+ enableDeleteButton(true);
+
delete.setOnClickListener(v -> {
- delete.setEnabled(false);
- delete.setTextColor(getResources().getColor(R.color.deleteButtonLight));
+
AlertDialog.Builder alert = new AlertDialog.Builder(getActivity());
alert.setMessage("Why should this file be deleted?");
final EditText input = new EditText(getActivity());
@@ -317,6 +334,7 @@ public class MediaDetailFragment extends CommonsDaggerSupportFragment {
String reason = input.getText().toString();
DeleteTask deleteTask = new DeleteTask(getActivity(), media, reason);
deleteTask.execute();
+ enableDeleteButton(false);
}
});
alert.setNegativeButton(R.string.cancel, new DialogInterface.OnClickListener() {
@@ -358,6 +376,15 @@ public class MediaDetailFragment extends CommonsDaggerSupportFragment {
}
}
+ private void enableDeleteButton(boolean visibility) {
+ delete.setEnabled(visibility);
+ if(visibility) {
+ delete.setTextColor(getResources().getColor(R.color.primaryTextColor));
+ } else {
+ delete.setTextColor(getResources().getColor(R.color.deleteButtonLight));
+ }
+ }
+
private void rebuildCatList() {
categoryContainer.removeAllViews();
// @fixme add the category items
diff --git a/app/src/main/java/fr/free/nrw/commons/media/MediaDetailPagerFragment.java b/app/src/main/java/fr/free/nrw/commons/media/MediaDetailPagerFragment.java
index be7aea836..c0564c603 100644
--- a/app/src/main/java/fr/free/nrw/commons/media/MediaDetailPagerFragment.java
+++ b/app/src/main/java/fr/free/nrw/commons/media/MediaDetailPagerFragment.java
@@ -55,14 +55,16 @@ public class MediaDetailPagerFragment extends CommonsDaggerSupportFragment imple
private ViewPager pager;
private Boolean editable;
+ private boolean isFeaturedImage;
public MediaDetailPagerFragment() {
- this(false);
+ this(false, false);
}
@SuppressLint("ValidFragment")
- public MediaDetailPagerFragment(Boolean editable) {
+ public MediaDetailPagerFragment(Boolean editable, boolean isFeaturedImage) {
this.editable = editable;
+ this.isFeaturedImage = isFeaturedImage;
}
@Override
@@ -96,6 +98,7 @@ public class MediaDetailPagerFragment extends CommonsDaggerSupportFragment imple
super.onSaveInstanceState(outState);
outState.putInt("current-page", pager.getCurrentItem());
outState.putBoolean("editable", editable);
+ outState.putBoolean("isFeaturedImage", isFeaturedImage);
}
@Override
@@ -103,6 +106,7 @@ public class MediaDetailPagerFragment extends CommonsDaggerSupportFragment imple
super.onCreate(savedInstanceState);
if (savedInstanceState != null) {
editable = savedInstanceState.getBoolean("editable");
+ isFeaturedImage = savedInstanceState.getBoolean("isFeaturedImage");
}
setHasOptionsMenu(true);
}
@@ -291,7 +295,7 @@ public class MediaDetailPagerFragment extends CommonsDaggerSupportFragment imple
// See bug https://code.google.com/p/android/issues/detail?id=27526
pager.postDelayed(() -> getActivity().supportInvalidateOptionsMenu(), 5);
}
- return MediaDetailFragment.forMedia(i, editable);
+ return MediaDetailFragment.forMedia(i, editable, isFeaturedImage);
}
@Override
diff --git a/app/src/main/java/fr/free/nrw/commons/nearby/DirectUpload.java b/app/src/main/java/fr/free/nrw/commons/nearby/DirectUpload.java
index b58afa82a..7ab427b2d 100644
--- a/app/src/main/java/fr/free/nrw/commons/nearby/DirectUpload.java
+++ b/app/src/main/java/fr/free/nrw/commons/nearby/DirectUpload.java
@@ -8,6 +8,7 @@ import android.support.v7.app.AlertDialog;
import fr.free.nrw.commons.R;
import fr.free.nrw.commons.contributions.ContributionController;
+import timber.log.Timber;
import static android.Manifest.permission.READ_EXTERNAL_STORAGE;
import static android.Manifest.permission.WRITE_EXTERNAL_STORAGE;
@@ -23,46 +24,25 @@ class DirectUpload {
this.controller = controller;
}
- void initiateCameraUpload() {
- if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.M) {
- if (ContextCompat.checkSelfPermission(fragment.getActivity(), WRITE_EXTERNAL_STORAGE) != PERMISSION_GRANTED) {
- if (fragment.getActivity().shouldShowRequestPermissionRationale(WRITE_EXTERNAL_STORAGE)) {
- new AlertDialog.Builder(fragment.getActivity())
- .setMessage(fragment.getActivity().getString(R.string.write_storage_permission_rationale))
- .setPositiveButton("OK", (dialog, which) -> {
- fragment.getActivity().requestPermissions(new String[]{WRITE_EXTERNAL_STORAGE}, 3);
- dialog.dismiss();
- })
- .setNegativeButton("Cancel", null)
- .create()
- .show();
- } else {
- fragment.getActivity().requestPermissions(new String[]{WRITE_EXTERNAL_STORAGE}, 3);
- }
- } else {
- controller.startCameraCapture();
- }
- } else {
- controller.startCameraCapture();
- }
- }
-
+ // These permission requests will be handled by the Fragments.
+ // Do not use requestCode 1 as it will conflict with NearbyActivity's requestCodes
void initiateGalleryUpload() {
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.M) {
if (ContextCompat.checkSelfPermission(fragment.getActivity(), READ_EXTERNAL_STORAGE) != PERMISSION_GRANTED) {
- if (fragment.getActivity().shouldShowRequestPermissionRationale(READ_EXTERNAL_STORAGE)) {
+ if (fragment.shouldShowRequestPermissionRationale(READ_EXTERNAL_STORAGE)) {
new AlertDialog.Builder(fragment.getActivity())
.setMessage(fragment.getActivity().getString(R.string.read_storage_permission_rationale))
.setPositiveButton("OK", (dialog, which) -> {
- fragment.getActivity().requestPermissions(new String[]{READ_EXTERNAL_STORAGE}, 1);
+ Timber.d("Requesting permissions for read external storage");
+ fragment.requestPermissions(new String[]{READ_EXTERNAL_STORAGE}, 4);
dialog.dismiss();
})
.setNegativeButton("Cancel", null)
.create()
.show();
} else {
- fragment.getActivity().requestPermissions(new String[]{READ_EXTERNAL_STORAGE},
- 1);
+ fragment.requestPermissions(new String[]{READ_EXTERNAL_STORAGE},
+ 4);
}
} else {
controller.startGalleryPick();
@@ -72,4 +52,28 @@ class DirectUpload {
controller.startGalleryPick();
}
}
+
+ void initiateCameraUpload() {
+ if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.M) {
+ if (ContextCompat.checkSelfPermission(fragment.getActivity(), WRITE_EXTERNAL_STORAGE) != PERMISSION_GRANTED) {
+ if (fragment.shouldShowRequestPermissionRationale(WRITE_EXTERNAL_STORAGE)) {
+ new AlertDialog.Builder(fragment.getActivity())
+ .setMessage(fragment.getActivity().getString(R.string.write_storage_permission_rationale))
+ .setPositiveButton("OK", (dialog, which) -> {
+ fragment.requestPermissions(new String[]{WRITE_EXTERNAL_STORAGE}, 5);
+ dialog.dismiss();
+ })
+ .setNegativeButton("Cancel", null)
+ .create()
+ .show();
+ } else {
+ fragment.requestPermissions(new String[]{WRITE_EXTERNAL_STORAGE}, 5);
+ }
+ } else {
+ controller.startCameraCapture();
+ }
+ } else {
+ controller.startCameraCapture();
+ }
+ }
}
diff --git a/app/src/main/java/fr/free/nrw/commons/nearby/NearbyActivity.java b/app/src/main/java/fr/free/nrw/commons/nearby/NearbyActivity.java
index 88d5880f5..ea88de341 100644
--- a/app/src/main/java/fr/free/nrw/commons/nearby/NearbyActivity.java
+++ b/app/src/main/java/fr/free/nrw/commons/nearby/NearbyActivity.java
@@ -10,17 +10,14 @@ import android.os.Build;
import android.os.Bundle;
import android.support.annotation.NonNull;
import android.support.design.widget.BottomSheetBehavior;
-
import android.support.v4.app.FragmentTransaction;
import android.support.v7.app.AlertDialog;
-import android.util.Log;
import android.view.Menu;
import android.view.MenuInflater;
import android.view.MenuItem;
import android.view.View;
import android.widget.LinearLayout;
import android.widget.ProgressBar;
-import android.widget.Toast;
import com.google.gson.Gson;
import com.google.gson.GsonBuilder;
@@ -31,7 +28,6 @@ import javax.inject.Inject;
import butterknife.BindView;
import butterknife.ButterKnife;
-
import fr.free.nrw.commons.R;
import fr.free.nrw.commons.location.LatLng;
import fr.free.nrw.commons.location.LocationServiceManager;
@@ -39,13 +35,11 @@ import fr.free.nrw.commons.location.LocationUpdateListener;
import fr.free.nrw.commons.theme.NavigationBaseActivity;
import fr.free.nrw.commons.utils.NetworkUtils;
import fr.free.nrw.commons.utils.UriSerializer;
-
import fr.free.nrw.commons.utils.ViewUtil;
import io.reactivex.Observable;
import io.reactivex.android.schedulers.AndroidSchedulers;
import io.reactivex.disposables.Disposable;
import io.reactivex.schedulers.Schedulers;
-
import timber.log.Timber;
@@ -68,7 +62,7 @@ public class NearbyActivity extends NavigationBaseActivity implements LocationUp
@Inject
NearbyController nearbyController;
- private LatLng curLatLang;
+ private LatLng curLatLng;
private Bundle bundle;
private Disposable placesDisposable;
private boolean lockNearbyView; //Determines if the nearby places needs to be refreshed
@@ -136,11 +130,17 @@ public class NearbyActivity extends NavigationBaseActivity implements LocationUp
@Override
public boolean onOptionsItemSelected(MenuItem item) {
+
// Handle item selection
switch (item.getItemId()) {
case R.id.action_display_list:
- bottomSheetBehaviorForDetails.setState(BottomSheetBehavior.STATE_HIDDEN);
- bottomSheetBehavior.setState(BottomSheetBehavior.STATE_EXPANDED);
+ if(bottomSheetBehavior.getState()==BottomSheetBehavior.STATE_COLLAPSED || bottomSheetBehavior.getState()==BottomSheetBehavior.STATE_HIDDEN){
+ bottomSheetBehaviorForDetails.setState(BottomSheetBehavior.STATE_HIDDEN);
+ bottomSheetBehavior.setState(BottomSheetBehavior.STATE_EXPANDED);
+ }else if(bottomSheetBehavior.getState()==BottomSheetBehavior.STATE_EXPANDED){
+ bottomSheetBehavior.setState(BottomSheetBehavior.STATE_COLLAPSED);
+ }
+
return true;
default:
return super.onOptionsItemSelected(item);
@@ -165,6 +165,11 @@ public class NearbyActivity extends NavigationBaseActivity implements LocationUp
showLocationPermissionDeniedErrorDialog();
}
}
+ break;
+
+ default:
+ // This is needed to allow the request codes from the Fragments to be routed appropriately
+ super.onRequestPermissionsResult(requestCode, permissions, grantResults);
}
}
@@ -262,8 +267,6 @@ public class NearbyActivity extends NavigationBaseActivity implements LocationUp
@Override
protected void onStop() {
super.onStop();
- locationManager.removeLocationListener(this);
- locationManager.unregisterLocationManager();
}
@Override
@@ -292,8 +295,13 @@ public class NearbyActivity extends NavigationBaseActivity implements LocationUp
// to the retained fragment object to perform its own cleanup.
removeMapFragment();
removeListFragment();
- unregisterReceiver(broadcastReceiver);
+
}
+ unregisterReceiver(broadcastReceiver);
+ broadcastReceiver = null;
+ locationManager.removeLocationListener(this);
+ locationManager.unregisterLocationManager();
+
}
private void addNetworkBroadcastReceiver() {
@@ -334,12 +342,12 @@ public class NearbyActivity extends NavigationBaseActivity implements LocationUp
locationManager.registerLocationManager();
LatLng lastLocation = locationManager.getLastLocation();
- if (curLatLang != null && curLatLang.equals(lastLocation)) { //refresh view only if location has changed
+ if (curLatLng != null && curLatLng.equals(lastLocation)) { //refresh view only if location has changed
return;
}
- curLatLang = lastLocation;
+ curLatLng = lastLocation;
- if (curLatLang == null) {
+ if (curLatLng == null) {
Timber.d("Skipping update of nearby places as location is unavailable");
return;
}
@@ -348,7 +356,7 @@ public class NearbyActivity extends NavigationBaseActivity implements LocationUp
.equals(LocationServiceManager.LocationChangeType.LOCATION_SIGNIFICANTLY_CHANGED)) {
progressBar.setVisibility(View.VISIBLE);
placesDisposable = Observable.fromCallable(() -> nearbyController
- .loadAttractionsFromLocation(curLatLang))
+ .loadAttractionsFromLocation(curLatLng))
.subscribeOn(Schedulers.io())
.observeOn(AndroidSchedulers.mainThread())
.subscribe(this::populatePlaces);
@@ -357,7 +365,7 @@ public class NearbyActivity extends NavigationBaseActivity implements LocationUp
Gson gson = new GsonBuilder()
.registerTypeAdapter(Uri.class, new UriSerializer())
.create();
- String gsonCurLatLng = gson.toJson(curLatLang);
+ String gsonCurLatLng = gson.toJson(curLatLng);
bundle.putString("CurLatLng", gsonCurLatLng);
updateMapFragment(true);
}
@@ -370,7 +378,7 @@ public class NearbyActivity extends NavigationBaseActivity implements LocationUp
.registerTypeAdapter(Uri.class, new UriSerializer())
.create();
String gsonPlaceList = gson.toJson(placeList);
- String gsonCurLatLng = gson.toJson(curLatLang);
+ String gsonCurLatLng = gson.toJson(curLatLng);
String gsonBoundaryCoordinates = gson.toJson(boundaryCoordinates);
if (placeList.size() == 0) {
@@ -422,6 +430,7 @@ public class NearbyActivity extends NavigationBaseActivity implements LocationUp
if (nearbyMapFragment != null) {
android.support.v4.app.FragmentManager fm = getSupportFragmentManager();
fm.beginTransaction().remove(nearbyMapFragment).commit();
+ nearbyMapFragment = null;
}
}
@@ -433,6 +442,7 @@ public class NearbyActivity extends NavigationBaseActivity implements LocationUp
if (nearbyListFragment != null) {
android.support.v4.app.FragmentManager fm = getSupportFragmentManager();
fm.beginTransaction().remove(nearbyListFragment).commit();
+ nearbyListFragment = null;
}
}
@@ -447,34 +457,34 @@ public class NearbyActivity extends NavigationBaseActivity implements LocationUp
NearbyMapFragment nearbyMapFragment = getMapFragment();
- if (nearbyMapFragment != null && curLatLang != null) {
+ if (nearbyMapFragment != null && curLatLng != null) {
hideProgressBar(); // In case it is visible (this happens, not an impossible case)
/*
* If we are close to nearby places boundaries, we need a significant update to
* get new nearby places. Check order is south, north, west, east
* */
if (nearbyMapFragment.boundaryCoordinates != null
- && (curLatLang.getLatitude() <= nearbyMapFragment.boundaryCoordinates[0].getLatitude()
- || curLatLang.getLatitude() >= nearbyMapFragment.boundaryCoordinates[1].getLatitude()
- || curLatLang.getLongitude() <= nearbyMapFragment.boundaryCoordinates[2].getLongitude()
- || curLatLang.getLongitude() >= nearbyMapFragment.boundaryCoordinates[3].getLongitude())) {
+ && (curLatLng.getLatitude() <= nearbyMapFragment.boundaryCoordinates[0].getLatitude()
+ || curLatLng.getLatitude() >= nearbyMapFragment.boundaryCoordinates[1].getLatitude()
+ || curLatLng.getLongitude() <= nearbyMapFragment.boundaryCoordinates[2].getLongitude()
+ || curLatLng.getLongitude() >= nearbyMapFragment.boundaryCoordinates[3].getLongitude())) {
// populate places
placesDisposable = Observable.fromCallable(() -> nearbyController
- .loadAttractionsFromLocation(curLatLang))
+ .loadAttractionsFromLocation(curLatLng))
.subscribeOn(Schedulers.io())
.observeOn(AndroidSchedulers.mainThread())
.subscribe(this::populatePlaces);
- nearbyMapFragment.setArguments(bundle);
+ nearbyMapFragment.setBundleForUpdtes(bundle);
nearbyMapFragment.updateMapSignificantly();
updateListFragment();
return;
}
if (isSlightUpdate) {
- nearbyMapFragment.setArguments(bundle);
+ nearbyMapFragment.setBundleForUpdtes(bundle);
nearbyMapFragment.updateMapSlightly();
} else {
- nearbyMapFragment.setArguments(bundle);
+ nearbyMapFragment.setBundleForUpdtes(bundle);
nearbyMapFragment.updateMapSignificantly();
updateListFragment();
}
@@ -488,7 +498,7 @@ public class NearbyActivity extends NavigationBaseActivity implements LocationUp
}
private void updateListFragment() {
- nearbyListFragment.setArguments(bundle);
+ nearbyListFragment.setBundleForUpdates(bundle);
nearbyListFragment.updateNearbyListSignificantly();
}
diff --git a/app/src/main/java/fr/free/nrw/commons/nearby/NearbyController.java b/app/src/main/java/fr/free/nrw/commons/nearby/NearbyController.java
index 0ecf09160..015d22135 100644
--- a/app/src/main/java/fr/free/nrw/commons/nearby/NearbyController.java
+++ b/app/src/main/java/fr/free/nrw/commons/nearby/NearbyController.java
@@ -54,41 +54,47 @@ public class NearbyController {
}
List places = nearbyPlaces.getFromWikidataQuery(curLatLng, Locale.getDefault().getLanguage());
- LatLng[] boundaryCoordinates = {places.get(0).location, // south
- places.get(0).location, // north
- places.get(0).location, // west
- places.get(0).location};// east, init with a random location
+ if (places.size() > 0) {
+ LatLng[] boundaryCoordinates = {places.get(0).location, // south
+ places.get(0).location, // north
+ places.get(0).location, // west
+ places.get(0).location};// east, init with a random location
- if (curLatLng != null) {
- Timber.d("Sorting places by distance...");
- final Map distances = new HashMap<>();
- for (Place place: places) {
- distances.put(place, computeDistanceBetween(place.location, curLatLng));
- // Find boundaries with basic find max approach
- if (place.location.getLatitude() < boundaryCoordinates[0].getLatitude()) {
- boundaryCoordinates[0] = place.location;
- }
- if (place.location.getLatitude() > boundaryCoordinates[1].getLatitude()) {
- boundaryCoordinates[1] = place.location;
- }
- if (place.location.getLongitude() < boundaryCoordinates[2].getLongitude()) {
- boundaryCoordinates[2] = place.location;
- }
- if (place.location.getLongitude() > boundaryCoordinates[3].getLongitude()) {
- boundaryCoordinates[3] = place.location;
- }
- }
- Collections.sort(places,
- (lhs, rhs) -> {
- double lhsDistance = distances.get(lhs);
- double rhsDistance = distances.get(rhs);
- return (int) (lhsDistance - rhsDistance);
+
+ if (curLatLng != null) {
+ Timber.d("Sorting places by distance...");
+ final Map distances = new HashMap<>();
+ for (Place place : places) {
+ distances.put(place, computeDistanceBetween(place.location, curLatLng));
+ // Find boundaries with basic find max approach
+ if (place.location.getLatitude() < boundaryCoordinates[0].getLatitude()) {
+ boundaryCoordinates[0] = place.location;
}
- );
+ if (place.location.getLatitude() > boundaryCoordinates[1].getLatitude()) {
+ boundaryCoordinates[1] = place.location;
+ }
+ if (place.location.getLongitude() < boundaryCoordinates[2].getLongitude()) {
+ boundaryCoordinates[2] = place.location;
+ }
+ if (place.location.getLongitude() > boundaryCoordinates[3].getLongitude()) {
+ boundaryCoordinates[3] = place.location;
+ }
+ }
+ Collections.sort(places,
+ (lhs, rhs) -> {
+ double lhsDistance = distances.get(lhs);
+ double rhsDistance = distances.get(rhs);
+ return (int) (lhsDistance - rhsDistance);
+ }
+ );
+ }
+ nearbyPlacesInfo.placeList = places;
+ nearbyPlacesInfo.boundaryCoordinates = boundaryCoordinates;
+ return nearbyPlacesInfo;
+ }
+ else {
+ return null;
}
- nearbyPlacesInfo.placeList = places;
- nearbyPlacesInfo.boundaryCoordinates = boundaryCoordinates;
- return nearbyPlacesInfo;
}
/**
diff --git a/app/src/main/java/fr/free/nrw/commons/nearby/NearbyListFragment.java b/app/src/main/java/fr/free/nrw/commons/nearby/NearbyListFragment.java
index dcc7f5e24..4a2be8476 100644
--- a/app/src/main/java/fr/free/nrw/commons/nearby/NearbyListFragment.java
+++ b/app/src/main/java/fr/free/nrw/commons/nearby/NearbyListFragment.java
@@ -33,6 +33,8 @@ import static android.app.Activity.RESULT_OK;
import static android.content.pm.PackageManager.PERMISSION_GRANTED;
public class NearbyListFragment extends DaggerFragment {
+ private Bundle bundleForUpdates; // Carry information from activity about changed nearby places and current location
+
private static final Type LIST_TYPE = new TypeToken>() {
}.getType();
private static final Type CUR_LAT_LNG_TYPE = new TypeToken() {
@@ -80,8 +82,7 @@ public class NearbyListFragment extends DaggerFragment {
}
public void updateNearbyListSignificantly() {
- Bundle bundle = this.getArguments();
- adapterFactory.updateAdapterData(getPlaceListFromBundle(bundle),
+ adapterFactory.updateAdapterData(getPlaceListFromBundle(bundleForUpdates),
(RVRendererAdapter) recyclerView.getAdapter());
}
@@ -106,8 +107,8 @@ public class NearbyListFragment extends DaggerFragment {
Timber.d("onRequestPermissionsResult: req code = " + " perm = " + permissions + " grant =" + grantResults);
switch (requestCode) {
- // 1 = "Read external storage" allowed when gallery selected
- case 1: {
+ // 4 = "Read external storage" allowed when gallery selected
+ case 4: {
if (grantResults.length > 0 && grantResults[0] == PERMISSION_GRANTED) {
Timber.d("Call controller.startGalleryPick()");
controller.startGalleryPick();
@@ -115,8 +116,8 @@ public class NearbyListFragment extends DaggerFragment {
}
break;
- // 3 = "Write external storage" allowed when camera selected
- case 3: {
+ // 5 = "Write external storage" allowed when camera selected
+ case 5: {
if (grantResults.length > 0 && grantResults[0] == PackageManager.PERMISSION_GRANTED) {
Timber.d("Call controller.startCameraCapture()");
controller.startCameraCapture();
@@ -140,4 +141,8 @@ public class NearbyListFragment extends DaggerFragment {
}
}
+ public void setBundleForUpdates(Bundle bundleForUpdates) {
+ this.bundleForUpdates = bundleForUpdates;
+ }
+
}
\ No newline at end of file
diff --git a/app/src/main/java/fr/free/nrw/commons/nearby/NearbyMapFragment.java b/app/src/main/java/fr/free/nrw/commons/nearby/NearbyMapFragment.java
index d541a8e45..b84e04a57 100644
--- a/app/src/main/java/fr/free/nrw/commons/nearby/NearbyMapFragment.java
+++ b/app/src/main/java/fr/free/nrw/commons/nearby/NearbyMapFragment.java
@@ -53,8 +53,10 @@ import javax.inject.Named;
import dagger.android.support.DaggerFragment;
import fr.free.nrw.commons.R;
+import fr.free.nrw.commons.Utils;
import fr.free.nrw.commons.contributions.ContributionController;
import fr.free.nrw.commons.utils.UriDeserializer;
+import fr.free.nrw.commons.utils.ViewUtil;
import timber.log.Timber;
import static android.app.Activity.RESULT_OK;
@@ -97,6 +99,7 @@ public class NearbyMapFragment extends DaggerFragment {
private Animation fab_open;
private Animation rotate_forward;
private ContributionController controller;
+ private DirectUpload directUpload;
private Place place;
private Marker selected;
@@ -105,7 +108,10 @@ public class NearbyMapFragment extends DaggerFragment {
private PolygonOptions currentLocationPolygonOptions;
private boolean isBottomListSheetExpanded;
- private final double CAMERA_TARGET_SHIFT_FACTOR = 0.06;
+ private final double CAMERA_TARGET_SHIFT_FACTOR_PORTRAIT = 0.06;
+ private final double CAMERA_TARGET_SHIFT_FACTOR_LANDSCAPE = 0.04;
+
+ private Bundle bundleForUpdtes;// Carry information from activity about changed nearby places and current location
@Inject
@Named("prefs")
@@ -120,6 +126,10 @@ public class NearbyMapFragment extends DaggerFragment {
@Override
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
+
+ controller = new ContributionController(this);
+ directUpload = new DirectUpload(this, controller);
+
Bundle bundle = this.getArguments();
Gson gson = new GsonBuilder()
.registerTypeAdapter(Uri.class, new UriDeserializer())
@@ -184,14 +194,12 @@ public class NearbyMapFragment extends DaggerFragment {
}
public void updateMapSlightly() {
- // Get arguments from bundle for new location
- Bundle bundle = this.getArguments();
if (mapboxMap != null) {
Gson gson = new GsonBuilder()
.registerTypeAdapter(Uri.class, new UriDeserializer())
.create();
- if (bundle != null) {
- String gsonLatLng = bundle.getString("CurLatLng");
+ if (bundleForUpdtes != null) {
+ String gsonLatLng = bundleForUpdtes.getString("CurLatLng");
Type curLatLngType = new TypeToken() {}.getType();
curLatLng = gson.fromJson(gsonLatLng, curLatLngType);
}
@@ -201,17 +209,15 @@ public class NearbyMapFragment extends DaggerFragment {
}
public void updateMapSignificantly() {
-
- Bundle bundle = this.getArguments();
if (mapboxMap != null) {
- if (bundle != null) {
+ if (bundleForUpdtes != null) {
Gson gson = new GsonBuilder()
.registerTypeAdapter(Uri.class, new UriDeserializer())
.create();
- String gsonPlaceList = bundle.getString("PlaceList");
- String gsonLatLng = bundle.getString("CurLatLng");
- String gsonBoundaryCoordinates = bundle.getString("BoundaryCoord");
+ String gsonPlaceList = bundleForUpdtes.getString("PlaceList");
+ String gsonLatLng = bundleForUpdtes.getString("CurLatLng");
+ String gsonBoundaryCoordinates = bundleForUpdtes.getString("BoundaryCoord");
Type listType = new TypeToken>() {}.getType();
List placeList = gson.fromJson(gsonPlaceList, listType);
Type curLatLngType = new TypeToken() {}.getType();
@@ -253,13 +259,28 @@ public class NearbyMapFragment extends DaggerFragment {
}
// Make camera to follow user on location change
- CameraPosition position = new CameraPosition.Builder()
- .target(isBottomListSheetExpanded ?
- new LatLng(curMapBoxLatLng.getLatitude()- CAMERA_TARGET_SHIFT_FACTOR,
- curMapBoxLatLng.getLongitude())
- : curMapBoxLatLng ) // Sets the new camera position
- .zoom(mapboxMap.getCameraPosition().zoom) // Same zoom level
- .build();
+ CameraPosition position ;
+ if(ViewUtil.isPortrait(getActivity())){
+ position = new CameraPosition.Builder()
+ .target(isBottomListSheetExpanded ?
+ new LatLng(curMapBoxLatLng.getLatitude()- CAMERA_TARGET_SHIFT_FACTOR_PORTRAIT,
+ curMapBoxLatLng.getLongitude())
+ : curMapBoxLatLng ) // Sets the new camera position
+ .zoom(isBottomListSheetExpanded ?
+ 11 // zoom level is fixed to 11 when bottom sheet is expanded
+ :mapboxMap.getCameraPosition().zoom) // Same zoom level
+ .build();
+ }else {
+ position = new CameraPosition.Builder()
+ .target(isBottomListSheetExpanded ?
+ new LatLng(curMapBoxLatLng.getLatitude()- CAMERA_TARGET_SHIFT_FACTOR_LANDSCAPE,
+ curMapBoxLatLng.getLongitude())
+ : curMapBoxLatLng ) // Sets the new camera position
+ .zoom(isBottomListSheetExpanded ?
+ 11 // zoom level is fixed to 11 when bottom sheet is expanded
+ :mapboxMap.getCameraPosition().zoom) // Same zoom level
+ .build();
+ }
mapboxMap.animateCamera(CameraUpdateFactory
.newCameraPosition(position), 1000);
@@ -273,12 +294,21 @@ public class NearbyMapFragment extends DaggerFragment {
if (mapboxMap != null && curLatLng != null) {
if (isBottomListSheetExpanded) {
// Make camera to follow user on location change
- position = new CameraPosition.Builder()
- .target(new LatLng(curLatLng.getLatitude() - CAMERA_TARGET_SHIFT_FACTOR,
- curLatLng.getLongitude())) // Sets the new camera target above
- // current to make it visible when sheet is expanded
- .zoom(11) // Same zoom level
- .build();
+ if(ViewUtil.isPortrait(getActivity())) {
+ position = new CameraPosition.Builder()
+ .target(new LatLng(curLatLng.getLatitude() - CAMERA_TARGET_SHIFT_FACTOR_PORTRAIT,
+ curLatLng.getLongitude())) // Sets the new camera target above
+ // current to make it visible when sheet is expanded
+ .zoom(11) // Fixed zoom level
+ .build();
+ } else {
+ position = new CameraPosition.Builder()
+ .target(new LatLng(curLatLng.getLatitude() - CAMERA_TARGET_SHIFT_FACTOR_LANDSCAPE,
+ curLatLng.getLongitude())) // Sets the new camera target above
+ // current to make it visible when sheet is expanded
+ .zoom(11) // Fixed zoom level
+ .build();
+ }
} else {
// Make camera to follow user on location change
@@ -344,10 +374,29 @@ public class NearbyMapFragment extends DaggerFragment {
fabRecenter.setOnClickListener(view -> {
if (curLatLng != null) {
mapView.getMapAsync(mapboxMap -> {
- CameraPosition position = new CameraPosition.Builder()
- .target(new LatLng(curLatLng.getLatitude(), curLatLng.getLongitude())) // Sets the new camera position
- .zoom(11) // Sets the zoom
- .build(); // Creates a CameraPosition from the builder
+ CameraPosition position;
+
+ if(ViewUtil.isPortrait(getActivity())){
+ position = new CameraPosition.Builder()
+ .target(isBottomListSheetExpanded ?
+ new LatLng(curLatLng.getLatitude()- CAMERA_TARGET_SHIFT_FACTOR_PORTRAIT,
+ curLatLng.getLongitude())
+ : new LatLng(curLatLng.getLatitude(), curLatLng.getLongitude(), 0)) // Sets the new camera position
+ .zoom(isBottomListSheetExpanded ?
+ 11 // zoom level is fixed to 11 when bottom sheet is expanded
+ :mapboxMap.getCameraPosition().zoom) // Same zoom level
+ .build();
+ }else {
+ position = new CameraPosition.Builder()
+ .target(isBottomListSheetExpanded ?
+ new LatLng(curLatLng.getLatitude()- CAMERA_TARGET_SHIFT_FACTOR_LANDSCAPE,
+ curLatLng.getLongitude())
+ : new LatLng(curLatLng.getLatitude(), curLatLng.getLongitude(), 0)) // Sets the new camera position
+ .zoom(isBottomListSheetExpanded ?
+ 11 // zoom level is fixed to 11 when bottom sheet is expanded
+ :mapboxMap.getCameraPosition().zoom) // Same zoom level
+ .build();
+ }
mapboxMap.animateCamera(CameraUpdateFactory
.newCameraPosition(position), 1000);
@@ -406,6 +455,8 @@ public class NearbyMapFragment extends DaggerFragment {
private void setupMapView(Bundle savedInstanceState) {
MapboxMapOptions options = new MapboxMapOptions()
+ .compassGravity(Gravity.BOTTOM | Gravity.LEFT)
+ .compassMargins(new int[]{12, 0, 0, 24})
.styleUrl(Style.OUTDOORS)
.logoEnabled(false)
.attributionEnabled(false)
@@ -534,7 +585,9 @@ public class NearbyMapFragment extends DaggerFragment {
transparentView.setAlpha(0);
closeFabs(isFabOpen);
hideFAB();
- this.getView().requestFocus();
+ if (this.getView() != null) {
+ this.getView().requestFocus();
+ }
break;
}
}
@@ -613,7 +666,7 @@ public class NearbyMapFragment extends DaggerFragment {
directionsButton.setOnClickListener(view -> {
//Open map app at given position
- Intent mapIntent = new Intent(Intent.ACTION_VIEW, place.location.getGmmIntentUri());
+ Intent mapIntent = new Intent(Intent.ACTION_VIEW, this.place.location.getGmmIntentUri());
if (mapIntent.resolveActivity(getActivity().getPackageManager()) != null) {
startActivity(mapIntent);
}
@@ -633,9 +686,6 @@ public class NearbyMapFragment extends DaggerFragment {
fabCamera.setOnClickListener(view -> {
if (fabCamera.isShown()) {
Timber.d("Camera button tapped. Image title: " + place.getName() + "Image desc: " + place.getLongDescription());
- controller = new ContributionController(this);
-
- DirectUpload directUpload = new DirectUpload(this, controller);
storeSharedPrefs();
directUpload.initiateCameraUpload();
}
@@ -644,9 +694,6 @@ public class NearbyMapFragment extends DaggerFragment {
fabGallery.setOnClickListener(view -> {
if (fabGallery.isShown()) {
Timber.d("Gallery button tapped. Image title: " + place.getName() + "Image desc: " + place.getLongDescription());
- controller = new ContributionController(this);
-
- DirectUpload directUpload = new DirectUpload(this, controller);
storeSharedPrefs();
directUpload.initiateGalleryUpload();
}
@@ -665,9 +712,10 @@ public class NearbyMapFragment extends DaggerFragment {
public void onRequestPermissionsResult(int requestCode, @NonNull String[] permissions, @NonNull int[] grantResults) {
Timber.d("onRequestPermissionsResult: req code = " + " perm = " + permissions + " grant =" + grantResults);
+ // Do not use requestCode 1 as it will conflict with NearbyActivity's requestCodes
switch (requestCode) {
- // 1 = "Read external storage" allowed when gallery selected
- case 1: {
+ // 4 = "Read external storage" allowed when gallery selected
+ case 4: {
if (grantResults.length > 0 && grantResults[0] == PERMISSION_GRANTED) {
Timber.d("Call controller.startGalleryPick()");
controller.startGalleryPick();
@@ -675,8 +723,8 @@ public class NearbyMapFragment extends DaggerFragment {
}
break;
- // 3 = "Write external storage" allowed when camera selected
- case 3: {
+ // 5 = "Write external storage" allowed when camera selected
+ case 5: {
if (grantResults.length > 0 && grantResults[0] == PackageManager.PERMISSION_GRANTED) {
Timber.d("Call controller.startCameraCapture()");
controller.startCameraCapture();
@@ -700,8 +748,7 @@ public class NearbyMapFragment extends DaggerFragment {
}
private void openWebView(Uri link) {
- Intent browserIntent = new Intent(Intent.ACTION_VIEW, link);
- startActivity(browserIntent);
+ Utils.handleWebUrl(getContext(), link);
}
private void animateFAB(boolean isFabOpen) {
@@ -724,7 +771,7 @@ public class NearbyMapFragment extends DaggerFragment {
}
}
- private void closeFabs ( boolean isFabOpen){
+ private void closeFabs ( boolean isFabOpen){
if (isFabOpen) {
fabPlus.startAnimation(rotate_backward);
fabCamera.startAnimation(fab_close);
@@ -735,6 +782,11 @@ public class NearbyMapFragment extends DaggerFragment {
}
}
+ public void setBundleForUpdtes(Bundle bundleForUpdtes) {
+ this.bundleForUpdtes = bundleForUpdtes;
+ }
+
+
@Override
public void onStart() {
if (mapView != null) {
@@ -776,6 +828,9 @@ public class NearbyMapFragment extends DaggerFragment {
if (mapView != null) {
mapView.onDestroy();
}
+ selected = null;
+ currentLocationMarker = null;
+
super.onDestroyView();
}
diff --git a/app/src/main/java/fr/free/nrw/commons/nearby/PlaceRenderer.java b/app/src/main/java/fr/free/nrw/commons/nearby/PlaceRenderer.java
index 5216dc36d..9cbe28db4 100644
--- a/app/src/main/java/fr/free/nrw/commons/nearby/PlaceRenderer.java
+++ b/app/src/main/java/fr/free/nrw/commons/nearby/PlaceRenderer.java
@@ -27,6 +27,7 @@ import butterknife.BindView;
import butterknife.ButterKnife;
import fr.free.nrw.commons.CommonsApplication;
import fr.free.nrw.commons.R;
+import fr.free.nrw.commons.Utils;
import fr.free.nrw.commons.contributions.ContributionController;
import fr.free.nrw.commons.di.ApplicationlessInjection;
import timber.log.Timber;
@@ -200,8 +201,7 @@ public class PlaceRenderer extends Renderer {
}
private void openWebView(Uri link) {
- Intent browserIntent = new Intent(Intent.ACTION_VIEW, link);
- view.getContext().startActivity(browserIntent);
+ Utils.handleWebUrl(getContext(), link);
}
private boolean showMenu() {
diff --git a/app/src/main/java/fr/free/nrw/commons/notification/NotificationActivity.java b/app/src/main/java/fr/free/nrw/commons/notification/NotificationActivity.java
index 7c01a44b8..dc52f198a 100644
--- a/app/src/main/java/fr/free/nrw/commons/notification/NotificationActivity.java
+++ b/app/src/main/java/fr/free/nrw/commons/notification/NotificationActivity.java
@@ -6,6 +6,7 @@ import android.content.Context;
import android.content.Intent;
import android.net.Uri;
import android.os.Bundle;
+import android.support.design.widget.Snackbar;
import android.support.v7.widget.DividerItemDecoration;
import android.support.v7.widget.LinearLayoutManager;
import android.support.v7.widget.RecyclerView;
@@ -15,6 +16,7 @@ import android.widget.RelativeLayout;
import com.pedrogomez.renderers.RVRendererAdapter;
+import java.lang.ref.WeakReference;
import java.util.Collections;
import java.util.List;
@@ -25,6 +27,7 @@ import butterknife.ButterKnife;
import fr.free.nrw.commons.R;
import fr.free.nrw.commons.Utils;
import fr.free.nrw.commons.theme.NavigationBaseActivity;
+import fr.free.nrw.commons.utils.NetworkUtils;
import fr.free.nrw.commons.utils.ViewUtil;
import io.reactivex.Observable;
import io.reactivex.android.schedulers.AndroidSchedulers;
@@ -62,9 +65,23 @@ public class NotificationActivity extends NavigationBaseActivity {
recyclerView.setLayoutManager(new LinearLayoutManager(this));
DividerItemDecoration itemDecor = new DividerItemDecoration(recyclerView.getContext(), DividerItemDecoration.VERTICAL);
recyclerView.addItemDecoration(itemDecor);
- addNotifications();
+ refresh();
}
+ private void refresh() {
+ if (!NetworkUtils.isInternetConnectionEstablished(this)) {
+ progressBar.setVisibility(View.GONE);
+ Snackbar.make(relativeLayout , R.string.no_internet, Snackbar.LENGTH_INDEFINITE)
+ .setAction(R.string.retry, view -> {
+ refresh();
+ }).show();
+ }else {
+ progressBar.setVisibility(View.VISIBLE);
+ addNotifications();
+ }
+ }
+
+
@SuppressLint("CheckResult")
private void addNotifications() {
Timber.d("Add notifications");
@@ -124,4 +141,4 @@ public class NotificationActivity extends NavigationBaseActivity {
.commit();
mNotificationWorkerFragment.setNotificationList(notificationList);
}
-}
\ No newline at end of file
+}
diff --git a/app/src/main/java/fr/free/nrw/commons/notification/NotificationRenderer.java b/app/src/main/java/fr/free/nrw/commons/notification/NotificationRenderer.java
index 73dcaf7b5..17a318e74 100644
--- a/app/src/main/java/fr/free/nrw/commons/notification/NotificationRenderer.java
+++ b/app/src/main/java/fr/free/nrw/commons/notification/NotificationRenderer.java
@@ -47,8 +47,8 @@ public class NotificationRenderer extends Renderer {
@Override
public void render() {
Notification notification = getContent();
- StringBuilder str = new StringBuilder(notification.notificationText.trim());
- str.append(" ");
+ String str = notification.notificationText.trim();
+ str = str.concat(" ");
title.setText(str);
time.setText(notification.date);
switch (notification.notificationType) {
diff --git a/app/src/main/java/fr/free/nrw/commons/settings/SettingsFragment.java b/app/src/main/java/fr/free/nrw/commons/settings/SettingsFragment.java
index 741905e30..037f0d792 100644
--- a/app/src/main/java/fr/free/nrw/commons/settings/SettingsFragment.java
+++ b/app/src/main/java/fr/free/nrw/commons/settings/SettingsFragment.java
@@ -151,8 +151,9 @@ public class SettingsFragment extends PreferenceFragment {
emailSelectorIntent.setData(Uri.parse("mailto:"));
//initialize the emailIntent
final Intent emailIntent = new Intent(Intent.ACTION_SEND);
- emailIntent.putExtra(Intent.EXTRA_EMAIL, new String[]{CommonsApplication.FEEDBACK_EMAIL});
- emailIntent.putExtra(Intent.EXTRA_SUBJECT, String.format(CommonsApplication.FEEDBACK_EMAIL_SUBJECT, BuildConfig.VERSION_NAME));
+ // Logs must be sent to the PRIVATE email. Please do not modify this without good reason!
+ emailIntent.putExtra(Intent.EXTRA_EMAIL, new String[]{CommonsApplication.LOGS_PRIVATE_EMAIL});
+ emailIntent.putExtra(Intent.EXTRA_SUBJECT, String.format(CommonsApplication.LOGS_PRIVATE_EMAIL_SUBJECT, BuildConfig.VERSION_NAME));
emailIntent.addFlags(Intent.FLAG_GRANT_READ_URI_PERMISSION);
emailIntent.addFlags(Intent.FLAG_GRANT_WRITE_URI_PERMISSION);
emailIntent.setSelector( emailSelectorIntent );
diff --git a/app/src/main/java/fr/free/nrw/commons/theme/NavigationBaseActivity.java b/app/src/main/java/fr/free/nrw/commons/theme/NavigationBaseActivity.java
index b65d6aa25..acd9b7646 100644
--- a/app/src/main/java/fr/free/nrw/commons/theme/NavigationBaseActivity.java
+++ b/app/src/main/java/fr/free/nrw/commons/theme/NavigationBaseActivity.java
@@ -28,6 +28,7 @@ import fr.free.nrw.commons.WelcomeActivity;
import fr.free.nrw.commons.auth.AccountUtil;
import fr.free.nrw.commons.auth.LoginActivity;
import fr.free.nrw.commons.contributions.ContributionsActivity;
+import fr.free.nrw.commons.featured.FeaturedImagesActivity;
import fr.free.nrw.commons.nearby.NearbyActivity;
import fr.free.nrw.commons.notification.NotificationActivity;
import fr.free.nrw.commons.settings.SettingsActivity;
@@ -154,6 +155,10 @@ public abstract class NavigationBaseActivity extends BaseActivity
drawerLayout.closeDrawer(navigationView);
NotificationActivity.startYourself(this);
return true;
+ case R.id.action_featured_images:
+ drawerLayout.closeDrawer(navigationView);
+ startActivityWithFlags(this, FeaturedImagesActivity.class, Intent.FLAG_ACTIVITY_REORDER_TO_FRONT);
+ return true;
default:
Timber.e("Unknown option [%s] selected from the navigation menu", itemId);
return false;
diff --git a/app/src/main/java/fr/free/nrw/commons/upload/DetectUnwantedPicturesAsync.java b/app/src/main/java/fr/free/nrw/commons/upload/DetectUnwantedPicturesAsync.java
index b383601ec..ab9fa5602 100644
--- a/app/src/main/java/fr/free/nrw/commons/upload/DetectUnwantedPicturesAsync.java
+++ b/app/src/main/java/fr/free/nrw/commons/upload/DetectUnwantedPicturesAsync.java
@@ -1,12 +1,18 @@
package fr.free.nrw.commons.upload;
+import android.app.Activity;
import android.content.Context;
+import android.content.Intent;
import android.graphics.BitmapRegionDecoder;
import android.net.Uri;
import android.os.AsyncTask;
+import android.support.v7.app.AlertDialog;
import java.io.IOException;
+import java.lang.ref.WeakReference;
+import fr.free.nrw.commons.R;
+import fr.free.nrw.commons.contributions.ContributionsActivity;
import fr.free.nrw.commons.utils.ImageUtils;
import timber.log.Timber;
@@ -21,16 +27,13 @@ import timber.log.Timber;
public class DetectUnwantedPicturesAsync extends AsyncTask {
- interface Callback {
- void onResult(ImageUtils.Result result);
- }
-
- private final Callback callback;
private final String imageMediaFilePath;
+ public final WeakReference activityWeakReference;
- DetectUnwantedPicturesAsync(String imageMediaFilePath, Callback callback) {
- this.callback = callback;
+ DetectUnwantedPicturesAsync(WeakReference activityWeakReference, String imageMediaFilePath) {
+ //this.callback = callback;
this.imageMediaFilePath = imageMediaFilePath;
+ this.activityWeakReference = activityWeakReference;
}
@Override
@@ -53,7 +56,29 @@ public class DetectUnwantedPicturesAsync extends AsyncTask {
+ //user does not wish to upload the picture, take them back to ContributionsActivity
+ Intent intent = new Intent(activity, ContributionsActivity.class);
+ dialogInterface.dismiss();
+ activity.startActivity(intent);
+ });
+ errorDialogBuilder.setNegativeButton(activity.getString(R.string.yes), (dialogInterface, i) -> {
+ //user wishes to go ahead with the upload of this picture, just dismiss this dialog
+ dialogInterface.dismiss();
+ });
+
+ AlertDialog errorDialog = errorDialogBuilder.create();
+ if (!activity.isFinishing()) {
+ errorDialog.show();
+ }
+ }
}
}
diff --git a/app/src/main/java/fr/free/nrw/commons/upload/MultipleShareActivity.java b/app/src/main/java/fr/free/nrw/commons/upload/MultipleShareActivity.java
index ac0afa979..5525f1ba7 100644
--- a/app/src/main/java/fr/free/nrw/commons/upload/MultipleShareActivity.java
+++ b/app/src/main/java/fr/free/nrw/commons/upload/MultipleShareActivity.java
@@ -237,7 +237,7 @@ public class MultipleShareActivity extends AuthenticatedActivity
private void showDetail(int i) {
if (mediaDetails == null || !mediaDetails.isVisible()) {
- mediaDetails = new MediaDetailPagerFragment(true);
+ mediaDetails = new MediaDetailPagerFragment(true, false);
getSupportFragmentManager()
.beginTransaction()
.replace(R.id.uploadsFragmentContainer, mediaDetails)
diff --git a/app/src/main/java/fr/free/nrw/commons/upload/ShareActivity.java b/app/src/main/java/fr/free/nrw/commons/upload/ShareActivity.java
index f5e1820b8..aca17601c 100644
--- a/app/src/main/java/fr/free/nrw/commons/upload/ShareActivity.java
+++ b/app/src/main/java/fr/free/nrw/commons/upload/ShareActivity.java
@@ -415,31 +415,9 @@ public class ShareActivity
private void performUnwantedPictureDetectionProcess() {
String imageMediaFilePath = FileUtils.getPath(this,mediaUri);
- DetectUnwantedPicturesAsync detectUnwantedPicturesAsync = new DetectUnwantedPicturesAsync(imageMediaFilePath, result -> {
-
- if (result != ImageUtils.Result.IMAGE_OK) {
- //show appropriate error message
- String errorMessage = result == ImageUtils.Result.IMAGE_DARK ? getString(R.string.upload_image_too_dark) : getString(R.string.upload_image_blurry);
- AlertDialog.Builder errorDialogBuilder = new AlertDialog.Builder(this);
- errorDialogBuilder.setMessage(errorMessage);
- errorDialogBuilder.setTitle(getString(R.string.warning));
- errorDialogBuilder.setPositiveButton(getString(R.string.no), (dialogInterface, i) -> {
- //user does not wish to upload the picture, take them back to ContributionsActivity
- Intent intent = new Intent(ShareActivity.this, ContributionsActivity.class);
- dialogInterface.dismiss();
- startActivity(intent);
- });
- errorDialogBuilder.setNegativeButton(getString(R.string.yes), (dialogInterface, i) -> {
- //user wishes to go ahead with the upload of this picture, just dismiss this dialog
- dialogInterface.dismiss();
- });
-
- AlertDialog errorDialog = errorDialogBuilder.create();
- if (!isFinishing()) {
- errorDialog.show();
- }
- }
- });
+ DetectUnwantedPicturesAsync detectUnwantedPicturesAsync
+ = new DetectUnwantedPicturesAsync(new WeakReference(this)
+ , imageMediaFilePath);
detectUnwantedPicturesAsync.execute();
}
diff --git a/app/src/main/java/fr/free/nrw/commons/upload/SingleUploadFragment.java b/app/src/main/java/fr/free/nrw/commons/upload/SingleUploadFragment.java
index 0fa98e530..a88d03c03 100644
--- a/app/src/main/java/fr/free/nrw/commons/upload/SingleUploadFragment.java
+++ b/app/src/main/java/fr/free/nrw/commons/upload/SingleUploadFragment.java
@@ -14,7 +14,9 @@ import android.support.annotation.NonNull;
import android.support.v4.view.ViewCompat;
import android.support.v7.app.AlertDialog;
import android.text.Editable;
+import android.text.Html;
import android.text.TextWatcher;
+import android.text.method.LinkMovementMethod;
import android.util.Log;
import android.view.LayoutInflater;
import android.view.Menu;
@@ -225,18 +227,6 @@ public class SingleUploadFragment extends CommonsDaggerSupportFragment {
.commit();
}
- @OnTouch(R.id.share_license_summary)
- boolean showLicence(View view, MotionEvent motionEvent) {
- if (motionEvent.getActionMasked() == ACTION_DOWN) {
- Intent intent = new Intent();
- intent.setAction(Intent.ACTION_VIEW);
- intent.setData(Uri.parse(licenseUrlFor(license)));
- startActivity(intent);
- return true;
- } else {
- return false;
- }
- }
@OnClick(R.id.titleDescButton)
void setTitleDescButton() {
@@ -294,8 +284,10 @@ public class SingleUploadFragment extends CommonsDaggerSupportFragment {
@SuppressLint("StringFormatInvalid")
private void setLicenseSummary(String license) {
- licenseSummaryView.setText(getString(R.string.share_license_summary, getString(Utils.licenseNameFor(license))));
- }
+ String licenseHyperLink = ""+ getString(Utils.licenseNameFor(license)) + "
";
+ licenseSummaryView.setMovementMethod(LinkMovementMethod.getInstance());
+ licenseSummaryView.setText(Html.fromHtml(getString(R.string.share_license_summary, licenseHyperLink)));
+ }
@Override
public void onActivityCreated(Bundle savedInstanceState) {
diff --git a/app/src/main/java/fr/free/nrw/commons/utils/NetworkUtils.java b/app/src/main/java/fr/free/nrw/commons/utils/NetworkUtils.java
index e934e53e5..b9da22e6e 100644
--- a/app/src/main/java/fr/free/nrw/commons/utils/NetworkUtils.java
+++ b/app/src/main/java/fr/free/nrw/commons/utils/NetworkUtils.java
@@ -9,7 +9,7 @@ public class NetworkUtils {
public static boolean isInternetConnectionEstablished(Context context) {
ConnectivityManager cm =
- (ConnectivityManager)context.getSystemService(Context.CONNECTIVITY_SERVICE);
+ (ConnectivityManager)context.getApplicationContext().getSystemService(Context.CONNECTIVITY_SERVICE);
NetworkInfo activeNetwork = cm.getActiveNetworkInfo();
return activeNetwork != null &&
diff --git a/app/src/main/java/fr/free/nrw/commons/utils/ViewUtil.java b/app/src/main/java/fr/free/nrw/commons/utils/ViewUtil.java
index 91e2114a9..b4b26746b 100644
--- a/app/src/main/java/fr/free/nrw/commons/utils/ViewUtil.java
+++ b/app/src/main/java/fr/free/nrw/commons/utils/ViewUtil.java
@@ -1,7 +1,9 @@
package fr.free.nrw.commons.utils;
+import android.app.Activity;
import android.content.Context;
import android.support.design.widget.Snackbar;
+import android.view.Display;
import android.view.View;
import android.widget.Toast;
@@ -16,4 +18,13 @@ public class ViewUtil {
Toast.LENGTH_LONG).show();
}
+ public static boolean isPortrait(Context context) {
+ Display orientation = ((Activity)context).getWindowManager().getDefaultDisplay();
+ if(orientation.getWidth() < orientation.getHeight()){
+ return true;
+ } else {
+ return false;
+ }
+ }
+
}
diff --git a/app/src/main/res/drawable-mdpi/share.png b/app/src/main/res/drawable-mdpi/share.png
new file mode 100644
index 000000000..17473572e
Binary files /dev/null and b/app/src/main/res/drawable-mdpi/share.png differ
diff --git a/app/src/main/res/drawable/ic_share_black_24dp.xml b/app/src/main/res/drawable/ic_share_black_24dp.xml
new file mode 100644
index 000000000..01c81322d
--- /dev/null
+++ b/app/src/main/res/drawable/ic_share_black_24dp.xml
@@ -0,0 +1,5 @@
+
+
+
diff --git a/app/src/main/res/drawable/ic_star_black_24dp.xml b/app/src/main/res/drawable/ic_star_black_24dp.xml
new file mode 100644
index 000000000..a87ca098d
--- /dev/null
+++ b/app/src/main/res/drawable/ic_star_black_24dp.xml
@@ -0,0 +1,9 @@
+
+
+
diff --git a/app/src/main/res/layout/activity_about.xml b/app/src/main/res/layout/activity_about.xml
index 9551e6e64..60519f591 100644
--- a/app/src/main/res/layout/activity_about.xml
+++ b/app/src/main/res/layout/activity_about.xml
@@ -111,7 +111,7 @@
android:layout_marginTop="@dimen/standard_gap"
android:gravity="center"
android:textColor="@color/primaryColor"
- android:text="@string/about_rate_us" />
+ />
+ />
+ />
+ />
-
-
diff --git a/app/src/main/res/layout/activity_featured_images.xml b/app/src/main/res/layout/activity_featured_images.xml
new file mode 100644
index 000000000..755fe4983
--- /dev/null
+++ b/app/src/main/res/layout/activity_featured_images.xml
@@ -0,0 +1,44 @@
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
\ No newline at end of file
diff --git a/app/src/main/res/layout/activity_welcome.xml b/app/src/main/res/layout/activity_welcome.xml
index 6fa7c7847..60e296fd0 100644
--- a/app/src/main/res/layout/activity_welcome.xml
+++ b/app/src/main/res/layout/activity_welcome.xml
@@ -14,6 +14,7 @@
android:id="@+id/welcomePagerIndicator"
android:layout_height="@dimen/half_standard_height"
android:layout_width="match_parent"
- android:layout_gravity="bottom" />
+ android:layout_gravity="bottom"
+ android:padding="5dp" />
\ No newline at end of file
diff --git a/app/src/main/res/layout/bottom_sheet_details.xml b/app/src/main/res/layout/bottom_sheet_details.xml
index 2be0f6cf7..c964fda87 100644
--- a/app/src/main/res/layout/bottom_sheet_details.xml
+++ b/app/src/main/res/layout/bottom_sheet_details.xml
@@ -37,8 +37,11 @@
android:id="@+id/title"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
- android:textSize="16sp" />
-
+ android:textSize="16sp"
+ android:layout_marginRight="50dp"
+ android:maxLines="2"
+ android:ellipsize="end"
+ />
-
+
\ No newline at end of file
diff --git a/app/src/main/res/layout/fragment_featured_images.xml b/app/src/main/res/layout/fragment_featured_images.xml
new file mode 100644
index 000000000..ca45f44c3
--- /dev/null
+++ b/app/src/main/res/layout/fragment_featured_images.xml
@@ -0,0 +1,40 @@
+
+
+
+
+
+
+
+
+
+
\ No newline at end of file
diff --git a/app/src/main/res/layout/fragment_media_detail.xml b/app/src/main/res/layout/fragment_media_detail.xml
index 190eb011d..f265bc3ea 100644
--- a/app/src/main/res/layout/fragment_media_detail.xml
+++ b/app/src/main/res/layout/fragment_media_detail.xml
@@ -80,6 +80,39 @@
android:textSize="@dimen/description_text_size" />
+
+
+
+
+
+
+
+
+
diff --git a/app/src/main/res/layout/fragment_single_upload.xml b/app/src/main/res/layout/fragment_single_upload.xml
index a340e0213..7eb2ed38a 100644
--- a/app/src/main/res/layout/fragment_single_upload.xml
+++ b/app/src/main/res/layout/fragment_single_upload.xml
@@ -74,6 +74,8 @@
android:layout_height="wrap_content"
android:layout_marginTop="@dimen/standard_gap"
android:gravity="center"
+ android:clickable="true"
+ android:textColorLink="@color/button_blue"
android:text="@string/share_license_summary" />
\ No newline at end of file
diff --git a/app/src/main/res/layout/layout_featured_images.xml b/app/src/main/res/layout/layout_featured_images.xml
new file mode 100644
index 000000000..399321719
--- /dev/null
+++ b/app/src/main/res/layout/layout_featured_images.xml
@@ -0,0 +1,66 @@
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
\ No newline at end of file
diff --git a/app/src/main/res/layout/toolbar.xml b/app/src/main/res/layout/toolbar.xml
index c7aac814a..f4e6d7cb4 100644
--- a/app/src/main/res/layout/toolbar.xml
+++ b/app/src/main/res/layout/toolbar.xml
@@ -9,4 +9,5 @@
android:minHeight="?attr/actionBarSize"
app:theme="@style/ThemeOverlay.AppCompat.Dark.ActionBar"
android:background="?attr/colorPrimaryDark">
+
\ No newline at end of file
diff --git a/app/src/main/res/menu/drawer.xml b/app/src/main/res/menu/drawer.xml
index 61c0739fe..ae6e0cce2 100644
--- a/app/src/main/res/menu/drawer.xml
+++ b/app/src/main/res/menu/drawer.xml
@@ -9,6 +9,12 @@
android:id="@+id/action_nearby"
android:icon="@drawable/ic_location_black_24dp"
android:title="@string/navigation_item_nearby" />
+
+
+
-
+
\ No newline at end of file
diff --git a/app/src/main/res/values-ab/error.xml b/app/src/main/res/values-ab/error.xml
index 80c41ae0f..f532642b5 100644
--- a/app/src/main/res/values-ab/error.xml
+++ b/app/src/main/res/values-ab/error.xml
@@ -1,4 +1,7 @@
+
Аиҧҟьара
Иҭабуп!
diff --git a/app/src/main/res/values-ab/strings.xml b/app/src/main/res/values-ab/strings.xml
index 2474f35ea..76caf25de 100644
--- a/app/src/main/res/values-ab/strings.xml
+++ b/app/src/main/res/values-ab/strings.xml
@@ -1,4 +1,8 @@
+
Архиарақәа
Ахархәаҩ ихьӡ
diff --git a/app/src/main/res/values-af/error.xml b/app/src/main/res/values-af/error.xml
index 929624a87..28e9241ea 100644
--- a/app/src/main/res/values-af/error.xml
+++ b/app/src/main/res/values-af/error.xml
@@ -1,4 +1,7 @@
+
Commons het omgeval
Oeps. Er is iets misgegaan.
diff --git a/app/src/main/res/values-ais/error.xml b/app/src/main/res/values-ais/error.xml
index 85a4b4366..e34da7329 100644
--- a/app/src/main/res/values-ais/error.xml
+++ b/app/src/main/res/values-ais/error.xml
@@ -1,4 +1,7 @@
+
kukay
diff --git a/app/src/main/res/values-ar/error.xml b/app/src/main/res/values-ar/error.xml
index 27612983b..a530cf38e 100644
--- a/app/src/main/res/values-ar/error.xml
+++ b/app/src/main/res/values-ar/error.xml
@@ -1,4 +1,8 @@
+
لقد تعطل كومنز
عفوا. حدث خطأ!
diff --git a/app/src/main/res/values-ar/strings.xml b/app/src/main/res/values-ar/strings.xml
index b9ad6a10a..6d9c94c1d 100644
--- a/app/src/main/res/values-ar/strings.xml
+++ b/app/src/main/res/values-ar/strings.xml
@@ -1,4 +1,19 @@
+
عام
كومنز
diff --git a/app/src/main/res/values-arc/error.xml b/app/src/main/res/values-arc/error.xml
index ce31ff09b..7c57e2649 100644
--- a/app/src/main/res/values-arc/error.xml
+++ b/app/src/main/res/values-arc/error.xml
@@ -1,4 +1,7 @@
+
ܬܘܕܝ ܠܟ!
diff --git a/app/src/main/res/values-ast/error.xml b/app/src/main/res/values-ast/error.xml
index e382e1176..8f03dc62e 100644
--- a/app/src/main/res/values-ast/error.xml
+++ b/app/src/main/res/values-ast/error.xml
@@ -1,4 +1,7 @@
+
Commons colgóse
Vaya. ¡Daqué funcionó mal!
diff --git a/app/src/main/res/values-ast/strings.xml b/app/src/main/res/values-ast/strings.xml
index 062b34fe8..532a4897e 100644
--- a/app/src/main/res/values-ast/strings.xml
+++ b/app/src/main/res/values-ast/strings.xml
@@ -1,4 +1,7 @@
+
Aspeutu
Xeneral
@@ -59,6 +62,7 @@
Guetar categoríes
Guardar
Refrescar
+ Llista
El GPS ta desactiváu nel preséu. ¿Quiés activalu?
Activar GPS
Inda nun hai xubes
@@ -151,8 +155,8 @@
Ensin descripción
Llicencia desconocida
Refrescar
- Permisu riquíu: llectura d\'almacenamientu esternu. L\'aplicación nun puede funcionar ensin él.
- Permisu riquíu: escritura d\'almacenamientu esternu. L\'aplicación nun puede funcionar ensin él.
+ Permisu riquíu: llectura d\'almacenamientu esternu. L\'aplicación nun puede entrar na to galería ensin él.
+ Permisu necesariu: Escritura n\'almacenamientu esternu. L\'aplicación nun puede aportar a la cámara ensin él.
Permisu opcional: llograr l\'allugamientu actual pa suxerir categoríes
Aceutar
Llugares cercanos
@@ -211,6 +215,7 @@
nun s\'atoparon descripciones
Páxina del ficheru en Commons
Elementu de WikiData
+ Artículu de Wikipedia
Error al poner les fotos na caché
Un títulu descriptivu únicu pal ficheru, que sirvirá para da-y nome al ficheru. Se pue usar llinguax normal con espacios. Nun amiestes la estensión del ficheru
Por favor, describi l\'elementu multimedia tantu como sía posible: ¿ónde se tomó?, ¿qué amuesa?, ¿cuál ye\'l contestu? Por favor, describi los oxetos o persones. Revela la información que nun pueda aldovinase de mou cenciellu, por casu el momentu del día si ye un paisaxe. Si\'l mediu amuesa daqué desacostumao, esplica qué lo fai raro.
@@ -224,6 +229,9 @@
Unviar ficheru de rexistru a los desendolcadores per corréu electrónicu
Nun s\'alcontró un restolador p\'abrir la URL
¡Error! Nun s\'alcontró la URL
+ Marcada pa desaniciar
+ Esta imaxe marcóse pa desaniciar.
+ Ver nel restolador
L\'allugamientu nun camudó.
L\'allugamientu nun ta disponible.
Ríquese permisu p\'amosar una llista de llugares cercanos
@@ -234,6 +242,21 @@
Gracies por facer una edición
%1$s te mentó en %2$s.
Alternar vista
- Entrugues más frecuentes
+ CÓMO LLEGAR
+ WIKIDATA
+ WIKIPEDIA
+ COMMONS
+ <u>Puntúanos</u>
+ <u>EMF</u>
Saltar el tutorial
+ Internet nun ta disponible
+ Internet ta disponible
+ Error al llograr les notificaciones
+ Nun s\'alcontraron notificaciones
+ <u>Traducir</u>
+ Llingües
+ Escueye l\'idioma pal que quies unviar traducciones
+ Siguir
+ Encaboxar
+ Retentar
diff --git a/app/src/main/res/values-az/error.xml b/app/src/main/res/values-az/error.xml
index ec14bbe6a..e698eab9d 100644
--- a/app/src/main/res/values-az/error.xml
+++ b/app/src/main/res/values-az/error.xml
@@ -1,4 +1,8 @@
+
Nasazlıq
Uups. Nəsə düzgün çalışmır!
diff --git a/app/src/main/res/values-azb/error.xml b/app/src/main/res/values-azb/error.xml
index 3d3a4d5b5..260cb0ce3 100644
--- a/app/src/main/res/values-azb/error.xml
+++ b/app/src/main/res/values-azb/error.xml
@@ -1,4 +1,7 @@
+
کامانز ایشدن دوشدو
اوخ. بیر خطا قاباغا گلدی!
diff --git a/app/src/main/res/values-b+be+tarask/error.xml b/app/src/main/res/values-b+be+tarask/error.xml
index d39823584..8f37a7ccc 100644
--- a/app/src/main/res/values-b+be+tarask/error.xml
+++ b/app/src/main/res/values-b+be+tarask/error.xml
@@ -1,4 +1,7 @@
+
Дзякуем!
diff --git a/app/src/main/res/values-b+hif+Latn/error.xml b/app/src/main/res/values-b+hif+Latn/error.xml
index 87f0c91a8..edd98b397 100644
--- a/app/src/main/res/values-b+hif+Latn/error.xml
+++ b/app/src/main/res/values-b+hif+Latn/error.xml
@@ -1,4 +1,7 @@
+
Commons crash hoe gais
Oops, Koi chij wrong hoe gais
diff --git a/app/src/main/res/values-b+kk+Cyrl/error.xml b/app/src/main/res/values-b+kk+Cyrl/error.xml
index 1b0279528..905077822 100644
--- a/app/src/main/res/values-b+kk+Cyrl/error.xml
+++ b/app/src/main/res/values-b+kk+Cyrl/error.xml
@@ -1,4 +1,7 @@
+
Рақмет!
diff --git a/app/src/main/res/values-b+nds+NL/error.xml b/app/src/main/res/values-b+nds+NL/error.xml
index 8ef805a5c..e16b388e5 100644
--- a/app/src/main/res/values-b+nds+NL/error.xml
+++ b/app/src/main/res/values-b+nds+NL/error.xml
@@ -1,4 +1,7 @@
+
Commons is vasteleupen
Oeps. Der gung iets mis.
diff --git a/app/src/main/res/values-b+roa+tara/error.xml b/app/src/main/res/values-b+roa+tara/error.xml
index 7a575379f..1a3607129 100644
--- a/app/src/main/res/values-b+roa+tara/error.xml
+++ b/app/src/main/res/values-b+roa+tara/error.xml
@@ -1,4 +1,7 @@
+
Commons ha sckattate
Mudu. Quacchecose ha sciute male!
diff --git a/app/src/main/res/values-b+sr+Latn/error.xml b/app/src/main/res/values-b+sr+Latn/error.xml
index 80d668c8b..7c22f8337 100644
--- a/app/src/main/res/values-b+sr+Latn/error.xml
+++ b/app/src/main/res/values-b+sr+Latn/error.xml
@@ -1,4 +1,7 @@
+
Ostava se srušila
Ups! Nešto je pošlo naopako.
diff --git a/app/src/main/res/values-b+sr+Latn/strings.xml b/app/src/main/res/values-b+sr+Latn/strings.xml
index f11ee10ab..0cd72a167 100644
--- a/app/src/main/res/values-b+sr+Latn/strings.xml
+++ b/app/src/main/res/values-b+sr+Latn/strings.xml
@@ -1,4 +1,9 @@
+
Ostava
Podešavanja
@@ -134,8 +139,8 @@
Nema opisa
Nepoznata licenca
Osveži
- Potrebna dozvola: Provera spoljašnje memorije. Aplikacija bez ovoga ne može da funkcioniše.
- Neophodna dozvola: Pisanje spoljašnjeg skladišta. Aplikacija ne može da funkcioniše bez ovoga.
+ Potrebna dozvola: Provera spoljašnje memorije. Aplikacija bez ovoga ne može da funkcioniše.
+ Neophodna dozvola: Pisanje spoljašnjeg skladišta. Aplikacija ne može da funkcioniše bez ovoga.
Opciona dozvola: Preuzmi trenutnu lokaciju za predloge kategorija
U redu
Mesta u blizini
diff --git a/app/src/main/res/values-b+tg+Cyrl/error.xml b/app/src/main/res/values-b+tg+Cyrl/error.xml
index 478aa98ea..6348c138a 100644
--- a/app/src/main/res/values-b+tg+Cyrl/error.xml
+++ b/app/src/main/res/values-b+tg+Cyrl/error.xml
@@ -1,4 +1,7 @@
+
Ташаккур!
diff --git a/app/src/main/res/values-ba/error.xml b/app/src/main/res/values-ba/error.xml
index d57fd8936..1dbf89be0 100644
--- a/app/src/main/res/values-ba/error.xml
+++ b/app/src/main/res/values-ba/error.xml
@@ -1,4 +1,7 @@
+
Рәхмәт!
diff --git a/app/src/main/res/values-ba/strings.xml b/app/src/main/res/values-ba/strings.xml
index b8ebc950b..293dd3f73 100644
--- a/app/src/main/res/values-ba/strings.xml
+++ b/app/src/main/res/values-ba/strings.xml
@@ -1,4 +1,9 @@
+
Тышҡы күренеш
Ғәҙәти
@@ -149,8 +154,8 @@
Һүрәтләүе юҡ
Билдәһеҙ лицензия
Яңыртып алыу
- Кәрәкле рөхсәт: тышҡы һаҡлағыстан алып уҡыу. Ҡушымта шунһыҙ эшләмәйәсәк.
- Кәрәкле рөхсәт: тышҡы һаҡлағысҡа яҙыу. Ҡушымта шунһыҙ эшләмәйәсәк.
+ Кәрәкле рөхсәт: тышҡы һаҡлағыстан алып уҡыу. Ҡушымта шунһыҙ эшләмәйәсәк.
+ Кәрәкле рөхсәт: тышҡы һаҡлағысҡа яҙыу. Ҡушымта шунһыҙ эшләмәйәсәк.
Мотлаҡ булмаған рөхсәт: категория тәҡдиме өсөн ошо урынды алыу
Яҡындағы урындар
Яҡындағы урындар табылманы
diff --git a/app/src/main/res/values-bcl/error.xml b/app/src/main/res/values-bcl/error.xml
index 06e509b92..502ca53b1 100644
--- a/app/src/main/res/values-bcl/error.xml
+++ b/app/src/main/res/values-bcl/error.xml
@@ -1,4 +1,7 @@
+
Kagrugaringan nagkagarabá
Oops. May bagay an napasala!
diff --git a/app/src/main/res/values-bg/error.xml b/app/src/main/res/values-bg/error.xml
index 8a51406c3..e20b5f568 100644
--- a/app/src/main/res/values-bg/error.xml
+++ b/app/src/main/res/values-bg/error.xml
@@ -1,4 +1,8 @@
+
Неуспех с Общомедия
Опа. Нещо се обърка!
diff --git a/app/src/main/res/values-bg/strings.xml b/app/src/main/res/values-bg/strings.xml
index dd5cbfe8f..cfaf021f9 100644
--- a/app/src/main/res/values-bg/strings.xml
+++ b/app/src/main/res/values-bg/strings.xml
@@ -1,4 +1,11 @@
+
Общомедия
Настройки
diff --git a/app/src/main/res/values-bn/error.xml b/app/src/main/res/values-bn/error.xml
index f972038e4..2c929f8b5 100644
--- a/app/src/main/res/values-bn/error.xml
+++ b/app/src/main/res/values-bn/error.xml
@@ -1,4 +1,9 @@
+
কমন্স ক্র্যাশ করেছে
ওহ, কিছু একটা ত্রুটি হয়েছে!
diff --git a/app/src/main/res/values-bn/strings.xml b/app/src/main/res/values-bn/strings.xml
index cbfd8e322..679c50803 100644
--- a/app/src/main/res/values-bn/strings.xml
+++ b/app/src/main/res/values-bn/strings.xml
@@ -1,4 +1,15 @@
+
অবয়ব
সাধারণ
@@ -59,6 +70,7 @@
বিষয়শ্রেণী অনুসন্ধান
সংরক্ষণ
পুনঃসতেজ
+ তালিকা
GPS আপনার ডিভাইসে অক্ষম করা আছে। আপনি কি এটি সক্ষম করতে চান?
GPS সক্রিয় করুন
এখনো কোন আপলোড নেই
@@ -80,6 +92,7 @@
বিষয়শ্রেণীসমূহ
সেটিং
নিবন্ধন করুন
+ নির্বাচিত ছবি
পরিচিতি
উইকিমিডিয়া কমন্স অ্যাপ হচ্ছে একটি উন্মুক্ত উৎস সম্বলিত অ্যাপ যা উইকিমিডিয়া সম্প্রদায়ের ব্যবহারকারী ও সেচ্ছাসেবকবৃন্দ কর্তৃক তৈরিকৃত এবং পরিচালিত। উইকিমিডিয়া ফাউন্ডেশন এই অ্যাপ তৈরি, উন্নয়ন বা রক্ষণাবেক্ষণে জড়িত নয়।
কোন সমস্যা ও পরামর্শের জন্য <a href=\"https://github.com/commons-app/apps-android-commons/issues\">গিটহাব ইস্যু</a> তৈরি করুন।
@@ -150,8 +163,8 @@
বিবরণ নেই
অজানা লাইসেন্স
পুনঃসতেজ
- প্রয়োজনীয় অনুমতি: বহিঃস্ত সঞ্চয়স্থান পড়া। এটি ছাড়া অ্যাপ কাজ করবে না।
- অনুমতি প্রয়োজন: অালাদাভাবে সংযুক্ত স্টোরেজ লিখুন। এটি ছাড়া অ্যাপটি চলতে পারেনা।
+ প্রয়োজনীয় অনুমতি: বহিঃস্ত সঞ্চয়স্থান পড়া। এটি ছাড়া অ্যাপ কাজ করবে না।
+ অনুমতি প্রয়োজন: অালাদাভাবে সংযুক্ত স্টোরেজ লিখুন। এটি ছাড়া অ্যাপটি চলতে পারেনা।
ঐচ্ছিক অনুমতি: বিষয়শ্রেণী পরামর্শের জন্য বর্তমান অবস্থান নেয়
ঠিক আছে
কাছাকাছি স্থান
@@ -164,6 +177,7 @@
মিডিয়ার শিরোনাম
বিবরণ
মিডিয়ার বিবরণ এখানে যাবে। এই মোটামুটি দীর্ঘ হতে পারে এবং একাধিক লাইনে লিখতে হতে পারে। আমরা আশা করি এটি দেখতে সুন্দর হবে।
+ স্রষ্টা
আপলোডের তারিখ
লাইসেন্স
স্থানাঙ্কসমূহ
@@ -206,10 +220,12 @@
প্রস্থান
ভূমিকা
বিজ্ঞপ্তি
+ নির্বাচিত
অবস্থানের অনুমতি ছাড়া কাছাকাছি জায়গাগুলি প্রদর্শন করা যাবে না
কোন বিবরণ পাওয়া যায়নি
কমন্সে ফাইলের পাতা
উইকিউপাত্ত পদ
+ উইকিপিডিয়া নিবন্ধ
ছবি আনার সময় ত্রুটি
ফাইলের একটি স্বতন্ত্র বর্ণনামূলক নাম যা ফাইলের নাম হিসাবে কাজ করবে। অাপনি সাধারণ ভাষা ব্যবহার করতে পারেন শূন্যস্থানসহ। ফাইলের এক্সটেনশন যুক্ত করবেন না।
যতটা সম্ভব মিডিয়াটি বর্ণনা করুন: এটি কোথায় ধারণ করা হয়েছিল? এটি কি প্রদর্শন করে? এটির প্রসঙ্গ কি? ধারণকৃত বস্তু অথবা ব্যক্তির বর্ণনা করুন। সহজে অনুমান করা যায়না সেরকম তথ্য উদঘাটন করুন, উদাহরণস্বরূপ, যদি ল্যান্ডস্কেপ হয় তাহলে দিবসকালের সময় দিন।
@@ -222,6 +238,8 @@
লগ ফাইল পাঠান
ইমেইলের মাধ্যমে উন্নয়নকারীর কাছে লগ ফাইল পাঠান
ত্রুটি! ইউআরএল পাওয়া যায়নি
+ অপসারণের জন্য মনোনীত
+ ব্রাউজারে দেখুন
অবস্থান পরিবর্তন হয়নি।
অবস্থান উপলব্ধ নয়।
কাছাকাছি স্থানসমূহের একটি তালিকা প্রদর্শন করতে অনুমতি প্রয়োজন
@@ -231,6 +249,14 @@
%1$s আপনার আলাপ পাতায় একটি বার্তা দিয়েছেন
একটি সম্পাদনা করার জন্য আপনাকে ধন্যবাদ
%1$s আপনাকে %2$s-এ উল্লেখ করেছেন।
- প্রায়শই জিজ্ঞাসিত প্রশ্নসমূহ
+ দিকনির্দেশ
+ উইকিউপাত্ত
+ উইকিপিডিয়া
+ কমন্স
+ প্রায়শই জিজ্ঞাসিত প্রশ্নসমূহ
টিউটোরিয়াল এড়ান
+ ইন্টারনেট অনুপলব্ধ
+ ইন্টারনেট উপলব্ধ
+ কোন বিজ্ঞপ্তি পাওয়া যায়নি
+ পুনঃচেষ্টা করুন
diff --git a/app/src/main/res/values-br/error.xml b/app/src/main/res/values-br/error.xml
index b1dfa421e..bb219551f 100644
--- a/app/src/main/res/values-br/error.xml
+++ b/app/src/main/res/values-br/error.xml
@@ -1,4 +1,8 @@
+
Commons zo aet er c\'hleuz
Hopala ! Un dra bennak a-dreuz zo bet !
diff --git a/app/src/main/res/values-br/strings.xml b/app/src/main/res/values-br/strings.xml
index bff5c79f8..8383f7cbe 100644
--- a/app/src/main/res/values-br/strings.xml
+++ b/app/src/main/res/values-br/strings.xml
@@ -1,4 +1,11 @@
+
Neuz
Hollek
@@ -146,8 +153,8 @@
Deskrivadur ebet
Aotre-implijout dizanv
Freskaat
- Aotre rekis : lenn ur stokañ diavaez. Hep se, n\'hall ket an arload mont en-dro.
- Aotre ret ; skrivañ war al lec\'h stokañ diavaez. Ne c\'hall ket an arload mont en-dro hep an dra-se.
+ Aotre rekis : lenn ur stokañ diavaez. Hep se, n\'hall ket an arload mont en-dro.
+ Aotre ret ; skrivañ war al lec\'h stokañ diavaez. Ne c\'hall ket an arload mont en-dro hep an dra-se.
Aotre diret : kaout al lec\'hiadur red evit kinnig rummadoù
Mat eo
Lec\'hioù nes
diff --git a/app/src/main/res/values-bs/error.xml b/app/src/main/res/values-bs/error.xml
index b266e3d6f..27a611f8b 100644
--- a/app/src/main/res/values-bs/error.xml
+++ b/app/src/main/res/values-bs/error.xml
@@ -1,4 +1,7 @@
+
Commons se srušio
Ups. Nešto je pošlo po zlu!
diff --git a/app/src/main/res/values-bs/strings.xml b/app/src/main/res/values-bs/strings.xml
index 6efaf7898..6c0097089 100644
--- a/app/src/main/res/values-bs/strings.xml
+++ b/app/src/main/res/values-bs/strings.xml
@@ -1,4 +1,9 @@
+
Commons
Postavke
@@ -133,7 +138,7 @@
Nema opisa
Nepoznata licenca
Osvježi
- Potrebna dozvola: Čitanje vanjske memorije. Aplikacija ne može raditi bez ovog.
+ Potrebna dozvola: Čitanje vanjske memorije. Aplikacija ne može raditi bez ovog.
Neobavezna dozvola: Dobavljanje trenutne lokacije za predlaganje kategorija
U redu
Mjesta u blizini
diff --git a/app/src/main/res/values-ca/error.xml b/app/src/main/res/values-ca/error.xml
index 8bea1c50e..6752fa848 100644
--- a/app/src/main/res/values-ca/error.xml
+++ b/app/src/main/res/values-ca/error.xml
@@ -1,4 +1,8 @@
+
El Commons s\'ha penjat
Uups ! Quelcom ha anat malament !
diff --git a/app/src/main/res/values-ca/strings.xml b/app/src/main/res/values-ca/strings.xml
index dcc406b73..f7f40f427 100644
--- a/app/src/main/res/values-ca/strings.xml
+++ b/app/src/main/res/values-ca/strings.xml
@@ -1,4 +1,14 @@
+
Aparença
Ubicació
@@ -181,5 +191,5 @@
LLEGIU L’ARTICLE
Gràcies per fer una modificació
%1$s us ha mencionat a %2$s.
- Preguntes freqüents
+ Preguntes freqüents
diff --git a/app/src/main/res/values-ce/error.xml b/app/src/main/res/values-ce/error.xml
index f8667a37d..75b00cf2f 100644
--- a/app/src/main/res/values-ce/error.xml
+++ b/app/src/main/res/values-ce/error.xml
@@ -1,4 +1,7 @@
+
Баркалла!
diff --git a/app/src/main/res/values-cs/error.xml b/app/src/main/res/values-cs/error.xml
index 050ae78d7..e6677dedc 100644
--- a/app/src/main/res/values-cs/error.xml
+++ b/app/src/main/res/values-cs/error.xml
@@ -1,6 +1,11 @@
+
- Commons spadly
+ Aplikace Commons spadla
Něco se pokazilo!
Řekněte nám, co jste dělali a dejte nám to vědět e-mailem. Pomůže sjednat nápravu!
Děkujeme vám!
diff --git a/app/src/main/res/values-cs/strings.xml b/app/src/main/res/values-cs/strings.xml
index f8e24cc7c..6e2453d6d 100644
--- a/app/src/main/res/values-cs/strings.xml
+++ b/app/src/main/res/values-cs/strings.xml
@@ -1,4 +1,19 @@
+
Vzhled
Obecné
@@ -59,6 +74,7 @@
Hledání kategorií
Uložit
Obnovit
+ Seznam
GPS ve vašem zařízení není povoleno. Chtěli byste ho spustit?
Spustit GPS
Žádné nahrané soubory
@@ -151,8 +167,8 @@
Bez popisu
Neznámá licence
Obnovit
- Požadováno oprávnění ke čtení externího úložiště. Aplikace bez toho nemůže pracovat.
- Požadováno oprávnění k zápisu do externího úložiště. Aplikace bez toho nemůže pracovat.
+ Požadované oprávnění: Čtení externího úložiště. Bez něj nemůže aplikace číst vaši galerii.
+ Požadované oprávnění: Zapisování do externího úložiště. Bez něj nemůže aplikace používat vaši kameru.
Volitelně: Umožněte aplikaci, aby získávala aktuální polohu a nabízela na jejím základě kategorie
OK
Místa v okolí
@@ -211,6 +227,7 @@
nebyl nalezen žádný popisek
Stránka souboru na Commons
Položka Wikidat
+ Článek na Wikipedii
Chyba při meziukládání obrázků
Unikátní a popisný název pro daný soubor, který bude sloužit jako název souboru. Můžete použít běžný psaný jazyk s mezerami; nezahrnujte koncovku souboru.
Popište prosím obrázek, jak jen to je možné: Kde byl pořízen? Co znázorňuje? Jaký je kontext obrázku? Popisujte prosím významné předměty nebo osoby na obrázku a nezapomeňte na informace, které není možné snadno odhadnout ze samotného obrázku, jako je například denní doba, pokud jde o krajinu. Pokud je na obrázku něco neobvyklého, popište, co to dělá neobvyklým.
@@ -225,6 +242,8 @@
Nebyl nalezen žádný webový prohlížeč k otevření URL
Chyba! URL nenalezeno
Navrhnout na smazání
+ Tento obrázek byl nominován na smazání.
+
Zobrazit v prohlížeči
Vaše umístění se nezměnilo.
Umístění není dostupné.
@@ -236,6 +255,21 @@
Děkujeme za vaši editaci
%1$s vás zmínil na %2$s.
Přepnout pohled
- Často kladené dotazy
+ POKYNY
+ WIKIDATA
+ WIKIPEDIE
+ COMMONS
+ <u>Ohodnoť nás</u>
+ <u>Často kladené otázky</u>
Přeskočit úvod
+ Internet je nedostupný
+ Internet je dostupný
+ Při načítání oznámení došlo k chybě
+ Nebyly nalezeny žádné oznámení
+ <u>Přeložit</u>
+ Jazyky
+ Vyberte jazyk, pro který chcete odeslat překlady
+ Pokračovat
+ Zrušit
+ Zkusit znovu
diff --git a/app/src/main/res/values-csb/error.xml b/app/src/main/res/values-csb/error.xml
index c2aef4ccb..aeead2d27 100644
--- a/app/src/main/res/values-csb/error.xml
+++ b/app/src/main/res/values-csb/error.xml
@@ -1,4 +1,7 @@
+
Pókôza sã fela Commons.
Wejle! Cos je lëchò pòszłé!
diff --git a/app/src/main/res/values-csb/strings.xml b/app/src/main/res/values-csb/strings.xml
index 3e08dac99..2d7b99904 100644
--- a/app/src/main/res/values-csb/strings.xml
+++ b/app/src/main/res/values-csb/strings.xml
@@ -1,4 +1,7 @@
+
Commons
Nastôwë
diff --git a/app/src/main/res/values-cy/error.xml b/app/src/main/res/values-cy/error.xml
index e592ad506..6c4fe8370 100644
--- a/app/src/main/res/values-cy/error.xml
+++ b/app/src/main/res/values-cy/error.xml
@@ -1,4 +1,8 @@
+
Aeth rhywbeth o\'i le yn Comin
Wwwwps. Aeth rhywbeth o\'i le!
diff --git a/app/src/main/res/values-cy/strings.xml b/app/src/main/res/values-cy/strings.xml
index f9dec6333..ef56bc3b0 100644
--- a/app/src/main/res/values-cy/strings.xml
+++ b/app/src/main/res/values-cy/strings.xml
@@ -1,4 +1,9 @@
+
Comin Wicimedia
Gosodiadau
diff --git a/app/src/main/res/values-da/error.xml b/app/src/main/res/values-da/error.xml
index 54eb27b27..493de925d 100644
--- a/app/src/main/res/values-da/error.xml
+++ b/app/src/main/res/values-da/error.xml
@@ -1,4 +1,8 @@
+
Commons gik ned
Ups. Noget gik galt!
diff --git a/app/src/main/res/values-da/strings.xml b/app/src/main/res/values-da/strings.xml
index 5edafa308..e10a93850 100644
--- a/app/src/main/res/values-da/strings.xml
+++ b/app/src/main/res/values-da/strings.xml
@@ -1,4 +1,12 @@
+
Udseende
Generelt
@@ -151,8 +159,8 @@
Ingen beskrivelse
Ukendt licens
Opdater
- Krævet tilladelse: Læs eksternt lager. Programmet kan ikke fungere uden denne tilladelse.
- Krævet tilladelse: Skriv til eksternt lager. Program kan ikke fungere uden denne funktion.
+ Krævet tilladelse: Læs eksternt lager. Programmet kan ikke fungere uden denne tilladelse.
+ Krævet tilladelse: Skriv til eksternt lager. Program kan ikke fungere uden denne funktion.
Valgfri tilladelse: Hent nuværende position for kategoriforslag
O.k.
Steder i nærheden
@@ -236,6 +244,6 @@
Tak fordi du lavede en redigering
%1$s nævnte dig på %2$s.
Skift visning
- Ofte stillede spørgsmål
+ Ofte stillede spørgsmål
Udelad øvelse
diff --git a/app/src/main/res/values-de/error.xml b/app/src/main/res/values-de/error.xml
index 9e54e12d2..43bb64ae5 100644
--- a/app/src/main/res/values-de/error.xml
+++ b/app/src/main/res/values-de/error.xml
@@ -1,4 +1,7 @@
+
Commons ist abgestürzt
Huch! Etwas ist schiefgelaufen.
diff --git a/app/src/main/res/values-de/strings.xml b/app/src/main/res/values-de/strings.xml
index 0f9e56bd3..60339308c 100644
--- a/app/src/main/res/values-de/strings.xml
+++ b/app/src/main/res/values-de/strings.xml
@@ -1,4 +1,11 @@
+
Erscheinung
Allgemein
@@ -81,6 +88,7 @@
Kategorien
Einstellungen
Registrieren
+ Vorgestellte Bilder
Über
Die Wikimedia-Commons-App ist eine Open-Source-App, entwickelt und gewartet von Freiwilligen der Wikimedia-Gemeinschaft. Die Wikimedia Foundation ist nicht bei der Erstellung, Entwicklung oder Wartung der App beteiligt.
Einen neuen <a href=\"https://github.com/commons-app/apps-android-commons/issues\">GitHub-Eintrag</a> für Fehlerberichte und Vorschläge erstellen.
@@ -152,8 +160,8 @@
Keine Beschreibung
Unbekannte Lizenz
Aktualisieren
- Erforderliche Berechtigung: Externen Speicher lesen. Die App funktioniert ohne diese Berechtigung nicht.
- Erforderliche Berechtigung: Externen Speicher beschreiben. Die App kann ohne dies nicht funktionieren.
+ Erforderliche Berechtigung: Externen Speicher lesen. Die App kann ohne diese Berechtigung nicht auf deine Galerie zugreifen.
+ Erforderliche Berechtigung: Externen Speicher beschreiben. Die App kann ohne diese Berechtigung nicht auf deine Kamera zugreifen.
Optionale Berechtigung: Ruft den aktuellen Standort für Kategorievorschläge ab
Okay
Orte in der Nähe
@@ -166,6 +174,8 @@
Titel des Mediums
Beschreibung
Hier folgt die Beschreibung des Mediums. Diese kann möglicherweise ziemlich lang sein und erfordert dann einen Umbruch auf mehreren Zeilen. Wir hoffen, dass sie dennoch gut aussieht.
+ Autor
+ Hier steht der Benutzername des Autors des vorgestellten Bildes.
Hochgeladen am
Lizenz
Koordinaten
@@ -208,6 +218,7 @@
Abmelden
Anleitung
Benachrichtigungen
+ Vorgestellt
Orte in der Nähe können ohne Berechtigung zur Standortbestimmung nicht ermittelt werden
Keine Beschreibung gefunden
Commons-Dateiseite
@@ -227,6 +238,8 @@
Zum Öffnen der URL wurde kein Webbrowser gefunden
Fehler! URL nicht gefunden
Zur Löschung vorschlagen
+ Dieses Bild wurde zur Löschung vorgeschlagen.
+
Im Browser ansehen
Der Standort hat sich nicht geändert.
Der Standort ist nicht verfügbar.
@@ -242,7 +255,17 @@
WIKIDATA
WIKIPEDIA
COMMONS
-
- Häufig gestellte Fragen
+ <u>Bewerte uns</u>
+ <u>Häufig gestellte Fragen</u>
Tutorial überspringen
+ Internet nicht verfügbar
+ Internet verfügbar
+ Fehler beim Abruf der Benachrichtigungen
+ Keine Benachrichtigungen gefunden
+ <u>Übersetzen</u>
+ Sprachen
+ Wähle die Sprache aus, für die du Übersetzungen durchführen möchtest.
+ Fortfahren
+ Abbrechen
+ Erneut versuchen
diff --git a/app/src/main/res/values-diq/error.xml b/app/src/main/res/values-diq/error.xml
index 98e5e8d23..a9cbfb85a 100644
--- a/app/src/main/res/values-diq/error.xml
+++ b/app/src/main/res/values-diq/error.xml
@@ -1,7 +1,13 @@
+
Commons lığiya
Oops. Thebayo nigurweyino!
Şıma se kerd bı, marê vacê. Dıma e-posta ra bırışê marê. Ney timar kerdışi de marê beno desteg!
- Teşekur kena
+ Teşekur kenan!
diff --git a/app/src/main/res/values-diq/strings.xml b/app/src/main/res/values-diq/strings.xml
index f8b2e7033..b88e412e7 100644
--- a/app/src/main/res/values-diq/strings.xml
+++ b/app/src/main/res/values-diq/strings.xml
@@ -1,4 +1,13 @@
+
Commons
Eyari
@@ -26,7 +35,7 @@
Barkerdışê mınê peyêni
Ratneya
- Nêbı
+ Ebe ser nêkewt
%1$d%% temamya
Bar beno
Galeri ra
diff --git a/app/src/main/res/values-dty/error.xml b/app/src/main/res/values-dty/error.xml
index 08524cb53..9233ecdae 100644
--- a/app/src/main/res/values-dty/error.xml
+++ b/app/src/main/res/values-dty/error.xml
@@ -1,4 +1,7 @@
+
हैत्मरा। केइचीज गलत भयो।
धन्यवाद!
diff --git a/app/src/main/res/values-el/error.xml b/app/src/main/res/values-el/error.xml
index ee39f1a00..68b5922d4 100644
--- a/app/src/main/res/values-el/error.xml
+++ b/app/src/main/res/values-el/error.xml
@@ -1,4 +1,9 @@
+
Τα Commons παρουσίασαν σφάλμα
Ωχ. Κάτι πήγε στραβά!
diff --git a/app/src/main/res/values-el/strings.xml b/app/src/main/res/values-el/strings.xml
index c01f9ab3a..759c44920 100644
--- a/app/src/main/res/values-el/strings.xml
+++ b/app/src/main/res/values-el/strings.xml
@@ -1,4 +1,15 @@
+
Εμφάνιση
Γενικά
@@ -81,6 +92,7 @@
Κατηγορίες
Ρυθμίσεις
Εγγραφή
+ Προβεβλημμένες εικόνες
Σχετικά
Λογισμικό ανοικτού κωδικού που κυκλοφορεί υπό την <a href=\"https://github.com/commons-app/apps-android-commons/blob/master/COPYING\">Άδεια Apache v2</a>. Το Wikimedia Commons και το λογότυπο είναι εμπορικά σήματα του Ιδρύματος Wikimedia και χρησιμοποιούνται με άδεια από το Ίδρυμα Wikimedia. Δεν συμμετέχουμε στην δημιουργία, ανάπτυξη ή συντήρηση του Ιδρύματος Wikimedia.
Δημιουργήστε ένα νέο <a href=\"https://github.com/commons-app/apps-android-commons/issues\">GitHub θέμα</a> για αναφορές σφαλμάτων και προτάσεις.
@@ -152,8 +164,8 @@
Καμία περιγραφή
Άγνωστη άδεια
Ανανέωση
- Απαιτούμενη άδεια: Ανάγνωση εξωτερικής αποθήκευσης. Η εφαρμογή δεν μπορεί να λειτουργήσει χωρίς αυτή.
- Απαιτούμενη άδεια: Με εξωτερική αποθήκευση.Το πρόγραμμα δεν μπορεί να λειτουργήσει με αυτήν.
+ Απαιτούμενη άδεια: Ανάγνωση εξωτερικής αποθήκευσης. Η εφαρμογή δεν μπορεί να έχει πρόσβαση στην συλλογή σας χωρίς αυτή.
+ Απαιτούμενη άδεια: Με εξωτερική αποθήκευση. Το πρόγραμμα δεν μπορεί να έχει πρόσβαση στην κάμερα σας χωρίς αυτήν.
Προαιρετική άδεια: Ανάκτηση τρέχουσας θέσης σας για προτάσεις κατηγοριών
Εντάξει
Κοντινοί Τόποι
@@ -166,6 +178,8 @@
Τίτλος πολυμέσου
Περιγραφή
Η περιγραφή του πολυμέσου μπαίνει εδώ. Αυτή μπορεί να είναι σχετικά μεγάλη, και θα χρειαστεί να αναδιπλωθεί σε πολλές γραμμές. Ελπίζουμε ωστόσο ότι θα φαίνεται όμορφα.
+ Συγγραφέας
+ Το όνομα χρήστη του συγγραφέα της επιλεγμένης εικόνας πάει εδώ.
Ημερομηνία φόρτωσης
Άδεια
Συντεταγμένες
@@ -208,6 +222,7 @@
Αποσύνδεση
Σεμινάριο
Ενημερώσεις
+ Επιλεγμένο
Οι κοντινές τοποθεσίες δεν μπορούν να προβληθούν δίχως τις άδειες τοποθεσίας
δεν βρέθηκε περιγραφή
Σελίδα φακέλλου κοινής χρήσης
@@ -227,6 +242,8 @@
Δεν βρέθηκε φυλλομετρητής για το άνοιγμα της διευθύνσεως URL
Σφάλμα! Η διεύθυνση URL δεν βρέθηκε
Προτείνετε για διαγραφή
+ Αυτή εικόνα έχει προταθεί για διαγραφή.
+
Προβολή στον περιηγητή
Ο εντοπισμός δεν έχει αλλάξει.
Ο τόπος δεν είναι διαθέσιμος.
@@ -242,7 +259,17 @@
Βικιδεδομένα
Βικιπαίδεια
Κοινά
-
- Συχνές ερωτήσεις
+ <u>Βαθμολογήστε μας</u>
+ <u>Συχνές ερωτήσεις</u>
Παράβλεψη εισαγωγής
+ Το διαδίκτυο δεν είναι διαθέσιμο
+ Το διαδίκτυο είναι διαθέσιμο
+ Σφάλμα κατά την συγκέντρωση ειδοποιήσεων
+ Δεν βρέθηκαν ειδοποιήσεις
+ <u>Μεταφράστε</u>
+ Γλώσσες
+ Επιλέξτε την γλώσσα που θα θέλατε να υποβάλετε μεταφράσεις για αυτή
+ Συνέχεια
+ Ακύρωση
+ Ξαναπροσπαθήστε
diff --git a/app/src/main/res/values-es/error.xml b/app/src/main/res/values-es/error.xml
index a7bb0ac06..f10caf6e4 100644
--- a/app/src/main/res/values-es/error.xml
+++ b/app/src/main/res/values-es/error.xml
@@ -1,4 +1,9 @@
+
Commons falló
Vaya. ¡Algo salió mal!
diff --git a/app/src/main/res/values-es/strings.xml b/app/src/main/res/values-es/strings.xml
index ab044505c..c1a45b309 100644
--- a/app/src/main/res/values-es/strings.xml
+++ b/app/src/main/res/values-es/strings.xml
@@ -1,4 +1,15 @@
+
Apariencia
Generales
@@ -59,6 +70,7 @@
Buscar categorías
Guardar
Actualizar
+ Lista
El GPS está desactivado en tu dispositivo. ¿Quieres activarlo?
Activar GPS
No hay subidas aún
@@ -80,6 +92,7 @@
Categorías
Ajustes
Regístrate
+ Imágenes en destaque
Acerca de
La aplicación de código abierto Wikimedia Commons fue creada por, y recibe mantenimiento de, cesionarios y voluntarios de la comunidad de Wikimedia. La Fundación Wikimedia no está involucrada en la creación, el desarrollo ni el mantenimiento de la aplicación.
Notifica de problemas y sugerencias en <a href=\"https://github.com/commons-app/apps-android-commons/issues\">GitHub</a>.
@@ -125,7 +138,7 @@
Wikimedia Commons aloja la mayoría de las imágenes utilizadas en Wikipedia.
¡Tus imágenes ayudan a instruir a personas de todo el mundo!
Carga únicamente imágenes capturadas o creadas por ti.
- - Objetos naturales (flores, animales, montañas)\n- Objetos útiles (bicicletas, estaciones de tren)\n- Personas famosas (tu alcalde, algún atleta olímpico que conociste)
+ Objetos naturales (flores, animales, montañas)\n• Objetos útiles (bicicletas, estaciones de tren)\n• Personas famosas (tu alcalde, algún atleta olímpico que conociste)
Naturaleza (flores, animales, montañas)
Objetos utilitarios (bicicletas, estaciones de tren)
Gente famosa (tu regente, algún atleta que hayas conocido…)
@@ -138,6 +151,7 @@
- Título: Casa de la Ópera de Sídney\n- Descripción: Casa de la Ópera de Sídney vista desde el otro lado de la bahía\n- Categorías: Casa de la Ópera de Sídney desde el oeste, Vistas a distancia de la Casa de la Ópera de Sídney
Título: Ópera de Sídney
Descripción: La Ópera de Sídney, vista desde el otro lado de la bahía
+ Categorías: Ópera de Sídney desde el oeste, Vistas a distancia de la Ópera de Sídney
Contribuye con tus imágenes.\n¡Ayuda a que los artículos de Wikipedia tengan vida!
Las imágenes en Wikipedia proceden de\nWikimedia Commons.
Tus imágenes ayudan a educar a la gente\nalrededor del mundo.
@@ -150,8 +164,8 @@
Sin descripción
Licencia desconocida
Actualizar
- Permiso obligatorio: lectura de almacenamiento externo. La aplicación no puede funcionar sin él.
- Permiso necesario: Escribir en almacenamiento externo. La aplicación no puede funcionar sin él.
+ Permiso obligatorio: lectura de almacenamiento externo. La aplicación no puede acceder a la galería sin él.
+ Permiso necesario: Escribir en almacenamiento externo. La aplicación no puede acceder a la cámara sin él.
Permiso opcional: obtener la ubicación actual para sugerir categorías
Aceptar
Lugares cercanos
@@ -164,6 +178,7 @@
Título del multimedia
Descripción
Aquí va la descripción del archivo multimedia. Esta puede ser muy extensa, en cuyo caso deberá ajustarse en varios renglones. No obstante, esperamos que se vea bien.
+ Autor
Fecha de subida
Licencia
Coordenadas
@@ -206,10 +221,12 @@
Salir
Tutorial
Notificaciones
+ En destaque
Los sitios cercanos no pueden mostrarse sin los permisos de ubicación
no se encontró ninguna descripción
Página del archivo en Commons
Elemento de Wikidata
+ Artículo de Wikipedia
Error al almacenar imágenes en la antememoria
Un título único descriptivo para el archivo, que servirá como un nombre de archivo. Puede usar un lenguaje claro con espacios. No incluya la extensión del archivo.
Por favor, describa el elemento multimedia tanto como sea posible: ¿dónde fue tomado?, ¿qué muestra?, ¿cuál es el contexto? Por favor, describa los objetos o personas. Ofrezca la información que no puede ser inferida tan fácilmente, por ejemplo el momento del día si es un paisaje. Si el medio muestra algo inusual, explique qué lo hace insual.
@@ -224,6 +241,7 @@
No se encontró ningún navegador con el que abrir el URL
Error: no se encontró el URL
Nominar para borrado
+ Se ha nominado esta imagen para su borrado.
Ver en navegador
La ubicación no ha cambiado.
La ubicación no está disponible.
@@ -234,5 +252,19 @@
%1$s dejó un mensaje en tu página de discusión
Gracias por realizar una edición
%1$s te ha mencionado en %2$s.
- Preguntas frecuentes
+ CÓMO LLEGAR
+ WIKIDATA
+ WIKIPEDIA
+ COMMONS
+ <u>Preguntas frecuentes</u>
+ Omitir tutorial
+ Internet no disponible
+ Internet disponible
+ Error al recuperar las notificaciones
+ No se encontró ninguna notificación
+ <u>Traducir</u>
+ Idiomas
+ Selecciona el idioma en que quieres enviar traducciones
+ Cancelar
+ Reintentar
diff --git a/app/src/main/res/values-eu/error.xml b/app/src/main/res/values-eu/error.xml
index 003667ad2..ff745c32a 100644
--- a/app/src/main/res/values-eu/error.xml
+++ b/app/src/main/res/values-eu/error.xml
@@ -1,4 +1,7 @@
+
Commons apurtu da
Uiii. Zerbait gaizki dabil!
diff --git a/app/src/main/res/values-eu/strings.xml b/app/src/main/res/values-eu/strings.xml
index ba6c22cca..f44262e05 100644
--- a/app/src/main/res/values-eu/strings.xml
+++ b/app/src/main/res/values-eu/strings.xml
@@ -1,4 +1,12 @@
+
Commons
Hobespenak
diff --git a/app/src/main/res/values-fa/error.xml b/app/src/main/res/values-fa/error.xml
index 638e3906e..3dd4bec2b 100644
--- a/app/src/main/res/values-fa/error.xml
+++ b/app/src/main/res/values-fa/error.xml
@@ -1,4 +1,10 @@
+
ویکیانبار متوقف شدهاست
اوه. خطایی در کار است!
diff --git a/app/src/main/res/values-fa/strings.xml b/app/src/main/res/values-fa/strings.xml
index 04f3832b6..d80b0772c 100644
--- a/app/src/main/res/values-fa/strings.xml
+++ b/app/src/main/res/values-fa/strings.xml
@@ -1,11 +1,27 @@
+
+ نمایش صفحه
+ عمومی
+ بازخورد
+ مکان
ویکیانبار
+ •
تنظیمات
نام کاربری
گذرواژه
به حساب کاربری ویکیانبار آزمایشی وارد شوید
ورود
+ رمز خود را فراموش کردهاید؟
ثبت نام
واردشدن
شکیبا باشید...
@@ -37,6 +53,7 @@
به اشتراکگذاشتن
مشاهده در مرورگر
عنوان
+ لطفاً نامی را برای این پرونده انتخاب کنید
توضیحات
قادر به ورود نیست - شکست شبکهای
ناتوانی در ورود - لطفاً نام کاربریتان را بررسی کنید
@@ -52,6 +69,7 @@
جستجوی ردهها
ذخیره
تازه کردن
+ فهرست
مکانیاب در دستگاه شما خاموش است. آیا دوست دارید فعال شود؟
فعال کردن مکانیاب
هنوز هیچ بارگذاری
@@ -72,8 +90,8 @@
درباره
اپلیکیشن ویکیانبار بنیاد ویکیمدیا یک نرمافزار آزاد است که توسط کاربران داوطلب و پاداشبگیر ایجاد و نگهداری میشود. بنیاد ویکیمدیا در ایجاد، نگهداری و توسعهٔ آن دخالتی ندارد.
ایجاد یک <a href=\"https://github.com/commons-app/apps-android-commons/issues\">درخواست در گیتهاب</a> برای گزارش باگ و یا پیشنهاد یک خصوصیت جدید.
- <a href=\"https://github.com/commons-app/apps-android-commons/wiki/Privacy-policy\">سیاست حفظ حریم خصوصی</a>
- <a href=\"https://github.com/commons-app/apps-android-commons/blob/master/CREDITS\">مجوز</a>
+ <u>سیاست حفظ حریم خصوصی</u>
+ <u>مجوز</u>
درباره
ارسال بازخورد (از طریق ایمیل)
نرمافزار ایمیل نصب نیست
@@ -85,7 +103,7 @@
این نگاره تحت مجوز %1$s است
با بارگذاری این تصویر، تأیید میکنم که این اثر کار خودم است و از محتوای دارای حق تکثیر یا سلفی برای ایجاد آن استفاده نکردهام و شرایط ذکر شده در By submitting this picture, I declare that this is my own work, that it does not contain copyrighted material or selfies, and otherwise adheres to <a href=\"https://commons.wikimedia.org/wiki/Commons:Policies_and_guidelines\">سیاستهای ویکیانبار</a> را رعایت میکند.
دریافت
- مجوز
+ مجوز پیشفرض
از عنوان/توضیحات پیشین استفاده کنید
دریافت خودکار موقعیت کنونی
درحال دریافت موقعیت برای پیشنهاد رده در صورتی که برچسب جغرافیایی وجود نداشته باشد.
@@ -114,7 +132,7 @@
ویکیانبار اکثر پروندههایی که در ویکیپدیا استفاده میشوند را در خود نگه میدارد.
تصاویر شما به مردم در اقصی نقاط دنیا کمک میکند!
لطفاً تصاویری که توسط خودتان گرفته شدهاند یا ایجاد شدهاند را بارگذاری کنید:
- -اجسام طبیعی (گیاه، جانور، کوه)\n-اجسام کاربردی (دوچرخه، ایستگاه قطار)\n-افراد مشهور (شهردار، قهرمانان المپیک)
+ •اجسام طبیعی (گیاه، جانور، کوه)\n•اجسام کاربردی (دوچرخه، ایستگاه قطار)\n•افراد مشهور (شهردار، قهرمانان المپیک)
لطفاً بارگذاری نکنید:
-سلفی خودتان یا تصویر دوستانتان\n-تصاویری که از اینترنت دانلود کردید\n-نماگرفت از دیگر اپلیکیشنها
نمونه بارگذاری:
@@ -131,8 +149,8 @@
بدون توضیحات
مجوز ناشناخته
تازهکردن
- اجازههای مورد نیاز: مطالعهٔ حافظهٔ خارجی. اپلیکیشن بدون آن نمیتواند کار کند.
- اجازههای مورد نیاز: نوشتن حافظهٔ خارجی. اپلیکیشن بدون آن نمیتواند کار کند.
+ اجازههای مورد نیاز: مطالعهٔ حافظهٔ خارجی. اپلیکیشن بدون آن نمیتواند کار کند.
+ اجازههای مورد نیاز: نوشتن حافظهٔ خارجی. اپلیکیشن بدون آن نمیتواند کار کند.
اجازههای اختیاری: دریافت موقعیت برای پیشنهاد رده
تأیید
مکانهای اطراف
@@ -202,6 +220,8 @@
ورود به حساب کاربریتان
ارسال فایل سیاهه
ارسال فایل سیاهه بهوسیلهٔ ایمیل برای توسعهدهندگان
+ .
+ مشاهده در مرورگر
مکان تغییر نکردهاست.
مکان موجود نیست.
برای نمایش مکانّای اطراف نیاز به اجازه است.
@@ -212,4 +232,18 @@
برای ویرایش ممنون
%1$s در %2$s به شما اشاره کردهاست.
دکمه نمایش
+ جهتها
+ ویکیداده
+ ویکیپدیا
+ ویکیانبار
+ <u>رتبه ما</u>
+ <u>سوالهای متداول</u>
+ رهاکردن آموزش
+ اینترنت در دسترس نیست
+ اینترنت در دسترس است
+ <u>ترجمه</u>
+ زبانها
+ ادامه
+ لغو
+ سعى دوباره
diff --git a/app/src/main/res/values-fi/error.xml b/app/src/main/res/values-fi/error.xml
index c5c3bc768..bc47fa3fb 100644
--- a/app/src/main/res/values-fi/error.xml
+++ b/app/src/main/res/values-fi/error.xml
@@ -1,4 +1,9 @@
+
Commons app on kaatunut
Pahoittelemme, virhe tapahtui.
diff --git a/app/src/main/res/values-fi/strings.xml b/app/src/main/res/values-fi/strings.xml
index e69997922..dd1d37993 100644
--- a/app/src/main/res/values-fi/strings.xml
+++ b/app/src/main/res/values-fi/strings.xml
@@ -1,4 +1,16 @@
+
Ulkoasu
Yleinen
@@ -149,8 +161,8 @@
Ei kuvausta
Tuntematon lisenssi
Päivitä
- Vaadittu oikeus: Ulkoisen tallennustilan luku. Appi ei toimi ilman tätä oikeutta.
- Vaadittava lupa: Kirjoita ulkoiseen tallennustilaan. Sovellus ei voi toimia ilman tätä.
+ Vaadittu oikeus: Ulkoisen tallennustilan luku. Appi ei toimi ilman tätä oikeutta.
+ Vaadittava lupa: Kirjoita ulkoiseen tallennustilaan. Sovellus ei voi toimia ilman tätä.
Valinnainen lupa: Saada tämänhetkinen sijainti loukkasuosituksia varten.
OK
Lähellä olevat paikat
@@ -231,6 +243,6 @@
Kiitos muokkaamisestasi
%1$s mainitsi sinut %2$s.
Vaihda näkymä
- Usein Kysytyt Kysymykset
+ Usein Kysytyt Kysymykset
Ohita opetus
diff --git a/app/src/main/res/values-fo/error.xml b/app/src/main/res/values-fo/error.xml
index 9c1462461..e06bb6e5e 100644
--- a/app/src/main/res/values-fo/error.xml
+++ b/app/src/main/res/values-fo/error.xml
@@ -1,4 +1,7 @@
+
Commons er óvirkið í løtuni
Ups. Okkurt gekk galið!
diff --git a/app/src/main/res/values-fo/strings.xml b/app/src/main/res/values-fo/strings.xml
index e5df10a2f..c4649407a 100644
--- a/app/src/main/res/values-fo/strings.xml
+++ b/app/src/main/res/values-fo/strings.xml
@@ -1,4 +1,7 @@
+
Wikimedia Commons
Innstillingar
diff --git a/app/src/main/res/values-fr/error.xml b/app/src/main/res/values-fr/error.xml
index 2cd1e09f3..743024b03 100644
--- a/app/src/main/res/values-fr/error.xml
+++ b/app/src/main/res/values-fr/error.xml
@@ -1,4 +1,7 @@
+
Commons a planté
Oups ! Quelque chose s’est mal passé !
diff --git a/app/src/main/res/values-fr/strings.xml b/app/src/main/res/values-fr/strings.xml
index 7003515d8..8494a7a36 100644
--- a/app/src/main/res/values-fr/strings.xml
+++ b/app/src/main/res/values-fr/strings.xml
@@ -1,4 +1,22 @@
+
Apparence
Général
@@ -28,8 +46,8 @@
Le téléversement de %1$s a échoué
Appuyer pour afficher
-
- %1$d fichier en cours de téléchargement
- - %1$d fichiers en cours de téléchargement
+ - %1$d fichier en cours de téléversement
+ - %1$d fichiers en cours de téléversement
Mes téléversements récents
Mis en file d\'attente
@@ -59,27 +77,29 @@
Rechercher des catégories
Enregistrer
Rafraîchir
+ Liste
Le GPS est désactivé sur votre appareil. Voulez-vous l’activer ?
Activer le GPS
Encore aucun téléversement
- \@string/contributions_subtitle_zero
- - %1$d téléchargement
- - %1$d téléchargements
+ - %1$d téléversement
+ - %1$d téléversements
- - %1$d téléchargement démarré
- - %1$d téléchargements démarrés
+ - %1$d téléversement démarré
+ - %1$d téléversements démarrés
- - %1$d téléchargement
- - %1$d téléchargements
+ - %1$d téléversement
+ - %1$d téléversements
Aucune catégorie correspondant à %1$s trouvée
Ajoutez des catégories pour rendre vos images plus simples à trouver sur Wikimedia Commons. \nCommencer à ajouter des catégories.
Catégories
Paramètres
S’inscrire
+ Images en vedette
À propos
L’application Wikimedia Commons est une application open source créée et tenue à jour par les bénéficiaires et volontaires de la communauté Wikimedia. La fondation Wikimedia n’est pas associée à la création, le développement ou l’entretien de l’application.
Créer un nouveau <a href=\"https://github.com/commons-app/apps-android-commons/issues\">signalement GitHub</a> pour signaler des bogues ou des suggestions.
@@ -151,8 +171,8 @@
Aucune description
Licence inconnue
Rafraîchir
- Autorisation nécessaire : Lire un stockage externe. L’application ne peut pas fonctionner sans cela.
- Permission obligatoire : Écriture sur stockage externe. L’application ne peut pas fonctionner sans cela.
+ Autorisation nécessaire : Lire un stockage externe. L’application ne peut pas accéder à votre galerie sans cela.
+ Permission obligatoire : Écriture sur stockage externe. L’application ne peut pas accéder à votre appareil photo sans cela.
Autorisation facultative : Obtenir l’emplacement actuel pour des suggestions de catégorie
OK
Endroits à proximité
@@ -165,6 +185,8 @@
Titre du média
Description
La description du média vient ici. Cela peut être potentiellement assez long, et devra être réparti sur plusieurs lignes. Nous espérons que cela restera joli néanmoins.
+ Auteur
+ Le nom de l’utilisateur auteur d’une image en vedette va ici.
Date de téléversement
Licence
Coordonnées
@@ -207,10 +229,12 @@
Déconnexion
Tutoriel
Notifications
+ Mis en vedette
Les endroits proches ne peuvent pas être affichés si vous ne partagez pas votre position géographique.
aucune description trouvée
Page des fichiers de Commons
Élément de Wikidata
+ Article Wikipédia
Erreur en mettant les images en cache
Un titre descriptif unique pour le fichier, qui servira de nom de fichier. Vous pouvez utiliser un langage simple avec des espaces. N’incluez pas l’extension du fichier
Veuillez décrire le média autant que possible : Où a-t-il été enregistré ? Que montre-t-il ? Quel est le contexte ? Veuillez décrire les objets ou les personnes. Révélez les informations qui ne peuvent pas être devinées facilement, par exemple l’heure de la journée si c’est un paysage. Si le média montre quelque chose d’inhabituel, veuillez expliquer ce qui le rend exceptionnel.
@@ -225,6 +249,8 @@
Pas d\'afficheur web trouvé pour ouvrir l\'URL
Erreur! URL non trouvée
Proposer pour suppression
+ Cette image a été citée pour suppression.
+
Afficher dans le navigateur
L\'emplacement n\'a pas changé.
Emplacement non disponible.
@@ -236,7 +262,21 @@
Merci de faire une modification
%1$s vous a mentionné sur %2$s .
Basculer l’affichage
-
- Questions posées fréquemment
+ DIRECTIONS
+ WIKIDATA
+ WIKIPÉDIA
+ COMMUNS
+ <u>Votre appréciation</u>
+ <u>FAQ</u>
Sauter le tutoriel
+ Internet indisponible
+ Internet disponible
+ Erreur sur recherche des notifications
+ Pas de notification trouvée
+ <u>Traduire</u>
+ Langues
+ Sélectionner la langue pour laquelle vous voulez soumettre des traductions
+ Continuer
+ Annuler
+ Réessayer
diff --git a/app/src/main/res/values-frp/error.xml b/app/src/main/res/values-frp/error.xml
index f7a658562..f94b6d47c 100644
--- a/app/src/main/res/values-frp/error.xml
+++ b/app/src/main/res/values-frp/error.xml
@@ -1,4 +1,7 @@
+
Grant-marci !
diff --git a/app/src/main/res/values-frr/error.xml b/app/src/main/res/values-frr/error.xml
index f4ec61282..b00633c95 100644
--- a/app/src/main/res/values-frr/error.xml
+++ b/app/src/main/res/values-frr/error.xml
@@ -1,4 +1,7 @@
+
Commons as ufstört
Uups, diar as wat skiaf gingen!
diff --git a/app/src/main/res/values-frr/strings.xml b/app/src/main/res/values-frr/strings.xml
index 6cd088696..f4866e705 100644
--- a/app/src/main/res/values-frr/strings.xml
+++ b/app/src/main/res/values-frr/strings.xml
@@ -1,4 +1,8 @@
+
Commons
Iinstelangen
@@ -133,7 +137,7 @@
Nian beskriiwang
Ünbekäänd lisens
Nei loose
- Ferlangd rochten: Ekstern seekrang lees. Det app koon saner detdiar rocht ei werke.
+ Ferlangd rochten: Ekstern seekrang lees. Det app koon saner detdiar rocht ei werke.
Mögelk rocht: Rept di aktuel plak för kategoriiföörslacher ap.
OK
Steeden naibi
diff --git a/app/src/main/res/values-fur/error.xml b/app/src/main/res/values-fur/error.xml
index 3f6f1ad21..0264c32b3 100644
--- a/app/src/main/res/values-fur/error.xml
+++ b/app/src/main/res/values-fur/error.xml
@@ -1,4 +1,7 @@
+
Ops. Alc al è lât mal!
Graziis!
diff --git a/app/src/main/res/values-gl/error.xml b/app/src/main/res/values-gl/error.xml
index b4c62454c..6a77c8d0c 100644
--- a/app/src/main/res/values-gl/error.xml
+++ b/app/src/main/res/values-gl/error.xml
@@ -1,4 +1,7 @@
+
Commons fallou
Vaites! Algo foi mal!
diff --git a/app/src/main/res/values-gl/strings.xml b/app/src/main/res/values-gl/strings.xml
index 5b5f67f18..e7c3a37c2 100644
--- a/app/src/main/res/values-gl/strings.xml
+++ b/app/src/main/res/values-gl/strings.xml
@@ -1,11 +1,26 @@
+
+ Aparencia
+ Xeral
+ Comentarios
+ Localización
Commons
+ •
Configuracións
Nome de usuario
Contrasinal
Acceda á súa conta de Commons Beta
Acceder ao sistema
+ Esqueceu o contrasinal?
Rexistrarse
Accedendo ao sistema
Por favor, agarde…
@@ -37,6 +52,7 @@
Compartir
Mostrar no navegador
Título
+ Por favor, proporcione un título para este ficheiro
Descrición
Erro ao acceder ao sistema: Fallou a rede
Erro ao acceder ao sistema: Comprobe o seu nome de usuario
@@ -52,6 +68,7 @@
Procurar categorías
Gardar
Refrescar
+ Lista
O GPS está desactivado no seu dispositivo. Quere activalo?
Activar GPS
Aínda non hai subas
@@ -76,8 +93,8 @@
Acerca de
A aplicación Wikimedia Commons é unha aplicación de código aberto creada e mantida polos cesionarios e voluntarios da comunidade de Wikimedia. A Fundación Wikimedia non está involucrada na creación, desenvolvemento ou mantemento da aplicación.
Crear unha nova <a href=\"https://github.com/commons-app/apps-android-commons/issues\">incidencia</a> para informar de problemas e suxestións.
- <a href=\"https://github.com/commons-app/apps-android-commons/wiki/Privacy-policy\">Política de privacidade</a>
- <a href=\"https://github.com/commons-app/apps-android-commons/blob/master/CREDITS\">Créditos</a>
+ <u>Política de privacidade</u>
+ <a href=\"https://github.com/commons-app/apps-android-commons/blob/master/CREDITS\">Créditos</a>
Acerca de
Enviar comentarios (por correo electrónico)
Non hai instalado ningún cliente de correo
@@ -89,7 +106,7 @@
Esta imaxe quedará baixo a licenza %1$s
Publicando esta imaxe, declaro que é da miña obra, que non contén material con dereitos de autor ou selfies e que se adhire ás <a href=\"https://commons.wikimedia.org/wiki/Commons:Policies_and_guidelines\">Políticas de Wikimedia Commons</a>.
Descargar
- Licenza
+ Licenza por defecto
Usar o título ou a descrición anterior
Obter automaticamente a localización actual
Obter a localización actual para ofrecer suxestións de categoría se a imaxe non está xeolocalizada
@@ -118,11 +135,20 @@
Wikimedia Commons alberga a maioría das imaxes usada en Wikipedia.
As súas imaxes axudan a educar a persoas de todo o mundoǃ
Por favor, suba unicamente imaxes capturadas ou creadas totalmente por vostedeː
- - Obxectos naturais (flores, animais, montañas)\n- Obxectos útiles (bicicletas, estacións de tren)\n- Personaxes famosos (o seu alcalde, atletas olímpicos que coñeza)
+ Obxectos naturais (flores, animais, montañas)\n• Obxectos útiles (bicicletas, estacións de ferrocarril)\n• Persoas famosas (o seu alcalde, atletas olímpicos que coñeza)
+ Natureza (flores, animais, montañas)
+ Obxectos útiles (bicicletas, estacións de ferrocarril)
+ Persoas famosas (o seu alcalde, atletas olímpicos que coñeza)
Por favor, NON subaː
- Selfies ou imaxes dos seus amigos\n- Imaxes descargadas de Internet\n- Capturas de pantalla de aplicacións con dereitos de autor
+ Autorretratos ou fotos dos seus amigos
+ Imaxes descargadas de Internet
+ Capturas de pantalla de aplicacións privativas
Exemplo de subaː
- Título: Ópera de Sydney\n- Descrición: A Ópera de Sydney vista dende a baía\n- Categorías: Sydney Opera House from the west, Sydney Opera House remote views
+ Título: Ópera de Sydney
+ Descrición: A Ópera de Sydney, vista desde o outro lado da baía
+ Categorías: Ópera de Sydney desde o oeste, vistas a distancia da Ópera de Sydney
Achegue as súas imaxes. Axude a que os artigos da Wikipedia cobren vida!
As imaxes da Wikipedia veñen da Wikimedia Commons.
As súas imaxes axudan a educar xente de todo o mundo.
@@ -135,8 +161,8 @@
Sen descrición
Licenza descoñecida
Refrescar
- Permiso necesarioː ler un almacenamento externo. A aplicación non pode funcionar sen isto.
- Permiso necesario: Escribir en almacenamento externo. A aplicación non pode funcionar sen el.
+ Permiso necesarioː ler un almacenamento externo. A aplicación non pode acceder á súa galería sen isto.
+ Permiso necesario: Escribir en almacenamento externo. A aplicación non pode acceder á súa cámara sen el.
Permiso opcionalː obter a localización actual para suxerir categorías
Aceptar
Lugares próximos
@@ -195,6 +221,7 @@
non se atopou descrición
Páxina do ficheiro en Commons
Elemento en Wikidata
+ Artigo de Wikipedia
Erro mentras se gardaban as imaxes na caché
Un título único descritivo para o ficheiro, que servirá como un nome de ficheiro. Pode usar unha linguaxe clara con espazos. Non inclúa a extensión do ficheiro
Por favor, describa o ficheiro todo o posibleː Onde se gravou? Cal é o contexto? Por favor, describa os obxectos ou persoas. Indique información que non pode ser adiviñada de forma doada, por exemplo, a hora do día se é unha paisaxe. Se o ficheiro amosa algo pouco habitual, por favor, explique que é o que o fai excepcional.
@@ -206,6 +233,11 @@
Comezar sesión na súa conta
Enviar ficheiro de rexistro
Enviar ficheiro de rexistro ós desenvolvedores por correo electrónico
+ Non se atopou ningún navegador co que abrir a URL
+ Errorǃ Nos se atopou a URL
+ Nomear para borrado
+ Esta imaxe foi nomeada para borrar.
+ Ver en navegador
A localización non cambiou.
A localización non está dispoñible.
Precísase permiso para amosar unha lista de lugares preto de aquí
@@ -216,4 +248,21 @@
Grazas por realizar unha edición
%1$s mencionouno en %2$s.
Cambiar modo de visualización
+ COMO CHEGAR
+ WIKIDATA
+ WIKIPEDIA
+ COMMONS
+ <u>Avalíenos</u>
+ <u>FAQ</u>
+ Saltar titorial
+ Internet non dispoñible
+ Internet dispoñible
+ Erro ó recuperar as notificacións
+ Non se atopou ningunha notificación
+ <u>Traducir</u>
+ Linguas
+ Seleccione a lingua para a que quere enviar as traducións
+ Proceder
+ Cancelar
+ Reintentar
diff --git a/app/src/main/res/values-gu/error.xml b/app/src/main/res/values-gu/error.xml
index 81ff69fbe..7f9e3762e 100644
--- a/app/src/main/res/values-gu/error.xml
+++ b/app/src/main/res/values-gu/error.xml
@@ -1,4 +1,7 @@
+
કોમન્સ ભાંગી પડ્યું છે
ઉપ્સ. કંઇક ખરાબ થયું છે!
diff --git a/app/src/main/res/values-haw/error.xml b/app/src/main/res/values-haw/error.xml
index 3efc364c9..145f13a97 100644
--- a/app/src/main/res/values-haw/error.xml
+++ b/app/src/main/res/values-haw/error.xml
@@ -1,4 +1,7 @@
+
Ua haki ʻO Kahilehulehu
ʻAuwē. Loaʻa i ka pilikia!
diff --git a/app/src/main/res/values-haw/strings.xml b/app/src/main/res/values-haw/strings.xml
index 028661090..a81ab120d 100644
--- a/app/src/main/res/values-haw/strings.xml
+++ b/app/src/main/res/values-haw/strings.xml
@@ -1,4 +1,7 @@
+
Kahilehulehu Wikimedia
Makemake
diff --git a/app/src/main/res/values-hi/error.xml b/app/src/main/res/values-hi/error.xml
index d4a796db4..8a9254afc 100644
--- a/app/src/main/res/values-hi/error.xml
+++ b/app/src/main/res/values-hi/error.xml
@@ -1,4 +1,8 @@
+
कॉमन्स क्रैश हो गया
ओह, कुछ गलत हो गया!
diff --git a/app/src/main/res/values-hi/strings.xml b/app/src/main/res/values-hi/strings.xml
index 869f6b72b..69bb67655 100644
--- a/app/src/main/res/values-hi/strings.xml
+++ b/app/src/main/res/values-hi/strings.xml
@@ -1,4 +1,19 @@
+
कॉमन्स
सेटिंग्स
@@ -134,8 +149,8 @@
कोई विवरण नहीं
अज्ञात लाइसेन्स
ताजा करें
- अनिवार्य अनुमति: बाहरी स्मृति पढ़ें। एप इसके बिना कार्य नहीं करेगा।
- अनिवार्य अनुमति:बाहरी कंप्यूटर स्टोरेज लिखना|इसके बिना एप कार्य नहीं करेगा।
+ अनिवार्य अनुमति: बाहरी स्मृति पढ़ें। एप इसके बिना कार्य नहीं करेगा।
+ अनिवार्य अनुमति:बाहरी कंप्यूटर स्टोरेज लिखना|इसके बिना एप कार्य नहीं करेगा।
वैकल्पिक अनुमति: श्रेणी सुझाव हेतु वर्तमान स्थान ज्ञात करें
ठीक है
आसपास के स्थान
@@ -218,4 +233,12 @@
विकीडाटा
विकीपीडिया
कॉमन्स
+ इंटरनेट उपलब्ध नहीं
+ इंटरनेट उपलब्ध
+ सूचनाएं लाने में त्रुटि
+ कोई सूचनाएँ नहीं मिलीं
+ भाषाएँ
+ आगे बढ़ें
+ रद्द करें
+ पुनः प्रयास करें
diff --git a/app/src/main/res/values-hrx/error.xml b/app/src/main/res/values-hrx/error.xml
index b61ba334d..24d908c6d 100644
--- a/app/src/main/res/values-hrx/error.xml
+++ b/app/src/main/res/values-hrx/error.xml
@@ -1,4 +1,7 @@
+
Commons (Allmend) ist abgestürzt
Huch! Etwas ist schiefgeloof.
diff --git a/app/src/main/res/values-hrx/strings.xml b/app/src/main/res/values-hrx/strings.xml
index 51c9ed9ec..7905a92d7 100644
--- a/app/src/main/res/values-hrx/strings.xml
+++ b/app/src/main/res/values-hrx/strings.xml
@@ -1,4 +1,8 @@
+
Wikimedia Commons (Wikimedia Allmend)
Instellunge
diff --git a/app/src/main/res/values-hsb/error.xml b/app/src/main/res/values-hsb/error.xml
index 0bc699dfd..9846f0d65 100644
--- a/app/src/main/res/values-hsb/error.xml
+++ b/app/src/main/res/values-hsb/error.xml
@@ -1,4 +1,7 @@
+
Commons je spadnył
Hopla. Něšto je so nimokuliło!
diff --git a/app/src/main/res/values-hsb/strings.xml b/app/src/main/res/values-hsb/strings.xml
index bba30831c..97b0d1af5 100644
--- a/app/src/main/res/values-hsb/strings.xml
+++ b/app/src/main/res/values-hsb/strings.xml
@@ -1,4 +1,7 @@
+
Wikimedia Commons
Nastajenja
diff --git a/app/src/main/res/values-hu/error.xml b/app/src/main/res/values-hu/error.xml
index 6d42fad35..765b80670 100644
--- a/app/src/main/res/values-hu/error.xml
+++ b/app/src/main/res/values-hu/error.xml
@@ -1,4 +1,9 @@
+
Az alkalmazás összeomlott
Hoppá! Valami elromlott!
diff --git a/app/src/main/res/values-hu/strings.xml b/app/src/main/res/values-hu/strings.xml
index 852f9b6c8..e17c0991a 100644
--- a/app/src/main/res/values-hu/strings.xml
+++ b/app/src/main/res/values-hu/strings.xml
@@ -1,11 +1,28 @@
+
+ Visszajelzés
+ Helyszín
Commons
+ •
Beállítások
Felhasználónév
Jelszó
Jelentkezz be a Commons Béta fiókoddal
Bejelentkezés
+ Elfelejtett jelszó:
Regisztráció
Belépés…
Kérlek várj…
@@ -52,6 +69,7 @@
Keresés a kategóriák között
Mentés
Frissítés
+ Lista
A GPS le van tiltva az eszközén. Szeretné engedélyezni?
GPS engedélyezése
Még nincsenek feltöltések
@@ -89,7 +107,7 @@
Ez a kép %1$s licenc alatt kerül feltöltésre
A kép feltöltésével kijelentem, hogy ez a saját munkám és nem tartalmaz jogvédett anyagot, nem szelfi és megfelel a<a href=\"https://commons.wikimedia.org/wiki/Commons:Policies_and_guidelines\">Wikimedia Commons irányelveinek</a>.
Letöltés
- Licenc
+ Alapértelmezett licenc
Előző cím/leírás használata
Automatikusan megkapja a jelenlegi helyet
Lekéri a jelenlegi helyet, hogy lehetőség legyen kategóriajavaslatokra a nem földrajzi címkézett képeknél.
@@ -123,6 +141,7 @@
- Szelfiket vagy képeket a barátaidról\n- Internetröl letöltött képeket\n- Kereskedelmi alkalmazások képernyőképeit
Példa feltöltés:
- Cím: Sydney-i Operaház\n- Leírás: A Sydney-i Operaház az öböl túlpartjáról\n- Kategóriák: Sydney Opera House from the west, Sydney Opera House remote views
+ Cím: Sydney-i Operaház
Tedd közzé a képeidet! Segíts életre kelteni a Wikipédia-szócikkeket!
A Wikipédián található képek a Wikimédia Commonsből származnak.
A képeid segítenek a világ minden táján élő emberek oktatásában.
@@ -135,8 +154,8 @@
Nincs leírás
Ismeretlen licenc
Frissítés
- Szükséges engedély: Külső tárhely olvasása. Az alkalmazás nem működik enélkül.
- Szükséges engedély: Külső tárhely írása. Az alkalmazás nem működik enélkül.
+ Szükséges engedély: Külső tárhely olvasása. Az alkalmazás nem működik enélkül.
+ Szükséges engedély: Külső tárhely írása. Az alkalmazás nem működik enélkül.
Lehetséges engedély: Jelenlegi hely megszerzése, a kategóriajavaslatok lehetőségéért.
OK
Közeli helyek
@@ -192,6 +211,7 @@
nincs leírás
Commons leírólap
Wikidata-elem
+ Wikipédia-cikk
Hiba a képek gyorsítótárazásakor
Egy egyedi, leíró cím a fájlnak, ami fájlnévként fog szolgálni. Egyszerű nyelvezetet használhatsz szóközökkel. Ne tedd bele a kiterjesztést.
Kérlek a lehető legteljesebb módon írd le a fájlt: hol készült, mit ábrázol, mi a kontextus? Kérlek add meg az objektumokat vagy személyeket a képen, valamint a nehezen kitalálható információkat (például a kép készítésének dátumát, ha az egy tájkép). Amennyiben a média valami szokatlant ábrázol, kérlek fejtsd ki, hogy mi teszi szokatlanná.
@@ -201,6 +221,8 @@
Bejelentkezés a fiókodba
Naplófájlok küldése
Naplófájlok küldése e-mailben a fejlesztőknek
+ Hiba! URL nem található.
+ Törlésre jelölés
A hely nem változott.
A hely nem érhető el.
Üdvözlünk a Wikimedia Commonson, %1$s! Örülünk, hogy itt vagy.
diff --git a/app/src/main/res/values-hy/error.xml b/app/src/main/res/values-hy/error.xml
index f8289a6ff..93541a611 100644
--- a/app/src/main/res/values-hy/error.xml
+++ b/app/src/main/res/values-hy/error.xml
@@ -1,4 +1,7 @@
+
Վաայ: Ինչ-որ բան սխալ գնաց
Շնորհակալություն
diff --git a/app/src/main/res/values-hyw/error.xml b/app/src/main/res/values-hyw/error.xml
index 40393662f..14f0ff1c3 100644
--- a/app/src/main/res/values-hyw/error.xml
+++ b/app/src/main/res/values-hyw/error.xml
@@ -1,4 +1,7 @@
+
Շնորհակալութիւն:
diff --git a/app/src/main/res/values-ia/error.xml b/app/src/main/res/values-ia/error.xml
index 6ca241fc3..877fcd28c 100644
--- a/app/src/main/res/values-ia/error.xml
+++ b/app/src/main/res/values-ia/error.xml
@@ -1,4 +1,7 @@
+
Commons: crash
Ups. Qualcosa ha facite fiasco!
diff --git a/app/src/main/res/values-in/error.xml b/app/src/main/res/values-in/error.xml
index 8279fe84f..0c7243d0a 100644
--- a/app/src/main/res/values-in/error.xml
+++ b/app/src/main/res/values-in/error.xml
@@ -1,4 +1,8 @@
+
Commons mendadak kacau
Ups. Ada yang tidak beres!
diff --git a/app/src/main/res/values-in/strings.xml b/app/src/main/res/values-in/strings.xml
index 47d50d14a..16185f35d 100644
--- a/app/src/main/res/values-in/strings.xml
+++ b/app/src/main/res/values-in/strings.xml
@@ -1,4 +1,12 @@
+
Commons
Pengaturan
diff --git a/app/src/main/res/values-is/error.xml b/app/src/main/res/values-is/error.xml
index d4150af3c..93e65f581 100644
--- a/app/src/main/res/values-is/error.xml
+++ b/app/src/main/res/values-is/error.xml
@@ -1,4 +1,7 @@
+
Commons-forritið hrundi
Úbbs. Eitthvað fór úrskeiðis!
diff --git a/app/src/main/res/values-is/strings.xml b/app/src/main/res/values-is/strings.xml
index c766bf7b2..3985a654b 100644
--- a/app/src/main/res/values-is/strings.xml
+++ b/app/src/main/res/values-is/strings.xml
@@ -1,4 +1,7 @@
+
Útlit
Almennt
@@ -59,6 +62,7 @@
Leita í flokkum
Vista
Endurlesa
+ Listi
GPS er óvirkt í tækinu þínu. Viltu virkja það?
Virkja GPS
Engar innsendingar ennþá
@@ -151,8 +155,8 @@
Engin lýsing
Óþekkt notkunarleyfi
Endurlesa
- Nauðsynlegar heimildir: Lesa ytri gagnageymslu. Forritið virkar ekki án þess.
- Nauðsynlegar heimildir: Skrifa í ytri gagnageymslu. Forritið virkar ekki án þess.
+ Nauðsynlegar heimildir: Lesa ytri gagnageymslu. Forritið fær ekki aðgang að myndasafni ekki án þessa.
+ Nauðsynlegar heimildir: Skrifa í ytri gagnageymslu. Forritið nær ekki sambandi við myndavél ekki án þessa.
Nauðsynlegar heimildir: Lesa núverandi staðsetningu til að geta stungið upp á flokkum
Í lagi
Staðir í nágrenninu
@@ -211,6 +215,7 @@
engin lýsing fannst
Síða Commons-skrár
Wikidata-atriði
+ Wikipedia-grein
Villa kom upp í skyndiminni mynda
Einstakur og lýsandi titill, sem mun verða skráarheiti. Þú mátt nota einfaldan texta með bilum. Ekki hafa með neina skráarendingu
Lýstu gögnunum eins vel og auðið er: Hvar er myndin tekin? Hvað sýnir hún? Hvert er samhengið? Lýstu fólki og fyrirbærum. Gefðu upp þær upplýsingar sem ekki er auðvelt að giska á, til dæmis á hvaða tíma dags myndin er tekin ef hún sýnir landslag. Ef gögnin sýna eitthvað óvenjulegt, útskýrðu þá hvað það er sem sé sérstakt.
@@ -224,6 +229,9 @@
Senda atvikaskrá til forritaranna með tölvupósti
Gat ekki ræst vefvafra til að opna slóð
Villa: Slóð fannst ekki
+ Tilnefna til eyðingar
+ Þessi mynd hefur verið valin til eyðingar.
+ Skoða í vafra
Staðsetning hefur ekki breyst.
Staðsetning ekki tiltæk.
Heimild þarf til að birta lista yfir staði í nágrenninu
@@ -234,6 +242,21 @@
Takk fyrir að hafa gert breytingar
%1$s minntist á þig á %2$s.
Víxla sýn
- Algengar spurningar
+ STEFNUR
+ WIKIDATA
+ WIKIPEDIA
+ COMMONS
+ <u>Gefðu okkur einkunn</u>
+ <u>Algengar spurningar</u>
Sleppa kennslu
+ Nettenging ekki tiltæk
+ Nettenging í boði
+ Villa við að sækja tilkynningar
+ Engar tilkynningar fundust
+ <u>Þýða</u>
+ Tungumál
+ Veldu tungumálið sem þú vill senda inn þýðingar fyrir
+ Halda áfram
+ Hætta við
+ Reyna aftur
diff --git a/app/src/main/res/values-it/error.xml b/app/src/main/res/values-it/error.xml
index 81389a530..ed0f872fd 100644
--- a/app/src/main/res/values-it/error.xml
+++ b/app/src/main/res/values-it/error.xml
@@ -1,4 +1,7 @@
+
Commons è andato in errore
Oops. Qualcosa è andato storto!
diff --git a/app/src/main/res/values-it/strings.xml b/app/src/main/res/values-it/strings.xml
index b0dcce458..27968b8d7 100644
--- a/app/src/main/res/values-it/strings.xml
+++ b/app/src/main/res/values-it/strings.xml
@@ -1,4 +1,13 @@
+
Aspetto
Generale
@@ -56,6 +65,7 @@
Cerca categorie
Salva
Aggiorna
+ Elenco
Il GPS è disabilitato nel dispositivo. Vuoi attivarlo?
Attiva GPS
Non è stato ancora caricato niente
@@ -150,6 +160,7 @@
Titolo
Titolo del file multimediale
Descrizione
+ Autore
Data di caricamento
Licenza
Coordinate
@@ -186,9 +197,11 @@
nessuna descrizione trovata
Pagina di Commons del file
Elemento Wikidata
+ Voce Wikipedia
Dai autorizzazione
Accedi alla tua utenza
Errore! URL non trovato
+ Questa immagine è stata proposta per la cancellazione.
La posizione non è cambiata.
Posizione non disponibile.
OTTIENI DIREZIONI
@@ -197,5 +210,13 @@
%1$s ti ha lasciato un messaggio nella tua pagina di discussione
Grazie per aver fatto una modifica
%1$s ti ha menzionato su %2$s.
- Domande frequenti
+ WIKIDATA
+ WIKIPEDIA
+ COMMONS
+ <u>Domande frequenti</u>
+ Internet non disponibile
+ Internet disponibile
+ Lingue
+ Annulla
+ Riprova
diff --git a/app/src/main/res/values-iw/error.xml b/app/src/main/res/values-iw/error.xml
index 3f64d1789..949fd6772 100644
--- a/app/src/main/res/values-iw/error.xml
+++ b/app/src/main/res/values-iw/error.xml
@@ -1,4 +1,7 @@
+
יישום ויקישיתוף קרס
אוי, משהו השתבש!
diff --git a/app/src/main/res/values-iw/strings.xml b/app/src/main/res/values-iw/strings.xml
index ed94cdc29..186df118a 100644
--- a/app/src/main/res/values-iw/strings.xml
+++ b/app/src/main/res/values-iw/strings.xml
@@ -1,4 +1,16 @@
+
מראה
כללי
@@ -58,6 +70,7 @@
חיפוש קטגוריות
שמירה
רענון
+ רשימה
ה־GPS במכשיר שלך אינו מופעל. האם להפעיל אותו?
הפעלת GPS
לא הועלה עדיין שום דבר
@@ -79,6 +92,7 @@
קטגוריות
הגדרות
רישום
+ תמונות מומלצות
אודות
יישום ויקישיתוף (Wikimedia Commons app) הוא יישום קוד פתוח שמפותח ומתוחזק על־ידי מקבלי מלגות ומתנדבים של קהילת ויקימדיה. קרן ויקימדיה אינה מעורבת ביצירה, פיתוח, או תחזוקה של היישום.
נא ליצור <a href=\"https://github.com/commons-app/apps-android-commons/issues\">דיווח בגיטהאב</a> בשביל באגים והצעות.
@@ -150,8 +164,8 @@
אין תיאור
רישיון לא ידוע
רענון
- הרשאה מחייבת: אחסון. היישום לא יכול לעבוד בלי זה.
- נדרשת הרשאה: כתיבה לאחסון חיצוני. היישום לא יכול לעבוד בלי זה.
+ נדרשת הרשאה: קריאת אחסון חיצוני. היישום לא יכול לגשת לגלריה שלך בלי זה.
+ נדרשת הרשאה: כתיבה לאחסון חיצוני. היישום לא יכול לגשת למצלמה שלך בלי זה.
הרשאה לא מחייבת: קבלת מיקום נוכחי בשביל הצעות קטגוריות
אישור
מקומות בסביבה
@@ -164,6 +178,8 @@
כותרת המדיה
תיאור
תיאור המדיה יהיה כאן. זה יכול להיות ארוך למדי, ולהתפרס על מספר שורות. אנחנו מקווים שזה נראה טוב.
+ יוצר
+ שם המשתמש של יוצר התמונה המומלצת.
תאריך העלאה
רישיון
נקודות ציון
@@ -205,6 +221,7 @@
יציאה
מדריך
הודעות
+ מומלץ
אי־אפשר להציג מקומות בסביבה ללא הרשאות מיקום
לא נמצא תיאור
דף קובץ בוויקישיתוף
@@ -221,6 +238,9 @@
שליחת קובץ יומן
שליחת קובץ יומן למפתחים בדואר אלקטרוני
לא נמצא דפדפן שיוכל לפתוח את הכתובת
+ להציע מחיקה
+ התמונה הזאת מועמדת למחיקה
+ הצגה בדפדפן
המיקום לא השתנה.
המיקום אינו זמין.
נדרשת הרשאה כדי להציג רשימה של מקומות בסביבה
@@ -231,6 +251,21 @@
תודה לך על העריכה
אוזכרת על ידי %2$s ב{{GRAMMAR:תחילית|%1$s}}.
החלפת מצב תצוגה
- שאלות נפוצות
+ כיוונים
+ ויקינתונים
+ ויקיפדיה
+ ויקישיתוף
+ <u>תנו לנו ציון</u>
+ <u>שאלות נפוצות</u>
לדלג על ההדרכה
+ האינטרנט אינו זמין
+ האינטרנט זמין
+ שגיאה באחזור התראות
+ לא נמצאו התראות
+ <u>תרגום</u>
+ שפות
+ נא לבחור את השפה שבה תשלחו את התרגומים
+ המשך
+ ביטול
+ לנסות שוב
diff --git a/app/src/main/res/values-ja/error.xml b/app/src/main/res/values-ja/error.xml
index e155388f2..9d95a7d2d 100644
--- a/app/src/main/res/values-ja/error.xml
+++ b/app/src/main/res/values-ja/error.xml
@@ -1,4 +1,7 @@
+
コモンズがクラッシュしました
エラーが発生しました!
diff --git a/app/src/main/res/values-ja/strings.xml b/app/src/main/res/values-ja/strings.xml
index 2095f3d31..e34c98432 100644
--- a/app/src/main/res/values-ja/strings.xml
+++ b/app/src/main/res/values-ja/strings.xml
@@ -1,5 +1,19 @@
+
+ フィードバック
+ 場所
コモンズ
設定
利用者名
@@ -71,8 +85,8 @@
このアプリについて
ウィキメディア・コモンズ・アプリはウィキメディア・コミュニティの助成金受給者とボランティアによって製作・メンテナンスされているオープンソースソフトウェアです。ウィキメディア財団はこのアプリの製作・開発・メンテナンスに関与していません。
バグとアイディアは <a href=\"https://github.com/commons-app/apps-android-commons/issues\">Github</a> へ。
- <a href=\"https://github.com/commons-app/apps-android-commons/wiki/プライバシー・ポリシー\">プライバシー・ポリシー</a>
- <a href=\"https://github.com/commons-app/apps-android-commons/blob/master/CREDITS\">クレジット</a>
+ <u>プライバシー・ポリシー</u>
+ <u>クレジット</u>
このアプリについて
フィードバックをメールで送信
メールアプリケーションが見つかりません
@@ -83,7 +97,7 @@
キャンセル
この画像が %1$s ライセンスでアップロードされます。
ダウンロード
- ライセンス
+ 既定のライセンス
前回のタイトルと記述を使用
現在の位置を自動的に取得
画像にジオタグが付いていない場合、現在の位置を取得してカテゴリを提案
@@ -129,8 +143,8 @@
説明はありません。
不明なライセンス
更新
- 必要な権限:外部ストレージを読み込みます。これがなければアプリは機能しません。
- 必要な権限:外部ストレージを作成します。これがなければアプリは機能しません。
+ 必要な権限:外部ストレージを読み込みます。これがなければアプリは機能しません。
+ 必要な権限:外部ストレージを作成します。これがなければアプリは機能しません。
オプションの権限:カテゴリ候補の現在の位置を取得する
承認
周りの場所
@@ -143,6 +157,7 @@
メディアのタイトル
記述
ここにメディアの説明が入ります。かなり長文になる場合には数行にわたることがあります。それでも見栄えがよいと願っています。
+ 作者
アップロード日時
ライセンス
緯度経度
@@ -183,6 +198,7 @@
場所の権限がないと、近くの場所を表示できません
説明がありません
ウィキデータ項目
+ ウィキペディアの記事
画像をキャッシュする際のエラー
ファイル固有の説明的な表題。ファイル名として使われます。平易な言葉を使い、空白を入れることができます。拡張子は含めないでください。
可能な限りメディアを説明してください:どこで撮られましたか?それは何を示していますか?文脈とは何ですか?物や人を説明してください。容易に推測できない情報、例えば風景の場合の時刻を明らかにする。メディアに珍しいことがある場合は、何が珍しいのかを説明してください。
@@ -192,6 +208,15 @@
自分のアカウントにログイン
ログファイルを送信する
メールで開発者にログファイルを送信する
+ ブラウザーで表示
場所は変更されていません。
位置が無効です。
+ 記事を読む
+ <u>評価する</u>
+ <u>FAQ</u>
+ チュートリアルをスキップする
+ <u>翻訳</u>
+ 言語
+ キャンセル
+ 再試行
diff --git a/app/src/main/res/values-ji/error.xml b/app/src/main/res/values-ji/error.xml
index e0fd55abb..e61d3b67d 100644
--- a/app/src/main/res/values-ji/error.xml
+++ b/app/src/main/res/values-ji/error.xml
@@ -1,4 +1,7 @@
+
קאמאנסט איז אײַנגעפֿאלן
אוי, עפעס טויג נישט!
diff --git a/app/src/main/res/values-ji/strings.xml b/app/src/main/res/values-ji/strings.xml
index b5ddb6339..9122cc710 100644
--- a/app/src/main/res/values-ji/strings.xml
+++ b/app/src/main/res/values-ji/strings.xml
@@ -1,4 +1,7 @@
+
קאמאנס
איינשטעלונגען
@@ -56,6 +59,7 @@
קאַטעגאריעס
איינשטעלונגען
+ רעקאמענדירטע בילדער
וועגן
וועגן
שיקן פֿידבעק (דורך בליצפאסט)
@@ -92,6 +96,7 @@
ווארענונג
יא
ניין
+ מחבר
ליצענץ
קאארדינאטן
טולפאן
@@ -105,4 +110,5 @@
איינשטעלונגען
פֿידבעק
אַרויסלאָגירן
+ רעקאמנדירט
diff --git a/app/src/main/res/values-jv/error.xml b/app/src/main/res/values-jv/error.xml
index b968dbb2e..26d4c0431 100644
--- a/app/src/main/res/values-jv/error.xml
+++ b/app/src/main/res/values-jv/error.xml
@@ -1,4 +1,7 @@
+
Commons lagi kaco
Wadhuh. Ana sing luput!
diff --git a/app/src/main/res/values-jv/strings.xml b/app/src/main/res/values-jv/strings.xml
index 15949cde8..e051b6f97 100644
--- a/app/src/main/res/values-jv/strings.xml
+++ b/app/src/main/res/values-jv/strings.xml
@@ -1,4 +1,7 @@
+
Commons
Setèlan
@@ -119,7 +122,7 @@
Tanpa katerangan
Lisènsi ora kaweruhan
Anyarana
- Butuh palilah: Maca panyimpenan njaba. Aplikasi mokal mlaku yèn tanpa iki.
+ Butuh palilah: Maca panyimpenan njaba. Aplikasi mokal mlaku yèn tanpa iki.
Palilah manasuka: Njupuk pernah saiki kanggo saran ing kategori
Oké
Papan Cedhak Kéné
diff --git a/app/src/main/res/values-ka/error.xml b/app/src/main/res/values-ka/error.xml
index 2e6b95c18..82ce98b94 100644
--- a/app/src/main/res/values-ka/error.xml
+++ b/app/src/main/res/values-ka/error.xml
@@ -1,4 +1,7 @@
+
ვიკისაწყობი გაითიშა
ვაი. რაღაც მოხდა!
diff --git a/app/src/main/res/values-ka/strings.xml b/app/src/main/res/values-ka/strings.xml
index 7e3b77917..2bb1c5191 100644
--- a/app/src/main/res/values-ka/strings.xml
+++ b/app/src/main/res/values-ka/strings.xml
@@ -1,4 +1,8 @@
+
ვიკისაწყობი
კონფიგურაცია
diff --git a/app/src/main/res/values-kab/error.xml b/app/src/main/res/values-kab/error.xml
index 922edaad0..f2602e6a5 100644
--- a/app/src/main/res/values-kab/error.xml
+++ b/app/src/main/res/values-kab/error.xml
@@ -1,4 +1,7 @@
+
Commons yeɣli
Ihuh. Yella wayen yeḍran!
diff --git a/app/src/main/res/values-kab/strings.xml b/app/src/main/res/values-kab/strings.xml
index ec93fdd67..342c615b9 100644
--- a/app/src/main/res/values-kab/strings.xml
+++ b/app/src/main/res/values-kab/strings.xml
@@ -1,4 +1,8 @@
+
Ayen yettwasnen
Iɣewwaren
@@ -134,8 +138,8 @@
Ulac aglam
Turagt tarussint
Smiren
- Yesra tasiregt: Ɣeṛ asekles azɣaray. Asnas ur yezmir ara ad yeddu s war aya.
- Ysera tasiregt: Aru deg usekles azɣaray. Asnas ur yezmir ara ad yeddu s war aya.
+ Yesra tasiregt: Ɣeṛ asekles azɣaray. Asnas ur yezmir ara ad yeddu s war aya.
+ Ysera tasiregt: Aru deg usekles azɣaray. Asnas ur yezmir ara ad yeddu s war aya.
Tasiregt tafrayant: Awi adig amiran i yisumar n taggayt
IH
Idigen iqeṛben
diff --git a/app/src/main/res/values-km/error.xml b/app/src/main/res/values-km/error.xml
index 631b36024..14986df3b 100644
--- a/app/src/main/res/values-km/error.xml
+++ b/app/src/main/res/values-km/error.xml
@@ -1,4 +1,7 @@
+
Commons ត្រូវបានគាំង
Opps. មានអ្វីមួយកំពុងមានបញ្ហា-កំហុស!
diff --git a/app/src/main/res/values-km/strings.xml b/app/src/main/res/values-km/strings.xml
index d4fb12f16..c057e04c7 100644
--- a/app/src/main/res/values-km/strings.xml
+++ b/app/src/main/res/values-km/strings.xml
@@ -1,4 +1,8 @@
+
Wikimedia Commons
ការកំណត់នានា
diff --git a/app/src/main/res/values-kn/error.xml b/app/src/main/res/values-kn/error.xml
index 16418bb1c..0916923c5 100644
--- a/app/src/main/res/values-kn/error.xml
+++ b/app/src/main/res/values-kn/error.xml
@@ -1,4 +1,7 @@
+
ಧನ್ಯವಾದಗಳು!
diff --git a/app/src/main/res/values-kn/strings.xml b/app/src/main/res/values-kn/strings.xml
index 6631cd1fb..7eeaf2713 100644
--- a/app/src/main/res/values-kn/strings.xml
+++ b/app/src/main/res/values-kn/strings.xml
@@ -1,4 +1,9 @@
+
ಕಾಮನ್ಸ್
ವ್ಯವಸ್ಥೆಗಳು
diff --git a/app/src/main/res/values-ko-rKP/strings.xml b/app/src/main/res/values-ko-rKP/strings.xml
index 7bb45e619..670479f75 100644
--- a/app/src/main/res/values-ko-rKP/strings.xml
+++ b/app/src/main/res/values-ko-rKP/strings.xml
@@ -1,4 +1,8 @@
+
공용
설정
diff --git a/app/src/main/res/values-ko/error.xml b/app/src/main/res/values-ko/error.xml
index dfec407ec..f8ae08908 100644
--- a/app/src/main/res/values-ko/error.xml
+++ b/app/src/main/res/values-ko/error.xml
@@ -1,4 +1,8 @@
+
공용 애플리케이션이 작동을 멈췄습니다
이런. 무언가가 잘못됐습니다!
diff --git a/app/src/main/res/values-ko/strings.xml b/app/src/main/res/values-ko/strings.xml
index 27c261d3d..11faee9c6 100644
--- a/app/src/main/res/values-ko/strings.xml
+++ b/app/src/main/res/values-ko/strings.xml
@@ -1,4 +1,16 @@
+
보이기
일반
@@ -59,6 +71,7 @@
분류 검색
저장
새로 고침
+ 목록
장치에서 GPS가 꺼져 있습니다. 켜시겠습니까?
GPS 사용
아직 올린 항목이 없습니다
@@ -78,9 +91,10 @@
분류
설정
가입하기
+ 알찬 그림
정보
위키미디어 공용 앱은 오픈 소스 애플리케이션이며 위키미디어 공동체 내의 자원봉사자에 의해 유지됩니다. 위키미디어 재단은 애플리케이션의 생성, 개발, 유지보수에 관여하지 않습니다.
- 소스 코드는 <a href=\"https://github.com/commons-app/apps-android-commons\">GitHub</a>에 있으며, 웹사이트는 <a href=\"https://commons-app.github.io/\">GitHub</a>에 있습니다. 버그나 기타 제안은 <a href=\" https://github.com/commons-app/apps-android-commons/issues\">GitHub</a>에 보고해주세요.
+ 버그나 기타 제안은 <a href=\" https://github.com/commons-app/apps-android-commons/issues\">GitHub</a>에 보고해주세요.
<u>개인정보 정책</u>
<u>제작진</u>
정보
@@ -134,6 +148,9 @@
사유 앱의 스크린샷
업로드 예시:
- 제목: 시드니 오페라 하우스\n- 설명: 항만 건너편에서 바라본 시드니 오페라 하우스\n- 분류: 시드니 오페라 하우스, 서쪽에서 본 시드니 오페라 하우스, 시드니 오페라 하우스 원경
+ 제목: 시드니 오페라 하우스
+ 설명: 강 건너에서 바라본 시드니 오페라 하우스
+ 분류: Sydney Opera House from the west, Sydney Opera House remote views
당신의 그림을 기여하세요. 위키백과 문서의 생명이 오는 데 도와주세요!
위키백과의 그림은 위키미디어 공용에서 옵니다.
당신의 그림은 전 세계 사람들을 교육하는 데 도움이 됩니다.
@@ -146,8 +163,8 @@
설명 없음
알 수 없는 라이선스
새로 고침
- 권한 필요: 외부 저장소 읽기. 이것이 없으면 앱은 동작하지 않습니다.
- 권한 필요: 외부 저장소 쓰기. 이것이 없으면 앱은 동작하지 않습니다.
+ 권한 필요: 외부 저장소 읽기. 이것이 없으면 앱은 갤러리에 접근할 수 없습니다.
+ 권한 필요: 외부 저장소 쓰기. 이것이 없으면 앱은 카메라에 접근할 수 없습니다.
선택적 권한: 분류 추천을 위해 현재 위치 정보를 가져옵니다.
확인
근처의 장소
@@ -160,6 +177,8 @@
미디어 제목
설명
여기에 미디어의 설명이 들어갑니다. 상당히 길어질 경우, 여러 줄에 걸쳐야 할 수 있습니다. 그래도 보기 좋았으면 좋겠네요.
+ 저자
+ 알찬 그림 저자의 사용자 이름은 여기에.들어갑니다.
올린 날짜
라이선스
좌표
@@ -175,6 +194,8 @@
정말 로그아웃하시겠습니까?
공용 로고
공용 웹사이트
+ 공용 페이스북 페이지
+ 공용 GitHub 소스 코드
배경 그림
미디어 그림 실패
그림이 없습니다
@@ -200,12 +221,16 @@
로그아웃
강좌
알림
+ 알참
위치 권한이 없으면 주변 장소를 표시할 수 없습니다
설명이 없습니다
공용 파일 문서
위키데이터 항목
+ 위키백과 문서
그림 캐시 처리 오류
이 파일을 설명할 수 있는 제목으로, 파일 이름으로 사용됩니다. 띄어쓰기를 포함한 일반적인 단어를 사용할 수 있습니다. 파일 확장자는 포함하지 마세요
+ 사진이 너무 어둡습니다. 정말 업로드하겠습니까? 위키미디어 공용은 사전적인 가치가 있는 사진을 위한 공간입니다.
+ 사진이 흐릿합니다. 정말 업로드하겠습니까? 위키미디어 공용은 사전적인 가치가 있는 사진을 위한 공간입니다.
권한 부여
외부 저장소 사용하기
장치의 인앱 카메라로 찍은 사진 저장하기
@@ -214,6 +239,8 @@
이메일로 개발자에게 로그 파일 보내기
URL을 열기 위한 웹 브라우저를 찾지 못했습니다
오류! URL을 찾을 수 없습니다
+ 삭제 신청
+ 이 그림은 삭제가 신청되었습니다.
브라우저에서 보기
위치가 변경되지 않았습니다.
위치를 사용할 수 없습니다.
@@ -222,6 +249,21 @@
%1$s님이 당신의 사용자 토론 문서에 글을 남겼습니다
편집해 주셔서 감사합니다
%1$s님이 %2$s에서 나를 언급했습니다.
- 자주 묻는 질문
+ 방향
+ 위키데이터
+ 위키백과
+ 공용
+ <u>평가</u>
+ <u>FAQ</u>
강좌 건너뛰기
+ 인터넷 사용 불가
+ 인터넷 사용 가능
+ 알림 가져오기 오류
+ 알림이 없습니다
+ <u>번역</u>
+ 언어
+ 번역 제출을 위한 언어를 선택하십시오
+ 진행
+ 취소
+ 다시 시도
diff --git a/app/src/main/res/values-krc/error.xml b/app/src/main/res/values-krc/error.xml
index f1393fc50..53c96d2c5 100644
--- a/app/src/main/res/values-krc/error.xml
+++ b/app/src/main/res/values-krc/error.xml
@@ -1,4 +1,7 @@
+
Халат
Не эсе да табсыз барды.
diff --git a/app/src/main/res/values-krc/strings.xml b/app/src/main/res/values-krc/strings.xml
index 3530f9454..5e0b33b98 100644
--- a/app/src/main/res/values-krc/strings.xml
+++ b/app/src/main/res/values-krc/strings.xml
@@ -1,4 +1,8 @@
+
Викигёзен
Джарашдырыула
diff --git a/app/src/main/res/values-ku/error.xml b/app/src/main/res/values-ku/error.xml
index a1785ef1c..2dc0c29fa 100644
--- a/app/src/main/res/values-ku/error.xml
+++ b/app/src/main/res/values-ku/error.xml
@@ -1,4 +1,8 @@
+
Commons xira bû
Haho. Tiştek nerast bû!
diff --git a/app/src/main/res/values-ku/strings.xml b/app/src/main/res/values-ku/strings.xml
index 9e2ce9c71..16ba9fe2f 100644
--- a/app/src/main/res/values-ku/strings.xml
+++ b/app/src/main/res/values-ku/strings.xml
@@ -1,4 +1,10 @@
+
Xuyabûn
Giştî
@@ -70,6 +76,6 @@
Paşragihandin
Derkeve
Destûr bide
- Pirsên ku pir têne pirsîn
+ <u>Pirsên ku pir têne pirsîn</u>
Rênîşandanê derbas bike
diff --git a/app/src/main/res/values-kum/error.xml b/app/src/main/res/values-kum/error.xml
index 706bdae51..fdf9e56db 100644
--- a/app/src/main/res/values-kum/error.xml
+++ b/app/src/main/res/values-kum/error.xml
@@ -1,4 +1,7 @@
+
Вагь. Бир зат чы терс гетди!
Этгенигизни язып бизге электрон почгъа йибери. О масъаланы чечме кёмек этежек!
diff --git a/app/src/main/res/values-ky/error.xml b/app/src/main/res/values-ky/error.xml
index 3e2d281c7..22687ad26 100644
--- a/app/src/main/res/values-ky/error.xml
+++ b/app/src/main/res/values-ky/error.xml
@@ -1,4 +1,7 @@
+
Кыйроо
Уупс. Бир нерсе туура эмес болду!
diff --git a/app/src/main/res/values-ky/strings.xml b/app/src/main/res/values-ky/strings.xml
index d16cdbaca..6d78e91fe 100644
--- a/app/src/main/res/values-ky/strings.xml
+++ b/app/src/main/res/values-ky/strings.xml
@@ -1,4 +1,8 @@
+
Уикиказына
Ырастоолор
diff --git a/app/src/main/res/values-la/error.xml b/app/src/main/res/values-la/error.xml
index 38942512c..82a85d3b5 100644
--- a/app/src/main/res/values-la/error.xml
+++ b/app/src/main/res/values-la/error.xml
@@ -1,4 +1,7 @@
+
Error
Error
diff --git a/app/src/main/res/values-lag/error.xml b/app/src/main/res/values-lag/error.xml
index a486a36be..49824dea8 100644
--- a/app/src/main/res/values-lag/error.xml
+++ b/app/src/main/res/values-lag/error.xml
@@ -1,4 +1,7 @@
+
Kuusa!
diff --git a/app/src/main/res/values-lb/error.xml b/app/src/main/res/values-lb/error.xml
index 075c16835..92d13b5b5 100644
--- a/app/src/main/res/values-lb/error.xml
+++ b/app/src/main/res/values-lb/error.xml
@@ -1,4 +1,7 @@
+
Commons ass down
Ups. Elo ass eppes schif gaang!
diff --git a/app/src/main/res/values-lb/strings.xml b/app/src/main/res/values-lb/strings.xml
index 3a642b8d1..321d2a189 100644
--- a/app/src/main/res/values-lb/strings.xml
+++ b/app/src/main/res/values-lb/strings.xml
@@ -1,4 +1,9 @@
+
Ausgesinn
Allgemeng
@@ -57,6 +62,7 @@
Kategorie sichen
Späicheren
Aktualiséieren
+ Lëscht
GPS ass op Ärem Apparat ausgeschalt. Wëllt Dir en aktivéieren?
GPS aktivéieren
Nach keng eropgeluede Fichieren
@@ -78,6 +84,7 @@
Kategorien
Astellungen
Mellt Iech un
+ Bemierkenswäert Biller
Iwwer
D\'App Wikimedia Commons ass eng \'Open-Source-App\' déi vu Fräiwëllege vun der Wikimedia Foundation entwéckelt gouf an och vun hinnen ënnerhal gëtt. D\'Wikimedia Foundation ass net an d\'Entwécklung oder den Ënnerhalt vun der App implizéiert.
Leet w.e.g. <a href=\"https://github.com/commons-app/apps-android-commons/issues\"> e GitHub Problem</a> fir Problemer ze mellen a Proposen ze maachen.
@@ -132,6 +139,7 @@
Biller déi Dir aus dem Internet erofgelueden hutt
Beispill-Upload:
- Titel: Sydney Opera House\n- Beschreiwung: Sydney Opera House vun der Bay aus gesinn\n- Kategorien: Sydney Opera House, Sydney Opera House vu Westen, Sydney Opera House vu wäitem
+ Titel: Oper vu Sydney
Beschreiwung:Oper vu Sydney esou wéi ee se vun der Bucht aus gesäit
Maacht mat mat Äre Biller. Hëlleft Wikipedia-Artikele méi lieweg ze maachen!
Biller op Wikipedia komme vu Wikimedia Commons.
@@ -145,7 +153,7 @@
Keng Beschreiwung
Onbekannt Lizenz
Aktualiséieren
- Obligatoresch Autorisatioun: Externe Späicher liesen. D\'App kann net ouni dat funktionéieren.
+ Obligatoresch Autorisatioun: Externe Späicher liesen. D\'App kann ouni dat net op d\'Galerie zougräifen.
Fakultativ Autorisatioun: Déi aktuell Plaz kréie fir Propose fir Kategorien
OK
Plazen nobäi
@@ -158,6 +166,7 @@
Titel vum Medium
Beschreiwung
D\' Beschreiwung vum Medium kënnt hei. Dëst ka méiglecherweis laang sinn a gëtt eventuell op méi Zeile verdeelt. Mir hoffen et gesäit trotzdeem gutt aus.
+ Auteur
Datum vum Eroplueden
Lizenz
Koordinaten
@@ -193,10 +202,12 @@
Ausloggen
Uleedung
Notifikatiounen
+ Bemierkenswäert
Plazen nobäi kënnen net gewise ginn ouni Rechter fir d\'Lokalisatioun
keng Beschreiwung fonnt
Commons-Fichierssäit
Wikidata-Element
+ Wikipedia-Artikel
Autorisatioun ginn
Externe Späicher benotzen
Biller späicheren déi mat der in-app Kamera vun Ärem Apparat gemaach goufen
@@ -205,6 +216,7 @@
Log-Fichier per E-Mail un d\'Entwéckler schécken
Feeler! URL net fonnt
Nominéiere fir ze Läschen
+ Dëst Bild gouf virgeschloe fir geläscht ze ginn.
Am Browser weisen
De Plaz huet net geännert.
Plaz ass net disponibel.
@@ -212,5 +224,20 @@
Wëllkomm op Wikimedia Commons, %1$s! Mir si frou datt Dir hei sidd.
Merci datt Dir eng Ännerung gemaach hutt
%1$s huet Iech op %2$s ernimmt.
- Dacks gestallt Froen
+ RICHTUNGEN
+ WIKIDATA
+ WIKIPEDIA
+ COMMONS
+ <u>Bewäert eis</u>
+ <u>FAQ</u>
+ Internet net disponibel
+ Internet disponibel
+ Feeler beim Ofruffe vun den Notifikatiounen
+ Keng Notifikatioune fonnt
+ <u>Iwwersetzen</u>
+ Sproochen
+ Sicht déi Sprooch eraus Fir déi Dir Iwwersetzunge maache wëllt
+ Virufueren
+ Ofbriechen
+ Nach eng Kéier probéieren
diff --git a/app/src/main/res/values-lez/error.xml b/app/src/main/res/values-lez/error.xml
index b8d73c3b0..6f921fb3a 100644
--- a/app/src/main/res/values-lez/error.xml
+++ b/app/src/main/res/values-lez/error.xml
@@ -1,4 +1,7 @@
+
Чlурукl хьана
Ёъ, вуч-ятlани масакl фена
diff --git a/app/src/main/res/values-li/error.xml b/app/src/main/res/values-li/error.xml
index 648886712..bffea09e0 100644
--- a/app/src/main/res/values-li/error.xml
+++ b/app/src/main/res/values-li/error.xml
@@ -1,4 +1,7 @@
+
Commons is vasgeloupe
Oj. Get góng verkieërdj!
diff --git a/app/src/main/res/values-li/strings.xml b/app/src/main/res/values-li/strings.xml
new file mode 100644
index 000000000..59dc53188
--- /dev/null
+++ b/app/src/main/res/values-li/strings.xml
@@ -0,0 +1,113 @@
+
+
+
+ Uterlik
+ Algemein
+ Feedback
+ Locatie
+ Commons
+ •
+ Instèllinge
+ Gebroekersnaam
+ Wachwaord
+ Meld dich aan mit diene Commons-Bètakonto
+ Melj dich aan
+ Wachwaord vergaete?
+ Teiken dich in
+ Aan \'nt melje...
+ Wach estebleef...
+ Aanmelje gelök!
+ Aanmelje mislök!
+ Bestandj neet gevónje. Perbeer \'n anger bestandj.
+ Verificatie mislök!
+ Upload begós!
+ %1$s upgeloadj!
+ Wies aan veur dienen upload te betrachte
+ Upload van %1$s aan \'nt vange
+ %1$s up \'nt loade
+ d\'n Upload van %1$s is vaerdig
+ d\'n Upload van %1$s is mislök
+ Wies aan veur te betrachte
+
+ - %1$d bestandj up \'nt loade
+ - %1$d bestenj up \'nt loade
+
+ Mien recènte uploads
+ Inne wachrie
+ Mislök
+ %1$d%% vaerdig
+ Up \'nt loade
+ Oete gallerie
+ Trèk foto aaf
+ Kórtbie
+ Mien uploads
+ Deil
+ Tuin in browser
+ Titel
+ Gaef estebleef \'ne naam veur dit bestandj
+ Besjrieving
+ Kan zich neet aanmelde - netwirkfout
+ Kan zich neet aanmelde - controleer de gebroekersnaam
+ Kan zich neet aanmelde - controleer die wachwaord
+ Te väöl mislökde kieëre geperbeerd. Perbeer estebleef oppernuuj euver e paar menuut.
+ Deze gebroeker is geblokkeerd op Commons
+ Doe mós diene twieëfaktorische bevestigingscode opgaeve.
+ Aanmelje mislök
+ Upload
+ Gaef dees verzameling \'ne naam
+ Aanpassinge
+ Upload
+ Zeuk categorieje
+ Slaon op
+ Vernuuj
+ Lies
+ GPS steit oet op die toestèl. Wils se \'t aanzètte?
+ Zèt GPS aan
+ Nag gein uploads
+
+ - \@string/contributions_subtitle_zero
+ - %1$d upload
+ - %1$d uploads
+
+
+ - Beginnendj mit %1$d upload
+ - Beginnendj mit %1$d uploads
+
+
+ - %1$d upload
+ - %1$d uploads
+
+ Gein categorieje die euvereinkómme mit %1$s gevónje
+ Veug categorieje toe veur dien plaetjes mekkeliker te kinne vinje op Wikimedia Commons.\nBegin mit tikke veur categorieje toe te veuge.
+ Categorieje
+ Instèllinge
+ Registreer
+ Oetgeleechde plaetjes
+ Euver
+ Naamsvermeljing-GeliekDeile 4.0
+ Naamsvermeljing 4.0
+ Naamsvermeljing-GeliekDeile 3.0
+ Naamsvermeljing 3.0
+ CC0
+ CC BY-SA 3.0
+ CC BY-SA 3.0 (Oeësteriek)
+ CC BY-SA 3.0 (Duutsjlandj)
+ CC BY-SA 3.0 (Eslandj)
+ CC BY-SA 3.0 (Spaanje)
+ CC BY-SA 3.0 (Kroatië)
+ CC BY-SA 3.0 (Luxemburg)
+ CC BY-SA 3.0 (Nederlandj)
+ CC BY-SA 3.0 (Noorwaeg)
+ CC BY-SA 3.0 (Pole)
+ CC BY-SA 3.0 (Roemenië)
+ CC BY 3.0
+ CC BY-SA 4.0
+ CC BY-4.0
+ CC Zero
+ Op Wikimedia Commons staon de meiste plaetjes die waere gebroek op Wikipedia.
+ Dien plaetjes helpe luuj oppe ganse werreld mit \'t opdoon van kènnis!
+ Vernuuj
+
diff --git a/app/src/main/res/values-lrc/error.xml b/app/src/main/res/values-lrc/error.xml
index e7c9b89ec..59bceed8b 100644
--- a/app/src/main/res/values-lrc/error.xml
+++ b/app/src/main/res/values-lrc/error.xml
@@ -1,4 +1,7 @@
+
دتو منمونیم!
diff --git a/app/src/main/res/values-lt/error.xml b/app/src/main/res/values-lt/error.xml
index ce344ed36..379c762cc 100644
--- a/app/src/main/res/values-lt/error.xml
+++ b/app/src/main/res/values-lt/error.xml
@@ -1,4 +1,9 @@
+
Vikiteka užstrigo
Oi. Kažkas nutiko!
diff --git a/app/src/main/res/values-lt/strings.xml b/app/src/main/res/values-lt/strings.xml
index 375734dee..c5c0813ab 100644
--- a/app/src/main/res/values-lt/strings.xml
+++ b/app/src/main/res/values-lt/strings.xml
@@ -1,4 +1,11 @@
+
Vikiteka
Nustatymai
@@ -109,7 +116,7 @@
Nėra aprašymo
Nežinoma licencija
Atnaujinti
- Reikalinga teisė: Skaityti išorinę talpyklą. Programėle be to negali funkcionuoti.
+ Reikalinga teisė: Skaityti išorinę talpyklą. Programėle be to negali funkcionuoti.
Neprivaloma teisė: Gauti dabartinę vietovę, kad būtų pasiūlomos kategorijos
Gerai
Netoliese Esančios Vietos
diff --git a/app/src/main/res/values-lv/error.xml b/app/src/main/res/values-lv/error.xml
index 5e0f9edbe..f49d27f00 100644
--- a/app/src/main/res/values-lv/error.xml
+++ b/app/src/main/res/values-lv/error.xml
@@ -1,4 +1,7 @@
+
Ups. Kaut kas nogāja greizi!
Paldies!
diff --git a/app/src/main/res/values-lv/strings.xml b/app/src/main/res/values-lv/strings.xml
index 5dfd96a47..d73312361 100644
--- a/app/src/main/res/values-lv/strings.xml
+++ b/app/src/main/res/values-lv/strings.xml
@@ -1,4 +1,9 @@
+
Commons
•
@@ -100,4 +105,7 @@
LASĪT RAKSTU
Paldies par labojumu
Pārslēgt skatu
+ Valodas
+ Turpināt
+ Atcelt
diff --git a/app/src/main/res/values-mg/error.xml b/app/src/main/res/values-mg/error.xml
index 3da2ac057..46d92fbd2 100644
--- a/app/src/main/res/values-mg/error.xml
+++ b/app/src/main/res/values-mg/error.xml
@@ -1,4 +1,7 @@
+
Misaotra indrindra!
diff --git a/app/src/main/res/values-mk/error.xml b/app/src/main/res/values-mk/error.xml
index 6e6e33a9e..938dd05cf 100644
--- a/app/src/main/res/values-mk/error.xml
+++ b/app/src/main/res/values-mk/error.xml
@@ -1,4 +1,7 @@
+
Ризницата се урна
Упс. Нешто не е во ред!
diff --git a/app/src/main/res/values-mk/strings.xml b/app/src/main/res/values-mk/strings.xml
index 0325dcf80..dd1e6f03e 100644
--- a/app/src/main/res/values-mk/strings.xml
+++ b/app/src/main/res/values-mk/strings.xml
@@ -1,4 +1,7 @@
+
Изглед
Општи
@@ -81,6 +84,7 @@
Категории
Нагодувања
Регистрација
+ Избрани слики
За извршникот
Прилогот на Ризницата има отворен код. Негови творци и одржувачи се примателите на наменските средства од Викимедиината заедница како и членовите на заедницата. Фондацијата Викимедија нема учество во нејзиното создавање, разработка и одржување.
Создајте нов <a href=\"https://github.com/commons-app/apps-android-commons/issues\">проблем на GitHub</a> за пријавување на грешки и давање предлози.
@@ -152,8 +156,8 @@
Нема опис
Непозната лиценца
Превчитај
- Потребна дозвола: Треба да се прочита од надворешен склад. Прилогот не може да работи без ова.
- Потребна дозвола: Треба да се запише на надворешен склад. Прилогот не може да работи без ова.
+ Потребна дозвола: Треба да се прочита од надворешен склад. Прилогот без ова нема пристап до вашата галерија.
+ Потребна дозвола: Треба да се запише на надворешен склад. Прилогот без ова нема пристап до вашата камера.
Дозвола по желба: Утврдување на тековната местоположба за предлагање категории
ОК
Околни места
@@ -166,6 +170,8 @@
Наслов на податотеката
Опис
Тука оди описот на податотеката. Ова потенцијално може да биде прилично долго, и ќе треба да се преломи во неколку реда. Се надеваме дека ќе изгледа добро.
+ Автор
+ Тука оди корисничкото име на авторот на избраната слика.
Датум на подигање
Лиценца
Координати
@@ -208,6 +214,7 @@
Одјава
Упатства
Известувања
+ Избрана
Местата во близина не можат да се прикажат без дозволи за местоположба.
не најдов описи
Податотечна страница
@@ -227,6 +234,7 @@
Не најдов прелистувач за да ја отворам URL
Грешка! Не ја пронајдов URL
Предложи за бришење
+ Сликава е предложена за бришење.
Погледај во прелистувач
Местоположбата не е сменета.
Местоположбата е недостапна.
@@ -242,6 +250,17 @@
ВИКИПОДАТОЦИ
ВИКИПЕДИЈА
РИЗНИЦА
- Често поставувани прашања
+ <u>Оценете нè</u>
+ <u>ЧПП</u>
Прескокни упатство
+ Нема семрежен пристап
+ Има семрежен пристап
+ Грешка при добивањето на известувањата
+ Не пронајдов известувања
+ <u>Преведи</u>
+ Јазици
+ Изберете за кој јазик сакате да поднесете преводи
+ Продолжи
+ Откажи
+ Пробај пак
diff --git a/app/src/main/res/values-ml/error.xml b/app/src/main/res/values-ml/error.xml
index b7ce3d08e..f1f80ba30 100644
--- a/app/src/main/res/values-ml/error.xml
+++ b/app/src/main/res/values-ml/error.xml
@@ -1,4 +1,7 @@
+
കോമൺസ് തകർന്നു
അയ്യോ. എന്തോ പ്രശ്നമുണ്ടായി!
diff --git a/app/src/main/res/values-ml/strings.xml b/app/src/main/res/values-ml/strings.xml
index c41148b5b..485e66acc 100644
--- a/app/src/main/res/values-ml/strings.xml
+++ b/app/src/main/res/values-ml/strings.xml
@@ -1,4 +1,9 @@
+
വിക്കിമീഡിയ കോമൺസ്
സജ്ജീകരണങ്ങൾ
diff --git a/app/src/main/res/values-mn/error.xml b/app/src/main/res/values-mn/error.xml
index 15872699e..4703516b3 100644
--- a/app/src/main/res/values-mn/error.xml
+++ b/app/src/main/res/values-mn/error.xml
@@ -1,4 +1,7 @@
+
Баярлалаа!
diff --git a/app/src/main/res/values-mr/error.xml b/app/src/main/res/values-mr/error.xml
index 81aa24b8e..453028dd9 100644
--- a/app/src/main/res/values-mr/error.xml
+++ b/app/src/main/res/values-mr/error.xml
@@ -1,4 +1,7 @@
+
कॉमन्स कोसळले आहे
ओह. काहीतरी गडबड झाली!
diff --git a/app/src/main/res/values-mr/strings.xml b/app/src/main/res/values-mr/strings.xml
index 90f8f6a0b..b88e021e7 100644
--- a/app/src/main/res/values-mr/strings.xml
+++ b/app/src/main/res/values-mr/strings.xml
@@ -1,4 +1,12 @@
+
स्वरूप
सामान्य
@@ -151,8 +159,8 @@
वर्णन नाही.
अनोळखी परवाना
ताजेतवाने करा
- परवानगी आवश्यक:बाह्य भंडारण वाचन. याशिवाय अॅप काम करू शकत नाही.
- परवानगी आवश्यक:बाह्य भंडारण वाचन. याशिवाय अॅप काम करू शकत नाही.
+ परवानगी आवश्यक:बाह्य भंडारण वाचन. याशिवाय अॅप काम करू शकत नाही.
+ परवानगी आवश्यक:बाह्य भंडारण वाचन. याशिवाय अॅप काम करू शकत नाही.
ऐच्छिक परवानगी:वर्ग सुचवण्यांसाठी सध्याचे स्थान मिळवा
ठीक आहे
जवळपासची स्थाने
@@ -234,7 +242,7 @@
तुमच्या संपादनासाठी तुमचे आभार !
%1$s यांनी तुमचा उल्लेख %2$s येथे केला.
टॉगल दृश्य
-
- सतत विचारले जाणारे प्रश्न
+
+ सतत विचारले जाणारे प्रश्न
ट्यूटोरियल वगळा
diff --git a/app/src/main/res/values-ms/error.xml b/app/src/main/res/values-ms/error.xml
index 185c2c977..3517a3ba6 100644
--- a/app/src/main/res/values-ms/error.xml
+++ b/app/src/main/res/values-ms/error.xml
@@ -1,4 +1,7 @@
+
Commons telah runtuh
Maaf, berlakunya ralat!
diff --git a/app/src/main/res/values-ms/strings.xml b/app/src/main/res/values-ms/strings.xml
index 45d5acf60..c5c0f18ab 100644
--- a/app/src/main/res/values-ms/strings.xml
+++ b/app/src/main/res/values-ms/strings.xml
@@ -1,4 +1,9 @@
+
Wikimedia Commons
Tetapan
diff --git a/app/src/main/res/values-mt/error.xml b/app/src/main/res/values-mt/error.xml
index 097f11c0f..611f79520 100644
--- a/app/src/main/res/values-mt/error.xml
+++ b/app/src/main/res/values-mt/error.xml
@@ -1,4 +1,7 @@
+
Commons waqaf jaħdem
Oops. Xi ħaġa marret ħażin!
diff --git a/app/src/main/res/values-nb/error.xml b/app/src/main/res/values-nb/error.xml
index 2ee9c302a..6cc0c1422 100644
--- a/app/src/main/res/values-nb/error.xml
+++ b/app/src/main/res/values-nb/error.xml
@@ -1,4 +1,7 @@
+
Commons har kræsjet
Oisann. Noe gikk galt!
diff --git a/app/src/main/res/values-nb/strings.xml b/app/src/main/res/values-nb/strings.xml
index d1499536f..9774035ee 100644
--- a/app/src/main/res/values-nb/strings.xml
+++ b/app/src/main/res/values-nb/strings.xml
@@ -1,4 +1,12 @@
+
Utseende
Tilbakemelding
@@ -143,8 +151,8 @@
Ingen beskrivelse
Ukjent lisens
Gjenoppfrisk
- Nødvendig tillatelse: Lese ekstern lagring. Appen virker ikke uten dette.
- Påkrevd tillatelse: Skriv til ekstern lagring. Appen fungerer ikke uten dette.
+ Nødvendig tillatelse: Lese ekstern lagring. Appen virker ikke uten dette.
+ Påkrevd tillatelse: Skriv til ekstern lagring. Appen fungerer ikke uten dette.
Valgfri tillatelse: Hent nåværende posisjon for kategoriforslag
OK
Plasser i nærheten
@@ -225,5 +233,8 @@
Takk for at du har gjort en redigering
%1$s nevnte deg på %2$s.
Skift visning
- Ofte stilte spørsmål
+ Ofte stilte spørsmål
+ Internett er utilgjengelig
+ <u>Oversett</u>
+ Prøv igjen
diff --git a/app/src/main/res/values-ne/error.xml b/app/src/main/res/values-ne/error.xml
index 4a182573c..832b90733 100644
--- a/app/src/main/res/values-ne/error.xml
+++ b/app/src/main/res/values-ne/error.xml
@@ -1,4 +1,8 @@
+
कमन्स दुर्घटनाग्रस्त भएको छ
ओहो। केही गल्ती भयो!
diff --git a/app/src/main/res/values-ne/strings.xml b/app/src/main/res/values-ne/strings.xml
index 168d95f99..be0d2f69f 100644
--- a/app/src/main/res/values-ne/strings.xml
+++ b/app/src/main/res/values-ne/strings.xml
@@ -1,4 +1,10 @@
+
कमन्स
सेटिङहरू
diff --git a/app/src/main/res/values-nl/error.xml b/app/src/main/res/values-nl/error.xml
index 34e295ff1..79f631d2e 100644
--- a/app/src/main/res/values-nl/error.xml
+++ b/app/src/main/res/values-nl/error.xml
@@ -1,4 +1,8 @@
+
Commons is gecrasht
Oeps. Er is iets misgegaan.
diff --git a/app/src/main/res/values-nl/strings.xml b/app/src/main/res/values-nl/strings.xml
index 421a8e8bc..f2688cffa 100644
--- a/app/src/main/res/values-nl/strings.xml
+++ b/app/src/main/res/values-nl/strings.xml
@@ -1,4 +1,13 @@
+
Commons
Instellingen
@@ -50,18 +59,19 @@
Categorieën zoeken
Opslaan
Vernieuwen
+ Lijst
Nog geen uploads
-
- - Nog geen uploads
- - 1 upload
+
+ - \@string/contributions_subtitle_zero
+ - %1$d upload
- %1$d uploads
- Bezig met 1 upload
- Bezig met %1$d uploads
-
- - 1 upload
+
+ - %1$d upload
- %1$d uploads
Er zijn geen categorieën met \"%1$s\" gevonden
@@ -129,7 +139,7 @@
Geen beschrijving
Onbekende licentie
Vernieuwen
- Benodigde toestemming: Lees externe opslag. Zonder deze toestemming kan de app niet functioneren.
+ Benodigde toestemming: Lees externe opslag. Zonder deze toestemming kan de app niet functioneren.
Optionele toestemming: Huidige locatie ophalen voor categoriesuggesties
OK
Plaatsen in de buurt
@@ -152,5 +162,20 @@
Instellingen
Terugkoppeling
Afmelden
+ Wikipedia-artikel
Error tijdens het laden van de afbeeldingen
+ Nomineer voor Verwijdering
+ Deze afbeelding is genomineerd voor verwijdering.
+ Bekijk in Browser
+ VERWIJZINGEN
+ WIKIDATA
+ Vaak gestelde vragen
+ Geen internet
+ Internet beschikbaar
+ Fout bij ophalen berichten.
+ Geen berichten.
+ Talen
+ Selecteer de taal waarvoor u vertalingen wil indienen
+ Ga door
+ Annuleren
diff --git a/app/src/main/res/values-oc/error.xml b/app/src/main/res/values-oc/error.xml
index f4134a9d7..a66e07397 100644
--- a/app/src/main/res/values-oc/error.xml
+++ b/app/src/main/res/values-oc/error.xml
@@ -1,4 +1,7 @@
+
Commons a fracassat
Ops! Quicòm a trucat !
diff --git a/app/src/main/res/values-oc/strings.xml b/app/src/main/res/values-oc/strings.xml
index ee4f65da8..803293a55 100644
--- a/app/src/main/res/values-oc/strings.xml
+++ b/app/src/main/res/values-oc/strings.xml
@@ -1,4 +1,9 @@
+
Commons
Paramètres
@@ -124,4 +129,14 @@
Títol del mèdia
Descripcion
Venir un bèta-testaire
+ Aqueste imatge es estat designat per supression
+ <u>Nos notar</u>
+ <u>FAQ</u>
+ Internet pas disponible
+ Internet disponible
+ Error en anant cercar las notificacions.
+ Cap de notificacion trobada.
+ <u>Revirar</u>
+ Seleccionatz la lenga dins la quala volriatz sometre de traduccions
+ Tornar ensajar
diff --git a/app/src/main/res/values-or/error.xml b/app/src/main/res/values-or/error.xml
index b474d76ff..88a2ad188 100644
--- a/app/src/main/res/values-or/error.xml
+++ b/app/src/main/res/values-or/error.xml
@@ -1,4 +1,7 @@
+
କମନ୍ସ ଅକାମୀ ହୋଇଗଲା
କିଛି ଗୋଟେ ଅଘଟଣ ଘଟିଲା!
diff --git a/app/src/main/res/values-or/strings.xml b/app/src/main/res/values-or/strings.xml
index 43bd74832..c1bc2b73f 100644
--- a/app/src/main/res/values-or/strings.xml
+++ b/app/src/main/res/values-or/strings.xml
@@ -1,4 +1,8 @@
+
ଉଇକିମିଡ଼ିଆ କମନ୍ସ
ସଂରଚନା
diff --git a/app/src/main/res/values-pa/error.xml b/app/src/main/res/values-pa/error.xml
index 219ec0084..5837b6f9e 100644
--- a/app/src/main/res/values-pa/error.xml
+++ b/app/src/main/res/values-pa/error.xml
@@ -1,4 +1,7 @@
+
ਕਾਮਨਜ਼ ਖ਼ਰਾਬ ਹੋ ਗਿਆ ਹੈ
ਓ ਹੋ। ਕੁਝ ਗ਼ਲਤ ਹੋ ਗਿਆ!
diff --git a/app/src/main/res/values-pa/strings.xml b/app/src/main/res/values-pa/strings.xml
index 1a24b278d..6937ab75d 100644
--- a/app/src/main/res/values-pa/strings.xml
+++ b/app/src/main/res/values-pa/strings.xml
@@ -1,4 +1,10 @@
+
ਵਿਕੀਮੀਡੀਆ ਕਾਮਨਜ਼
ਸੈਟਿੰਗ
@@ -131,7 +137,7 @@
ਕੋਈ ਵੇਰਵਾ ਨਹੀਂ
ਅਣਜਾਣ ਲਸੰਸ
ਤਾਜ਼ਾ ਕਰੋ
- ਆਗਿਆ ਚਾਹੀਦੀ ਹੈ: ਬਾਹਰੀ ਸਟੋਰੇਜ ਬਾਰੇ। ਇਸ ਤੋਂ ਬਿਨਾਂ ਐਪ ਕਾਰਜ ਨਹੀਂ ਕਰ ਸਕੇਗੀ।
+ ਆਗਿਆ ਚਾਹੀਦੀ ਹੈ: ਬਾਹਰੀ ਸਟੋਰੇਜ ਬਾਰੇ। ਇਸ ਤੋਂ ਬਿਨਾਂ ਐਪ ਕਾਰਜ ਨਹੀਂ ਕਰ ਸਕੇਗੀ।
ਠੀਕ ਹੈ
ਨਜ਼ਦੀਕੀ ਥਾਵਾਂ
ਕੋਈ ਨਜ਼ਦੀਕੀ ਥਾਵਾਂ ਨਹੀਂ ਮਿਲੀਆਂ
diff --git a/app/src/main/res/values-pl/error.xml b/app/src/main/res/values-pl/error.xml
index ab4cea30b..fe4ce8933 100644
--- a/app/src/main/res/values-pl/error.xml
+++ b/app/src/main/res/values-pl/error.xml
@@ -1,4 +1,9 @@
+
Wystąpił błąd Commons.
Ups. Coś poszło nie tak!
diff --git a/app/src/main/res/values-pl/strings.xml b/app/src/main/res/values-pl/strings.xml
index 009c00b9e..d19dfc7c8 100644
--- a/app/src/main/res/values-pl/strings.xml
+++ b/app/src/main/res/values-pl/strings.xml
@@ -1,4 +1,20 @@
+
Wygląd
Ogólne
@@ -80,7 +96,7 @@
Ustawienia
Zarejestruj się
O aplikacji
- Oprogramowanie Open Source, wydane na licencji <a href=\"https://github.com/commons-app/apps-android-commons/blob/master/COPYING\">Apache License v2</a>. Wikimedia Commons i jego logo są znakami towarowymi Wikimedia Foundation i są wykorzystywane za zgodą Wikimedia Foundation. Nie jesteśmy powiązani z Wikimedia Foundation.
+ Aplikacja Wikimedia Commons jest oprogramowaniem typu open-source tworzonym i rozwijanym przez stypendystów i wolontariuszy ze społeczności Wikimedii. Fundacja Wikimedia nie bierze udziału w tworzeniu, rozwijaniu ani utrzymywaniu aplikacji.
<a href=\"https://github.com/commons-app/apps-android-commons\">Kod źródłowy</a> oraz <a href=\"https://commons-app.github.io/\">strona internetowa</a> na GitHub. Aby zgłosić błąd lub sugestię, utwórz nowe <a href=\"https://github.com/commons-app/apps-android-commons/issues\">zgłoszenie na GitHub</a>.
<u>Polityka prywatności</u>
<u>Twórcy</u>
@@ -143,7 +159,7 @@
Brak opisu
Nieznana licencja
Odśwież
- Wymagane uprawnienia: odczyt z dysku zewnętrznego. Aplikacja nie będzie w stanie funkcjonować bez tego.
+ Wymagane uprawnienia: odczyt z dysku zewnętrznego. Aplikacja nie będzie w stanie funkcjonować bez tego.
Opcjonalne zezwolenie: uzyskiwanie bieżącej lokalizacji dla wygenerowania propozycji kategorii
OK
Pobliskie miejsca
@@ -195,6 +211,8 @@
Podaj krótką, opisową i unikalną nazwę, która będzie służyła jako nazwa pliku. Możesz używać prostego języka i spacji. Nie dodawaj rozszerzenia pliku.
Zaloguj się na swoje konto
Błąd! Nie znaleziono adresu URL
+ Ta grafika została zgłoszona do usunięcia.
+ Otwórz w przeglądarce
Witamy w Wikimedia Commons, %1$s! Cieszymy się, że tu jesteś.
Dziękujemy za dokonanie edycji
%1$s wspomniał o Tobie w %2$s.
@@ -203,6 +221,9 @@
WIKIDANE
WIKIPEDIA
POWSZECHNE
- Najczęściej zadawane pytania
+ <u>FAQ</u>
Pomiń samouczek
+ Nie znaleziono powiadomień
+ Języki
+ Anuluj
diff --git a/app/src/main/res/values-pms/error.xml b/app/src/main/res/values-pms/error.xml
index 68e222238..189f84be5 100644
--- a/app/src/main/res/values-pms/error.xml
+++ b/app/src/main/res/values-pms/error.xml
@@ -1,4 +1,7 @@
+
Commons a l\'é piantasse
Contacc! Cheicòs a l\'é andàit mal!
diff --git a/app/src/main/res/values-pms/strings.xml b/app/src/main/res/values-pms/strings.xml
index 9f577aba2..0cd748031 100644
--- a/app/src/main/res/values-pms/strings.xml
+++ b/app/src/main/res/values-pms/strings.xml
@@ -1,4 +1,7 @@
+
Aparensa
General
@@ -59,6 +62,7 @@
Sërché dle categorìe
Argistré
Agiorné
+ Lista
Ël GPS a l\'é disabilità su sò angign. Veul-lo ativelo?
Ativé ël GPS
Ancor gnun cariament
@@ -80,6 +84,7 @@
Categorìe
Paràmeter
Marchesse
+ Plance an evidensa
A propòsit
L\'aplicassion Wikimedia Commons a l\'é n\'aplicassion a sorgiss duverta creà e mantnùa da \'d përson-e pagà e da \'d volontari ëd la comunità Wikimedia. La Fondassion Wikimedia a l\'é nen amplicà ant la creassion, ël dësvlup, o la manutension dl\'aplicassion.
Creé na neuva <a href=\"https://github.com/commons-app/apps-android-commons/issues\">signalassion GitHub</a> për signalé dij givo e dij sugeriment.
@@ -151,8 +156,8 @@
Gnun-a descrission
Licensa sconossùa
Rinfrësché
- Autorisassion necessaria: Lese n\'anmagasinament estern. L\'aplicassion a peul pa marcé sensa lòn.
- Autorisassion necessaria: Scrive n\'anmagasinament estern. L\'aplicassion a peul pa marcé sensa \'d lòn.
+ Autorisassion necessaria: Lese n\'anmagasinament estern. L\'aplicassion a peul pa acede a soa galarìa sensa \'d lòn.
+ Autorisassion necessaria: Scrive an sn\'anmagasinament estern. L\'aplicassion a peul pa acede a soa màchina fòto sensa \'d lòn.
Autorisassion facoltativa: Oten-e la posission atual për dij sugeriment ëd categorìa
Va bin
Pòst davzin
@@ -165,6 +170,8 @@
Tìtol dël mojen
Descrission
La descrission dël mojen a va ambelessì. Sòn a podrìa esse potensialman longh, e a dovrà esse spantià su vàire linie. I speroma comsëssìa ch\'a ven-a grassios.
+ Autor
+ Lë stranòm ëd l\'autor ëd na plancia an evidensa a va ambelessì.
Dàita ëd cariament
Licensa
Coordinà
@@ -207,10 +214,12 @@
Seurte dal sistema
Cors d\'antrodussion
Notìfiche
+ Butà an evidensa
Ij pòst ant j\'anviron a peulo nen esse smonù sensa ij përmess ëd localisassion
gnun-a descrission trovà
Pàgina dj\'archivi ëd Comun
Element ëd WikiData
+ Artìcol ëd Wikipedia
Eror antramentre ch\'as butavo le plance an memòria local
Un tìtol dëscritiv ùnich për l\'archivi, che a servirà com nòm d\'archivi. A peul dovré un lengagi sempi con djë spassi. Ch\'a ancluda pa l\'estension dl\'archivi
Për piasì, ch\'a descriva ël mojen mej ch\'a peul: Andoa a l\'é stàit fàit? Për piasì, ch\'a descriva j\'oget o le përson-e. Ch\'a arvela j\'anformassion ch\'a l\'é nen belfé andviné, për esempi l\'ora dël dì, s\'a l\'é un panorama. Si ël mojen a smon cheicòs ëd foravìa, për piasì ch\'a spiega lòn ch\'a lo rend foravìa.
@@ -225,6 +234,7 @@
Gnun navigador trovà për duverté l\'adrëssa an sl\'aragnà
Eror! Liura nen trovà
Propon-e për la scancelassion
+ Sa plancia a l\'é stàita nominà për ël dëscancelament.
Smon-e ant ël navigador
Ël leu a l\'é nen cangià.
Leu nen disponìbil.
@@ -236,6 +246,21 @@
Mersì d\'avèj fàit na modìfica
%1$s a l\'ha massionalo su %2$s .
Cangé la visualisassion
- Chestion frequente
+ DIRESSION
+ WIKIDATA
+ WIKIPEDIA
+ COMUN
+ <u>Ch\'an vàluta</u>
+ <u>Chestion frequente</u>
Sauté lë spiegon
+ Aragnà nen disponìbil
+ Aragnà disponìbil
+ Eror an sl\'arserca dle notìfiche
+ Gnun-e notìfiche trovà
+ <u>Volté</u>
+ Lenghe
+ Selessioné la lenga për la qual a veul mandé dle tradussion
+ Andé anans
+ Anulé
+ Prové torna
diff --git a/app/src/main/res/values-ps/error.xml b/app/src/main/res/values-ps/error.xml
index 6fc0f00bb..94bb26441 100644
--- a/app/src/main/res/values-ps/error.xml
+++ b/app/src/main/res/values-ps/error.xml
@@ -1,4 +1,7 @@
+
مننه!
diff --git a/app/src/main/res/values-ps/strings.xml b/app/src/main/res/values-ps/strings.xml
index 7d67160e4..3e2b499e6 100644
--- a/app/src/main/res/values-ps/strings.xml
+++ b/app/src/main/res/values-ps/strings.xml
@@ -1,4 +1,10 @@
+
ځای
ويکي خونديځ
diff --git a/app/src/main/res/values-pt-rBR/error.xml b/app/src/main/res/values-pt-rBR/error.xml
index 04f295559..6ccec407e 100644
--- a/app/src/main/res/values-pt-rBR/error.xml
+++ b/app/src/main/res/values-pt-rBR/error.xml
@@ -1,4 +1,7 @@
+
Commons travou
Opa. Algo deu errado!
diff --git a/app/src/main/res/values-pt-rBR/strings.xml b/app/src/main/res/values-pt-rBR/strings.xml
index 762e45c0b..4bc478527 100644
--- a/app/src/main/res/values-pt-rBR/strings.xml
+++ b/app/src/main/res/values-pt-rBR/strings.xml
@@ -1,4 +1,19 @@
+
Aparência
Geral
@@ -59,6 +74,7 @@
Procurar categorias
Salvar
Atualizar
+ Lista
O GPS está desligado no seu aparelho. Gostarias de ligá-lo ?
GPS inapto.
Ainda não carregado
@@ -80,6 +96,7 @@
Categorias
Configurações
Criar conta
+ Imagens destacadas
Sobre
O Wikimedia Commons é um aplicativo de código aberto criado e mantido por beneficiários e voluntários da comunidade Wikimedia. A Wikimedia Foundation não está envolvida na criação, desenvolvimento ou manutenção do aplicativo.
Criar uma nova <a href=\"https://github.com/commons-app/apps-android-commons/issues\">publicação no GitHub</a> para informar erros e sugestões.
@@ -151,8 +168,8 @@
Sem descrição
Licença desconhecida
Atualizar
- Permissão necessária: Ler armazenamento externo. O aplicativo não pode funcionar sem isso.
- Permissão necessária: Escreva armazenamento externo. A aplicação não pode funcionar sem isso.
+ Permissão necessária: leia o armazenamento externo. App não pode acessar sua galeria sem isso.
+ Permissão necessária: escreva o armazenamento externo. App não pode acessar sua câmera sem isso.
Permissão opcional: Obter a localização atual de sugestões de categoria
OK
Lugares próximos
@@ -165,6 +182,8 @@
Título da mídia
Descrição
Descrição da mídia aqui. Isso pode ser potencialmente longo e precisará envolver múltiplas linhas. Esperamos que seja agradável.
+ Autor
+ O nome de usuário do autor da imagem destacada fica aqui.
Data de envio.
Licença
Coordenadas
@@ -207,10 +226,12 @@
Sair
Tutorial
Notificações
+ Destacado
Os locais próximos não podem ser exibidos sem permissões de localização
Nenhuma descrição encontrada
Página de arquivo do Commons
Item do Wikidata
+ Artigo na Wikipédia
Erro durante o cache de imagens
Um título descritivo exclusivo para o arquivo, que servirá como um nome de arquivo. Você pode usar linguagem simples com espaços. Não inclua a extensão do arquivo
Por favor, descreva a mídia tanto quanto possível: onde foi tomada? O que isso mostra? Qual é o contexto? Descreva os objetos ou pessoas. Revelar informações que não podem ser facilmente adivinhadas, por exemplo, a hora do dia, se for uma paisagem. Se a mídia mostrar algo incomum, explique o que torna incomum.
@@ -225,6 +246,7 @@
Nenhum navegador da Web foi encontrado para abrir o URL
Erro! URL não encontrado
Nomear para a exclusão
+ Esta imagem foi nomeada para eliminação.
Exibir no navegador
O local não mudou.
Localização não disponível.
@@ -236,6 +258,21 @@
Obrigado por ter realizado uma edição
%1$s fez menção a você em %2$s.
Visualização de alternância
- Perguntas mais frequentes
+ DIREÇÕES
+ WIKIDATA
+ WIKIPÉDIA
+ COMMONS
+ <u>Avalie-nos</u>
+ <u>FAQ</u>
Pular tutoril
+ A Internet não está disponível
+ A Internet está disponível
+ Erro ao tentar obter as notificações
+ Não foram encontradas notificações
+ <u>Traduzir</u>
+ Idiomas
+ Selecione o idioma para a qual quer enviar as traduções
+ Avançar
+ Cancelar
+ Tentar novamente
diff --git a/app/src/main/res/values-pt/error.xml b/app/src/main/res/values-pt/error.xml
index 45e439e92..36f02c778 100644
--- a/app/src/main/res/values-pt/error.xml
+++ b/app/src/main/res/values-pt/error.xml
@@ -1,4 +1,7 @@
+
O Commons falhou
Ups! Algo correu mal.
diff --git a/app/src/main/res/values-pt/strings.xml b/app/src/main/res/values-pt/strings.xml
index 954c3f99f..5e4862ecb 100644
--- a/app/src/main/res/values-pt/strings.xml
+++ b/app/src/main/res/values-pt/strings.xml
@@ -1,11 +1,29 @@
+
+ Aparência
+ Geral
+ Comentários
+ Localização
Wikimedia Commons
+ •
Configurações
Nome de utilizador(a)
Palavra-passe
Entre com a sua conta do Commons Beta
Iniciar sessão
+ Esqueceu-se da palavra-passe?
Registar-se
A iniciar sessão
Aguarde, por favor…
@@ -37,6 +55,7 @@
Partilhar
Ver no navegador
Título
+ Forneça um título para este ficheiro, por favor
Descrição
Não foi possível iniciar sessão - falha de rede
Não foi possível iniciar sessão - verifique o seu nome de utilizador(a)
@@ -52,6 +71,7 @@
Pesquisar categorias
Gravar
Atualizar
+ Lista
O GPS está desativado no seu dispositivo. Gostarias de ativá-lo?
Ativar GPS
Ainda não foram enviados ficheiros
@@ -73,11 +93,12 @@
Categorias
Configurações
Registar-se
+ Imagens destacadas
Sobre
A aplicação do Wikimedia Commons é uma aplicação de código aberto criada e mantida por bolseiros e voluntários da comunidade Wikimedia. A Wikimedia Foundation não está envolvida na criação, desenvolvimento ou manutenção da aplicação.
Criar uma nova <a href=\"https://github.com/commons-app/apps-android-commons/issues\">incidência no GitHub</a> para reportar erros e sugestões.
- <a href=\"https://github.com/commons-app/apps-android-commons/wiki/Privacy-policy\">Política de privacidade</a>
- <a href=\"https://github.com/commons-app/apps-android-commons/blob/master/CREDITS\">Créditos</a>
+ <u>Política de privacidade</u>
+ <u>Créditos</u>
Sobre
Enviar comentários (por e-mail)
Não foi instalado nenhum cliente de correio eletrónico
@@ -89,7 +110,7 @@
Essa imagem será licenciada sob %1$s
Ao carregar esta imagem, declaro que esta é a minha própria obra, que não contém material protegido ou selfies, e que adere às <a href=\"https://commons.wikimedia.org/wiki/Commons:Policies_and_guidelines/pt\">políticas do Wikimedia Commons</a>.
Descarregar
- Licença
+ Licença padrão
Usar título/descrição anteriores
Obter automaticamente a localização atual
Recuperar localização atual para oferecer sugestões da categoria se a imagem não é georreferenciada
@@ -118,11 +139,20 @@
Wikimedia Commons armazena a maioria das imagens que são usadas na Wikipédia.
As suas imagens ajudam a educar pessoas em todo o mundo!
Por favor, carregue apenas imagens tiradas ou criadas exclusivamente por si:
- - Objetos naturais (flores, animais, montanhas)\n- Objetos úteis (bicicletas, estações de comboio)\n- Pessoas famosas (o seu presidente da câmara, atletas olímpicos que conheça)
+ Objetos naturais (flores, animais, montanhas)\n• Objetos úteis (bicicletas, estações de comboio)\n• Pessoas famosas (o seu presidente da câmara, atletas olímpicos que conheça)
+ Objetos naturais (flores, animais, montanhas)
+ Objetos úteis (bicicletas, estações de comboio)
+ Pessoas famosas (o seu presidente da câmara, atletas olímpicos que conheça)
Por favor, NÃO carregue:
- Autorretratos ou imagens dos seus amigos\n- Imagens descarregadas da Internet\n- Capturas de ecrã de aplicações com direitos de autor
+ Autorretratos ou fotografias dos seus amigos
+ As imagens que descarregou da Internet
+ Capturas de ecrã de aplicações proprietárias
Exemplo de carregamento:
- Título: Ópera de Sydney\n- Descrição: A Ópera de Sydney vista do outro lado da baía\n- Categorias: Ópera de Sydney vista do ocidente, Vistas à distância da Ópera de Sydney
+ Título: Ópera de Sydney
+ Descrição: A Ópera de Sydney vista do outro lado da baía
+ Categorias: Ópera de Sydney vista do ocidente, vistas à distância da Ópera de Sydney
Contribua com as suas imagens. Ajude os artigos da Wikipédia a ganhar vida!
As imagens na Wikipédia provêm do Wikimedia Commons.
As suas imagens ajudam a educar as pessoas em todo o mundo.
@@ -135,8 +165,8 @@
Sem descrição
Licença desconhecida
Actualizar
- Permissão necessária: Ler a armazenagem externa. A aplicação não pode funcionar sem isto.
- Permissão necessária: Escrever na armazenagem externa. A aplicação não pode funcionar sem isto.
+ Permissão necessária: Ler a armazenagem externa. A aplicação não pode aceder à sua galeria sem isto.
+ Permissão necessária: Escrever na armazenagem externa. A aplicação não pode aceder à sua câmara sem isto.
Permissão opcional: Obter a localização atual para sugestões de categoria
OK
Locais Próximos
@@ -149,6 +179,8 @@
Título do ficheiro multimédia
Descrição
A descrição do ficheiro multimédia é colocada aqui. Ela pode ser bastante longa e precisar de ser dividida em várias linhas. No entanto, esperamos que tenha bom aspeto.
+ Autor
+ O nome de utilizador do autor da imagem destacada fica aqui.
Data de carregamento
Licença
Coordenadas
@@ -191,10 +223,12 @@
Sair
Tutorial
Notificações
+ Destacadas
Os sítios aqui perto não podem ser apresentados sem permissões de localização
não foi encontrada nenhuma descrição
Página do ficheiro no Commons
Item do Wikidata
+ Artigo na Wikipédia
Erro ao colocar imagens na cache
Um título descritivo exclusivo para o ficheiro, que servirá como um nome de ficheiro. Pode utilizar uma linguagem simples com espaços. Não inclua a extensão do ficheiro
Por favor, descreva o ficheiro da melhor forma possível: Onde foi tirado? O que isso mostra? Qual é o contexto? Por favor, descreva os objetos ou as pessoas. Indique as informações que não podem ser facilmente adivinhadas, por exemplo, a hora do dia, se for uma paisagem. Se o ficheiro mostrar algo incomum, explique o que torna incomum.
@@ -206,6 +240,12 @@
Inicie sessão na sua conta
Enviar ficheiro de registo
Enviar o ficheiro de registo aos programadores por correio eletrónico
+ Não foi encontrado nenhum navegador da Internet para abrir o URL
+ Erro! Não foi possível encontrar o URL
+ Nomear para eliminação
+ Esta imagem foi nomeada para eliminação.
+
+ Ver no navegador
A localização não foi alterada.
A localização não está disponível.
É necessária a permissão para mostrar uma lista dos sítios aqui perto
@@ -216,4 +256,21 @@
Obrigado por ter realizado uma edição
%1$s fez menção a si em %2$s.
Alternar modo de visionamento
+ DIREÇÕES
+ WIKIDATA
+ WIKIPÉDIA
+ COMMONS
+ <u>Avalie-nos</u>
+ <u>FAQ</u>
+ Saltar a explicação
+ A Internet não está disponível
+ A Internet está disponível
+ Erro ao tentar obter as notificações
+ Não foram encontradas notificações
+ <u>Traduzir</u>
+ Línguas
+ Selecione a língua para a qual quer enviar as traduções
+ Avançar
+ Cancelar
+ Tentar novamente
diff --git a/app/src/main/res/values-qq/error.xml b/app/src/main/res/values-qq/error.xml
index 0bc9e2f24..d6002a6a1 100644
--- a/app/src/main/res/values-qq/error.xml
+++ b/app/src/main/res/values-qq/error.xml
@@ -1,4 +1,7 @@
+
Title of dialog to show when the app crashes
Prompt asking people to enter info about what they were doing when the app crashed
diff --git a/app/src/main/res/values-qq/strings.xml b/app/src/main/res/values-qq/strings.xml
index 6312deb40..37c2978bf 100644
--- a/app/src/main/res/values-qq/strings.xml
+++ b/app/src/main/res/values-qq/strings.xml
@@ -1,4 +1,16 @@
+
{{Identical|General}}
The name of the application. A short form of \"Wikimedia Commons\". It is used in the app\'s launcher icon.\n{{Identical|Wikimedia Commons}}
@@ -50,6 +62,7 @@
This message is followed by a list of the categories.\n{{Identical|Search category}}
Hint text on menu item to save selected categories.\n{{Identical|Save}}
{{Identical|Refresh}}
+ {{Identical|List}}
{{Identical|Upload}}
Message shown to the user when no category matching what they searched for was found. %1$s represents the category name
Text explaining to users why and how to add categories to images. Users can also tap this message to skip adding categories.
@@ -97,6 +110,7 @@
{{Identical|No}}
{{Identical|Title}}
{{Identical|Description}}
+ {{Identical|Author}}
{{Identical|License}}
{{Identical|Coordinate}}
Describes \"coordinates\".
@@ -114,5 +128,13 @@
{{Identical|Upload}}
{{Identical|Nearby}}
{{Identical|Tutorial}}
- \'\'This message is empty, and it\'s probably invalid. See bug report: https://github.com/commons-app/apps-android-commons/issues/1333 .\'\'
+ {{Identical|Notification}}
+ \'\'This message is empty, and it\'s probably invalid. See bug report: https://github.com/commons-app/apps-android-commons/issues/1333 .\'\'
+ {{Identical|Wikidata}}
+ {{Identical|Wikipedia}}
+ Link text with underline.
+ Link text with underline.\n{{Identical|Translate}}
+ {{Identical|Language}}
+ {{Identical|Cancel}}
+ {{Identical|Retry}}
diff --git a/app/src/main/res/values-ro/error.xml b/app/src/main/res/values-ro/error.xml
index e4dc60913..7d5c88c85 100644
--- a/app/src/main/res/values-ro/error.xml
+++ b/app/src/main/res/values-ro/error.xml
@@ -1,4 +1,7 @@
+
Commons s-a blocat
Hopa! Ceva nu a mers bine!
diff --git a/app/src/main/res/values-ro/strings.xml b/app/src/main/res/values-ro/strings.xml
index a8e58ca46..b87abfbbf 100644
--- a/app/src/main/res/values-ro/strings.xml
+++ b/app/src/main/res/values-ro/strings.xml
@@ -1,4 +1,9 @@
+
Commons
Setări
diff --git a/app/src/main/res/values-ru/error.xml b/app/src/main/res/values-ru/error.xml
index ca0ece65e..647d7884d 100644
--- a/app/src/main/res/values-ru/error.xml
+++ b/app/src/main/res/values-ru/error.xml
@@ -1,4 +1,7 @@
+
Сбой
Ой. Что-то пошло не так!
diff --git a/app/src/main/res/values-ru/strings.xml b/app/src/main/res/values-ru/strings.xml
index 1c7c29231..c649398bb 100644
--- a/app/src/main/res/values-ru/strings.xml
+++ b/app/src/main/res/values-ru/strings.xml
@@ -1,4 +1,23 @@
+
Внешний вид
Общие
@@ -60,6 +79,7 @@
Выбор категорий
Сохранить
Обновить
+ Список
GPS отключён в вашем устройстве. Хотите включить его?
Включить GPS
Загрузок пока нет
@@ -84,6 +104,7 @@
Категории
Настройки
Зарегистрироваться
+ Избранные изображения
О приложении
Приложение «Викисклад» - это программа с открытым кодом, которую создали волонтёры и участники грантов Викимедиа. Фонд Викимедиа не участвует в создании, разработке или обслуживании этого приложения.
Вы можете создать <a href=\"https://github.com/commons-app/apps-android-commons/issues\">запрос на GitHub</a>, чтобы сообщить об ошибке или внести предложение.
@@ -126,7 +147,7 @@
CC BY-SA 4.0
CC BY 4.0
CC Zero
- Викисклад содержит большую часть изображений, которые используются в Википедии.
+ Викисклад содержит бо́льшую часть изображений, которые используются в Википедии.
Ваши изображения помогают образованию людей во всём мире!
Пожалуйста, загрузите фотографии, которые были сняты или созданы исключительно вами:
Природные объекты (например, цветы, животные, горы)\n• Полезные предметы (например, велосипеды, вокзалы)\n• Известные люди (например, ваш мэр, спортсмены-олимпийцы, которых вы встретили)
@@ -155,8 +176,8 @@
Нет описания
Неизвестная лицензия
Обновить
- Требуемые разрешения: чтение с внешнего хранилища. Приложение не сможет функционировать без этого.
- Требуемые разрешения: запись на внешнее хранилище. Приложение не сможет функционировать без этого.
+ Требуемые разрешения: чтение с внешнего хранилища. Приложение не сможет получить доступ к вашей галерее без этого разрешения.
+ Требуемые разрешения: запись на внешнее хранилище. Приложение не сможет получить доступ к камере без этого разрешения.
Необязательное разрешение: получение текущего местоположения для предложения категорий
OK
Места поблизости
@@ -166,9 +187,11 @@
Да
Нет
Название
- Заголовок носителя информации
+ Заголовок медиафайла
Описание
- Здесь располагается описание носителя информации. Оно потенциально может быть весьма длинным и даже располагаться в несколько строк. Однако мы надеемся, что это выглядит симпатично
+ Здесь располагается описание медиафайла. Оно может быть весьма длинным и даже располагаться в несколько строк. Однако, надеемся, будет выглядеть приемлемо.
+ Автор
+ Здесь указывается имя автора избранного изображения
Дата загрузки
Лицензия
Координаты
@@ -194,7 +217,7 @@
Ламы
Радужный мост
Тюльпан
- Нет сэлфи
+ Без селфи
Несвободное изображение
Добро пожаловать в Википедию
Добро пожаловать — авторские права
@@ -211,10 +234,12 @@
Выйти
Руководство
Уведомления
+ Избранное
Места поблизости не могут быть отображены без разрешения на геолокацию
описание не найдено
Страница файла на Викискладе
Элемент Викиданных
+ Статья Википедии
Ошибка при кэшировании картинок
Уникальное описание, которое будет сохранено как имя файла. Вы можете использовать естественный язык, разделяя слова пробелами. Пожалуйста, не указывайте расширение файла.
Пожалуйста, подробно опишите загружаемый файл: где он был снят? что на нём изображено? каков его контекст? Пожалуйста опишите изображённых персон или объекты. Добавьте информацию, о которой нельзя легко догадаться, например, время суток, когда снимался файл. Если снято что-то необычное, постарайтесь пояснить, что именно в этом необычного.
@@ -229,6 +254,8 @@
Не найден браузер, чтобы открыть ссылку
Ошибка! Ссылка не найдена
Номинировать к удалению
+ Этот файл был вынесен на удаление.
+
Просмотреть в браузере
Местоположение не изменено.
Местоположение недоступно.
@@ -240,7 +267,21 @@
Спасибо за правку
%1$s упомянул вас на %2$s.
Переключить режим просмотра
- *
- Часто задаваемые вопросы
+ НАПРАВЛЕНИЯ
+ ВИКИДАННЫЕ
+ ВИКИПЕДИЯ
+ ВИКИСКЛАД
+ <u>Оцените нас</u>
+ <u>Часто задаваемые вопросы</u>
Пропустить руководство
+ Интернет недоступен
+ Интернет доступен
+ Ошибка при получении уведомления
+ Уведомлений нет
+ <u>Перевести</u>
+ Языки
+ Выберите язык локализации, на который сможете перевести элементы интерфейса приложения
+ Выполняется
+ Отмена
+ Повторить
diff --git a/app/src/main/res/values-sat/error.xml b/app/src/main/res/values-sat/error.xml
index 8a52aebfb..e82212892 100644
--- a/app/src/main/res/values-sat/error.xml
+++ b/app/src/main/res/values-sat/error.xml
@@ -1,4 +1,7 @@
+
ᱥᱟᱨᱦᱟᱣ!
diff --git a/app/src/main/res/values-sd/error.xml b/app/src/main/res/values-sd/error.xml
index f793f50a8..11f7e484a 100644
--- a/app/src/main/res/values-sd/error.xml
+++ b/app/src/main/res/values-sd/error.xml
@@ -1,4 +1,7 @@
+
العام ڪريش ٿي پيو آھي
اڙي. ڪجھ غلط ٿي ويو!
diff --git a/app/src/main/res/values-sd/strings.xml b/app/src/main/res/values-sd/strings.xml
index 3ae6c2efe..3ccc39dd3 100644
--- a/app/src/main/res/values-sd/strings.xml
+++ b/app/src/main/res/values-sd/strings.xml
@@ -1,4 +1,8 @@
+
العام
ترتيبون
@@ -128,7 +132,7 @@
ڪا تشريح ناھي
اڻڄاتل لائسنس
تازو ڪريو
- گھربل اجازت: خارجي اسٽوريج پڙھڻ. ايپ ھن کانسواءِ فنڪشن نٿي ڪري سگھي.
+ گھربل اجازت: خارجي اسٽوريج پڙھڻ. ايپ ھن کانسواءِ فنڪشن نٿي ڪري سگھي.
چونڊ اجازت: زمرن جي تجويزن لاءِ ھاڻوڪي مڪانيت وٺو
ٺيڪ
ويجھڙائيءَ ۾ جڳھون
diff --git a/app/src/main/res/values-si/error.xml b/app/src/main/res/values-si/error.xml
index 9ff0e5094..24f06d1b0 100644
--- a/app/src/main/res/values-si/error.xml
+++ b/app/src/main/res/values-si/error.xml
@@ -1,4 +1,7 @@
+
කොමන්ස් බිඳ වැටී ඇත
අපොයි. යමක් වැරදිලා ගිහින්!
diff --git a/app/src/main/res/values-si/strings.xml b/app/src/main/res/values-si/strings.xml
index fd263b89a..4ae0db17c 100644
--- a/app/src/main/res/values-si/strings.xml
+++ b/app/src/main/res/values-si/strings.xml
@@ -1,4 +1,10 @@
+
කොමන්ස්
සැකසුම්
diff --git a/app/src/main/res/values-sk/error.xml b/app/src/main/res/values-sk/error.xml
index 9e7e6b605..8e61e5c1f 100644
--- a/app/src/main/res/values-sk/error.xml
+++ b/app/src/main/res/values-sk/error.xml
@@ -1,4 +1,7 @@
+
Commons sa zrútil
Hups. Niečo sa pokazilo!
diff --git a/app/src/main/res/values-sk/strings.xml b/app/src/main/res/values-sk/strings.xml
index 8662b9a81..90fac7f16 100644
--- a/app/src/main/res/values-sk/strings.xml
+++ b/app/src/main/res/values-sk/strings.xml
@@ -1,10 +1,22 @@
+
+ Vzhľad
+ Všeobecné
+ Spätná väzba
+ Poloha
Commons
+ •
Nastavenia
Používateľské meno
Heslo
+ Prihláste sa do svojho účtu Commons Beta
Prihlásiť sa
+ Zabudli ste heslo?
Zaregistrovať sa
Prihlasovanie
Čakajte prosím…
@@ -36,6 +48,7 @@
Zdieľať
Otvoriť v prehliadači
Názov
+ Prosím, dajte tomuto súboru názov
Opis
prihlásenie zlyhalo - zlyhanie siete
Prihlásenie zlyhalo - skontrolujte vaše používateľské meno
@@ -59,7 +72,7 @@
O aplikácii
Open Source softvér dostupný za podmienok <a href=\"https://github.com/commons-app/apps-android-commons/blob/master/COPYING\">Apache License v2</a>
Zdroj na <a href=\"https://github.com/commons-app/apps-android-commons\">GitHub</a>. Bugy na <a href=\" https://github.com/commons-app/apps-android-commons/issues\">Github</a>.
- <a href=\"https://github.com/commons-app/apps-android-commons/wiki/Privacy-policy\">Zásady ochrany súkromia</a>
+ <u>Zásady ochrany súkromia</u>
O aplikácii
Odoslať spätnú väzbu (emailom)
Nemáte nainštalovaného žiadneho e-mailového klienta
@@ -70,7 +83,7 @@
Zrušiť
Tento obrázok bude licencovaný podľa %1$s
Stiahnuť
- Licencia
+ Predvolená licencia
Použiť predchádzajúci názov/popis
Automaticky získať súčasnú polohu
Nočný režim
@@ -98,11 +111,20 @@
Na Wikimedia Commons sa nachádza väčšina obrázkov, ktoré sa používajú na Wikipédii.
Váš obrázok pomáha vzdelávať ľudí po celom svete!
Prosím, nahrávajte obrázky, ktoré ste odfotili alebo vytvorili vy:
- - Prírodu (kvety, zvieratá, hory)\n- Užitočné objekty (bicykle, železničné stanice)\n- Slávni ľudia (starosta, olympionici, s ktorými ste sa stretli)
+ Prírodu (kvety, zvieratá, hory)\n• Užitočné objekty (bicykle, železničné stanice)\n• Slávnych ľudí (starosta, olympionici, s ktorými ste sa stretli)
+ Prírodu (kvety, zvieratá, hory)
+ Užitočné objekty (bicykle, železničné stanice)
+ Slávnych ľudí (starosta, olympionici, s ktorými ste sa stretli)
Prosím NENAHRÁVAJTE:
- Selfies alebo fotky vašich priateľov\n- Obrázky prevzaté z internetu\n- Snímky obrazovky proprietárnych aplikácii
+ Selfies alebo fotky vašich priateľov
+ Obrázky prevzaté z internetu
+ Snímky obrazovky proprietárnych aplikácii
Príklad nahratia:
- Názov: Opera v Sydney\n- Opis: Opera v Sydney - pohľad spoza zátoky\n- Kategórie: Sydney Opera House from the west, Sydney Opera House remote views
+ Názov: Opera v Sydney
+ Popis: Opera v Sydney - pohľad spoza zátoky
+ Kategórie: Sydney Opera House from the west, Sydney Opera House remote views
Prispejte svojimi obrázkami. Pomôžte oživiť články na Wikipédií.
Obrázky na Wikipédií pochádzajú z Wikimedia Commons.
Vaše obrázky pomáhajú vzdelávať ľudí po celom svete.
@@ -125,14 +147,20 @@
Názov
Názov média
Popis
+ Autor
+ Dátum nahrania
Licencia
Súradnice
neposkytnuté
Staňte sa beta testerom
Naozaj sa chcete odhlásiť?
Logo Commons
+ Webová stránka Commons
+ Facebooková stránka Commons
+ Zdrojový kód Commons na Githube
Obrázok pozadia
Nenašiel sa žiaden obrázok
+ Nahrať obrázok
Hora Zaó
Lamy
Dúhový most
@@ -152,4 +180,15 @@
Návod
Upozornenia
nenašiel sa žiaden popis
+ Otvoriť v prehliadači
+ WIKIÚDAJE
+ WIKIPÉDIA
+ COMMONS
+ <u>Ohodnoťte nás</u>
+ <u>FAQ</u>
+ <u>Preložiť</u>
+ Jazyky
+ Pokračovať
+ Zrušiť
+ Obnoviť
diff --git a/app/src/main/res/values-skr/error.xml b/app/src/main/res/values-skr/error.xml
index 1061a7b8c..4829c95c2 100644
--- a/app/src/main/res/values-skr/error.xml
+++ b/app/src/main/res/values-skr/error.xml
@@ -1,4 +1,7 @@
+
شکریہ!
diff --git a/app/src/main/res/values-skr/strings.xml b/app/src/main/res/values-skr/strings.xml
index 5ff73b3fa..d1d1d5d87 100644
--- a/app/src/main/res/values-skr/strings.xml
+++ b/app/src/main/res/values-skr/strings.xml
@@ -1,4 +1,7 @@
+
شکل و صورت
عمومی
@@ -10,6 +13,7 @@
ورتݨ آلا ناں
پاس ورڈ
لاگ ان تھیوو
+ پاسورڈ بھل ڳئے ہو؟
سائن اپ
لاگ ان تھیندا پئے
انتظار کرو۔۔۔
@@ -45,6 +49,7 @@
قسماں دی ڳول
بچاؤ
سجرا، تازہ کرو
+ فہرست
جی پی ایس چلاؤ
اڄݨ ککھ وی اپ لوڈ نی تھیا
قسماں، زمرے
@@ -109,7 +114,17 @@
لاگ آؤٹ
ٹیٹوریل
وکی ڈیٹا آئٹم
+ وکی پیڈیا دا مضمون
اجازت ݙیوو
آپݨے کھاتے وچ لاگ ان تھیوو
لاگ فائل بھیجو
+ وکی ڈیٹا
+ وکی پیڈیا
+ عام
+ <u>عام طور تے پچھے ونڄݨ آلے سوال</u>
+ <u>ترجمہ کرو</u>
+ زباناں
+ اڳوں تے تھیوو
+ منسوخ
+ ولدا کوشش کرو
diff --git a/app/src/main/res/values-sr/error.xml b/app/src/main/res/values-sr/error.xml
index f8287ca14..a1c22c874 100644
--- a/app/src/main/res/values-sr/error.xml
+++ b/app/src/main/res/values-sr/error.xml
@@ -1,4 +1,8 @@
+
Остава се срушила
Упс! Нешто је пошло наопако.
diff --git a/app/src/main/res/values-sr/strings.xml b/app/src/main/res/values-sr/strings.xml
index 39fc19325..925b8a5ce 100644
--- a/app/src/main/res/values-sr/strings.xml
+++ b/app/src/main/res/values-sr/strings.xml
@@ -1,4 +1,15 @@
+
Изглед
Опште
@@ -151,8 +162,8 @@
Нема описа
Непозната лиценца
Освежи
- Потребна дозвола: читање спољашње меморије. \nАпликација не може да функционише без овога.
- Потребна дозвола: писање у спољашњој меморији. \nАпликација не може да функционише без овога.
+ Потребна дозвола: читање спољашње меморије. \nАпликација не може да функционише без овога.
+ Потребна дозвола: писање у спољашњој меморији. \nАпликација не може да функционише без овога.
Необавезна дозвола: преузми тренутну локацију за предлоге категорија
У реду
Места у близини
@@ -234,7 +245,7 @@
Хвала Вам за прављење измене
%1$s Вас је поменуо на страници %2$s.
Пребаци приказ
-
- Често постављана питања
+ <u>Оцените нас</u>
+ Често постављана питања
Прескочи туторијал
diff --git a/app/src/main/res/values-su/error.xml b/app/src/main/res/values-su/error.xml
index e85d8dd1c..8b8d77543 100644
--- a/app/src/main/res/values-su/error.xml
+++ b/app/src/main/res/values-su/error.xml
@@ -1,4 +1,8 @@
+
Commons ruksak
Euh. Aya masalah!
diff --git a/app/src/main/res/values-su/strings.xml b/app/src/main/res/values-su/strings.xml
index 5b09c3f63..b2604eefd 100644
--- a/app/src/main/res/values-su/strings.xml
+++ b/app/src/main/res/values-su/strings.xml
@@ -1,4 +1,9 @@
+
Commons
Séting
@@ -134,8 +139,8 @@
Tanpa pedaran
Lisénsi teu dipikanyaho
Segerkeun
- Merlukeun widi: Baca simpenan éksternal. Aplikasi teu bisa jalan tanpa ieu.
- Merlukeun widi: Baca simpenan éksternal. Aplikasi teu bisa jalan tanpa ieu.
+ Merlukeun widi: Baca simpenan éksternal. Aplikasi teu bisa jalan tanpa ieu.
+ Merlukeun widi: Baca simpenan éksternal. Aplikasi teu bisa jalan tanpa ieu.
Idin pilihan: Paké lokasi kiwari pikeun usulan kategori
Oké
Tempat Sabudeureun
diff --git a/app/src/main/res/values-sv/error.xml b/app/src/main/res/values-sv/error.xml
index 7ac3bea5e..124154ad6 100644
--- a/app/src/main/res/values-sv/error.xml
+++ b/app/src/main/res/values-sv/error.xml
@@ -1,4 +1,8 @@
+
Commons har kraschat
Oj. Något gick fel!
diff --git a/app/src/main/res/values-sv/strings.xml b/app/src/main/res/values-sv/strings.xml
index e7b16edca..fa5174ced 100644
--- a/app/src/main/res/values-sv/strings.xml
+++ b/app/src/main/res/values-sv/strings.xml
@@ -1,4 +1,13 @@
+
Utseende
Allmänt
@@ -59,6 +68,7 @@
Sök kategorier
Spara
Uppdatera
+ Lista
GPS:en är inaktiverad på denna enhet. Vill du aktivera den?
Aktivera GPS
Inga uppladdningar ännu
@@ -80,6 +90,7 @@
Kategorier
Inställningar
Registrera
+ Utvalda bild
Om
Wikimedia Commons är en app med öppen källkod som skapas och underhålls av frivilliga från Wikimedias gemenskap. Wikimedia Foundation är inte involverad i skapandet, utvecklingen eller underhållet av appen.
Skapa ett nytt <a href=\"https://github.com/commons-app/apps-android-commons/issues\">ärende på GitHub</a> för att rapportera buggar och förslag.
@@ -151,8 +162,8 @@
Ingen beskrivning
Okänd licens
Uppdatera
- Nödvändig behörighet: Läsa extern lagring. Appen fungerar inte utan detta.
- Nödvändig behörighet: Skriva till extern lagring. Appen kan inte fungera så här.
+ Nödvändig behörighet: Läsa extern lagring. Appen kan inte komma åt ditt galleri utan detta.
+ Nödvändig behörighet: Skriva till extern lagring. Appen kan inte komma åt din kamera utan detta.
Valfri behörighet: Hämta aktuell plats för kategoriförslag
OK
Platser i närheten
@@ -165,6 +176,8 @@
Mediatitel
Beskrivning
Beskrivningen för mediafilen ska vara här. Den kan vara riktig lång och kommer att behöva sträcka sig över flera rader. Vi hoppas i alla fall att det kommer se bra ut.
+ Skapare
+ Användarnamnet för den utvalda bildens skapare ska stå här.
Uppladdningsdatum
Licens
Koordinater
@@ -207,10 +220,12 @@
Logga ut
Guide
Meddelanden
+ Utvald
Platser i närheten kan inte visas utan platsbehörigheter
ingen beskrivning hittades
Commons-filsida
Wikidata-objekt
+ Wikipedia-artikel
Fel uppstod när bilder cachelagras
En unik beskrivande titel för filen, som kommer att fungera som ett filnamn. Du kan använda klarspråk med mellanslag. Ta inte med filändelsen
Beskriv mediafilen så mycket som möjligt. Var togs den? Vad visar den? Vad är sammanhanget? Beskriv föremålen eller personerna. Ge information som inte kan gissas fram, t.ex. tidpunkten om det är ett landskap. Om mediafilen visar någonting ovanligt, förklara vad som gör den ovanlig.
@@ -225,6 +240,8 @@
Ingen webbläsare hittades för att öppna webbadressen
Fel! Webbadressen hittades inte
Nominera för radering
+ Denna bild har nominerats för radering.
+
Visa i webbläsare
Platsen har inte ändrats.
Platsen är inte tillgänglig.
@@ -236,7 +253,21 @@
Tack för att du gjorde en redigering
%1$s nämnde dig på %2$s.
Växla vy
-
- Vanliga frågor och svar
+ VÄGBESKRIVNING
+ WIKIDATA
+ WIKIPEDIA
+ COMMONS
+ <u>Betygsätt oss</u>
+ <u>Vanliga frågor</u>
Hoppa över övning
+ Uppkopplingen bröts
+ Uppkopplingen återupprättades
+ Fel uppstod när aviseringar hämtades
+ Inga aviseringar hittades
+ <u>Översätt</u>
+ Språk
+ Välj språket som du vill skicka in översättningar för
+ Fortsätt
+ Avbryt
+ Försök igen
diff --git a/app/src/main/res/values-sw/error.xml b/app/src/main/res/values-sw/error.xml
index 5a1d03889..8c5feb5a1 100644
--- a/app/src/main/res/values-sw/error.xml
+++ b/app/src/main/res/values-sw/error.xml
@@ -1,4 +1,7 @@
+
Commons wa kuvunjika
Asante!
diff --git a/app/src/main/res/values-ta/error.xml b/app/src/main/res/values-ta/error.xml
index 0ad08846c..57a83c13a 100644
--- a/app/src/main/res/values-ta/error.xml
+++ b/app/src/main/res/values-ta/error.xml
@@ -1,4 +1,7 @@
+
நன்றி!
diff --git a/app/src/main/res/values-tcy/error.xml b/app/src/main/res/values-tcy/error.xml
index a8b78fa41..7e3086af6 100644
--- a/app/src/main/res/values-tcy/error.xml
+++ b/app/src/main/res/values-tcy/error.xml
@@ -1,4 +1,7 @@
+
ಉಸಬ್ಬಾ. ದಾದೋನಾ ತೊಂದರೆ ಅಂಡ್!
ಸೊಲ್ಮೆಲೋ
diff --git a/app/src/main/res/values-tcy/strings.xml b/app/src/main/res/values-tcy/strings.xml
index 85f56bdf6..c6469511e 100644
--- a/app/src/main/res/values-tcy/strings.xml
+++ b/app/src/main/res/values-tcy/strings.xml
@@ -1,4 +1,8 @@
+
ಕಾಮನ್ಸ್
ಸಂಯೋಜನೆಲು
diff --git a/app/src/main/res/values-te/error.xml b/app/src/main/res/values-te/error.xml
index bc25e3999..b52c3fdd0 100644
--- a/app/src/main/res/values-te/error.xml
+++ b/app/src/main/res/values-te/error.xml
@@ -1,4 +1,7 @@
+
కామన్స్ క్రాషయింది
అడెడె.. ఎక్కడో తప్పు జరిగింది!
diff --git a/app/src/main/res/values-te/strings.xml b/app/src/main/res/values-te/strings.xml
index bb47f6bf4..b2ad478b0 100644
--- a/app/src/main/res/values-te/strings.xml
+++ b/app/src/main/res/values-te/strings.xml
@@ -1,4 +1,9 @@
+
కామన్స్
అమరికలు
diff --git a/app/src/main/res/values-th/error.xml b/app/src/main/res/values-th/error.xml
index bdacb80a8..1932cef87 100644
--- a/app/src/main/res/values-th/error.xml
+++ b/app/src/main/res/values-th/error.xml
@@ -1,4 +1,7 @@
+
คอมมอนส์หยุดทำงาน
อ๊ะ มีบางอย่างผิดพลาดไป!
diff --git a/app/src/main/res/values-th/strings.xml b/app/src/main/res/values-th/strings.xml
index aa816cfc8..29b29d804 100644
--- a/app/src/main/res/values-th/strings.xml
+++ b/app/src/main/res/values-th/strings.xml
@@ -1,10 +1,22 @@
+
+ การแสดงผล
+ ทั่วไป
+ คำติชม
+ ที่ตั้ง
คอมมอนส์
+ •
การตั้งค่า
ชื่อผู้ใช้
รหัสผ่าน
- เข้าสู่ระบบ
+ ลงชื่อเข้าระบบบัญชีคอมมอนส์บีตาของคุณ
+ ลงชื่อเข้า
+ ลืมรหัสผ่านหรือ?
สมัครสมาชิก
กำลังเข้าสู่ระบบ
กรุณารอสักครู่…
@@ -33,6 +45,7 @@
แชร์
ดูในเบราว์เซอร์
ชื่อเรื่อง
+ กรุณาระบุชืิ่อเรื่องของไฟล์นี้
คำอธิบาย
ไม่สามารถเข้าสู่ระบบได้ - ความล้มเหลวของเครือข่าย
ไม่สามารถเข้าสู่ระบบได้ - กรุณาตรวจสอบชื่อผู้ใช้ของคุณ
@@ -48,6 +61,7 @@
ค้นหาหมวดหมู่
บันทึก
รีเฟรช
+ รายการ
GPS ถูกปิดใช้งานในอุปกรณ์ของคุณอยู่ คุณต้องการเปิดใช้งานหรือไม่?
เปิดใช้งาน GPS
ยังไม่มีการอัปโหลด
@@ -61,15 +75,15 @@
- การอัปโหลด %1$d รายการ
ไม่พบหมวดหมู่ที่ตรงกับ %$1s
- เพิ่มหมวดหมู่เพื่อทำให้รูปภาพของคุณค้นพบได้ง่ายขึ้นบน Wikimedia Commons\nเริ่มพิมพ์เพื่อเพิ่มหมวดหมู่
+ เพิ่มหมวดหมู่เพื่อทำให้รูปภาพของคุณค้นพบได้ง่ายขึ้นบนวิกิมีเดียคอมมอนส์\nเริ่มพิมพ์เพื่อเพิ่มหมวดหมู่
หมวดหมู่
การตั้งค่า
สมัครใช้งาน
เกี่ยวกับ
- แอป Wikimedia Commons เป็นแอปโอเพนซอร์สที่สร้างขึ้นและดูแลโดยผู้มีสิทธิและอาสาสมัครของชุมชนวิกิมีเดีย มูลนิธิวิกิมีเดียไม่มีส่วนเกี่ยวข้องในการสร้าง พัฒนา หรือการบำรุงรักษาแอปใดๆ ทั้งสิ้น
+ แอปวิกิมีเดียคอมมอนส์เป็นแอปโอเพนซอร์สที่สร้างขึ้นและดูแลโดยผู้มีสิทธิและอาสาสมัครของชุมชนวิกิมีเดีย มูลนิธิวิกิมีเดียไม่มีส่วนเกี่ยวข้องในการสร้าง พัฒนา หรือการบำรุงรักษาแอปใดๆ ทั้งสิ้น
สร้าง <a href=\"https://github.com/commons-app/apps-android-commons/issues\">GitHub issue</a> ใหม่เพื่อรายงานบั๊กและส่งข้อเสนอแนะ
- <a href=\"https://github.com/commons-app/apps-android-commons/wiki/Privacy-policy\">นโยบายความเป็นส่วนตัว</a>
- <a href=\"https://github.com/commons-app/apps-android-commons/blob/master/CREDITS\">เครดิต</a>
+ <u>นโยบายความเป็นส่วนตัว</u>
+ <u>เครดิต</u>
เกี่ยวกับ
ส่งคำติชม (ผ่านทางอีเมล)
ไม่ได้ติดตั้งไคลเอนต์อีเมล
@@ -81,17 +95,54 @@
รูปภาพนี้จะอนุญาตให้ใช้ได้ภายใต้สัญญาอนุญาต %1$s
โดยการส่งรูปภาพนี้ ฉันยืนยันว่านี่เป็นงานของฉันเอง ซึ่งไม่ประกอบด้วยเนื้อหาที่ละเมิดลิขสิทธิ์หรือภาพเซลฟี หรืออื่นๆ ตามที่ระบุใน<a href=\"https://commons.wikimedia.org/wiki/Commons:Policies_and_guidelines\">นโยบายของ Wikimedia Commons</a>
ดาวน์โหลด
- สัญญาอนุญาต
+ สัญญาอนุญาตปริยาย
ใช้ชื่อเรื่อง/คำอธิบายก่อนหน้านี้
รับข้อมูลตำแหน่งที่ตั้งปัจจุบันโดยอัตโนมัติ
ดึงข้อมูลตำแหน่งที่ตั้งปัจจุบันเพื่อรับข้อเสนอแนะเกี่ยวกับหมวดหมู่ถ้ารูปภาพไม่ได้ติดแท็กตำแหน่งที่ตั้งเอาไว้
โหมดกลางคืน
ใช้ธีมสีเข้ม
+ Attribution-ShareAlike 4.0
+ Attribution 4.0
+ Attribution-ShareAlike 3.0
+ Attribution 3.0
+ CC0
+ CC BY-SA 3.0
+ CC BY-SA 3.0 (ออสเตรีย)
+ CC BY-SA 3.0 (เยอรมนี)
+ CC BY-SA 3.0 (เอสโตเนีย)
+ CC BY-SA 3.0 (สเปน)
+ CC BY-SA 3.0 (โครเอเชีย)
+ CC BY-SA 3.0 (ลักเซมเบิร์ก)
+ CC BY-SA 3.0 (เนเธอร์แลนด์)
+ CC BY-SA 3.0 (นอร์เวย์)
+ CC BY-SA 3.0 (โปแลนด์)
+ CC BY-SA 3.0 (โรมาเนีย)
+ CC BY 3.0
+ CC BY-SA 4.0
+ CC BY 4.0
+ CC Zero
+ วิกิมีเดียคอมมอนส์เก็บรูปภาพทั้งหมดที่ถูกใช้ในวิกิพีเดีย
+ รูปภาพของคุณช่วยให้ความรู้แก่ผู้คนทั่วโลก!
โปรดอัปโหลดรูปภาพที่ถ่ายหรือสร้างด้วยตัวคุณเองทั้งหมด:
- - วัตถุธรรมชาติ (ดอกไม้ สัตว์ ภูเขา)\n- วัตถุที่สามารถใช้งานได้ (จักรยาน สถานีรถไฟ)\n- บุคคลที่มีชื่อเสียง (นายกเทศมนตรีของคุณ นักกีฬาโอลิมปิกที่คุณรู้จัก)
+ วัตถุธรรมชาติ (ดอกไม้ สัตว์ ภูเขา)\n• วัตถุที่สามารถใช้งานได้ (จักรยาน สถานีรถไฟ)\n• บุคคลที่มีชื่อเสียง (นายกเทศมนตรีของคุณ นักกีฬาโอลิมปิกที่คุณรู้จัก)
+ วัตถุธรรมชาติ (ดอกไม้ สัตว์ ภูเขา)
+ วัตถุที่สามารถใช้งานได้ (จักรยาน สถานีรถไฟ)
+ บุคคลที่มีชื่อเสียง (นายกเทศมนตรีของคุณ นักกีฬาโอลิมปิกที่คุณรู้จัก)
โปรดอย่าอัปโหลด:
- ภาพเซลฟีหรือภาพที่มีเพื่อนของคุณ\n- ภาพที่คุณดาวน์โหลดจากอินเทอร์เน็ต\n- ภาพหน้าจอแอปที่เป็นซอฟต์แวร์กรรมสิทธิ์
+ ภาพเซลฟีหรือภาพที่มีเพื่อนของคุณ
+ ภาพที่คุณดาวน์โหลดจากอินเทอร์เน็ต
+ ภาพหน้าจอแอปที่เป็นซอฟต์แวร์กรรมสิทธิ์
ตัวอย่างการอัปโหลด:
+ - ชื่อเรื่อง: โรงอุปรากรซิดนีย์\n- คำอธิบาย: โรงอุปรากรซิดนีย์เมื่อมองจากบริเวณอ่าวซิดนีย์\n- หมวดหมู่: โรงอุปรากรเมื่อมองจากทิศตะวันตก, ทิวทัศน์โรงอุปรากรซิดนีย์จากระยะไกล
+ ชื่อเรื่อง: โรงอุปรากรซิดนีย์
+ คำอธิบาย: โรงอุปรากรซิดนีย์เมื่อมองจากบริเวณอ่าวซิดนีย์
+ หมวดหมู่: โรงอุปรากรเมื่อมองจากทิศตะวันตก, ทิวทัศน์โรงอุปรากรซิดนีย์จากระยะไกล
+ ลงรูปของคุณ ช่วยให้บทความวิกิพีเดียมีชีวิตชีวา!
+ รูปภาพบนวิกิพีเดียมาจากวิกิพีเดียคอมมอนส์
+ รูปภาพของคุณช่วยให้การศึกษาแก่ผู้คนทั่วโลก
+ หลีกเลี่ยงเนื้อหาที่คุณพบในอินเทอร์เน็ต เช่น รูปภาพในโปสเตอร์ ปกหนังสือ ฯลฯ
+ คุณคิดว่าคุณเข้าใจแล้วใช่ไหม?
ใช่!
หมวดหมู่
กำลังโหลด…
@@ -99,8 +150,8 @@
ไม่มีคำอธิบาย
สัญญาอนุญาตที่ไม่รู้จัก
รีเฟรช
- สิทธิที่ต้องการ: อ่านที่เก็บข้อมูลภายนอก แอปไม่สามารถทำงานได้โดยไม่มีสิทธินี้
- สิทธิที่ต้องการ: เขียนที่เก็บข้อมูลภายนอก แอปไม่สามารถทำงานได้โดยไม่มีสิทธินี้
+ สิทธิที่ต้องการ: อ่านที่เก็บข้อมูลภายนอก แอปไม่สามารถเข้าถึงคลังภาพได้โดยไม่มีสิทธินี้
+ สิทธิที่ต้องการ: เขียนที่เก็บข้อมูลภายนอก แอปไม่สามารถเข้าถึงกล้องของคุณได้โดยไม่มีสิทธินี้
สิทธิทางเลือก: รับข้อมูลตำแหน่งที่ตั้งปัจจุบันสำหรับข้อเสนอแนะหมวดหมู่
ตกลง
สถานที่ใกล้เคียง
@@ -109,4 +160,99 @@
ไฟล์นี้มีอยู่แล้วบนคอมมอนส์ คุณแน่ใจหรือว่าคุณต้องการดำเนินการต่อ?
ใช่
ไม่
+ ชื่อเรื่อง
+ ชื่อเรื่องสื่อ
+ คำอธิบาย
+ ป้อนคำอธิบายสื่อที่นี่ คำอธิบายที่มีความยาวมากอาจมีหลายบรรทัด เราหวังว่ามันจะดูดี
+ ผู้สร้างสรรค์
+ วันที่อัปโหลด
+ สัญญาอนุญาต
+ พิกัด
+ ไม่ได้ระบุ
+ มาเป็นผู้ร่วมทดสอบบีตา
+ สมัครเข้าร่วมช่องทางบีตาบน Google Play และเข้าถึงคุณลักษณะใหม่ ๆ และการแก้ไขบั๊กก่อนเปิดตัว
+ รหัส 2FA
+ ขีดจำกัดการอัปโหลดล่าสุดของฉัน
+ ขีดจำกัดสูงสุด
+ ไม่สามารถแสดงมากกว่า 500 รายการได้
+ กำหนดขีดจำกัดการอัปโหลดล่าสุด
+ ไม่รองรับการยืนยันตัวบุคคลแบบสองขั้นตอนในขณะนี้
+ คุณต้องการออกจากระบบจริง ๆ หรือไม่?
+ โลโก้คอมมอนส์
+ เว็บไซต์คอมมอนส์
+ หน้าเฟซบุ๊กคอมมอนส์
+ ซอร์สโค้ดคอมมอนส์บน GitHub
+ ภาพพื้นหลัง
+ ภาพสื่อล้มเหลว
+ ไม่พบรูปภาพ
+ อัปโหลดรูปภาพ
+ ภูเขาซะโอ
+ ยามา
+ สะพานสายรุ้ง
+ ทิวลิป
+ ไม่มีภาพเซลฟี
+ ภาพกรรมสิทธิ์
+ ยินดีต้อนรับสู่วิกิพีเดีย
+ ลิขสิทธิ์ต้อนรับ
+ โรงอุปรากรซิดนีย์
+ ยกเลิก
+ เปิด
+ ปิด
+ หน้าหลัก
+ อัปโหลด
+ ใกล้เคียง
+ เกี่ยวกับ
+ การตั้งค่า
+ คำติชม
+ ลงชื่อออก
+ บทช่วยสอน
+ การแจ้งเตือน
+ ไม่สามารถแสดงสถานที่ใกล้เคียงได้โดยขาดสิทธิ์การเข้าถึงตำแหน่ง
+ ไม่พบคำอธิบาย
+ หน้าไฟล์คอมมอนส์
+ รายการวิกิสนเทศ
+ บทความวิกิพีเดีย
+ ข้อผิดพลาดขณะแคชภาพ
+ ชื่อเรื่องที่อธิบายลักษณะเฉพาะของไฟล์ ซึ่งจะใช้เป็นชื่อไฟล์ คุณอาจใช้ภาษาธรรมดาที่มีเว้นวรรคก็ได้ อย่ารวมนามสกุลไฟล์
+ โปรดอธิบายสื่อดังกล่าวให้มากที่สุดเท่าที่จะได้: สื่อนี้ถูกถ่ายที่ไหน? สื่อนี้แสดงถึงอะไร? บริบทคืออะไร? โปรดอธิบายถึงวัตถุหรือบุคคล เปิดเผยข้อมูลที่ไม่อาจคาดเดาได้อย่างง่ายดาย เช่น เวลาที่ถ่าย หากเป็นภาพทิวทัศน์ หากสื่อแสดงถึงสิ่งที่ไม่ธรรมดา โปรดอธิบายว่าอะไรทำให้สื่อดังกล่าวไม่ธรรมดา
+ ภาพนี้มืดเกินไป คุณแน่ใจหรือว่าคุณต้องการอัปโหลดภาพนี้? วิกิมีเดียคอมมอนส์นั้นมีไว้สำหรับรูปภาพที่มีคุณค่าในทางสารานุกรมเท่านั้น
+ ภาพนี้มัว คุณแน่ใจหรือว่าคุณต้องการอัปโหลดภาพนี้? วิกิมีเดียคอมมอนส์นั้นมีไว้สำหรับรูปภาพที่มีคุณค่าในทางสารานุกรมเท่านั้น
+ ให้สิทธิ์
+ ใช้ที่จัดเก็บข้อมูลภายนอก
+ บันทึกรูปภาพที่ถ่ายด้วยกล้องในแอปบนอุปกรณ์ของคุณ
+ ลงชื่อเข้าใช้บัญชีของคุณ
+ ส่งไฟล์ปูม
+ ส่งไฟล์ปูมไปยังนักพัฒนาผ่านทางอีเมล
+ ไม่พบเว็บเบราว์เซอร์ที่จะเปิด URL
+ ข้อผิดพลาด! ไม่พบ URL
+ เสนอการลบ
+ ภาพนี้ถูกเสนอการลบแล้ว
+ ดูในเบราว์เซอร์
+ ไม่ได้เปลี่ยนตำแหน่งที่ตั้ง
+ ตำแหน่งที่ตั้งไม่พร้อมใช้งาน
+ ต้องการสิทธิเพื่อแสดงรายการสถานที่ใกล้เคียง
+ สอบถามเส้นทาง
+ อ่านบทความ
+ ยินดีต้อนรับสู่วิกิมีเดียคอมมอนส์ %1$s! เราดีใจที่คุณอยู่ที่นี่
+ %1$s ส่งสารบนหน้าคุยของคุณ
+ ขอบคุณที่ร่วมแก้ไข
+ %1$s ได้กล่าวถึงคุณบน %2$s
+ สลับมุมมอง
+ เส้นทาง
+ วิกิสนเทศ
+ วิกิพีเดีย
+ คอมมอนส์
+ <u>ให้คะแนนเรา</u>
+ <u>FAQ</u>
+ ข้ามบทช่วยสอน
+ อินเทอร์เน็ตไม่พร้อมใช้งาน
+ อินเทอร์เน็ตพร้อมใช้งาน
+ เกิดข้อผิดพลาดในการดึงข้อมูลการแจ้งความ
+ ไม่พบการแจ้งความ
+ <u>แปล</u>
+ ภาษา
+ เลือกภาษาที่คุณต้องการส่งการแปล
+ ดำเนินการต่อ
+ ยกเลิก
+ ลองใหม่
diff --git a/app/src/main/res/values-tr/error.xml b/app/src/main/res/values-tr/error.xml
index 79c4c7768..7bfd32902 100644
--- a/app/src/main/res/values-tr/error.xml
+++ b/app/src/main/res/values-tr/error.xml
@@ -1,4 +1,8 @@
+
Commons çöktü
Hay Aksi! Bir şeyler yanlış gitti!
diff --git a/app/src/main/res/values-tr/strings.xml b/app/src/main/res/values-tr/strings.xml
index e0aa79c1e..94d383ff9 100644
--- a/app/src/main/res/values-tr/strings.xml
+++ b/app/src/main/res/values-tr/strings.xml
@@ -1,10 +1,27 @@
+
+ Görünüm
+ Genel
+ Geri bildirim
+ Konum
Commons
Ayarlar
Kullanıcı adı
Parola
+ Commons Beta hesabına giriş yap
Oturum aç
+ Parolamı Unuttum
Kaydol
Oturum açılıyor
Lütfen bekleyin…
@@ -36,6 +53,7 @@
Paylaş
Tarayıcıda görüntüle
Başlık
+ Lütfen bu dosya için bir başlık ekleyin
Açıklama
Oturum açılamıyor - ağ hatası
Oturum açılamıyor - lütfen kullanıcı adınızı kontrol edin
@@ -51,19 +69,20 @@
Kategorileri ara
Kaydet
Yenile
+ Liste
GPS, cihazınızda devre dışı bırakılmıştır. Etkinleştirmek ister misiniz?
GPS\'i etkinleştir
Henüz yüklenmedi
-
+
- \@string/contributions_subtitle_zero
- %1$d yükleme
- %1$d yükleme
-
+
- %1$d yüklenmeye başlanıyor
- %1$d yüklenmeye başlanıyor
-
+
- %1$d yükleme
- %1$d yükleme
@@ -74,9 +93,9 @@
Kaydol
Hakkında
Wikimedia Commons uygulaması, Wikimedia topluluğunun imtiyaz sahibi ve gönüllüleri tarafından oluşturulmuş ve sürdürülmüş açık kaynak kodlu bir uygulamadır. Vikipedi Vakfı, uygulamanın oluşturulması, geliştirilmesi veya bakımına dahil değildir.
- GitHub üzerinde <a href=\"https://github.com/commons-app/apps-android-commons\">Kaynak</a> ve <a href=\"https://commons-app.github.io/\">website</a>. Hata raporları ve önerileri için yeni bir <a href=\"https://github.com/commons-app/apps-android-commons/issues\">GitHub sorunu</a> oluştur.
- <a href=\"https://github.com/commons-app/apps-android-commons/wiki/Privacy-policy\">Gizlilik Politikası</a>
- <a href=\"https://github.com/commons-app/apps-android-commons/blob/master/CREDITS\">Katkıda bulunanlar</a>
+ GitHub üzerinde <a href=\"https://github.com/commons-app/apps-android-commons\">Kaynak</a> ve <a href=\"https://commons-app.github.io/\">website</a>. Hata raporları ve önerileri için yeni bir <a href=\"https://github.com/commons-app/apps-android-commons/issues\">GitHub sorunu</a> oluştur.
+ <a href=\"https://github.com/commons-app/apps-android-commons/wiki/Privacy-policy\">Gizlilik Politikası</a>
+ <a href=\"https://github.com/commons-app/apps-android-commons/blob/master/CREDITS\">Katkıda bulunanlar</a>
Hakkında
Geri Bildirim Gönder (E-posta ile)
Yüklü bir e-posta istemcisi yok
@@ -88,7 +107,7 @@
Bu resmi %1$s lisansı altında olacak.
Bu resmi göndererek bunun kendi eserim olduğumu, telif hakkıyla korunan materyal veya selfie içermediğini ve aksi takdirde <a href=\"https://commons.wikimedia.org/wiki/Commons:Policies_and_guidelines\">Wikimedia Commons politikalarına</a> uyduğunu beyan ederim.
İndir
- Lisans
+ Varsayılan lisans
Önceki başlığı/açıklamayı kullan
Otomatik olarak mevcut konumu al
Resim koordinat olarak etiketlendirilmemişse kategori önerileri için mevcut konum bulun
@@ -117,11 +136,19 @@
Wikimedia Commons, Vikipedi\'de kullanılan resimlerin çoğunu barındırır.
Resimleriniz dünyanın dört bir yanındaki insanlara eğitim vermeye yardımcı olur!
Lütfen tamamen kendiniz çektiğiniz veya oluşturduğunuz resimleri yükleyin:
- - Doğal nesneler (çiçekler, hayvanlar, dağlar)\n- Faydalı nesneler (bisiklet, tren istasyonları)\n- Ünlü insanlar (belediye başkanınız, tanıştığınız Olimpik atletler)
+ Doğal nesneler (çiçekler, hayvanlar, dağlar)\n- Faydalı nesneler (bisiklet, tren istasyonları)\n- Ünlü insanlar (belediye başkanınız, tanıştığınız Olimpik atletler)
+ Doğal objeler (çiçekler, hayvanlar, dağlar)
+ Kullanışlı objeler (bisikletler, tren istasyonları)
+ Ünlü kişiler (belediye başkanınız, tanıştığınız Olimpik atletler)
Lütfen şunları YÜKLEMEYİN:
- Öz çekimlerinizi ya da arkadaşlarınızın fotoğraflarını\n- İnternetten indirdiğiniz resimleri\n- Tescilli uygulamaların ekran görüntülerini
+ Selfiler veya arkadaşlarınızın fotoğrafları
+ İnternet\'ten indirdiğiniz fotoğraflar
+ Özel mülk uygulamaların ekran görüntüleri
Yüklenebileceklere örnekler:
- Başlık: Sydney Opera Binası\n- Tanım: Körfezin genelinden bakıldığında Sydney Opera Binası\n- Kategoriler: Sydney Opera Binası, batıdan Sydney Opera Binası
+ Başlık: Sidney Opera Binası
+ Açıklama: Sidney Opera Binası\'nın körfezin karşısından görünümü
Resimleriniz ile Vikipedi maddelerinin canlandırılmasına katkıda bulunabilirsiniz!
Vikipedi\'ye Wikimedia Commons\'tan gelen görüntüler.
Görüntüler dünya insanlarının eğitiminde yardımcı olur.
@@ -134,8 +161,8 @@
Açıklama yok
Bilinmeyen lisans
Yenile
- Gerekli izinler: Harici depolama biriminin okunması. Uygulama buna izin verilmeden çalışmaz.
- Gerekli izin: Harici depolama birimi üzerine yazma. Uygulama buna izin verilmeden çalışmaz.
+ Gerekli izinler: Harici depolama biriminin okunması. Uygulama buna izin verilmeden çalışmaz.
+ Gerekli izin: Harici depolama birimi üzerine yazma. Uygulama buna izin verilmeden çalışmaz.
İsteğe bağlı izin: Kategori önerileri için geçerli konum alma
Tamam
Yakındaki yerler
@@ -162,6 +189,9 @@
İki faktörlü kimlik doğrulama şu anda desteklenmiyor.
Gerçekten çıkış yapmak istiyor musunuz?
Commons Logo
+ Commons Websitesi
+ Commons Facebook Sayfası
+ Commons Github Kaynak Kodu
Arka plan görüntüsü
Medya Görüntüsü Başarısız Oldu
Resim Bulunamadı
@@ -191,18 +221,30 @@
hiçbir açıklama bulunamadı
Commons dosya sayfası
Vikiveri ögesi
+ Wikipedia makalesi
Resimler önbelleğe alınırken hata oluştu
Dosya için dosya adı olarak kullanılacak benzersiz açıklayıcı bir başlık olmalıdır. Boşluk bırakarak sade bir dil kullanabilirsiniz. Dosya uzantısını dahil etmeyin
Lütfen medyayı mümkün olduğunca açıklayın: Nerede çekildi? Ne gösteriyor? Bağlam nedir? Lütfen nesneleri veya kişileri tanımlayın. Kolay tahmin edilemeyen bilgileri açıklayın, örneğin bir manzara ise günün saatini belirtin. Medya alışılmadık bir şey gösteriyorsa lütfen olağandışı yapan şeyleri açıklayın.
+ Bu fotoğraf çok karanlık, yine de yüklemek istiyor musunuz? Wikimedia Commons yalnızca ansiklopedik değeri olan fotoğraflar içindir.
+ Bu fotoğraf bulanık, yine de yüklemek istiyor musunuz? Wikimedia Commons yalnızca ansiklopedik değeri olan fotoğraflar içindir.
İzin ver
Harici depolamayı kullanın
Uygulama kamerası kullanıldığında çekilen fotoğrafları cihazına kaydedin
Hesabınızda oturum açın
Kayıt dosyasını gönder
Kayıt dosyasını, e-posta aracılığıyla geliştiricilere gönderin
+ URL\'yi açabilecek bir tarayıcı bulunamadı
+ Hata! URL bulunamadı
+ Silinmesi için aday göster
+ Bu görsel silinmesi için aday gösterildi.
+ Tarayıcıda görüntüle
Konum değiştirilmedi
Konum kullanılamıyor.
Yakındaki yerler listesini görüntülemek için izin vermeniz gerekiyor
TALİMATLAR
MADDE OKU
+ Wikimedia Commons\'a hoşgedin %1$s! Burada olduğun için mutluyuz.
+ Düzenlemeniz için teşekkürler
+ %1$s , %2$s \'de senden bahsetti
+ YOL TARİFİ
diff --git a/app/src/main/res/values-ug/error.xml b/app/src/main/res/values-ug/error.xml
index 8b2c00876..b3107c966 100644
--- a/app/src/main/res/values-ug/error.xml
+++ b/app/src/main/res/values-ug/error.xml
@@ -1,4 +1,8 @@
+
بايلىقتىن ئورتاق بەھرىمەن بولۇش ، ھالاك بولدى
رەھمەت سىزگە!
diff --git a/app/src/main/res/values-ug/strings.xml b/app/src/main/res/values-ug/strings.xml
index 373766c44..3c180fbf2 100644
--- a/app/src/main/res/values-ug/strings.xml
+++ b/app/src/main/res/values-ug/strings.xml
@@ -1,4 +1,9 @@
+
بايلىق ھەمبەھىرلەش
تەڭشەكلەر
diff --git a/app/src/main/res/values-uk/error.xml b/app/src/main/res/values-uk/error.xml
index 8efa8f8f9..c5f14b12d 100644
--- a/app/src/main/res/values-uk/error.xml
+++ b/app/src/main/res/values-uk/error.xml
@@ -1,4 +1,9 @@
+
Крах додатку
Ой. Щось пішло не так!
diff --git a/app/src/main/res/values-uk/strings.xml b/app/src/main/res/values-uk/strings.xml
index cf5aeede7..a4ed20320 100644
--- a/app/src/main/res/values-uk/strings.xml
+++ b/app/src/main/res/values-uk/strings.xml
@@ -1,4 +1,14 @@
+
Зовнішній вигляд
Загальні
@@ -45,6 +55,7 @@
Поділитися
Відкрити у браузері
Назва
+ Будь ласка, вкажіть назву цього файлу
Опис
Неможливо увійти — збій у мережі
Неможливо увійти — будь ласка, перевірте своє ім\'я користувача
@@ -60,6 +71,7 @@
Пошук категорій
Зберегти
Оновити
+ Список
GPS вимкнено на Вашому пристрої. Бажаєте увімкнути його?
Увімкнути GPS
Ще нема завантажень
@@ -87,6 +99,7 @@
Категорії
Налаштування
Зареєструватися
+ Вибрані зображення
Про програму
Додаток «Вікісховище» — це програма з відкритим кодом, яку створили отримувачі грантів та волонтери спільноти Вікімедіа. Фонд Вікімедіа не брав участі у створенні, розробці чи обслуговуванні цього додатка.
Ви можете створити новий <a href=\"https://github.com/commons-app/apps-android-commons/issues\">запит на GitHub</a>, щоб повідомити про помилки, або висловити пропозиції.
@@ -133,10 +146,19 @@
Ваші зображення допомагають освіті людей по всьому світу!
Будь ласка, завантажуйте зображення, повністю виконані або створені Вами:
Природні об\'єкти (квіти, тварини, гори) \n• Корисні об\'єкти (велосипеди, залізничні вокзали) \n• Відомі люди (Ваш мер, олімпійські атлети, яких Ви зустрічали)
+ Природні об\'єкти (квіти, тварини, гори)
+ Корисні об\'єкти (велосипеди, залізничні станції)
+ Відомі люди (ваш мер, спортсмен-олімпієць, якого ви зустріли)
Будь ласка, НЕ завантажуйте:
u2022 Селфі або фото своїх друзів \nu2022 Зображення, які Ви завантажили з інтернету \nu2022 Скріншоти патентованих програм
+ Селфі чи фото ваших друзів
+ Зображення, які ви завантажили з інтернету
+ Знімки екрану пропрієтарних програм
Приклад завантаження:
- Назва: Сіднейський оперний театр \n- Опис: Вид на Сіднейський оперний театр з боку бухти \n- Категорії: Sydney Opera House, Sydney Opera House from the west, Sydney Opera House remote views
+ Назва: Сіднейський оперний театр
+ Опис: Сіднейський оперний театр, вид через затоку
+ Категорії: Sydney Opera House from the west, Sydney Opera House remote views
Надсилайте Ваші зображення. Допоможіть оживити статті Вікіпедії!
Зображення у Вікіпедії надходять з Вікісховища.
Ваші зображення допомагають освіті людей у всьому світі.
@@ -149,8 +171,8 @@
Немає опису
Невідома ліцензія
Оновити
- Обов\'язковий дозвіл: читання зовнішньої пам\'яті. Програма не може працювати без цього.
- Обов\'язковий дозвіл: записування на зовнішнє сховище. Програма не може працювати без цього.
+ Обов\'язковий дозвіл: читання зовнішньої пам\'яті. Без цього дозволу програма не зможе отримати доступ до вашої галереї.
+ Обов\'язковий дозвіл: записування на зовнішнє сховище. Програма не зможе отримати доступ до камери без цього дозволу.
Додатковий дозвіл: отримувати поточне розташування для підказок категорій
Гаразд
Місця поблизу
@@ -163,6 +185,8 @@
Назва медіафайлу
Опис
Сюди потрапляє опис медіафайлу. Він потенційно може бути досить довгим і розтягнутися на декілька рядків. Однак ми сподіваємось, що він виглядатиме гарно.
+ Автор
+ Тут вказується ім\'я автора вибраного зображеня
Дата завантаження
Ліцензія
Координати
@@ -205,10 +229,12 @@
Вийти
Посібник
Сповіщення
+ Вибране
Місця поблизу неможливо показати без дозволу на визначення місця розташування.
опис не знайдено
Сторінка файлу у Вікісховищі
Елемент Вікіданих
+ Стаття Вікіпедії
Помилка кешування зображень
Унікальна описова назва файлу. Ви можете використовувати простий текст з пробілами. Не вказуйте розширення файлу
Будь ласка, докладно опишіть файл: де його було зроблено? що на ньому зображено? який контекст? Будь ласка, опишіть об\'єкти чи осіб. Додайте інформацію, яку не можна легко здогадатися, наприклад, пору доби для фотографії пейзажу. Якщо зображено щось незвичайне, постарайтеся пояснити, що робить його незвичайним.
@@ -220,6 +246,12 @@
Увійдіть у свій обліковий запис
Надіслати лог-файл
Надіслати лог-файл розробникам електронною поштою
+ Не знайдено браузера, щоб відкрити посилання
+ Помилка! Посилання не знайдено
+ Номінувати на вилучення
+ Цей файл номіновано на вилучення.
+
+ Переглянути в браузері
Розташування не змінено
Місцезнаходження недоступне
Потрібний дозвіл для показу списку місць поблизу
@@ -230,4 +262,21 @@
Дякуємо за правку
%1$s згадав вас на %2$s.
Перемкнути режим перегляду
+ НАПРЯМКИ
+ ВІКІДАНІ
+ ВІКІПЕДІЯ
+ ВІКІСХОВИЩЕ
+ <u>Оцініть нас</u>
+ Часті запитання
+ Пропустити інструкцію
+ Інтернет недоступний
+ Інтернет доступний
+ Помилка при отриманні сповіщення
+ Сповіщень немає
+ <u>Перекласти</u>
+ Мови
+ Виберіть мову, переклади якою ви хочете відправити
+ Виконується
+ Скасувати
+ Повторити
diff --git a/app/src/main/res/values-ur/strings.xml b/app/src/main/res/values-ur/strings.xml
index f6dda9945..4fdd67514 100644
--- a/app/src/main/res/values-ur/strings.xml
+++ b/app/src/main/res/values-ur/strings.xml
@@ -1,4 +1,11 @@
+
کامنز
ترتیبات
@@ -51,6 +58,7 @@
زمرہ جات تلاش کریں
محفوظ کریں
تازہ کریں
+ فہرست
جی پی ایس آپ کے آلے میں غیر فعال ہے۔ آپ اس کو فعال کرنا چاہینگے؟
جی پی ایس فعال کریں
ابھی تک کوئی اپلوڈ نہیں
@@ -124,4 +132,9 @@
آپ کی رائے
لاگ آوٹ
معلمی
+ ہدایات
+ عام
+ انٹرنیٹ دستیاب نہیں
+ انٹرنیٹ دستیاب
+ دوبارہ کوشش کریں
diff --git a/app/src/main/res/values-vi/error.xml b/app/src/main/res/values-vi/error.xml
index 9d513aacb..2fcd46031 100644
--- a/app/src/main/res/values-vi/error.xml
+++ b/app/src/main/res/values-vi/error.xml
@@ -1,4 +1,8 @@
+
Commons đã có sự cố
Oái, đã có trục trặc xảy ra!
diff --git a/app/src/main/res/values-vi/strings.xml b/app/src/main/res/values-vi/strings.xml
index 118bd6aee..4cff15064 100644
--- a/app/src/main/res/values-vi/strings.xml
+++ b/app/src/main/res/values-vi/strings.xml
@@ -1,4 +1,10 @@
+
Commons
Thiết lập
@@ -124,8 +130,8 @@
Không miêu tả
Giấy phép không rõ
Làm tươi
- Yêu cầu cấp phép: Đọc thiết bị lưu trữ bên ngoài. Ứng dụng cần được phép đọc thiết bị lưu trữ bên ngoài để hoạt động.
- Yêu cầu cấp phép: Ghi vào thiết bị lưu trữ bên ngoài. Ứng dụng cần được phép ghi vào thiết bị lưu trữ bên ngoài để hoạt động.
+ Yêu cầu cấp phép: Đọc thiết bị lưu trữ bên ngoài. Ứng dụng cần được phép đọc thiết bị lưu trữ bên ngoài để hoạt động.
+ Yêu cầu cấp phép: Ghi vào thiết bị lưu trữ bên ngoài. Ứng dụng cần được phép ghi vào thiết bị lưu trữ bên ngoài để hoạt động.
Tùy chọn cấp phép: Định vị hiện tại để nhận gợi ý thể loại
OK
Nơi Lân cận
diff --git a/app/src/main/res/values-xmf/error.xml b/app/src/main/res/values-xmf/error.xml
index 850dde9fd..dd0c2adaf 100644
--- a/app/src/main/res/values-xmf/error.xml
+++ b/app/src/main/res/values-xmf/error.xml
@@ -1,4 +1,7 @@
+
ვიკიოწკარუექ აკორთუ
უი. მუდგაინქ ქჷმოხვადუǃ
diff --git a/app/src/main/res/values-xmf/strings.xml b/app/src/main/res/values-xmf/strings.xml
index 8cf2a7851..b9689f9e2 100644
--- a/app/src/main/res/values-xmf/strings.xml
+++ b/app/src/main/res/values-xmf/strings.xml
@@ -1,4 +1,7 @@
+
ვიკიოწკარუე
პარამეტრეფი
diff --git a/app/src/main/res/values-yue/error.xml b/app/src/main/res/values-yue/error.xml
index 081685201..82520f7e5 100644
--- a/app/src/main/res/values-yue/error.xml
+++ b/app/src/main/res/values-yue/error.xml
@@ -1,4 +1,7 @@
+
同享壞咗
哎呀。出咗錯!
diff --git a/app/src/main/res/values-zh-rTW/error.xml b/app/src/main/res/values-zh-rTW/error.xml
index dfd90899b..de2dd34f1 100644
--- a/app/src/main/res/values-zh-rTW/error.xml
+++ b/app/src/main/res/values-zh-rTW/error.xml
@@ -1,4 +1,8 @@
+
共享資源已當機
哎呀。出了錯 !
diff --git a/app/src/main/res/values-zh-rTW/strings.xml b/app/src/main/res/values-zh-rTW/strings.xml
index c41f82d81..4966d9c08 100644
--- a/app/src/main/res/values-zh-rTW/strings.xml
+++ b/app/src/main/res/values-zh-rTW/strings.xml
@@ -1,4 +1,15 @@
+
外觀
一般
@@ -81,6 +92,7 @@
分類
設定
註冊
+ 特色圖片
關於
維基共享資源應用程式是透過維基媒體社群上的受讓人,與志願者們所建立及維護的開放原始碼應用程式。維基媒體基金會並不涉及此應用程式的建立、開發,與維護方面。
建立新的<a href=\"https://github.com/commons-app/apps-android-commons/issues\"> GitHub 問題</a>來回報程式錯誤和提出建議。
@@ -152,8 +164,8 @@
無說明
不明授權
重新整理
- 必要權限:讀取外部存儲裝置。應用程式必須此功能,才能進行正確運作。
- 必要權限:寫入外部存儲裝置。應用程式必須此功能,才能進行正確運作。
+ 必要權限:讀取外部存儲裝置。否則應用程式無法存取您的圖庫。
+ 必要權限:寫入外部存儲裝置。否則應用程式無法取用您的相機。
可有可無的權限:獲取目前的地理位置,以用於分類建議
好
附近地點
@@ -166,6 +178,8 @@
媒體標題
說明
本媒體的說明。若內容很長,請換行,會好看一些。
+ 作者
+ 特色圖片作者使用者名稱於此。
上傳日期
授權協議
座標
@@ -208,6 +222,7 @@
登出
教程
通知
+ 特色
附近地點需要位置權限才可顯示
找不到說明
共享資源檔案頁面
@@ -226,7 +241,8 @@
經由電子郵件寄送日誌檔案給開發人員
找不到可以打開 URL 的網頁瀏覽器
錯誤!查無 URL
- 刪除指定
+ 提名刪除
+ 此圖片已被提名刪除。
於瀏覽器檢視
位置無法更改。
位置無效。
@@ -242,6 +258,17 @@
維基數據
維基百科
維基共享資源
- 常見問題
+ <u>為我們評分</u>
+ <u>常見問題</u>
跳過敎程
+ 網路不可用
+ 網路可用
+ 索取通知時錯誤
+ 查無通知
+ <u>翻譯</u>
+ 語言
+ 選擇您想要提交翻譯的語言
+ 已進行
+ 取消
+ 重試
diff --git a/app/src/main/res/values-zh/error.xml b/app/src/main/res/values-zh/error.xml
index f6fbb12c1..b82eba5cc 100644
--- a/app/src/main/res/values-zh/error.xml
+++ b/app/src/main/res/values-zh/error.xml
@@ -1,4 +1,9 @@
+
共享资源已崩溃
呀。出错啦!
diff --git a/app/src/main/res/values-zh/strings.xml b/app/src/main/res/values-zh/strings.xml
index aac4e06cc..83650b408 100644
--- a/app/src/main/res/values-zh/strings.xml
+++ b/app/src/main/res/values-zh/strings.xml
@@ -1,4 +1,13 @@
+
外观
一般
@@ -59,6 +68,7 @@
搜索分类
保存
刷新
+ 列表
您的设备禁用了GPS。您是否要启用它?
启用GPS
尚无上传
@@ -80,6 +90,7 @@
分类
设置
注册
+ 特色图片
关于
维基共享资源应用程序是由维基媒体社区的受助者和志愿者创建和维护的开源应用程序。维基媒体基金会不参与该应用程序的创立,开发或维护。
创建新的<a href=\"https://github.com/commons-app/apps-android-commons/issues\">GitHub问题</a>以发送错误报告和建议。
@@ -151,8 +162,8 @@
没有说明
未知许可协议
刷新
- 需要权限:读取外部存储。应用不能在没有它的情况下运行。
- 需要权限:写入外部存储。应用不能在没有它的情况下运行。
+ 需要权限:读取外部存储。应用不能在没有它的情况下访问您的图册。
+ 需要权限:写入外部存储。应用不能在没有它的情况下访问您的图册。
可选权限:获取当前位置以提供分类建议
确定
附近地点
@@ -165,6 +176,8 @@
媒体的标题
说明
在此填写媒体的说明。这可能会相当长,并将需要包裹在多行中。我们希望它看起来很好。
+ 作者
+ 这里有特色图片作者的用户名。
上传日期
许可协议
坐标
@@ -207,10 +220,12 @@
退出
教程
通知
+ 特色
附近地点不能在没有位置权限的情况下显示
找不到描述
共享资源文件页面
维基数据项
+ 维基百科条目
缓存图片时出错
用于文件的唯一描述性标题,它将作为文件名使用。您可以使用有空格的简明语言。请不要包含文件扩展名
请尽可能详细地描述媒体:拍摄在何地?显示什么?例文是什么?请描述对象或个人。透露一些不易猜想到的信息,例如这幅风景画的具体日期时间。如果媒体显示了一些不寻常的事物,请说明为什么它显得不寻常。
@@ -225,6 +240,7 @@
找不到可以打开URL的网页浏览器
错误!找不到URL
提交删除
+ 此图片已被提交删除。
在浏览器中预览
位置没有更新。
位置不可用。
@@ -236,6 +252,21 @@
感谢您做出编辑
%1$s在%2$s提到了您。
切换视图
- 常见问题
+ 方向
+ 维基数据
+ 维基百科
+ 共享资源
+ <u>评价我们</u>
+ <u>常见问题</u>
跳过指导
+ 互联网不可用
+ 互联网可用
+ 检索通知时出错
+ 找不到通知
+ <u>翻译</u>
+ 语言
+ 选择您希望提交翻译的语言
+ 已处理
+ 取消
+ 重试
diff --git a/app/src/main/res/values/strings.xml b/app/src/main/res/values/strings.xml
index 7b3931624..28ecaeb8f 100644
--- a/app/src/main/res/values/strings.xml
+++ b/app/src/main/res/values/strings.xml
@@ -82,12 +82,13 @@
Categories
Settings
Sign Up
+ Featured Images
About
The Wikimedia Commons app is an open-source app created and maintained by grantees and volunteers of the Wikimedia community. The Wikimedia Foundation is not involved in the creation, development, or maintenance of the app.
Wikimedia Commons
Create a new <a href=\"https://github.com/commons-app/apps-android-commons/issues\">GitHub issue</a> for bug reports and suggestions.
- Privacy policy
- Credits
+ Privacy policy]]>
+ Credits]]>
About
Send Feedback (via Email)
No email client installed
@@ -154,8 +155,8 @@
No description
Unknown license
Refresh
- Required permission: Read external storage. App cannot function without this.
- Required permission: Write external storage. App cannot function without this.
+ Required permission: Read external storage. App cannot access your gallery without this.
+ Required permission: Write external storage. App cannot access your camera without this.
Optional permission: Get current location for category suggestions
OK
Nearby Places
@@ -168,6 +169,8 @@
Title of the media
Description
Description of the media goes here. This can potentially be fairly long, and will need to wrap across multiple lines. We hope it looks nice though.
+ Author
+ Featured image author user name goes here.
Uploaded date
License
Coordinates
@@ -214,6 +217,7 @@
Logout
Tutorial
Notifications
+ Featured
Nearby places cannot be displayed without location permissions
no description found
Commons file page
@@ -252,20 +256,17 @@
WIKIDATA
WIKIPEDIA
COMMONS
-
- Rate us
- FAQ
+ Rate us]]>
+ FAQ]]>
Skip Tutorial
-
Internet unavailable
Internet available
Error fetching notifications
No notifications found
-
- Translate
+ Translate]]>
Languages
Select the language that you would like to submit translations for
Proceed
Cancel
-
+ Retry
diff --git a/app/src/test/java/fr/free/nrw/commons/FileUtilsTest.java b/app/src/test/java/fr/free/nrw/commons/FileUtilsTest.java
deleted file mode 100644
index c6febc1e4..000000000
--- a/app/src/test/java/fr/free/nrw/commons/FileUtilsTest.java
+++ /dev/null
@@ -1,40 +0,0 @@
-package fr.free.nrw.commons;
-
-import org.junit.Assert;
-import org.junit.Test;
-
-import java.io.BufferedInputStream;
-import java.io.BufferedOutputStream;
-import java.io.File;
-import java.io.FileInputStream;
-import java.io.FileOutputStream;
-import java.io.IOException;
-
-import fr.free.nrw.commons.upload.FileUtils;
-
-import static org.hamcrest.CoreMatchers.is;
-
-public class FileUtilsTest {
- @Test public void copiedFileIsIdenticalToSource() throws IOException {
- File source = File.createTempFile("temp", "");
- File dest = File.createTempFile("temp", "");
- writeToFile(source, "Hello, World");
- FileUtils.copy(new FileInputStream(source), new FileOutputStream(dest));
- Assert.assertThat(getString(dest), is(getString(source)));
- }
-
- private static void writeToFile(File file, String s) throws IOException {
- BufferedOutputStream buf = new BufferedOutputStream(new FileOutputStream(file));
- buf.write(s.getBytes());
- buf.close();
- }
-
- private static String getString(File file) throws IOException {
- int size = (int) file.length();
- byte[] bytes = new byte[size];
- BufferedInputStream buf = new BufferedInputStream(new FileInputStream(file));
- buf.read(bytes, 0, bytes.length);
- buf.close();
- return new String(bytes);
- }
-}
diff --git a/app/src/test/java/fr/free/nrw/commons/LatLngTests.java b/app/src/test/java/fr/free/nrw/commons/LatLngTests.java
deleted file mode 100644
index c2fb1b159..000000000
--- a/app/src/test/java/fr/free/nrw/commons/LatLngTests.java
+++ /dev/null
@@ -1,64 +0,0 @@
-package fr.free.nrw.commons;
-
-import org.junit.Assert;
-import org.junit.Test;
-
-import fr.free.nrw.commons.location.LatLng;
-
-import static org.hamcrest.CoreMatchers.is;
-
-public class LatLngTests {
- @Test public void testZeroZero() {
- LatLng place = new LatLng(0, 0, 0);
- String prettyString = place.getPrettyCoordinateString();
- Assert.assertThat(prettyString, is("0.0 N, 0.0 E"));
- }
-
- @Test public void testAntipode() {
- LatLng place = new LatLng(0, 180, 0);
- String prettyString = place.getPrettyCoordinateString();
- Assert.assertThat(prettyString, is("0.0 N, 180.0 W"));
- }
-
- @Test public void testNorthPole() {
- LatLng place = new LatLng(90, 0, 0);
- String prettyString = place.getPrettyCoordinateString();
- Assert.assertThat(prettyString, is("90.0 N, 0.0 E"));
- }
-
- @Test public void testSouthPole() {
- LatLng place = new LatLng(-90, 0, 0);
- String prettyString = place.getPrettyCoordinateString();
- Assert.assertThat(prettyString, is("90.0 S, 0.0 E"));
- }
-
- @Test public void testLargerNumbers() {
- LatLng place = new LatLng(120, 380, 0);
- String prettyString = place.getPrettyCoordinateString();
- Assert.assertThat(prettyString, is("90.0 N, 20.0 E"));
- }
-
- @Test public void testNegativeNumbers() {
- LatLng place = new LatLng(-120, -30, 0);
- String prettyString = place.getPrettyCoordinateString();
- Assert.assertThat(prettyString, is("90.0 S, 30.0 W"));
- }
-
- @Test public void testTooBigWestValue() {
- LatLng place = new LatLng(20, -190, 0);
- String prettyString = place.getPrettyCoordinateString();
- Assert.assertThat(prettyString, is("20.0 N, 170.0 E"));
- }
-
- @Test public void testRounding() {
- LatLng place = new LatLng(0.1234567, -0.33333333, 0);
- String prettyString = place.getPrettyCoordinateString();
- Assert.assertThat(prettyString, is("0.1235 N, 0.3333 W"));
- }
-
- @Test public void testRoundingAgain() {
- LatLng place = new LatLng(-0.000001, -0.999999, 0);
- String prettyString = place.getPrettyCoordinateString();
- Assert.assertThat(prettyString, is("0.0 S, 1.0 W"));
- }
-}
diff --git a/app/src/test/java/fr/free/nrw/commons/LengthUtilsTest.java b/app/src/test/java/fr/free/nrw/commons/LengthUtilsTest.java
deleted file mode 100644
index 561f3f0e6..000000000
--- a/app/src/test/java/fr/free/nrw/commons/LengthUtilsTest.java
+++ /dev/null
@@ -1,46 +0,0 @@
-package fr.free.nrw.commons;
-
-import org.junit.Assert;
-import org.junit.Test;
-
-import fr.free.nrw.commons.location.LatLng;
-import fr.free.nrw.commons.utils.LengthUtils;
-
-import static org.hamcrest.CoreMatchers.is;
-
-public class LengthUtilsTest {
- @Test public void testZeroDistance() {
- LatLng pointA = new LatLng(0, 0, 0);
- LatLng pointB = new LatLng(0, 0, 0);
- String distance = LengthUtils.formatDistanceBetween(pointA, pointB);
- Assert.assertThat(distance, is("0m"));
- }
-
- @Test public void testOneDegreeOnEquator() {
- LatLng pointA = new LatLng(0, 0, 0);
- LatLng pointB = new LatLng(0, 1, 0);
- String distance = LengthUtils.formatDistanceBetween(pointA, pointB);
- Assert.assertThat(distance, is("111.2km"));
- }
-
- @Test public void testOneDegreeFortyFiveDegrees() {
- LatLng pointA = new LatLng(45, 0, 0);
- LatLng pointB = new LatLng(45, 1, 0);
- String distance = LengthUtils.formatDistanceBetween(pointA, pointB);
- Assert.assertThat(distance, is("78.6km"));
- }
-
- @Test public void testOneDegreeSouthPole() {
- LatLng pointA = new LatLng(-90, 0, 0);
- LatLng pointB = new LatLng(-90, 1, 0);
- String distance = LengthUtils.formatDistanceBetween(pointA, pointB);
- Assert.assertThat(distance, is("0m"));
- }
-
- @Test public void testPoleToPole() {
- LatLng pointA = new LatLng(90, 0, 0);
- LatLng pointB = new LatLng(-90, 0, 0);
- String distance = LengthUtils.formatDistanceBetween(pointA, pointB);
- Assert.assertThat(distance, is("20,015.1km"));
- }
-}
diff --git a/app/src/test/java/fr/free/nrw/commons/MediaTest.java b/app/src/test/java/fr/free/nrw/commons/MediaTest.java
deleted file mode 100644
index 4f53351ad..000000000
--- a/app/src/test/java/fr/free/nrw/commons/MediaTest.java
+++ /dev/null
@@ -1,25 +0,0 @@
-package fr.free.nrw.commons;
-
-import org.junit.Test;
-import org.junit.runner.RunWith;
-import org.robolectric.RobolectricTestRunner;
-import org.robolectric.annotation.Config;
-
-import static org.hamcrest.CoreMatchers.is;
-import static org.junit.Assert.assertThat;
-
-@RunWith(RobolectricTestRunner.class)
-@Config(constants = BuildConfig.class, sdk = 21, application = TestCommonsApplication.class)
-public class MediaTest {
- @Test
- public void displayTitleShouldStripExtension() {
- Media m = new Media("File:Example.jpg");
- assertThat(m.getDisplayTitle(), is("Example"));
- }
-
- @Test
- public void displayTitleShouldUseSpaceForUnderscore() {
- Media m = new Media("File:Example 1_2.jpg");
- assertThat(m.getDisplayTitle(), is("Example 1 2"));
- }
-}
diff --git a/app/src/test/java/fr/free/nrw/commons/NearbyControllerTest.java b/app/src/test/java/fr/free/nrw/commons/NearbyControllerTest.java
deleted file mode 100644
index 752b7404d..000000000
--- a/app/src/test/java/fr/free/nrw/commons/NearbyControllerTest.java
+++ /dev/null
@@ -1,44 +0,0 @@
-package fr.free.nrw.commons;
-
-import org.junit.Test;
-import org.junit.runner.RunWith;
-import org.robolectric.RobolectricTestRunner;
-import org.robolectric.RuntimeEnvironment;
-import org.robolectric.annotation.Config;
-
-import java.util.ArrayList;
-import java.util.List;
-
-import fr.free.nrw.commons.location.LatLng;
-import fr.free.nrw.commons.nearby.NearbyBaseMarker;
-import fr.free.nrw.commons.nearby.Place;
-
-import static fr.free.nrw.commons.nearby.NearbyController.loadAttractionsFromLocationToBaseMarkerOptions;
-import static org.hamcrest.CoreMatchers.is;
-import static org.junit.Assert.assertThat;
-
-@RunWith(RobolectricTestRunner.class)
-@Config(constants = BuildConfig.class, sdk = 21, application = TestCommonsApplication.class)
-public class NearbyControllerTest {
-
- @Test
- public void testNullAttractions() {
- LatLng location = new LatLng(0, 0, 0);
-
- List options = loadAttractionsFromLocationToBaseMarkerOptions(
- location, null, RuntimeEnvironment.application);
-
- assertThat(options.size(), is(0));
- }
-
- @Test
- public void testEmptyList() {
- LatLng location = new LatLng(0, 0, 0);
- List emptyList = new ArrayList<>();
-
- List options = loadAttractionsFromLocationToBaseMarkerOptions(
- location, emptyList, RuntimeEnvironment.application);
-
- assertThat(options.size(), is(0));
- }
-}
diff --git a/app/src/test/java/fr/free/nrw/commons/PageTitleTest.java b/app/src/test/java/fr/free/nrw/commons/PageTitleTest.java
deleted file mode 100644
index 16336b1b0..000000000
--- a/app/src/test/java/fr/free/nrw/commons/PageTitleTest.java
+++ /dev/null
@@ -1,70 +0,0 @@
-package fr.free.nrw.commons;
-
-import org.junit.Test;
-import org.junit.runner.RunWith;
-import org.robolectric.RobolectricTestRunner;
-import org.robolectric.annotation.Config;
-
-import java.net.URLEncoder;
-
-import static org.hamcrest.CoreMatchers.is;
-import static org.junit.Assert.assertThat;
-
-@RunWith(RobolectricTestRunner.class)
-@Config(constants = BuildConfig.class, sdk = 21, application = TestCommonsApplication.class)
-public class PageTitleTest {
- @Test
- public void displayTextShouldNotBeUnderscored() {
- assertThat(new PageTitle("Ex_1 ").getDisplayText(),
- is("Ex 1"));
- }
-
- @Test
- public void moreThanTwoColons() {
- assertThat(new PageTitle("File:sample:a.jpg").getPrefixedText(),
- is("File:Sample:a.jpg"));
- }
-
- @Test
- public void getTextShouldReturnWithoutNamespace() {
- assertThat(new PageTitle("File:sample.jpg").getText(),
- is("Sample.jpg"));
- }
-
-
- @Test
- public void capitalizeNameAfterNamespace() {
- assertThat(new PageTitle("File:sample.jpg").getPrefixedText(),
- is("File:Sample.jpg"));
- }
-
- @Test
- public void prefixedTextShouldBeUnderscored() {
- assertThat(new PageTitle("Ex 1 ").getPrefixedText(),
- is("Ex_1"));
- }
-
- @Test
- public void getMobileUriForTest() {
- assertThat(new PageTitle("Test").getMobileUri().toString(),
- is(BuildConfig.MOBILE_HOME_URL + "Test"));
- }
-
- @Test
- public void spaceBecomesUnderscoreInUri() {
- assertThat(new PageTitle("File:Ex 1.jpg").getCanonicalUri().toString(),
- is(BuildConfig.HOME_URL + "File:Ex_1.jpg"));
- }
-
- @Test
- public void leaveSubpageNamesUncapitalizedInUri() {
- assertThat(new PageTitle("User:Ex/subpage").getCanonicalUri().toString(),
- is(BuildConfig.HOME_URL + "User:Ex/subpage"));
- }
-
- @Test
- public void unicodeUri() throws Throwable {
- assertThat(new PageTitle("User:例").getCanonicalUri().toString(),
- is(BuildConfig.HOME_URL + "User:" + URLEncoder.encode("例", "utf-8")));
- }
-}
diff --git a/app/src/test/java/fr/free/nrw/commons/TestCommonsApplication.java b/app/src/test/java/fr/free/nrw/commons/TestCommonsApplication.java
deleted file mode 100644
index 9f7bc6184..000000000
--- a/app/src/test/java/fr/free/nrw/commons/TestCommonsApplication.java
+++ /dev/null
@@ -1,181 +0,0 @@
-package fr.free.nrw.commons;
-
-import android.content.Context;
-import android.content.SharedPreferences;
-import android.support.v4.util.LruCache;
-
-import com.squareup.leakcanary.RefWatcher;
-
-import org.mockito.Mock;
-import org.mockito.MockitoAnnotations;
-
-import javax.inject.Named;
-
-import dagger.Provides;
-import fr.free.nrw.commons.auth.AccountUtil;
-import fr.free.nrw.commons.auth.SessionManager;
-import fr.free.nrw.commons.caching.CacheController;
-import fr.free.nrw.commons.data.DBOpenHelper;
-import fr.free.nrw.commons.di.CommonsApplicationComponent;
-import fr.free.nrw.commons.di.CommonsApplicationModule;
-import fr.free.nrw.commons.di.DaggerCommonsApplicationComponent;
-import fr.free.nrw.commons.location.LocationServiceManager;
-import fr.free.nrw.commons.mwapi.MediaWikiApi;
-import fr.free.nrw.commons.nearby.NearbyPlaces;
-import fr.free.nrw.commons.upload.UploadController;
-
-public class TestCommonsApplication extends CommonsApplication {
-
- CommonsApplicationComponent mockApplicationComponent;
-
- @Mock
- CommonsApplicationModule commonsApplicationModule;
- @Mock
- AccountUtil accountUtil;
- @Mock
- SharedPreferences appSharedPreferences;
- @Mock
- SharedPreferences defaultSharedPreferences;
- @Mock
- SharedPreferences otherSharedPreferences;
- @Mock
- UploadController uploadController;
- @Mock
- SessionManager sessionManager;
- @Mock
- MediaWikiApi mediaWikiApi;
- @Mock
- LocationServiceManager locationServiceManager;
- @Mock
- CacheController cacheController;
- @Mock
- DBOpenHelper dbOpenHelper;
- @Mock
- NearbyPlaces nearbyPlaces;
- @Mock
- LruCache lruCache;
-
- @Override
- public void onCreate() {
- MockitoAnnotations.initMocks(this);
- if (mockApplicationComponent == null) {
- mockApplicationComponent = DaggerCommonsApplicationComponent.builder()
- .appModule(new CommonsApplicationModule(this) {
- @Override
- public AccountUtil providesAccountUtil(Context context) {
- return accountUtil;
- }
-
- @Override
- public SharedPreferences providesApplicationSharedPreferences(Context context) {
- return appSharedPreferences;
- }
-
- @Override
- public SharedPreferences providesDefaultSharedPreferences(Context context) {
- return defaultSharedPreferences;
- }
-
- @Override
- public SharedPreferences providesOtherSharedPreferences(Context context) {
- return otherSharedPreferences;
- }
-
- @Override
- public UploadController providesUploadController(SessionManager sessionManager, SharedPreferences sharedPreferences, Context context) {
- return uploadController;
- }
-
- @Override
- public SessionManager providesSessionManager(Context context, MediaWikiApi mediaWikiApi, SharedPreferences sharedPreferences) {
- return sessionManager;
- }
-
- @Override
- public MediaWikiApi provideMediaWikiApi(Context context, SharedPreferences sharedPreferences) {
- return mediaWikiApi;
- }
-
- @Override
- public LocationServiceManager provideLocationServiceManager(Context context) {
- return locationServiceManager;
- }
-
- @Override
- public CacheController provideCacheController() {
- return cacheController;
- }
-
- @Override
- public DBOpenHelper provideDBOpenHelper(Context context) {
- return dbOpenHelper;
- }
-
- @Override
- public NearbyPlaces provideNearbyPlaces() {
- return nearbyPlaces;
- }
-
- @Override
- public LruCache provideLruCache() {
- return lruCache;
- }
- }).build();
- }
- super.onCreate();
- }
-
- @Override
- protected RefWatcher setupLeakCanary() {
- // No leakcanary in unit tests.
- return RefWatcher.DISABLED;
- }
-
- public AccountUtil getAccountUtil() {
- return accountUtil;
- }
-
- public SharedPreferences getAppSharedPreferences() {
- return appSharedPreferences;
- }
-
- public SharedPreferences getDefaultSharedPreferences() {
- return defaultSharedPreferences;
- }
-
- public SharedPreferences getOtherSharedPreferences() {
- return otherSharedPreferences;
- }
-
- public UploadController getUploadController() {
- return uploadController;
- }
-
- public SessionManager getSessionManager() {
- return sessionManager;
- }
-
- public MediaWikiApi getMediaWikiApi() {
- return mediaWikiApi;
- }
-
- public LocationServiceManager getLocationServiceManager() {
- return locationServiceManager;
- }
-
- public CacheController getCacheController() {
- return cacheController;
- }
-
- public DBOpenHelper getDbOpenHelper() {
- return dbOpenHelper;
- }
-
- public NearbyPlaces getNearbyPlaces() {
- return nearbyPlaces;
- }
-
- public LruCache getLruCache() {
- return lruCache;
- }
-}
diff --git a/app/src/test/java/fr/free/nrw/commons/UtilsFixExtensionTest.java b/app/src/test/java/fr/free/nrw/commons/UtilsFixExtensionTest.java
deleted file mode 100644
index 186f30df9..000000000
--- a/app/src/test/java/fr/free/nrw/commons/UtilsFixExtensionTest.java
+++ /dev/null
@@ -1,57 +0,0 @@
-package fr.free.nrw.commons;
-
-import org.junit.Assert;
-import org.junit.Test;
-
-import static org.hamcrest.CoreMatchers.is;
-
-public class UtilsFixExtensionTest {
-
- @Test public void jpegResultsInJpg() {
- Assert.assertThat(Utils.fixExtension("SampleFile.jpeg", "jpeg"), is("SampleFile.jpg"));
- }
-
- @Test public void capitalJpegWithNoHintResultsInJpg() {
- Assert.assertThat(Utils.fixExtension("SampleFile.JPEG", null), is("SampleFile.jpg"));
- }
-
- @Test public void jpegWithBogusHintResultsInJpg() {
- Assert.assertThat(Utils.fixExtension("SampleFile.jpeg", null), is("SampleFile.jpg"));
- }
-
- @Test public void jpegToCapitalJpegResultsInJpg() {
- Assert.assertThat(Utils.fixExtension("SampleFile.jpeg", "JPEG"), is("SampleFile.jpg"));
- }
-
- @Test public void jpgToJpegResultsInJpg() {
- Assert.assertThat(Utils.fixExtension("SampleFile.jpg", "jpeg"), is("SampleFile.jpg"));
- }
-
- @Test public void jpegToJpgResultsInJpg() {
- Assert.assertThat(Utils.fixExtension("SampleFile.jpeg", "jpg"), is("SampleFile.jpg"));
- }
-
- @Test public void jpgRemainsJpg() {
- Assert.assertThat(Utils.fixExtension("SampleFile.jpg", "jpg"), is("SampleFile.jpg"));
- }
-
- @Test public void pngRemainsPng() {
- Assert.assertThat(Utils.fixExtension("SampleFile.png", "png"), is("SampleFile.png"));
- }
-
- @Test public void jpgHintResultsInJpg() {
- Assert.assertThat(Utils.fixExtension("SampleFile", "jpg"), is("SampleFile.jpg"));
- }
-
- @Test public void jpegHintResultsInJpg() {
- Assert.assertThat(Utils.fixExtension("SampleFile", "jpeg"), is("SampleFile.jpg"));
- }
-
- @Test public void dotLessJpgToJpgResultsInJpg() {
- Assert.assertThat(Utils.fixExtension("SAMPLEjpg", "jpg"), is("SAMPLEjpg.jpg"));
- }
-
- @Test public void inWordJpegToJpgResultsInJpg() {
- Assert.assertThat(Utils.fixExtension("X.jpeg.SAMPLE", "jpg"),is("X.jpeg.SAMPLE.jpg"));
- }
-}
diff --git a/app/src/test/java/fr/free/nrw/commons/category/CategoryDaoTest.java b/app/src/test/java/fr/free/nrw/commons/category/CategoryDaoTest.java
deleted file mode 100644
index 1cf0c338b..000000000
--- a/app/src/test/java/fr/free/nrw/commons/category/CategoryDaoTest.java
+++ /dev/null
@@ -1,294 +0,0 @@
-package fr.free.nrw.commons.category;
-
-import android.content.ContentProviderClient;
-import android.content.ContentValues;
-import android.database.Cursor;
-import android.database.MatrixCursor;
-import android.database.sqlite.SQLiteDatabase;
-import android.net.Uri;
-import android.os.RemoteException;
-import android.support.annotation.NonNull;
-
-import org.junit.Before;
-import org.junit.Test;
-import org.junit.runner.RunWith;
-import org.mockito.ArgumentCaptor;
-import org.mockito.Captor;
-import org.mockito.InOrder;
-import org.mockito.Mock;
-import org.mockito.Mockito;
-import org.mockito.MockitoAnnotations;
-import org.robolectric.RobolectricTestRunner;
-import org.robolectric.annotation.Config;
-
-import java.util.Arrays;
-import java.util.Date;
-import java.util.List;
-
-import fr.free.nrw.commons.BuildConfig;
-import fr.free.nrw.commons.TestCommonsApplication;
-import fr.free.nrw.commons.category.CategoryDao.Table;
-
-import static fr.free.nrw.commons.category.CategoryContentProvider.BASE_URI;
-import static fr.free.nrw.commons.category.CategoryContentProvider.uriForId;
-import static junit.framework.Assert.assertEquals;
-import static junit.framework.Assert.assertNull;
-import static junit.framework.Assert.assertTrue;
-import static org.mockito.Matchers.any;
-import static org.mockito.Matchers.anyString;
-import static org.mockito.Matchers.eq;
-import static org.mockito.Matchers.isA;
-import static org.mockito.Matchers.isNull;
-import static org.mockito.Mockito.mock;
-import static org.mockito.Mockito.verify;
-import static org.mockito.Mockito.verifyZeroInteractions;
-import static org.mockito.Mockito.when;
-
-@RunWith(RobolectricTestRunner.class)
-@Config(constants = BuildConfig.class, sdk = 21, application = TestCommonsApplication.class)
-public class CategoryDaoTest {
-
- @Mock
- private ContentProviderClient client;
- @Mock
- private SQLiteDatabase database;
- @Captor
- private ArgumentCaptor captor;
- @Captor
- private ArgumentCaptor queryCaptor;
-
- private CategoryDao testObject;
-
- @Before
- public void setUp() throws Exception {
- MockitoAnnotations.initMocks(this);
- testObject = new CategoryDao(() -> client);
- }
-
- @Test
- public void createTable() {
- Table.onCreate(database);
- verify(database).execSQL(Table.CREATE_TABLE_STATEMENT);
- }
-
- @Test
- public void deleteTable() {
- Table.onDelete(database);
- InOrder inOrder = Mockito.inOrder(database);
- inOrder.verify(database).execSQL(Table.DROP_TABLE_STATEMENT);
- inOrder.verify(database).execSQL(Table.CREATE_TABLE_STATEMENT);
- }
-
- @Test
- public void migrateTableVersionFrom_v1_to_v2() {
- Table.onUpdate(database, 1, 2);
- // Table didnt exist before v5
- verifyZeroInteractions(database);
- }
-
- @Test
- public void migrateTableVersionFrom_v2_to_v3() {
- Table.onUpdate(database, 2, 3);
- // Table didnt exist before v5
- verifyZeroInteractions(database);
- }
-
- @Test
- public void migrateTableVersionFrom_v3_to_v4() {
- Table.onUpdate(database, 3, 4);
- // Table didnt exist before v5
- verifyZeroInteractions(database);
- }
-
- @Test
- public void migrateTableVersionFrom_v4_to_v5() {
- Table.onUpdate(database, 4, 5);
- verify(database).execSQL(Table.CREATE_TABLE_STATEMENT);
- }
-
- @Test
- public void migrateTableVersionFrom_v5_to_v6() {
- Table.onUpdate(database, 5, 6);
- // Table didnt change in version 6
- verifyZeroInteractions(database);
- }
-
- @Test
- public void createFromCursor() {
- MatrixCursor cursor = createCursor(1);
- cursor.moveToFirst();
- Category category = testObject.fromCursor(cursor);
-
- assertEquals(uriForId(1), category.getContentUri());
- assertEquals("foo", category.getName());
- assertEquals(123, category.getLastUsed().getTime());
- assertEquals(2, category.getTimesUsed());
- }
-
- @Test
- public void saveExistingCategory() throws Exception {
- MatrixCursor cursor = createCursor(1);
- cursor.moveToFirst();
- Category category = testObject.fromCursor(cursor);
-
- testObject.save(category);
-
- verify(client).update(eq(category.getContentUri()), captor.capture(), isNull(String.class), isNull(String[].class));
- ContentValues cv = captor.getValue();
- assertEquals(3, cv.size());
- assertEquals(category.getName(), cv.getAsString(Table.COLUMN_NAME));
- assertEquals(category.getLastUsed().getTime(), cv.getAsLong(Table.COLUMN_LAST_USED).longValue());
- assertEquals(category.getTimesUsed(), cv.getAsInteger(Table.COLUMN_TIMES_USED).intValue());
- }
-
- @Test
- public void saveNewCategory() throws Exception {
- Uri contentUri = CategoryContentProvider.uriForId(111);
- when(client.insert(isA(Uri.class), isA(ContentValues.class))).thenReturn(contentUri);
- Category category = new Category(null, "foo", new Date(234L), 1);
-
- testObject.save(category);
-
- verify(client).insert(eq(BASE_URI), captor.capture());
- ContentValues cv = captor.getValue();
- assertEquals(3, cv.size());
- assertEquals(category.getName(), cv.getAsString(Table.COLUMN_NAME));
- assertEquals(category.getLastUsed().getTime(), cv.getAsLong(Table.COLUMN_LAST_USED).longValue());
- assertEquals(category.getTimesUsed(), cv.getAsInteger(Table.COLUMN_TIMES_USED).intValue());
- assertEquals(contentUri, category.getContentUri());
- }
-
- @Test(expected = RuntimeException.class)
- public void testSaveTranslatesRemoteExceptions() throws Exception {
- when(client.insert(isA(Uri.class), isA(ContentValues.class))).thenThrow(new RemoteException(""));
- testObject.save(new Category());
- }
-
- @Test
- public void whenTheresNoDataFindReturnsNull_nullCursor() throws Exception {
- when(client.query(any(), any(), anyString(), any(), anyString())).thenReturn(null);
-
- assertNull(testObject.find("foo"));
- }
-
- @Test
- public void whenTheresNoDataFindReturnsNull_emptyCursor() throws Exception {
- when(client.query(any(), any(), anyString(), any(), anyString())).thenReturn(createCursor(0));
-
- assertNull(testObject.find("foo"));
- }
-
- @Test
- public void cursorsAreClosedAfterUse() throws Exception {
- Cursor mockCursor = mock(Cursor.class);
- when(client.query(any(), any(), anyString(), any(), anyString())).thenReturn(mockCursor);
- when(mockCursor.moveToFirst()).thenReturn(false);
-
- testObject.find("foo");
-
- verify(mockCursor).close();
- }
-
- @Test
- public void findCategory() throws Exception {
- when(client.query(any(), any(), anyString(), any(), anyString())).thenReturn(createCursor(1));
-
- Category category = testObject.find("foo");
-
- assertEquals(uriForId(1), category.getContentUri());
- assertEquals("foo", category.getName());
- assertEquals(123, category.getLastUsed().getTime());
- assertEquals(2, category.getTimesUsed());
-
- verify(client).query(
- eq(BASE_URI),
- eq(Table.ALL_FIELDS),
- eq(Table.COLUMN_NAME + "=?"),
- queryCaptor.capture(),
- isNull(String.class)
- );
- assertEquals("foo", queryCaptor.getValue()[0]);
- }
-
- @Test(expected = RuntimeException.class)
- public void findCategoryTranslatesExceptions() throws Exception {
- when(client.query(any(), any(), anyString(), any(), anyString())).thenThrow(new RemoteException(""));
- testObject.find("foo");
- }
-
- @Test(expected = RuntimeException.class)
- public void recentCategoriesTranslatesExceptions() throws Exception {
- when(client.query(any(), any(), anyString(), any(), anyString())).thenThrow(new RemoteException(""));
- testObject.recentCategories(1);
- }
-
- @Test
- public void recentCategoriesReturnsEmptyList_nullCursor() throws Exception {
- when(client.query(any(), any(), anyString(), any(), anyString())).thenReturn(null);
-
- assertTrue(testObject.recentCategories(1).isEmpty());
- }
-
- @Test
- public void recentCategoriesReturnsEmptyList_emptyCursor() throws Exception {
- when(client.query(any(), any(), anyString(), any(), anyString())).thenReturn(createCursor(0));
-
- assertTrue(testObject.recentCategories(1).isEmpty());
- }
-
- @Test
- public void cursorsAreClosedAfterRecentCategoriesQuery() throws Exception {
- Cursor mockCursor = mock(Cursor.class);
- when(client.query(any(), any(), anyString(), any(), anyString())).thenReturn(mockCursor);
- when(mockCursor.moveToFirst()).thenReturn(false);
-
- testObject.recentCategories(1);
-
- verify(mockCursor).close();
- }
-
- @Test
- public void recentCategoriesReturnsLessThanLimit() throws Exception {
- when(client.query(any(), any(), anyString(), any(), anyString())).thenReturn(createCursor(1));
-
- List result = testObject.recentCategories(10);
-
- assertEquals(1, result.size());
- assertEquals("foo", result.get(0));
-
- verify(client).query(
- eq(BASE_URI),
- eq(Table.ALL_FIELDS),
- isNull(String.class),
- queryCaptor.capture(),
- eq(Table.COLUMN_LAST_USED + " DESC")
- );
- assertEquals(0, queryCaptor.getValue().length);
- }
-
- @Test
- public void recentCategoriesHomorsLimit() throws Exception {
- when(client.query(any(), any(), anyString(), any(), anyString())).thenReturn(createCursor(10));
-
- List result = testObject.recentCategories(5);
-
- assertEquals(5, result.size());
- }
-
- @NonNull
- private MatrixCursor createCursor(int rowCount) {
- MatrixCursor cursor = new MatrixCursor(new String[]{
- Table.COLUMN_ID,
- Table.COLUMN_NAME,
- Table.COLUMN_LAST_USED,
- Table.COLUMN_TIMES_USED
- }, rowCount);
-
- for (int i = 0; i < rowCount; i++) {
- cursor.addRow(Arrays.asList("1", "foo", "123", "2"));
- }
-
- return cursor;
- }
-
-}
\ No newline at end of file
diff --git a/app/src/test/java/fr/free/nrw/commons/contributions/ContributionDaoTest.java b/app/src/test/java/fr/free/nrw/commons/contributions/ContributionDaoTest.java
deleted file mode 100644
index 15e37e640..000000000
--- a/app/src/test/java/fr/free/nrw/commons/contributions/ContributionDaoTest.java
+++ /dev/null
@@ -1,370 +0,0 @@
-package fr.free.nrw.commons.contributions;
-
-import android.content.ContentProviderClient;
-import android.content.ContentValues;
-import android.database.MatrixCursor;
-import android.database.sqlite.SQLiteDatabase;
-import android.net.Uri;
-import android.os.RemoteException;
-import android.support.annotation.NonNull;
-
-import org.junit.Before;
-import org.junit.Test;
-import org.junit.runner.RunWith;
-import org.mockito.ArgumentCaptor;
-import org.mockito.Captor;
-import org.mockito.InOrder;
-import org.mockito.Mock;
-import org.mockito.Mockito;
-import org.mockito.MockitoAnnotations;
-import org.robolectric.RobolectricTestRunner;
-import org.robolectric.annotation.Config;
-
-import java.util.Arrays;
-import java.util.Date;
-
-import fr.free.nrw.commons.BuildConfig;
-import fr.free.nrw.commons.TestCommonsApplication;
-import fr.free.nrw.commons.Utils;
-
-import static fr.free.nrw.commons.contributions.Contribution.SOURCE_CAMERA;
-import static fr.free.nrw.commons.contributions.Contribution.SOURCE_GALLERY;
-import static fr.free.nrw.commons.contributions.Contribution.STATE_COMPLETED;
-import static fr.free.nrw.commons.contributions.Contribution.STATE_QUEUED;
-import static fr.free.nrw.commons.contributions.ContributionDao.Table;
-import static fr.free.nrw.commons.contributions.ContributionsContentProvider.BASE_URI;
-import static fr.free.nrw.commons.contributions.ContributionsContentProvider.uriForId;
-import static org.junit.Assert.assertEquals;
-import static org.junit.Assert.assertFalse;
-import static org.junit.Assert.assertNull;
-import static org.junit.Assert.assertTrue;
-import static org.mockito.Matchers.any;
-import static org.mockito.Matchers.eq;
-import static org.mockito.Matchers.isA;
-import static org.mockito.Matchers.isNull;
-import static org.mockito.Mockito.verify;
-import static org.mockito.Mockito.verifyZeroInteractions;
-import static org.mockito.Mockito.when;
-
-@RunWith(RobolectricTestRunner.class)
-@Config(constants = BuildConfig.class, sdk = 21, application = TestCommonsApplication.class)
-public class ContributionDaoTest {
-
- private static final String LOCAL_URI = "http://example.com/";
- @Mock
- private ContentProviderClient client;
- @Mock
- private SQLiteDatabase database;
- @Captor
- private ArgumentCaptor captor;
-
- private Uri contentUri;
- private ContributionDao testObject;
-
- @Before
- public void setUp() {
- MockitoAnnotations.initMocks(this);
-
- contentUri = uriForId(111);
-
- testObject = new ContributionDao(() -> client);
- }
-
- @Test
- public void createTable() {
- Table.onCreate(database);
- verify(database).execSQL(Table.CREATE_TABLE_STATEMENT);
- }
-
- @Test
- public void deleteTable() {
- Table.onDelete(database);
-
- InOrder inOrder = Mockito.inOrder(database);
- inOrder.verify(database).execSQL(Table.DROP_TABLE_STATEMENT);
- inOrder.verify(database).execSQL(Table.CREATE_TABLE_STATEMENT);
- }
-
- @Test
- public void upgradeDatabase_v1_to_v2() {
- Table.onUpdate(database, 1, 2);
-
- InOrder inOrder = Mockito.inOrder(database);
- inOrder.verify(database).execSQL(Table.ADD_DESCRIPTION_FIELD);
- inOrder.verify(database).execSQL(Table.ADD_CREATOR_FIELD);
- }
-
- @Test
- public void upgradeDatabase_v2_to_v3() {
- Table.onUpdate(database, 2, 3);
-
- InOrder inOrder = Mockito.inOrder(database);
- inOrder.verify(database).execSQL(Table.ADD_MULTIPLE_FIELD);
- inOrder.verify(database).execSQL(Table.SET_DEFAULT_MULTIPLE);
- }
-
- @Test
- public void upgradeDatabase_v3_to_v4() {
- Table.onUpdate(database, 3, 4);
-
- // No changes
- verifyZeroInteractions(database);
- }
-
- @Test
- public void upgradeDatabase_v4_to_v5() {
- Table.onUpdate(database, 4, 5);
-
- // No changes
- verifyZeroInteractions(database);
- }
-
- @Test
- public void upgradeDatabase_v5_to_v6() {
- Table.onUpdate(database, 5, 6);
-
- InOrder inOrder = Mockito.inOrder(database);
- inOrder.verify(database).execSQL(Table.ADD_WIDTH_FIELD);
- inOrder.verify(database).execSQL(Table.SET_DEFAULT_WIDTH);
- inOrder.verify(database).execSQL(Table.ADD_HEIGHT_FIELD);
- inOrder.verify(database).execSQL(Table.SET_DEFAULT_HEIGHT);
- inOrder.verify(database).execSQL(Table.ADD_LICENSE_FIELD);
- inOrder.verify(database).execSQL(Table.SET_DEFAULT_LICENSE);
- }
-
- @Test
- public void saveNewContribution_nonNullFields() throws Exception {
- when(client.insert(isA(Uri.class), isA(ContentValues.class))).thenReturn(contentUri);
- Contribution contribution = createContribution(true, null, null, null, null);
-
- testObject.save(contribution);
-
- assertEquals(contentUri, contribution.getContentUri());
- verify(client).insert(eq(BASE_URI), captor.capture());
- ContentValues cv = captor.getValue();
-
- // Long fields
- assertEquals(222L, cv.getAsLong(Table.COLUMN_LENGTH).longValue());
- assertEquals(321L, cv.getAsLong(Table.COLUMN_TIMESTAMP).longValue());
- assertEquals(333L, cv.getAsLong(Table.COLUMN_TRANSFERRED).longValue());
-
- // Integer fields
- assertEquals(STATE_COMPLETED, cv.getAsInteger(Table.COLUMN_STATE).intValue());
- assertEquals(640, cv.getAsInteger(Table.COLUMN_WIDTH).intValue());
- assertEquals(480, cv.getAsInteger(Table.COLUMN_HEIGHT).intValue());
-
- // String fields
- assertEquals(SOURCE_CAMERA, cv.getAsString(Table.COLUMN_SOURCE));
- assertEquals("desc", cv.getAsString(Table.COLUMN_DESCRIPTION));
- assertEquals("create", cv.getAsString(Table.COLUMN_CREATOR));
- assertEquals("007", cv.getAsString(Table.COLUMN_LICENSE));
- }
-
- @Test
- public void saveNewContribution_nullableFieldsAreNull() throws Exception {
- when(client.insert(isA(Uri.class), isA(ContentValues.class))).thenReturn(contentUri);
- Contribution contribution = createContribution(true, null, null, null, null);
-
- testObject.save(contribution);
-
- assertEquals(contentUri, contribution.getContentUri());
- verify(client).insert(eq(BASE_URI), captor.capture());
- ContentValues cv = captor.getValue();
-
- // Nullable fields are absent if null
- assertFalse(cv.containsKey(Table.COLUMN_LOCAL_URI));
- assertFalse(cv.containsKey(Table.COLUMN_IMAGE_URL));
- assertFalse(cv.containsKey(Table.COLUMN_UPLOADED));
- }
-
- @Test
- public void saveNewContribution_nullableImageUrlUsesFileAsBackup() throws Exception {
- when(client.insert(isA(Uri.class), isA(ContentValues.class))).thenReturn(contentUri);
- Contribution contribution = createContribution(true, null, null, null, "file");
-
- testObject.save(contribution);
-
- assertEquals(contentUri, contribution.getContentUri());
- verify(client).insert(eq(BASE_URI), captor.capture());
- ContentValues cv = captor.getValue();
-
- // Nullable fields are absent if null
- assertFalse(cv.containsKey(Table.COLUMN_LOCAL_URI));
- assertFalse(cv.containsKey(Table.COLUMN_UPLOADED));
-
- assertEquals(Utils.makeThumbBaseUrl("file"), cv.getAsString(Table.COLUMN_IMAGE_URL));
- }
-
- @Test
- public void saveNewContribution_nullableFieldsAreNonNull() throws Exception {
- when(client.insert(isA(Uri.class), isA(ContentValues.class))).thenReturn(contentUri);
- Contribution contribution = createContribution(true, Uri.parse(LOCAL_URI),
- "image", new Date(456L), null);
-
- testObject.save(contribution);
-
- assertEquals(contentUri, contribution.getContentUri());
- verify(client).insert(eq(BASE_URI), captor.capture());
- ContentValues cv = captor.getValue();
-
- assertEquals(LOCAL_URI, cv.getAsString(Table.COLUMN_LOCAL_URI));
- assertEquals("image", cv.getAsString(Table.COLUMN_IMAGE_URL));
- assertEquals(456L, cv.getAsLong(Table.COLUMN_UPLOADED).longValue());
- }
-
- @Test
- public void saveNewContribution_booleanEncodesTrue() throws Exception {
- when(client.insert(isA(Uri.class), isA(ContentValues.class))).thenReturn(contentUri);
- Contribution contribution = createContribution(true, null, null, null, null);
-
- testObject.save(contribution);
-
- assertEquals(contentUri, contribution.getContentUri());
- verify(client).insert(eq(BASE_URI), captor.capture());
- ContentValues cv = captor.getValue();
-
- // Boolean true --> 1 for ths encoding scheme
- assertEquals("Boolean true should be encoded as 1", 1,
- cv.getAsInteger(Table.COLUMN_MULTIPLE).intValue());
- }
-
- @Test
- public void saveNewContribution_booleanEncodesFalse() throws Exception {
- when(client.insert(isA(Uri.class), isA(ContentValues.class))).thenReturn(contentUri);
- Contribution contribution = createContribution(false, null, null, null, null);
-
- testObject.save(contribution);
-
- assertEquals(contentUri, contribution.getContentUri());
- verify(client).insert(eq(BASE_URI), captor.capture());
- ContentValues cv = captor.getValue();
-
- // Boolean true --> 1 for ths encoding scheme
- assertEquals("Boolean false should be encoded as 0", 0,
- cv.getAsInteger(Table.COLUMN_MULTIPLE).intValue());
- }
-
- @Test
- public void saveExistingContribution() throws Exception {
- Contribution contribution = createContribution(false, null, null, null, null);
- contribution.setContentUri(contentUri);
-
- testObject.save(contribution);
-
- verify(client).update(eq(contentUri), isA(ContentValues.class), isNull(String.class), isNull(String[].class));
- }
-
- @Test(expected = RuntimeException.class)
- public void saveTranslatesExceptions() throws Exception {
- when(client.insert(isA(Uri.class), isA(ContentValues.class))).thenThrow(new RemoteException(""));
-
- testObject.save(createContribution(false, null, null, null, null));
- }
-
- @Test(expected = RuntimeException.class)
- public void deleteTranslatesExceptions() throws Exception {
- when(client.delete(isA(Uri.class), any(), any())).thenThrow(new RemoteException(""));
-
- Contribution contribution = createContribution(false, null, null, null, null);
- contribution.setContentUri(contentUri);
- testObject.delete(contribution);
- }
-
- @Test(expected = RuntimeException.class)
- public void exceptionThrownWhenAttemptingToDeleteUnsavedContribution() {
- testObject.delete(createContribution(false, null, null, null, null));
- }
-
- @Test
- public void deleteExistingContribution() throws Exception {
- Contribution contribution = createContribution(false, null, null, null, null);
- contribution.setContentUri(contentUri);
-
- testObject.delete(contribution);
-
- verify(client).delete(eq(contentUri), isNull(String.class), isNull(String[].class));
- }
-
- @Test
- public void createFromCursor() {
- long created = 321L;
- long uploaded = 456L;
- MatrixCursor mc = createCursor(created, uploaded, false, LOCAL_URI);
-
- Contribution c = testObject.fromCursor(mc);
-
- assertEquals(uriForId(111), c.getContentUri());
- assertEquals("file", c.getFilename());
- assertEquals(LOCAL_URI, c.getLocalUri().toString());
- assertEquals("image", c.getImageUrl());
- assertEquals(created, c.getTimestamp().getTime());
- assertEquals(created, c.getDateCreated().getTime());
- assertEquals(STATE_QUEUED, c.getState());
- assertEquals(222L, c.getDataLength());
- assertEquals(uploaded, c.getDateUploaded().getTime());
- assertEquals(88L, c.getTransferred());
- assertEquals(SOURCE_GALLERY, c.getSource());
- assertEquals("desc", c.getDescription());
- assertEquals("create", c.getCreator());
- assertEquals(640, c.getWidth());
- assertEquals(480, c.getHeight());
- assertEquals("007", c.getLicense());
- }
-
- @Test
- public void createFromCursor_nullableTimestamps() {
- MatrixCursor mc = createCursor(0L, 0L, false, LOCAL_URI);
-
- Contribution c = testObject.fromCursor(mc);
-
- assertNull(c.getTimestamp());
- assertNull(c.getDateCreated());
- assertNull(c.getDateUploaded());
- }
-
- @Test
- public void createFromCursor_nullableLocalUri() {
- MatrixCursor mc = createCursor(0L, 0L, false, "");
-
- Contribution c = testObject.fromCursor(mc);
-
- assertNull(c.getLocalUri());
- assertNull(c.getDateCreated());
- assertNull(c.getDateUploaded());
- }
-
- @Test
- public void createFromCursor_booleanEncoding() {
- MatrixCursor mcFalse = createCursor(0L, 0L, false, LOCAL_URI);
- assertFalse(testObject.fromCursor(mcFalse).getMultiple());
-
- MatrixCursor mcHammer = createCursor(0L, 0L, true, LOCAL_URI);
- assertTrue(testObject.fromCursor(mcHammer).getMultiple());
- }
-
- @NonNull
- private MatrixCursor createCursor(long created, long uploaded, boolean multiple, String localUri) {
- MatrixCursor mc = new MatrixCursor(Table.ALL_FIELDS, 1);
- mc.addRow(Arrays.asList("111", "file", localUri, "image",
- created, STATE_QUEUED, 222L, uploaded, 88L, SOURCE_GALLERY, "desc",
- "create", multiple ? 1 : 0, 640, 480, "007"));
- mc.moveToFirst();
- return mc;
- }
-
- @NonNull
- private Contribution createContribution(boolean multiple, Uri localUri,
- String imageUrl, Date dateUploaded, String filename) {
- Contribution contribution = new Contribution(localUri, imageUrl, filename, "desc", 222L,
- new Date(321L), dateUploaded, "create", "edit", "coords");
- contribution.setState(STATE_COMPLETED);
- contribution.setTransferred(333L);
- contribution.setSource(SOURCE_CAMERA);
- contribution.setLicense("007");
- contribution.setMultiple(multiple);
- contribution.setTimestamp(new Date(321L));
- contribution.setWidth(640);
- contribution.setHeight(480); // VGA should be enough for anyone, right?
- return contribution;
- }
-}
\ No newline at end of file
diff --git a/app/src/test/java/fr/free/nrw/commons/modifications/ModifierSequenceDaoTest.java b/app/src/test/java/fr/free/nrw/commons/modifications/ModifierSequenceDaoTest.java
deleted file mode 100644
index ef290500d..000000000
--- a/app/src/test/java/fr/free/nrw/commons/modifications/ModifierSequenceDaoTest.java
+++ /dev/null
@@ -1,181 +0,0 @@
-package fr.free.nrw.commons.modifications;
-
-import android.content.ContentProviderClient;
-import android.content.ContentValues;
-import android.database.MatrixCursor;
-import android.database.sqlite.SQLiteDatabase;
-import android.net.Uri;
-import android.os.RemoteException;
-import android.support.annotation.NonNull;
-
-import org.junit.Before;
-import org.junit.Test;
-import org.junit.runner.RunWith;
-import org.mockito.ArgumentCaptor;
-import org.mockito.Captor;
-import org.mockito.InOrder;
-import org.mockito.Mock;
-import org.mockito.MockitoAnnotations;
-import org.robolectric.RobolectricTestRunner;
-import org.robolectric.annotation.Config;
-
-import java.util.Arrays;
-
-import fr.free.nrw.commons.BuildConfig;
-import fr.free.nrw.commons.TestCommonsApplication;
-
-import static fr.free.nrw.commons.modifications.ModificationsContentProvider.BASE_URI;
-import static org.junit.Assert.assertEquals;
-import static org.junit.Assert.assertTrue;
-import static org.mockito.Matchers.eq;
-import static org.mockito.Matchers.isA;
-import static org.mockito.Matchers.isNull;
-import static org.mockito.Mockito.inOrder;
-import static org.mockito.Mockito.verify;
-import static org.mockito.Mockito.when;
-
-@RunWith(RobolectricTestRunner.class)
-@Config(constants = BuildConfig.class, sdk = 21, application = TestCommonsApplication.class)
-public class ModifierSequenceDaoTest {
-
- private static final String EXPECTED_MEDIA_URI = "http://example.com/";
-
- @Mock
- ContentProviderClient client;
- @Mock
- SQLiteDatabase database;
- @Captor
- ArgumentCaptor contentValuesCaptor;
-
- private ModifierSequenceDao testObject;
-
- @Before
- public void setUp() throws Exception {
- MockitoAnnotations.initMocks(this);
- testObject = new ModifierSequenceDao(() -> client);
- }
-
- @Test
- public void createFromCursorWithEmptyModifiers() {
- MatrixCursor cursor = createCursor("");
-
- ModifierSequence seq = testObject.fromCursor(cursor);
-
- assertEquals(EXPECTED_MEDIA_URI, seq.getMediaUri().toString());
- assertEquals(BASE_URI.buildUpon().appendPath("1").toString(), seq.getContentUri().toString());
- assertTrue(seq.getModifiers().isEmpty());
- }
-
- @Test
- public void createFromCursorWtihCategoryModifier() {
- MatrixCursor cursor = createCursor("{\"name\": \"CategoriesModifier\", \"data\": {}}");
-
- ModifierSequence seq = testObject.fromCursor(cursor);
-
- assertEquals(1, seq.getModifiers().size());
- assertTrue(seq.getModifiers().get(0) instanceof CategoryModifier);
- }
-
- @Test
- public void createFromCursorWithRemoveModifier() {
- MatrixCursor cursor = createCursor("{\"name\": \"TemplateRemoverModifier\", \"data\": {}}");
-
- ModifierSequence seq = testObject.fromCursor(cursor);
-
- assertEquals(1, seq.getModifiers().size());
- assertTrue(seq.getModifiers().get(0) instanceof TemplateRemoveModifier);
- }
-
- @Test
- public void deleteSequence() throws Exception {
- when(client.delete(isA(Uri.class), isNull(String.class), isNull(String[].class))).thenReturn(1);
- ModifierSequence seq = testObject.fromCursor(createCursor(""));
-
- testObject.delete(seq);
-
- verify(client).delete(eq(seq.getContentUri()), isNull(String.class), isNull(String[].class));
- }
-
- @Test(expected = RuntimeException.class)
- public void deleteTranslatesRemoteExceptions() throws Exception {
- when(client.delete(isA(Uri.class), isNull(String.class), isNull(String[].class))).thenThrow(new RemoteException(""));
- ModifierSequence seq = testObject.fromCursor(createCursor(""));
-
- testObject.delete(seq);
- }
-
- @Test
- public void saveExistingSequence() throws Exception {
- String modifierJson = "{\"name\":\"CategoriesModifier\",\"data\":{}}";
- String expectedData = "{\"modifiers\":[" + modifierJson + "]}";
- MatrixCursor cursor = createCursor(modifierJson);
-
- testObject.save(testObject.fromCursor(cursor));
-
- verify(client).update(eq(testObject.fromCursor(cursor).getContentUri()), contentValuesCaptor.capture(), isNull(String.class), isNull(String[].class));
- ContentValues cv = contentValuesCaptor.getValue();
- assertEquals(2, cv.size());
- assertEquals(EXPECTED_MEDIA_URI, cv.get(ModifierSequenceDao.Table.COLUMN_MEDIA_URI));
- assertEquals(expectedData, cv.get(ModifierSequenceDao.Table.COLUMN_DATA));
- }
-
- @Test
- public void saveNewSequence() throws Exception {
- Uri expectedContentUri = BASE_URI.buildUpon().appendPath("1").build();
- when(client.insert(isA(Uri.class), isA(ContentValues.class))).thenReturn(expectedContentUri);
-
- ModifierSequence seq = new ModifierSequence(Uri.parse(EXPECTED_MEDIA_URI));
- testObject.save(seq);
-
- verify(client).insert(eq(ModificationsContentProvider.BASE_URI), contentValuesCaptor.capture());
- ContentValues cv = contentValuesCaptor.getValue();
- assertEquals(2, cv.size());
- assertEquals(EXPECTED_MEDIA_URI, cv.get(ModifierSequenceDao.Table.COLUMN_MEDIA_URI));
- assertEquals("{\"modifiers\":[]}", cv.get(ModifierSequenceDao.Table.COLUMN_DATA));
- assertEquals(expectedContentUri.toString(), seq.getContentUri().toString());
- }
-
- @Test(expected = RuntimeException.class)
- public void saveTranslatesRemoteExceptions() throws Exception {
- when(client.insert(isA(Uri.class), isA(ContentValues.class))).thenThrow(new RemoteException(""));
-
- testObject.save(new ModifierSequence(Uri.parse(EXPECTED_MEDIA_URI)));
- }
-
- @Test
- public void createTable() {
- ModifierSequenceDao.Table.onCreate(database);
-
- verify(database).execSQL(ModifierSequenceDao.Table.CREATE_TABLE_STATEMENT);
- }
-
- @Test
- public void updateTable() {
- ModifierSequenceDao.Table.onUpdate(database, 1, 2);
-
- InOrder inOrder = inOrder(database);
- inOrder.verify(database).execSQL(ModifierSequenceDao.Table.DROP_TABLE_STATEMENT);
- inOrder.verify(database).execSQL(ModifierSequenceDao.Table.CREATE_TABLE_STATEMENT);
- }
-
- @Test
- public void deleteTable() {
- ModifierSequenceDao.Table.onDelete(database);
-
- InOrder inOrder = inOrder(database);
- inOrder.verify(database).execSQL(ModifierSequenceDao.Table.DROP_TABLE_STATEMENT);
- inOrder.verify(database).execSQL(ModifierSequenceDao.Table.CREATE_TABLE_STATEMENT);
- }
-
- @NonNull
- private MatrixCursor createCursor(String modifierJson) {
- MatrixCursor cursor = new MatrixCursor(new String[]{
- ModifierSequenceDao.Table.COLUMN_ID,
- ModifierSequenceDao.Table.COLUMN_MEDIA_URI,
- ModifierSequenceDao.Table.COLUMN_DATA
- }, 1);
- cursor.addRow(Arrays.asList("1", EXPECTED_MEDIA_URI, "{\"modifiers\": [" + modifierJson + "]}"));
- cursor.moveToFirst();
- return cursor;
- }
-}
\ No newline at end of file
diff --git a/app/src/test/java/fr/free/nrw/commons/mwapi/ApacheHttpClientMediaWikiApiTest.java b/app/src/test/java/fr/free/nrw/commons/mwapi/ApacheHttpClientMediaWikiApiTest.java
deleted file mode 100644
index e2c8b82f6..000000000
--- a/app/src/test/java/fr/free/nrw/commons/mwapi/ApacheHttpClientMediaWikiApiTest.java
+++ /dev/null
@@ -1,248 +0,0 @@
-package fr.free.nrw.commons.mwapi;
-
-import android.content.SharedPreferences;
-import android.os.Build;
-import android.preference.PreferenceManager;
-
-import org.junit.After;
-import org.junit.Before;
-import org.junit.Test;
-import org.junit.runner.RunWith;
-import org.robolectric.RobolectricTestRunner;
-import org.robolectric.RuntimeEnvironment;
-import org.robolectric.annotation.Config;
-
-import java.io.IOException;
-import java.io.UnsupportedEncodingException;
-import java.net.URLDecoder;
-import java.util.HashMap;
-import java.util.Map;
-import java.util.Set;
-
-import fr.free.nrw.commons.BuildConfig;
-import fr.free.nrw.commons.TestCommonsApplication;
-import io.reactivex.observers.TestObserver;
-import okhttp3.HttpUrl;
-import okhttp3.mockwebserver.MockResponse;
-import okhttp3.mockwebserver.MockWebServer;
-import okhttp3.mockwebserver.RecordedRequest;
-
-import static org.junit.Assert.assertEquals;
-import static org.junit.Assert.assertFalse;
-import static org.junit.Assert.assertTrue;
-
-@RunWith(RobolectricTestRunner.class)
-@Config(constants = BuildConfig.class, sdk = 21, application = TestCommonsApplication.class)
-public class ApacheHttpClientMediaWikiApiTest {
-
- private ApacheHttpClientMediaWikiApi testObject;
- private MockWebServer server;
- private SharedPreferences sharedPreferences;
-
- @Before
- public void setUp() throws Exception {
- server = new MockWebServer();
- sharedPreferences = PreferenceManager.getDefaultSharedPreferences(RuntimeEnvironment.application);
- testObject = new ApacheHttpClientMediaWikiApi(RuntimeEnvironment.application, "http://" + server.getHostName() + ":" + server.getPort() + "/", sharedPreferences);
- testObject.setWikiMediaToolforgeUrl("http://" + server.getHostName() + ":" + server.getPort() + "/");
- }
-
- @After
- public void teardown() throws IOException {
- server.shutdown();
- }
-
- @Test
- public void authCookiesAreHandled() {
- assertEquals("", testObject.getAuthCookie());
-
- testObject.setAuthCookie("cookie=chocolate-chip");
-
- assertEquals("cookie=chocolate-chip", testObject.getAuthCookie());
- }
-
- @Test
- public void simpleLoginWithWrongPassword() throws Exception {
- server.enqueue(new MockResponse().setBody(""));
- server.enqueue(new MockResponse().setBody(""));
-
- String result = testObject.login("foo", "bar");
-
- RecordedRequest loginTokenRequest = assertBasicRequestParameters(server, "POST");
- Map body = parseBody(loginTokenRequest.getBody().readUtf8());
- assertEquals("xml", body.get("format"));
- assertEquals("query", body.get("action"));
- assertEquals("login", body.get("type"));
- assertEquals("tokens", body.get("meta"));
-
- RecordedRequest loginRequest = assertBasicRequestParameters(server, "POST");
- body = parseBody(loginRequest.getBody().readUtf8());
- assertEquals("1", body.get("rememberMe"));
- assertEquals("foo", body.get("username"));
- assertEquals("bar", body.get("password"));
- assertEquals("baz", body.get("logintoken"));
- assertEquals("https://commons.wikimedia.org", body.get("loginreturnurl"));
- assertEquals("xml", body.get("format"));
-
- assertEquals("wrongpassword", result);
- }
-
- @Test
- public void simpleLogin() throws Exception {
- server.enqueue(new MockResponse().setBody(""));
- server.enqueue(new MockResponse().setBody(""));
-
- String result = testObject.login("foo", "bar");
-
- RecordedRequest loginTokenRequest = assertBasicRequestParameters(server, "POST");
- Map body = parseBody(loginTokenRequest.getBody().readUtf8());
- assertEquals("xml", body.get("format"));
- assertEquals("query", body.get("action"));
- assertEquals("login", body.get("type"));
- assertEquals("tokens", body.get("meta"));
-
- RecordedRequest loginRequest = assertBasicRequestParameters(server, "POST");
- body = parseBody(loginRequest.getBody().readUtf8());
- assertEquals("1", body.get("rememberMe"));
- assertEquals("foo", body.get("username"));
- assertEquals("bar", body.get("password"));
- assertEquals("baz", body.get("logintoken"));
- assertEquals("https://commons.wikimedia.org", body.get("loginreturnurl"));
- assertEquals("xml", body.get("format"));
-
- assertEquals("PASS", result);
- }
-
- @Test
- public void twoFactorLogin() throws Exception {
- server.enqueue(new MockResponse().setBody(""));
- server.enqueue(new MockResponse().setBody(""));
-
- String result = testObject.login("foo", "bar", "2fa");
-
- RecordedRequest loginTokenRequest = assertBasicRequestParameters(server, "POST");
- Map body = parseBody(loginTokenRequest.getBody().readUtf8());
- assertEquals("xml", body.get("format"));
- assertEquals("query", body.get("action"));
- assertEquals("login", body.get("type"));
- assertEquals("tokens", body.get("meta"));
-
- RecordedRequest loginRequest = assertBasicRequestParameters(server, "POST");
- body = parseBody(loginRequest.getBody().readUtf8());
- assertEquals("true", body.get("rememberMe"));
- assertEquals("foo", body.get("username"));
- assertEquals("bar", body.get("password"));
- assertEquals("baz", body.get("logintoken"));
- assertEquals("true", body.get("logincontinue"));
- assertEquals("2fa", body.get("OATHToken"));
- assertEquals("xml", body.get("format"));
-
- assertEquals("PASS", result);
- }
-
- @Test
- public void validateLoginForLoggedInUser() throws Exception {
- server.enqueue(new MockResponse().setBody(""));
-
- boolean result = testObject.validateLogin();
-
- RecordedRequest loginTokenRequest = assertBasicRequestParameters(server, "GET");
- Map body = parseQueryParams(loginTokenRequest);
- assertEquals("xml", body.get("format"));
- assertEquals("query", body.get("action"));
- assertEquals("userinfo", body.get("meta"));
-
- assertTrue(result);
- }
-
- @Test
- public void validateLoginForLoggedOutUser() throws Exception {
- server.enqueue(new MockResponse().setBody(""));
-
- boolean result = testObject.validateLogin();
-
- RecordedRequest loginTokenRequest = assertBasicRequestParameters(server, "GET");
- Map params = parseQueryParams(loginTokenRequest);
- assertEquals("xml", params.get("format"));
- assertEquals("query", params.get("action"));
- assertEquals("userinfo", params.get("meta"));
-
- assertFalse(result);
- }
-
- @Test
- public void editToken() throws Exception {
- server.enqueue(new MockResponse().setBody(""));
-
- String result = testObject.getEditToken();
-
- RecordedRequest loginTokenRequest = assertBasicRequestParameters(server, "GET");
- Map params = parseQueryParams(loginTokenRequest);
- assertEquals("xml", params.get("format"));
- assertEquals("tokens", params.get("action"));
- assertEquals("edit", params.get("type"));
-
- assertEquals("baz", result);
- }
-
- @Test
- public void fileExistsWithName_FileNotFound() throws Exception {
- server.enqueue(new MockResponse().setBody(" "));
-
- boolean result = testObject.fileExistsWithName("foo");
-
- RecordedRequest request = assertBasicRequestParameters(server, "GET");
- Map params = parseQueryParams(request);
- assertEquals("xml", params.get("format"));
- assertEquals("query", params.get("action"));
- assertEquals("imageinfo", params.get("prop"));
- assertEquals("File:foo", params.get("titles"));
-
- assertFalse(result);
- }
-
- @Test
- public void getUploadCount() throws InterruptedException {
- server.enqueue(new MockResponse().setBody("23\n"));
-
- TestObserver testObserver = testObject.getUploadCount("testUsername").test();
-
- RecordedRequest request = server.takeRequest();
- Map params = parseQueryParams(request);
- assertEquals("testUsername", params.get("user"));
-
- assertEquals(1, testObserver.valueCount());
- assertEquals(23, (int)testObserver.values().get(0));
- }
-
- private RecordedRequest assertBasicRequestParameters(MockWebServer server, String method) throws InterruptedException {
- RecordedRequest request = server.takeRequest();
- assertEquals("/", request.getRequestUrl().encodedPath());
- assertEquals(method, request.getMethod());
- assertEquals("Commons/" + BuildConfig.VERSION_NAME + " (https://mediawiki.org/wiki/Apps/Commons) Android/" + Build.VERSION.RELEASE, request.getHeader("User-Agent"));
- if ("POST".equals(method)) {
- assertEquals("application/x-www-form-urlencoded", request.getHeader("Content-Type"));
- }
- return request;
- }
-
- private Map parseQueryParams(RecordedRequest request) {
- Map result = new HashMap<>();
- HttpUrl url = request.getRequestUrl();
- Set params = url.queryParameterNames();
- for (String name : params) {
- result.put(name, url.queryParameter(name));
- }
- return result;
- }
-
- private Map parseBody(String body) throws UnsupportedEncodingException {
- String[] props = body.split("&");
- Map result = new HashMap<>();
- for (String prop : props) {
- String[] pair = prop.split("=");
- result.put(pair[0], URLDecoder.decode(pair[1], "utf-8"));
- }
- return result;
- }
-}
diff --git a/app/src/test/java/fr/free/nrw/commons/utils/StringSortingUtilsTest.java b/app/src/test/java/fr/free/nrw/commons/utils/StringSortingUtilsTest.java
deleted file mode 100644
index 6384fb096..000000000
--- a/app/src/test/java/fr/free/nrw/commons/utils/StringSortingUtilsTest.java
+++ /dev/null
@@ -1,41 +0,0 @@
-package fr.free.nrw.commons.utils;
-
-import org.junit.Assert;
-import org.junit.Test;
-
-import java.util.Arrays;
-import java.util.Collections;
-import java.util.List;
-
-public class StringSortingUtilsTest {
-
- @Test
- public void testSortingNumbersBySimilarity() throws Exception {
- List actualList = Arrays.asList("1234567", "4567", "12345", "123", "1234");
- List expectedList = Arrays.asList("1234", "12345", "123", "1234567", "4567");
-
- Collections.sort(actualList, StringSortingUtils.sortBySimilarity("1234"));
- Assert.assertEquals(expectedList, actualList);
- }
-
- @Test
- public void testSortingTextBySimilarity() throws Exception {
- List actualList = Arrays.asList("The quick brown fox",
- "quick brown fox",
- "The",
- "The quick ",
- "The fox",
- "brown fox",
- "fox");
- List expectedList = Arrays.asList("The",
- "The fox",
- "The quick ",
- "The quick brown fox",
- "quick brown fox",
- "brown fox",
- "fox");
-
- Collections.sort(actualList, StringSortingUtils.sortBySimilarity("The"));
- Assert.assertEquals(expectedList, actualList);
- }
-}
\ No newline at end of file
diff --git a/app/src/test/kotlin/fr/free/nrw/commons/FileUtilsTest.kt b/app/src/test/kotlin/fr/free/nrw/commons/FileUtilsTest.kt
new file mode 100644
index 000000000..8be291d4d
--- /dev/null
+++ b/app/src/test/kotlin/fr/free/nrw/commons/FileUtilsTest.kt
@@ -0,0 +1,33 @@
+package fr.free.nrw.commons
+
+import fr.free.nrw.commons.upload.FileUtils
+import org.junit.Assert.assertEquals
+import org.junit.Test
+import java.io.*
+
+class FileUtilsTest {
+ @Test
+ fun copiedFileIsIdenticalToSource() {
+ val source = File.createTempFile("temp", "")
+ val dest = File.createTempFile("temp", "")
+ writeToFile(source, "Hello, World")
+
+ FileUtils.copy(FileInputStream(source), FileOutputStream(dest))
+
+ assertEquals(getString(source), getString(dest))
+ }
+
+ private fun writeToFile(file: File, s: String) {
+ val buf = BufferedOutputStream(FileOutputStream(file))
+ buf.write(s.toByteArray())
+ buf.close()
+ }
+
+ private fun getString(file: File): String {
+ val bytes = ByteArray(file.length().toInt())
+ val buf = BufferedInputStream(FileInputStream(file))
+ buf.read(bytes, 0, bytes.size)
+ buf.close()
+ return String(bytes)
+ }
+}
diff --git a/app/src/test/kotlin/fr/free/nrw/commons/LatLngTests.kt b/app/src/test/kotlin/fr/free/nrw/commons/LatLngTests.kt
new file mode 100644
index 000000000..efafa4e3a
--- /dev/null
+++ b/app/src/test/kotlin/fr/free/nrw/commons/LatLngTests.kt
@@ -0,0 +1,64 @@
+package fr.free.nrw.commons
+
+import fr.free.nrw.commons.location.LatLng
+import org.junit.Assert.assertEquals
+import org.junit.Test
+
+class LatLngTests {
+ @Test
+ fun testZeroZero() {
+ val place = LatLng(0.0, 0.0, 0f)
+ assertPrettyCoordinateString("0.0 N, 0.0 E", place)
+ }
+
+ @Test
+ fun testAntipode() {
+ val place = LatLng(0.0, 180.0, 0f)
+ assertPrettyCoordinateString("0.0 N, 180.0 W", place)
+ }
+
+ @Test
+ fun testNorthPole() {
+ val place = LatLng(90.0, 0.0, 0f)
+ assertPrettyCoordinateString("90.0 N, 0.0 E", place)
+ }
+
+ @Test
+ fun testSouthPole() {
+ val place = LatLng(-90.0, 0.0, 0f)
+ assertPrettyCoordinateString("90.0 S, 0.0 E", place)
+ }
+
+ @Test
+ fun testLargerNumbers() {
+ val place = LatLng(120.0, 380.0, 0f)
+ assertPrettyCoordinateString("90.0 N, 20.0 E", place)
+ }
+
+ @Test
+ fun testNegativeNumbers() {
+ val place = LatLng(-120.0, -30.0, 0f)
+ assertPrettyCoordinateString("90.0 S, 30.0 W", place)
+ }
+
+ @Test
+ fun testTooBigWestValue() {
+ val place = LatLng(20.0, -190.0, 0f)
+ assertPrettyCoordinateString("20.0 N, 170.0 E", place)
+ }
+
+ @Test
+ fun testRounding() {
+ val place = LatLng(0.1234567, -0.33333333, 0f)
+ assertPrettyCoordinateString("0.1235 N, 0.3333 W", place)
+ }
+
+ @Test
+ fun testRoundingAgain() {
+ val place = LatLng(-0.000001, -0.999999, 0f)
+ assertPrettyCoordinateString("0.0 S, 1.0 W", place)
+ }
+
+ private fun assertPrettyCoordinateString(expected: String, place: LatLng) =
+ assertEquals(expected, place.prettyCoordinateString)
+}
diff --git a/app/src/test/kotlin/fr/free/nrw/commons/LengthUtilsTest.kt b/app/src/test/kotlin/fr/free/nrw/commons/LengthUtilsTest.kt
new file mode 100644
index 000000000..63b0b4d0a
--- /dev/null
+++ b/app/src/test/kotlin/fr/free/nrw/commons/LengthUtilsTest.kt
@@ -0,0 +1,46 @@
+package fr.free.nrw.commons
+
+import fr.free.nrw.commons.location.LatLng
+import fr.free.nrw.commons.utils.LengthUtils
+import org.junit.Assert.assertEquals
+import org.junit.Test
+
+class LengthUtilsTest {
+ @Test
+ fun testZeroDistance() {
+ val pointA = LatLng(0.0, 0.0, 0f)
+ val pointB = LatLng(0.0, 0.0, 0f)
+ assertDistanceBetween("0m", pointA, pointB)
+ }
+
+ @Test
+ fun testOneDegreeOnEquator() {
+ val pointA = LatLng(0.0, 0.0, 0f)
+ val pointB = LatLng(0.0, 1.0, 0f)
+ assertDistanceBetween("111.2km", pointA, pointB)
+ }
+
+ @Test
+ fun testOneDegreeFortyFiveDegrees() {
+ val pointA = LatLng(45.0, 0.0, 0f)
+ val pointB = LatLng(45.0, 1.0, 0f)
+ assertDistanceBetween("78.6km", pointA, pointB)
+ }
+
+ @Test
+ fun testOneDegreeSouthPole() {
+ val pointA = LatLng(-90.0, 0.0, 0f)
+ val pointB = LatLng(-90.0, 1.0, 0f)
+ assertDistanceBetween("0m", pointA, pointB)
+ }
+
+ @Test
+ fun testPoleToPole() {
+ val pointA = LatLng(90.0, 0.0, 0f)
+ val pointB = LatLng(-90.0, 0.0, 0f)
+ assertDistanceBetween("20,015.1km", pointA, pointB)
+ }
+
+ private fun assertDistanceBetween(expected: String, pointA: LatLng, pointB: LatLng) =
+ assertEquals(expected, LengthUtils.formatDistanceBetween(pointA, pointB))
+}
diff --git a/app/src/test/kotlin/fr/free/nrw/commons/MediaTest.kt b/app/src/test/kotlin/fr/free/nrw/commons/MediaTest.kt
new file mode 100644
index 000000000..f75c34568
--- /dev/null
+++ b/app/src/test/kotlin/fr/free/nrw/commons/MediaTest.kt
@@ -0,0 +1,23 @@
+package fr.free.nrw.commons
+
+import org.junit.Assert.assertEquals
+import org.junit.Test
+import org.junit.runner.RunWith
+import org.robolectric.RobolectricTestRunner
+import org.robolectric.annotation.Config
+
+@RunWith(RobolectricTestRunner::class)
+@Config(constants = BuildConfig::class, sdk = intArrayOf(21), application = TestCommonsApplication::class)
+class MediaTest {
+ @Test
+ fun displayTitleShouldStripExtension() {
+ val m = Media("File:Example.jpg")
+ assertEquals("Example", m.displayTitle)
+ }
+
+ @Test
+ fun displayTitleShouldUseSpaceForUnderscore() {
+ val m = Media("File:Example 1_2.jpg")
+ assertEquals("Example 1 2", m.displayTitle)
+ }
+}
diff --git a/app/src/test/kotlin/fr/free/nrw/commons/NearbyControllerTest.kt b/app/src/test/kotlin/fr/free/nrw/commons/NearbyControllerTest.kt
new file mode 100644
index 000000000..fc0be84d0
--- /dev/null
+++ b/app/src/test/kotlin/fr/free/nrw/commons/NearbyControllerTest.kt
@@ -0,0 +1,35 @@
+package fr.free.nrw.commons
+
+import fr.free.nrw.commons.location.LatLng
+import fr.free.nrw.commons.nearby.NearbyController.loadAttractionsFromLocationToBaseMarkerOptions
+import org.junit.Assert.assertEquals
+import org.junit.Test
+import org.junit.runner.RunWith
+import org.robolectric.RobolectricTestRunner
+import org.robolectric.RuntimeEnvironment
+import org.robolectric.annotation.Config
+
+@RunWith(RobolectricTestRunner::class)
+@Config(constants = BuildConfig::class, sdk = intArrayOf(21), application = TestCommonsApplication::class)
+class NearbyControllerTest {
+
+ @Test
+ fun testNullAttractions() {
+ val location = LatLng(0.0, 0.0, 0f)
+
+ val options = loadAttractionsFromLocationToBaseMarkerOptions(
+ location, null, RuntimeEnvironment.application)
+
+ assertEquals(0, options.size.toLong())
+ }
+
+ @Test
+ fun testEmptyList() {
+ val location = LatLng(0.0, 0.0, 0f)
+
+ val options = loadAttractionsFromLocationToBaseMarkerOptions(
+ location, emptyList(), RuntimeEnvironment.application)
+
+ assertEquals(0, options.size.toLong())
+ }
+}
diff --git a/app/src/test/kotlin/fr/free/nrw/commons/PageTitleTest.kt b/app/src/test/kotlin/fr/free/nrw/commons/PageTitleTest.kt
new file mode 100644
index 000000000..28112b196
--- /dev/null
+++ b/app/src/test/kotlin/fr/free/nrw/commons/PageTitleTest.kt
@@ -0,0 +1,67 @@
+package fr.free.nrw.commons
+
+import org.junit.Assert.assertEquals
+import org.junit.Test
+import org.junit.runner.RunWith
+import org.robolectric.RobolectricTestRunner
+import org.robolectric.annotation.Config
+import java.net.URLEncoder
+
+@RunWith(RobolectricTestRunner::class)
+@Config(constants = BuildConfig::class, sdk = intArrayOf(21), application = TestCommonsApplication::class)
+class PageTitleTest {
+ @Test
+ fun displayTextShouldNotBeUnderscored() {
+ val pageTitle = PageTitle("Ex_1 ")
+ assertEquals("Ex 1", pageTitle.displayText)
+ }
+
+ @Test
+ fun moreThanTwoColons() {
+ val pageTitle = PageTitle("File:sample:a.jpg")
+ assertEquals("File:Sample:a.jpg", pageTitle.prefixedText)
+ }
+
+ @Test
+ fun getTextShouldReturnWithoutNamespace() {
+ val pageTitle = PageTitle("File:sample.jpg")
+ assertEquals("Sample.jpg", pageTitle.text)
+ }
+
+
+ @Test
+ fun capitalizeNameAfterNamespace() {
+ val pageTitle = PageTitle("File:sample.jpg")
+ assertEquals("File:Sample.jpg", pageTitle.prefixedText)
+ }
+
+ @Test
+ fun prefixedTextShouldBeUnderscored() {
+ val pageTitle = PageTitle("Ex 1 ")
+ assertEquals("Ex_1", pageTitle.prefixedText)
+ }
+
+ @Test
+ fun getMobileUriForTest() {
+ val pageTitle = PageTitle("Test")
+ assertEquals(BuildConfig.MOBILE_HOME_URL + "Test", pageTitle.mobileUri.toString())
+ }
+
+ @Test
+ fun spaceBecomesUnderscoreInUri() {
+ val pageTitle = PageTitle("File:Ex 1.jpg")
+ assertEquals(BuildConfig.HOME_URL + "File:Ex_1.jpg", pageTitle.canonicalUri.toString())
+ }
+
+ @Test
+ fun leaveSubpageNamesUncapitalizedInUri() {
+ val pageTitle = PageTitle("User:Ex/subpage")
+ assertEquals(BuildConfig.HOME_URL + "User:Ex/subpage", pageTitle.canonicalUri.toString())
+ }
+
+ @Test
+ fun unicodeUri() {
+ val pageTitle = PageTitle("User:例")
+ assertEquals(BuildConfig.HOME_URL + "User:" + URLEncoder.encode("例", "utf-8"), pageTitle.canonicalUri.toString())
+ }
+}
diff --git a/app/src/test/kotlin/fr/free/nrw/commons/TestCommonsApplication.kt b/app/src/test/kotlin/fr/free/nrw/commons/TestCommonsApplication.kt
new file mode 100644
index 000000000..73760dd40
--- /dev/null
+++ b/app/src/test/kotlin/fr/free/nrw/commons/TestCommonsApplication.kt
@@ -0,0 +1,72 @@
+package fr.free.nrw.commons
+
+import android.content.Context
+import android.content.SharedPreferences
+import android.support.v4.util.LruCache
+import com.nhaarman.mockito_kotlin.mock
+import com.squareup.leakcanary.RefWatcher
+import fr.free.nrw.commons.auth.AccountUtil
+import fr.free.nrw.commons.auth.SessionManager
+import fr.free.nrw.commons.caching.CacheController
+import fr.free.nrw.commons.data.DBOpenHelper
+import fr.free.nrw.commons.di.CommonsApplicationComponent
+import fr.free.nrw.commons.di.CommonsApplicationModule
+import fr.free.nrw.commons.di.DaggerCommonsApplicationComponent
+import fr.free.nrw.commons.location.LocationServiceManager
+import fr.free.nrw.commons.mwapi.MediaWikiApi
+import fr.free.nrw.commons.nearby.NearbyPlaces
+import fr.free.nrw.commons.upload.UploadController
+
+class TestCommonsApplication : CommonsApplication() {
+ private var mockApplicationComponent: CommonsApplicationComponent? = null
+
+ override fun onCreate() {
+ if (mockApplicationComponent == null) {
+ mockApplicationComponent = DaggerCommonsApplicationComponent.builder()
+ .appModule(MockCommonsApplicationModule(this)).build()
+ }
+ super.onCreate()
+ }
+
+ // No leakcanary in unit tests.
+ override fun setupLeakCanary(): RefWatcher = RefWatcher.DISABLED
+}
+
+class MockCommonsApplicationModule(appContext: Context) : CommonsApplicationModule(appContext) {
+ val accountUtil: AccountUtil = mock()
+ val appSharedPreferences: SharedPreferences = mock()
+ val defaultSharedPreferences: SharedPreferences = mock()
+ val otherSharedPreferences: SharedPreferences = mock()
+ val uploadController: UploadController = mock()
+ val mockSessionManager: SessionManager = mock()
+ val mediaWikiApi: MediaWikiApi = mock()
+ val locationServiceManager: LocationServiceManager = mock()
+ val cacheController: CacheController = mock()
+ val mockDbOpenHelper: DBOpenHelper = mock()
+ val nearbyPlaces: NearbyPlaces = mock()
+ val lruCache: LruCache = mock()
+
+ override fun providesAccountUtil(context: Context): AccountUtil = accountUtil
+
+ override fun providesApplicationSharedPreferences(context: Context): SharedPreferences = appSharedPreferences
+
+ override fun providesDefaultSharedPreferences(context: Context): SharedPreferences = defaultSharedPreferences
+
+ override fun providesOtherSharedPreferences(context: Context): SharedPreferences = otherSharedPreferences
+
+ override fun providesUploadController(sessionManager: SessionManager, sharedPreferences: SharedPreferences, context: Context): UploadController = uploadController
+
+ override fun providesSessionManager(context: Context, mediaWikiApi: MediaWikiApi, sharedPreferences: SharedPreferences): SessionManager = mockSessionManager
+
+ override fun provideMediaWikiApi(context: Context, sharedPreferences: SharedPreferences): MediaWikiApi = mediaWikiApi
+
+ override fun provideLocationServiceManager(context: Context): LocationServiceManager = locationServiceManager
+
+ override fun provideCacheController(): CacheController = cacheController
+
+ override fun provideDBOpenHelper(context: Context): DBOpenHelper = mockDbOpenHelper
+
+ override fun provideNearbyPlaces(): NearbyPlaces = nearbyPlaces
+
+ override fun provideLruCache(): LruCache = lruCache
+}
\ No newline at end of file
diff --git a/app/src/test/kotlin/fr/free/nrw/commons/UtilsFixExtensionTest.kt b/app/src/test/kotlin/fr/free/nrw/commons/UtilsFixExtensionTest.kt
new file mode 100644
index 000000000..0082b9d28
--- /dev/null
+++ b/app/src/test/kotlin/fr/free/nrw/commons/UtilsFixExtensionTest.kt
@@ -0,0 +1,68 @@
+package fr.free.nrw.commons
+
+import fr.free.nrw.commons.Utils.fixExtension
+import org.junit.Assert.assertEquals
+import org.junit.Test
+
+class UtilsFixExtensionTest {
+
+ @Test
+ fun jpegResultsInJpg() {
+ assertEquals("SampleFile.jpg", fixExtension("SampleFile.jpeg", "jpeg"))
+ }
+
+ @Test
+ fun capitalJpegWithNoHintResultsInJpg() {
+ assertEquals("SampleFile.jpg", fixExtension("SampleFile.JPEG", null))
+ }
+
+ @Test
+ fun jpegWithBogusHintResultsInJpg() {
+ assertEquals("SampleFile.jpg", fixExtension("SampleFile.jpeg", null))
+ }
+
+ @Test
+ fun jpegToCapitalJpegResultsInJpg() {
+ assertEquals("SampleFile.jpg", fixExtension("SampleFile.jpeg", "JPEG"))
+ }
+
+ @Test
+ fun jpgToJpegResultsInJpg() {
+ assertEquals("SampleFile.jpg", fixExtension("SampleFile.jpg", "jpeg"))
+ }
+
+ @Test
+ fun jpegToJpgResultsInJpg() {
+ assertEquals("SampleFile.jpg", fixExtension("SampleFile.jpeg", "jpg"))
+ }
+
+ @Test
+ fun jpgRemainsJpg() {
+ assertEquals("SampleFile.jpg", fixExtension("SampleFile.jpg", "jpg"))
+ }
+
+ @Test
+ fun pngRemainsPng() {
+ assertEquals("SampleFile.png", fixExtension("SampleFile.png", "png"))
+ }
+
+ @Test
+ fun jpgHintResultsInJpg() {
+ assertEquals("SampleFile.jpg", fixExtension("SampleFile", "jpg"))
+ }
+
+ @Test
+ fun jpegHintResultsInJpg() {
+ assertEquals("SampleFile.jpg", fixExtension("SampleFile", "jpeg"))
+ }
+
+ @Test
+ fun dotLessJpgToJpgResultsInJpg() {
+ assertEquals("SAMPLEjpg.jpg", fixExtension("SAMPLEjpg", "jpg"))
+ }
+
+ @Test
+ fun inWordJpegToJpgResultsInJpg() {
+ assertEquals("X.jpeg.SAMPLE.jpg", fixExtension("X.jpeg.SAMPLE", "jpg"))
+ }
+}
diff --git a/app/src/test/kotlin/fr/free/nrw/commons/category/CategoryDaoTest.kt b/app/src/test/kotlin/fr/free/nrw/commons/category/CategoryDaoTest.kt
new file mode 100644
index 000000000..b64d3b8aa
--- /dev/null
+++ b/app/src/test/kotlin/fr/free/nrw/commons/category/CategoryDaoTest.kt
@@ -0,0 +1,257 @@
+package fr.free.nrw.commons.category
+
+import android.content.ContentProviderClient
+import android.content.ContentValues
+import android.database.Cursor
+import android.database.MatrixCursor
+import android.database.sqlite.SQLiteDatabase
+import android.os.RemoteException
+import com.nhaarman.mockito_kotlin.*
+import fr.free.nrw.commons.BuildConfig
+import fr.free.nrw.commons.TestCommonsApplication
+import fr.free.nrw.commons.category.CategoryContentProvider.BASE_URI
+import fr.free.nrw.commons.category.CategoryContentProvider.uriForId
+import fr.free.nrw.commons.category.CategoryDao.Table.*
+import org.junit.Assert.*
+import org.junit.Before
+import org.junit.Test
+import org.junit.runner.RunWith
+import org.robolectric.RobolectricTestRunner
+import org.robolectric.annotation.Config
+import java.util.*
+
+@RunWith(RobolectricTestRunner::class)
+@Config(constants = BuildConfig::class, sdk = [21], application = TestCommonsApplication::class)
+class CategoryDaoTest {
+
+ private val columns = arrayOf(COLUMN_ID, COLUMN_NAME, COLUMN_LAST_USED, COLUMN_TIMES_USED)
+ private val client: ContentProviderClient = mock()
+ private val database: SQLiteDatabase = mock()
+ private val captor = argumentCaptor()
+ private val queryCaptor = argumentCaptor>()
+
+ private lateinit var testObject: CategoryDao
+
+ @Before
+ fun setUp() {
+ testObject = CategoryDao { client }
+ }
+
+ @Test
+ fun createTable() {
+ onCreate(database)
+ verify(database).execSQL(CREATE_TABLE_STATEMENT)
+ }
+
+ @Test
+ fun deleteTable() {
+ onDelete(database)
+ inOrder(database) {
+ verify(database).execSQL(DROP_TABLE_STATEMENT)
+ verify(database).execSQL(CREATE_TABLE_STATEMENT)
+ }
+ }
+
+ @Test
+ fun migrateTableVersionFrom_v1_to_v2() {
+ onUpdate(database, 1, 2)
+ // Table didnt exist before v5
+ verifyZeroInteractions(database)
+ }
+
+ @Test
+ fun migrateTableVersionFrom_v2_to_v3() {
+ onUpdate(database, 2, 3)
+ // Table didnt exist before v5
+ verifyZeroInteractions(database)
+ }
+
+ @Test
+ fun migrateTableVersionFrom_v3_to_v4() {
+ onUpdate(database, 3, 4)
+ // Table didnt exist before v5
+ verifyZeroInteractions(database)
+ }
+
+ @Test
+ fun migrateTableVersionFrom_v4_to_v5() {
+ onUpdate(database, 4, 5)
+ verify(database).execSQL(CREATE_TABLE_STATEMENT)
+ }
+
+ @Test
+ fun migrateTableVersionFrom_v5_to_v6() {
+ onUpdate(database, 5, 6)
+ // Table didnt change in version 6
+ verifyZeroInteractions(database)
+ }
+
+ @Test
+ fun createFromCursor() {
+ createCursor(1).let { cursor ->
+ cursor.moveToFirst()
+ testObject.fromCursor(cursor).let {
+ assertEquals(uriForId(1), it.contentUri)
+ assertEquals("foo", it.name)
+ assertEquals(123, it.lastUsed.time)
+ assertEquals(2, it.timesUsed)
+ }
+ }
+ }
+
+ @Test
+ fun saveExistingCategory() {
+ createCursor(1).let {
+ val category = testObject.fromCursor(it.apply { moveToFirst() })
+
+ testObject.save(category)
+
+ verify(client).update(eq(category.contentUri), captor.capture(), isNull(), isNull())
+ captor.firstValue.let { cv ->
+ assertEquals(3, cv.size())
+ assertEquals(category.name, cv.getAsString(COLUMN_NAME))
+ assertEquals(category.lastUsed.time, cv.getAsLong(COLUMN_LAST_USED))
+ assertEquals(category.timesUsed, cv.getAsInteger(COLUMN_TIMES_USED))
+ }
+ }
+ }
+
+ @Test
+ fun saveNewCategory() {
+ val contentUri = CategoryContentProvider.uriForId(111)
+ whenever(client.insert(isA(), isA())).thenReturn(contentUri)
+ val category = Category(null, "foo", Date(234L), 1)
+
+ testObject.save(category)
+
+ verify(client).insert(eq(BASE_URI), captor.capture())
+ captor.firstValue.let { cv ->
+ assertEquals(3, cv.size())
+ assertEquals(category.name, cv.getAsString(COLUMN_NAME))
+ assertEquals(category.lastUsed.time, cv.getAsLong(COLUMN_LAST_USED))
+ assertEquals(category.timesUsed, cv.getAsInteger(COLUMN_TIMES_USED))
+ assertEquals(contentUri, category.contentUri)
+ }
+ }
+
+ @Test(expected = RuntimeException::class)
+ fun testSaveTranslatesRemoteExceptions() {
+ whenever(client.insert(isA(), isA())).thenThrow(RemoteException(""))
+ testObject.save(Category())
+ }
+
+ @Test
+ fun whenTheresNoDataFindReturnsNull_nullCursor() {
+ whenever(client.query(any(), any(), any(), any(), any())).thenReturn(null)
+ assertNull(testObject.find("foo"))
+ }
+
+ @Test
+ fun whenTheresNoDataFindReturnsNull_emptyCursor() {
+ whenever(client.query(any(), any(), any(), any(), any())).thenReturn(createCursor(0))
+ assertNull(testObject.find("foo"))
+ }
+
+ @Test
+ fun cursorsAreClosedAfterUse() {
+ val mockCursor: Cursor = mock()
+ whenever(client.query(any(), any(), any(), any(), anyOrNull())).thenReturn(mockCursor)
+ whenever(mockCursor.moveToFirst()).thenReturn(false)
+
+ testObject.find("foo")
+
+ verify(mockCursor).close()
+ }
+
+ @Test
+ fun findCategory() {
+ whenever(client.query(any(), any(), any(), any(), anyOrNull())).thenReturn(createCursor(1))
+
+ val category = testObject.find("foo")
+ assertNotNull(category)
+
+ assertEquals(uriForId(1), category?.contentUri)
+ assertEquals("foo", category?.name)
+ assertEquals(123L, category?.lastUsed?.time)
+ assertEquals(2, category?.timesUsed)
+
+ verify(client).query(
+ eq(BASE_URI),
+ eq(ALL_FIELDS),
+ eq("$COLUMN_NAME=?"),
+ queryCaptor.capture(),
+ isNull()
+ )
+ assertEquals("foo", queryCaptor.firstValue[0])
+ }
+
+ @Test(expected = RuntimeException::class)
+ fun findCategoryTranslatesExceptions() {
+ whenever(client.query(any(), any(), any(), any(), anyOrNull())).thenThrow(RemoteException(""))
+ testObject.find("foo")
+ }
+
+ @Test(expected = RuntimeException::class)
+ fun recentCategoriesTranslatesExceptions() {
+ whenever(client.query(any(), any(), anyOrNull(), any(), any())).thenThrow(RemoteException(""))
+ testObject.recentCategories(1)
+ }
+
+ @Test
+ fun recentCategoriesReturnsEmptyList_nullCursor() {
+ whenever(client.query(any(), any(), anyOrNull(), any(), any())).thenReturn(null)
+ assertTrue(testObject.recentCategories(1).isEmpty())
+ }
+
+ @Test
+ fun recentCategoriesReturnsEmptyList_emptyCursor() {
+ whenever(client.query(any(), any(), any(), any(), any())).thenReturn(createCursor(0))
+ assertTrue(testObject.recentCategories(1).isEmpty())
+ }
+
+ @Test
+ fun cursorsAreClosedAfterRecentCategoriesQuery() {
+ val mockCursor: Cursor = mock()
+ whenever(client.query(any(), any(), anyOrNull(), any(), any())).thenReturn(mockCursor)
+ whenever(mockCursor.moveToFirst()).thenReturn(false)
+
+ testObject.recentCategories(1)
+
+ verify(mockCursor).close()
+ }
+
+ @Test
+ fun recentCategoriesReturnsLessThanLimit() {
+ whenever(client.query(any(), any(), anyOrNull(), any(), any())).thenReturn(createCursor(1))
+
+ val result = testObject.recentCategories(10)
+
+ assertEquals(1, result.size)
+ assertEquals("foo", result[0])
+
+ verify(client).query(
+ eq(BASE_URI),
+ eq(ALL_FIELDS),
+ isNull(),
+ queryCaptor.capture(),
+ eq("$COLUMN_LAST_USED DESC")
+ )
+ assertEquals(0, queryCaptor.firstValue.size)
+ }
+
+ @Test
+ fun recentCategoriesHonorsLimit() {
+ whenever(client.query(any(), any(), anyOrNull(), any(), any())).thenReturn(createCursor(10))
+
+ val result = testObject.recentCategories(5)
+
+ assertEquals(5, result.size)
+ }
+
+ private fun createCursor(rowCount: Int) = MatrixCursor(columns, rowCount).apply {
+ for (i in 0 until rowCount) {
+ addRow(listOf("1", "foo", "123", "2"))
+ }
+ }
+
+}
\ No newline at end of file
diff --git a/app/src/test/kotlin/fr/free/nrw/commons/contributions/ContributionDaoTest.kt b/app/src/test/kotlin/fr/free/nrw/commons/contributions/ContributionDaoTest.kt
new file mode 100644
index 000000000..762e0bb85
--- /dev/null
+++ b/app/src/test/kotlin/fr/free/nrw/commons/contributions/ContributionDaoTest.kt
@@ -0,0 +1,335 @@
+package fr.free.nrw.commons.contributions
+
+import android.content.ContentProviderClient
+import android.content.ContentValues
+import android.database.MatrixCursor
+import android.database.sqlite.SQLiteDatabase
+import android.net.Uri
+import android.os.RemoteException
+import com.nhaarman.mockito_kotlin.*
+import fr.free.nrw.commons.BuildConfig
+import fr.free.nrw.commons.TestCommonsApplication
+import fr.free.nrw.commons.Utils
+import fr.free.nrw.commons.contributions.Contribution.*
+import fr.free.nrw.commons.contributions.ContributionDao.Table
+import fr.free.nrw.commons.contributions.ContributionsContentProvider.BASE_URI
+import fr.free.nrw.commons.contributions.ContributionsContentProvider.uriForId
+import org.junit.Assert.*
+import org.junit.Before
+import org.junit.Test
+import org.junit.runner.RunWith
+import org.robolectric.RobolectricTestRunner
+import org.robolectric.annotation.Config
+import java.util.*
+
+@RunWith(RobolectricTestRunner::class)
+@Config(constants = BuildConfig::class, sdk = [21], application = TestCommonsApplication::class)
+class ContributionDaoTest {
+ private val localUri = "http://example.com/"
+ private val client: ContentProviderClient = mock()
+ private val database: SQLiteDatabase = mock()
+ private val captor = argumentCaptor()
+
+ private lateinit var contentUri: Uri
+ private lateinit var testObject: ContributionDao
+
+ @Before
+ fun setUp() {
+ contentUri = uriForId(111)
+ testObject = ContributionDao { client }
+ }
+
+ @Test
+ fun createTable() {
+ Table.onCreate(database)
+ verify(database).execSQL(Table.CREATE_TABLE_STATEMENT)
+ }
+
+ @Test
+ fun deleteTable() {
+ Table.onDelete(database)
+
+ inOrder(database) {
+ verify(database).execSQL(Table.DROP_TABLE_STATEMENT)
+ verify(database).execSQL(Table.CREATE_TABLE_STATEMENT)
+ }
+ }
+
+ @Test
+ fun upgradeDatabase_v1_to_v2() {
+ Table.onUpdate(database, 1, 2)
+
+ inOrder(database) {
+ verify(database).execSQL(Table.ADD_DESCRIPTION_FIELD)
+ verify(database).execSQL(Table.ADD_CREATOR_FIELD)
+ }
+ }
+
+ @Test
+ fun upgradeDatabase_v2_to_v3() {
+ Table.onUpdate(database, 2, 3)
+
+ inOrder(database) {
+ verify(database).execSQL(Table.ADD_MULTIPLE_FIELD)
+ verify(database).execSQL(Table.SET_DEFAULT_MULTIPLE)
+ }
+ }
+
+ @Test
+ fun upgradeDatabase_v3_to_v4() {
+ Table.onUpdate(database, 3, 4)
+
+ // No changes
+ verifyZeroInteractions(database)
+ }
+
+ @Test
+ fun upgradeDatabase_v4_to_v5() {
+ Table.onUpdate(database, 4, 5)
+
+ // No changes
+ verifyZeroInteractions(database)
+ }
+
+ @Test
+ fun upgradeDatabase_v5_to_v6() {
+ Table.onUpdate(database, 5, 6)
+
+ inOrder(database) {
+ verify(database).execSQL(Table.ADD_WIDTH_FIELD)
+ verify(database).execSQL(Table.SET_DEFAULT_WIDTH)
+ verify(database).execSQL(Table.ADD_HEIGHT_FIELD)
+ verify(database).execSQL(Table.SET_DEFAULT_HEIGHT)
+ verify(database).execSQL(Table.ADD_LICENSE_FIELD)
+ verify(database).execSQL(Table.SET_DEFAULT_LICENSE)
+ }
+ }
+
+ @Test
+ fun saveNewContribution_nonNullFields() {
+ whenever(client.insert(isA(), isA())).thenReturn(contentUri)
+ val contribution = createContribution(true, null, null, null, null)
+
+ testObject.save(contribution)
+
+ assertEquals(contentUri, contribution.contentUri)
+ verify(client).insert(eq(BASE_URI), captor.capture())
+ captor.firstValue.let {
+ // Long fields
+ assertEquals(222L, it.getAsLong(Table.COLUMN_LENGTH))
+ assertEquals(321L, it.getAsLong(Table.COLUMN_TIMESTAMP))
+ assertEquals(333L, it.getAsLong(Table.COLUMN_TRANSFERRED))
+
+ // Integer fields
+ assertEquals(STATE_COMPLETED, it.getAsInteger(Table.COLUMN_STATE))
+ assertEquals(640, it.getAsInteger(Table.COLUMN_WIDTH))
+ assertEquals(480, it.getAsInteger(Table.COLUMN_HEIGHT))
+
+ // String fields
+ assertEquals(SOURCE_CAMERA, it.getAsString(Table.COLUMN_SOURCE))
+ assertEquals("desc", it.getAsString(Table.COLUMN_DESCRIPTION))
+ assertEquals("create", it.getAsString(Table.COLUMN_CREATOR))
+ assertEquals("007", it.getAsString(Table.COLUMN_LICENSE))
+ }
+ }
+
+ @Test
+ fun saveNewContribution_nullableFieldsAreNull() {
+ whenever(client.insert(isA(), isA())).thenReturn(contentUri)
+ val contribution = createContribution(true, null, null, null, null)
+
+ testObject.save(contribution)
+
+ assertEquals(contentUri, contribution.contentUri)
+ verify(client).insert(eq(BASE_URI), captor.capture())
+ captor.firstValue.let {
+ // Nullable fields are absent if null
+ assertFalse(it.containsKey(Table.COLUMN_LOCAL_URI))
+ assertFalse(it.containsKey(Table.COLUMN_IMAGE_URL))
+ assertFalse(it.containsKey(Table.COLUMN_UPLOADED))
+ }
+ }
+
+ @Test
+ fun saveNewContribution_nullableImageUrlUsesFileAsBackup() {
+ whenever(client.insert(isA(), isA())).thenReturn(contentUri)
+ val contribution = createContribution(true, null, null, null, "file")
+
+ testObject.save(contribution)
+
+ assertEquals(contentUri, contribution.contentUri)
+ verify(client).insert(eq(BASE_URI), captor.capture())
+ captor.firstValue.let {
+ // Nullable fields are absent if null
+ assertFalse(it.containsKey(Table.COLUMN_LOCAL_URI))
+ assertFalse(it.containsKey(Table.COLUMN_UPLOADED))
+ assertEquals(Utils.makeThumbBaseUrl("file"), it.getAsString(Table.COLUMN_IMAGE_URL))
+ }
+ }
+
+ @Test
+ fun saveNewContribution_nullableFieldsAreNonNull() {
+ whenever(client.insert(isA(), isA())).thenReturn(contentUri)
+ val contribution = createContribution(true, Uri.parse(localUri),
+ "image", Date(456L), null)
+
+ testObject.save(contribution)
+
+ assertEquals(contentUri, contribution.contentUri)
+ verify(client).insert(eq(BASE_URI), captor.capture())
+ captor.firstValue.let {
+ assertEquals(localUri, it.getAsString(Table.COLUMN_LOCAL_URI))
+ assertEquals("image", it.getAsString(Table.COLUMN_IMAGE_URL))
+ assertEquals(456L, it.getAsLong(Table.COLUMN_UPLOADED))
+ }
+ }
+
+ @Test
+ fun saveNewContribution_booleanEncodesTrue() {
+ whenever(client.insert(isA(), isA())).thenReturn(contentUri)
+ val contribution = createContribution(true, null, null, null, null)
+
+ testObject.save(contribution)
+
+ assertEquals(contentUri, contribution.contentUri)
+ verify(client).insert(eq(BASE_URI), captor.capture())
+
+ // Boolean true --> 1 for ths encoding scheme
+ assertEquals("Boolean true should be encoded as 1", 1,
+ captor.firstValue.getAsInteger(Table.COLUMN_MULTIPLE))
+ }
+
+ @Test
+ fun saveNewContribution_booleanEncodesFalse() {
+ whenever(client.insert(isA(), isA())).thenReturn(contentUri)
+ val contribution = createContribution(false, null, null, null, null)
+
+ testObject.save(contribution)
+
+ assertEquals(contentUri, contribution.contentUri)
+ verify(client).insert(eq(BASE_URI), captor.capture())
+
+ // Boolean true --> 1 for ths encoding scheme
+ assertEquals("Boolean false should be encoded as 0", 0,
+ captor.firstValue.getAsInteger(Table.COLUMN_MULTIPLE))
+ }
+
+ @Test
+ fun saveExistingContribution() {
+ val contribution = createContribution(false, null, null, null, null)
+ contribution.contentUri = contentUri
+
+ testObject.save(contribution)
+
+ verify(client).update(eq(contentUri), isA(), isNull(), isNull())
+ }
+
+ @Test(expected = RuntimeException::class)
+ fun saveTranslatesExceptions() {
+ whenever(client.insert(isA(), isA())).thenThrow(RemoteException(""))
+
+ testObject.save(createContribution(false, null, null, null, null))
+ }
+
+ @Test(expected = RuntimeException::class)
+ fun deleteTranslatesExceptions() {
+ whenever(client.delete(anyOrNull(), anyOrNull(), anyOrNull())).thenThrow(RemoteException(""))
+
+ val contribution = createContribution(false, null, null, null, null)
+ contribution.contentUri = contentUri
+ testObject.delete(contribution)
+ }
+
+ @Test(expected = RuntimeException::class)
+ fun exceptionThrownWhenAttemptingToDeleteUnsavedContribution() {
+ testObject.delete(createContribution(false, null, null, null, null))
+ }
+
+ @Test
+ fun deleteExistingContribution() {
+ val contribution = createContribution(false, null, null, null, null)
+ contribution.contentUri = contentUri
+
+ testObject.delete(contribution)
+
+ verify(client).delete(eq(contentUri), isNull(), isNull())
+ }
+
+ @Test
+ fun createFromCursor() {
+ val created = 321L
+ val uploaded = 456L
+ createCursor(created, uploaded, false, localUri).let { mc ->
+ testObject.fromCursor(mc).let {
+ assertEquals(uriForId(111), it.contentUri)
+ assertEquals("file", it.filename)
+ assertEquals(localUri, it.localUri.toString())
+ assertEquals("image", it.imageUrl)
+ assertEquals(created, it.timestamp.time)
+ assertEquals(created, it.dateCreated.time)
+ assertEquals(STATE_QUEUED, it.state)
+ assertEquals(222L, it.dataLength)
+ assertEquals(uploaded, it.dateUploaded?.time)
+ assertEquals(88L, it.transferred)
+ assertEquals(SOURCE_GALLERY, it.source)
+ assertEquals("desc", it.description)
+ assertEquals("create", it.creator)
+ assertEquals(640, it.width)
+ assertEquals(480, it.height)
+ assertEquals("007", it.license)
+ }
+ }
+ }
+
+ @Test
+ fun createFromCursor_nullableTimestamps() {
+ createCursor(0L, 0L, false, localUri).let { mc ->
+ testObject.fromCursor(mc).let {
+ assertNull(it.timestamp)
+ assertNull(it.dateCreated)
+ assertNull(it.dateUploaded)
+ }
+ }
+ }
+
+ @Test
+ fun createFromCursor_nullableLocalUri() {
+ createCursor(0L, 0L, false, "").let { mc ->
+ testObject.fromCursor(mc).let {
+ assertNull(it.localUri)
+ assertNull(it.dateCreated)
+ assertNull(it.dateUploaded)
+ }
+ }
+ }
+
+ @Test
+ fun createFromCursor_booleanEncoding() {
+ val mcFalse = createCursor(0L, 0L, false, localUri)
+ assertFalse(testObject.fromCursor(mcFalse).multiple)
+
+ val mcHammer = createCursor(0L, 0L, true, localUri)
+ assertTrue(testObject.fromCursor(mcHammer).multiple)
+ }
+
+ private fun createCursor(created: Long, uploaded: Long, multiple: Boolean, localUri: String) =
+ MatrixCursor(Table.ALL_FIELDS, 1).apply {
+ addRow(listOf("111", "file", localUri, "image",
+ created, STATE_QUEUED, 222L, uploaded, 88L, SOURCE_GALLERY, "desc",
+ "create", if (multiple) 1 else 0, 640, 480, "007"))
+ moveToFirst()
+ }
+
+ private fun createContribution(isMultiple: Boolean, localUri: Uri?, imageUrl: String?, dateUploaded: Date?, filename: String?) =
+ Contribution(localUri, imageUrl, filename, "desc", 222L, Date(321L), dateUploaded,
+ "create", "edit", "coords").apply {
+ state = STATE_COMPLETED
+ transferred = 333L
+ source = SOURCE_CAMERA
+ license = "007"
+ multiple = isMultiple
+ timestamp = Date(321L)
+ width = 640
+ height = 480 // VGA should be enough for anyone, right?
+ }
+}
\ No newline at end of file
diff --git a/app/src/test/kotlin/fr/free/nrw/commons/modifications/ModifierSequenceDaoTest.kt b/app/src/test/kotlin/fr/free/nrw/commons/modifications/ModifierSequenceDaoTest.kt
new file mode 100644
index 000000000..bf0ddf772
--- /dev/null
+++ b/app/src/test/kotlin/fr/free/nrw/commons/modifications/ModifierSequenceDaoTest.kt
@@ -0,0 +1,156 @@
+package fr.free.nrw.commons.modifications
+
+import android.content.ContentProviderClient
+import android.content.ContentValues
+import android.database.MatrixCursor
+import android.database.sqlite.SQLiteDatabase
+import android.net.Uri
+import android.os.RemoteException
+import com.nhaarman.mockito_kotlin.*
+import fr.free.nrw.commons.BuildConfig
+import fr.free.nrw.commons.TestCommonsApplication
+import fr.free.nrw.commons.modifications.ModificationsContentProvider.BASE_URI
+import fr.free.nrw.commons.modifications.ModifierSequenceDao.Table.*
+import org.junit.Assert.assertEquals
+import org.junit.Assert.assertTrue
+import org.junit.Before
+import org.junit.Test
+import org.junit.runner.RunWith
+import org.robolectric.RobolectricTestRunner
+import org.robolectric.annotation.Config
+
+@RunWith(RobolectricTestRunner::class)
+@Config(constants = BuildConfig::class, sdk = [21], application = TestCommonsApplication::class)
+class ModifierSequenceDaoTest {
+
+ private val mediaUrl = "http://example.com/"
+ private val columns = arrayOf(COLUMN_ID, COLUMN_MEDIA_URI, COLUMN_DATA)
+ private val client: ContentProviderClient = mock()
+ private val database: SQLiteDatabase = mock()
+ private val contentValuesCaptor = argumentCaptor()
+
+ private lateinit var testObject: ModifierSequenceDao
+
+ @Before
+ fun setUp() {
+ testObject = ModifierSequenceDao { client }
+ }
+
+ @Test
+ fun createFromCursorWithEmptyModifiers() {
+ testObject.fromCursor(createCursor("")).let {
+ assertEquals(mediaUrl, it.mediaUri.toString())
+ assertEquals(BASE_URI.buildUpon().appendPath("1").toString(), it.contentUri.toString())
+ assertTrue(it.modifiers.isEmpty())
+ }
+ }
+
+ @Test
+ fun createFromCursorWtihCategoryModifier() {
+ val cursor = createCursor("{\"name\": \"CategoriesModifier\", \"data\": {}}")
+
+ val seq = testObject.fromCursor(cursor)
+
+ assertEquals(1, seq.modifiers.size)
+ assertTrue(seq.modifiers[0] is CategoryModifier)
+ }
+
+ @Test
+ fun createFromCursorWithRemoveModifier() {
+ val cursor = createCursor("{\"name\": \"TemplateRemoverModifier\", \"data\": {}}")
+
+ val seq = testObject.fromCursor(cursor)
+
+ assertEquals(1, seq.modifiers.size)
+ assertTrue(seq.modifiers[0] is TemplateRemoveModifier)
+ }
+
+ @Test
+ fun deleteSequence() {
+ whenever(client.delete(isA(), isNull(), isNull())).thenReturn(1)
+ val seq = testObject.fromCursor(createCursor(""))
+
+ testObject.delete(seq)
+
+ verify(client).delete(eq(seq.contentUri), isNull(), isNull())
+ }
+
+ @Test(expected = RuntimeException::class)
+ fun deleteTranslatesRemoteExceptions() {
+ whenever(client.delete(isA(), isNull(), isNull())).thenThrow(RemoteException(""))
+ val seq = testObject.fromCursor(createCursor(""))
+
+ testObject.delete(seq)
+ }
+
+ @Test
+ fun saveExistingSequence() {
+ val modifierJson = "{\"name\":\"CategoriesModifier\",\"data\":{}}"
+ val expectedData = "{\"modifiers\":[$modifierJson]}"
+ val cursor = createCursor(modifierJson)
+ val seq = testObject.fromCursor(cursor)
+
+ testObject.save(seq)
+
+ verify(client).update(eq(seq.contentUri), contentValuesCaptor.capture(), isNull(), isNull())
+ contentValuesCaptor.firstValue.let {
+ assertEquals(2, it.size())
+ assertEquals(mediaUrl, it.get(COLUMN_MEDIA_URI))
+ assertEquals(expectedData, it.get(COLUMN_DATA))
+ }
+ }
+
+ @Test
+ fun saveNewSequence() {
+ val expectedContentUri = BASE_URI.buildUpon().appendPath("1").build()
+ whenever(client.insert(isA(), isA())).thenReturn(expectedContentUri)
+ val seq = ModifierSequence(Uri.parse(mediaUrl))
+
+ testObject.save(seq)
+
+ assertEquals(expectedContentUri.toString(), seq.contentUri.toString())
+ verify(client).insert(eq(ModificationsContentProvider.BASE_URI), contentValuesCaptor.capture())
+ contentValuesCaptor.firstValue.let {
+ assertEquals(2, it.size())
+ assertEquals(mediaUrl, it.get(COLUMN_MEDIA_URI))
+ assertEquals("{\"modifiers\":[]}", it.get(COLUMN_DATA))
+ }
+ }
+
+ @Test(expected = RuntimeException::class)
+ fun saveTranslatesRemoteExceptions() {
+ whenever(client.insert(isA(), isA())).thenThrow(RemoteException(""))
+ testObject.save(ModifierSequence(Uri.parse(mediaUrl)))
+ }
+
+ @Test
+ fun createTable() {
+ onCreate(database)
+ verify(database).execSQL(CREATE_TABLE_STATEMENT)
+ }
+
+ @Test
+ fun updateTable() {
+ onUpdate(database, 1, 2)
+
+ inOrder(database) {
+ verify(database).execSQL(DROP_TABLE_STATEMENT)
+ verify(database).execSQL(CREATE_TABLE_STATEMENT)
+ }
+ }
+
+ @Test
+ fun deleteTable() {
+ onDelete(database)
+
+ inOrder(database) {
+ verify(database).execSQL(DROP_TABLE_STATEMENT)
+ verify(database).execSQL(CREATE_TABLE_STATEMENT)
+ }
+ }
+
+ private fun createCursor(modifierJson: String) = MatrixCursor(columns, 1).apply {
+ addRow(listOf("1", mediaUrl, "{\"modifiers\": [$modifierJson]}"))
+ moveToFirst()
+ }
+}
\ No newline at end of file
diff --git a/app/src/test/kotlin/fr/free/nrw/commons/mwapi/ApacheHttpClientMediaWikiApiTest.kt b/app/src/test/kotlin/fr/free/nrw/commons/mwapi/ApacheHttpClientMediaWikiApiTest.kt
new file mode 100644
index 000000000..c51d354c2
--- /dev/null
+++ b/app/src/test/kotlin/fr/free/nrw/commons/mwapi/ApacheHttpClientMediaWikiApiTest.kt
@@ -0,0 +1,246 @@
+package fr.free.nrw.commons.mwapi
+
+import android.content.SharedPreferences
+import android.os.Build
+import android.preference.PreferenceManager
+import fr.free.nrw.commons.BuildConfig
+import fr.free.nrw.commons.TestCommonsApplication
+import okhttp3.mockwebserver.MockResponse
+import okhttp3.mockwebserver.MockWebServer
+import okhttp3.mockwebserver.RecordedRequest
+import org.junit.After
+import org.junit.Assert.*
+import org.junit.Before
+import org.junit.Test
+import org.junit.runner.RunWith
+import org.robolectric.RobolectricTestRunner
+import org.robolectric.RuntimeEnvironment
+import org.robolectric.annotation.Config
+import java.net.URLDecoder
+import java.util.*
+
+@RunWith(RobolectricTestRunner::class)
+@Config(constants = BuildConfig::class, sdk = intArrayOf(21), application = TestCommonsApplication::class)
+class ApacheHttpClientMediaWikiApiTest {
+
+ private lateinit var testObject: ApacheHttpClientMediaWikiApi
+ private lateinit var server: MockWebServer
+ private lateinit var sharedPreferences: SharedPreferences
+
+ @Before
+ fun setUp() {
+ server = MockWebServer()
+ sharedPreferences = PreferenceManager.getDefaultSharedPreferences(RuntimeEnvironment.application)
+ testObject = ApacheHttpClientMediaWikiApi(RuntimeEnvironment.application, "http://" + server.hostName + ":" + server.port + "/", sharedPreferences)
+ testObject.setWikiMediaToolforgeUrl("http://" + server.hostName + ":" + server.port + "/")
+ }
+
+ @After
+ fun teardown() {
+ server.shutdown()
+ }
+
+ @Test
+ fun authCookiesAreHandled() {
+ assertEquals("", testObject.authCookie)
+
+ testObject.authCookie = "cookie=chocolate-chip"
+
+ assertEquals("cookie=chocolate-chip", testObject.authCookie)
+ }
+
+ @Test
+ fun simpleLoginWithWrongPassword() {
+ server.enqueue(MockResponse().setBody(""))
+ server.enqueue(MockResponse().setBody(""))
+
+ val result = testObject.login("foo", "bar")
+
+ assertBasicRequestParameters(server, "POST").let { loginTokenRequest ->
+ parseBody(loginTokenRequest.body.readUtf8()).let { body ->
+ assertEquals("xml", body["format"])
+ assertEquals("query", body["action"])
+ assertEquals("login", body["type"])
+ assertEquals("tokens", body["meta"])
+ }
+ }
+
+ assertBasicRequestParameters(server, "POST").let { loginRequest ->
+ parseBody(loginRequest.body.readUtf8()).let { body ->
+ assertEquals("1", body["rememberMe"])
+ assertEquals("foo", body["username"])
+ assertEquals("bar", body["password"])
+ assertEquals("baz", body["logintoken"])
+ assertEquals("https://commons.wikimedia.org", body["loginreturnurl"])
+ assertEquals("xml", body["format"])
+ }
+ }
+
+ assertEquals("wrongpassword", result)
+ }
+
+ @Test
+ fun simpleLogin() {
+ server.enqueue(MockResponse().setBody(""))
+ server.enqueue(MockResponse().setBody(""))
+
+ val result = testObject.login("foo", "bar")
+
+ assertBasicRequestParameters(server, "POST").let { loginTokenRequest ->
+ parseBody(loginTokenRequest.body.readUtf8()).let { body ->
+ assertEquals("xml", body["format"])
+ assertEquals("query", body["action"])
+ assertEquals("login", body["type"])
+ assertEquals("tokens", body["meta"])
+ }
+ }
+
+ assertBasicRequestParameters(server, "POST").let { loginRequest ->
+ parseBody(loginRequest.body.readUtf8()).let { body ->
+ assertEquals("1", body["rememberMe"])
+ assertEquals("foo", body["username"])
+ assertEquals("bar", body["password"])
+ assertEquals("baz", body["logintoken"])
+ assertEquals("https://commons.wikimedia.org", body["loginreturnurl"])
+ assertEquals("xml", body["format"])
+ }
+ }
+
+ assertEquals("PASS", result)
+ }
+
+ @Test
+ fun twoFactorLogin() {
+ server.enqueue(MockResponse().setBody(""))
+ server.enqueue(MockResponse().setBody(""))
+
+ val result = testObject.login("foo", "bar", "2fa")
+
+ assertBasicRequestParameters(server, "POST").let { loginTokenRequest ->
+ parseBody(loginTokenRequest.body.readUtf8()).let { body ->
+ assertEquals("xml", body["format"])
+ assertEquals("query", body["action"])
+ assertEquals("login", body["type"])
+ assertEquals("tokens", body["meta"])
+ }
+ }
+
+ assertBasicRequestParameters(server, "POST").let { loginRequest ->
+ parseBody(loginRequest.body.readUtf8()).let { body ->
+ assertEquals("true", body["rememberMe"])
+ assertEquals("foo", body["username"])
+ assertEquals("bar", body["password"])
+ assertEquals("baz", body["logintoken"])
+ assertEquals("true", body["logincontinue"])
+ assertEquals("2fa", body["OATHToken"])
+ assertEquals("xml", body["format"])
+ }
+ }
+
+ assertEquals("PASS", result)
+ }
+
+ @Test
+ fun validateLoginForLoggedInUser() {
+ server.enqueue(MockResponse().setBody(""))
+
+ val result = testObject.validateLogin()
+
+ assertBasicRequestParameters(server, "GET").let { loginTokenRequest ->
+ parseQueryParams(loginTokenRequest).let { body ->
+ assertEquals("xml", body["format"])
+ assertEquals("query", body["action"])
+ assertEquals("userinfo", body["meta"])
+ }
+ }
+
+ assertTrue(result)
+ }
+
+ @Test
+ fun validateLoginForLoggedOutUser() {
+ server.enqueue(MockResponse().setBody(""))
+
+ val result = testObject.validateLogin()
+
+ assertBasicRequestParameters(server, "GET").let { loginTokenRequest ->
+ parseQueryParams(loginTokenRequest).let { params ->
+ assertEquals("xml", params["format"])
+ assertEquals("query", params["action"])
+ assertEquals("userinfo", params["meta"])
+ }
+ }
+
+ assertFalse(result)
+ }
+
+ @Test
+ fun editToken() {
+ server.enqueue(MockResponse().setBody(""))
+
+ val result = testObject.editToken
+
+ assertBasicRequestParameters(server, "GET").let { loginTokenRequest ->
+ parseQueryParams(loginTokenRequest).let { params ->
+ assertEquals("xml", params["format"])
+ assertEquals("tokens", params["action"])
+ assertEquals("edit", params["type"])
+ }
+ }
+
+ assertEquals("baz", result)
+ }
+
+ @Test
+ fun fileExistsWithName_FileNotFound() {
+ server.enqueue(MockResponse().setBody(" "))
+
+ val result = testObject.fileExistsWithName("foo")
+
+ assertBasicRequestParameters(server, "GET").let { request ->
+ parseQueryParams(request).let { params ->
+ assertEquals("xml", params["format"])
+ assertEquals("query", params["action"])
+ assertEquals("imageinfo", params["prop"])
+ assertEquals("File:foo", params["titles"])
+ }
+ }
+
+ assertFalse(result)
+ }
+
+ @Test
+ fun getUploadCount() {
+ server.enqueue(MockResponse().setBody("23\n"))
+
+ val testObserver = testObject.getUploadCount("testUsername").test()
+
+ assertEquals("testUsername", parseQueryParams(server.takeRequest())["user"])
+ assertEquals(1, testObserver.valueCount())
+ assertEquals(23, testObserver.values()[0])
+ }
+
+ private fun assertBasicRequestParameters(server: MockWebServer, method: String): RecordedRequest = server.takeRequest().let {
+ assertEquals("/", it.requestUrl.encodedPath())
+ assertEquals(method, it.method)
+ assertEquals("Commons/${BuildConfig.VERSION_NAME} (https://mediawiki.org/wiki/Apps/Commons) Android/${Build.VERSION.RELEASE}",
+ it.getHeader("User-Agent"))
+ if ("POST" == method) {
+ assertEquals("application/x-www-form-urlencoded", it.getHeader("Content-Type"))
+ }
+ return it
+ }
+
+ private fun parseQueryParams(request: RecordedRequest) = HashMap().apply {
+ request.requestUrl.let {
+ it.queryParameterNames().forEach { name -> put(name, it.queryParameter(name)) }
+ }
+ }
+
+ private fun parseBody(body: String): Map = HashMap().apply {
+ body.split("&".toRegex()).dropLastWhile { it.isEmpty() }.toTypedArray().forEach { prop ->
+ val pair = prop.split("=".toRegex()).dropLastWhile { it.isEmpty() }.toTypedArray()
+ put(pair[0], URLDecoder.decode(pair[1], "utf-8"))
+ }
+ }
+}
diff --git a/app/src/test/kotlin/fr/free/nrw/commons/utils/StringSortingUtilsTest.kt b/app/src/test/kotlin/fr/free/nrw/commons/utils/StringSortingUtilsTest.kt
new file mode 100644
index 000000000..83e2f7169
--- /dev/null
+++ b/app/src/test/kotlin/fr/free/nrw/commons/utils/StringSortingUtilsTest.kt
@@ -0,0 +1,41 @@
+package fr.free.nrw.commons.utils
+
+import fr.free.nrw.commons.utils.StringSortingUtils.sortBySimilarity
+import org.junit.Assert.assertEquals
+import org.junit.Test
+import java.util.Collections.sort
+
+class StringSortingUtilsTest {
+
+ @Test
+ fun testSortingNumbersBySimilarity() {
+ val actualList = listOf("1234567", "4567", "12345", "123", "1234")
+ val expectedList = listOf("1234", "12345", "123", "1234567", "4567")
+
+ sort(actualList, sortBySimilarity("1234"))
+
+ assertEquals(expectedList, actualList)
+ }
+
+ @Test
+ fun testSortingTextBySimilarity() {
+ val actualList = listOf("The quick brown fox",
+ "quick brown fox",
+ "The",
+ "The quick ",
+ "The fox",
+ "brown fox",
+ "fox")
+ val expectedList = listOf("The",
+ "The fox",
+ "The quick ",
+ "The quick brown fox",
+ "quick brown fox",
+ "brown fox",
+ "fox")
+
+ sort(actualList, sortBySimilarity("The"))
+
+ assertEquals(expectedList, actualList)
+ }
+}
\ No newline at end of file
diff --git a/build.gradle b/build.gradle
index b0e8b6718..42dfeec75 100644
--- a/build.gradle
+++ b/build.gradle
@@ -1,6 +1,6 @@
// Top-level build file where you can add configuration options common to all sub-projects/modules.
buildscript {
- ext.kotlin_version = '1.1.51'
+ ext.kotlin_version = '1.2.31'
repositories {
jcenter()
mavenCentral()