diff --git a/app/build.gradle b/app/build.gradle index 21883df4..a7f566ac 100644 --- a/app/build.gradle +++ b/app/build.gradle @@ -20,8 +20,8 @@ android { applicationId APP_ID minSdkVersion 21 targetSdkVersion 29 - versionCode 77 - versionName "13.0" + versionCode 78 + versionName "13.1" testInstrumentationRunner "androidx.test.runner.AndroidJUnitRunner" vectorDrawables.useSupportLibrary = true @@ -101,8 +101,8 @@ ext.roomVersion = '2.2.5' ext.retrofitVersion = '2.9.0' ext.okhttpVersion = '4.9.0' ext.glideVersion = '4.11.0' -ext.daggerVersion = '2.29.1' -ext.materialdrawerVersion = '8.1.8' +ext.daggerVersion = '2.30.1' +ext.materialdrawerVersion = '8.2.0' // if libraries are changed here, they should also be changed in LicenseActivity dependencies { @@ -111,10 +111,10 @@ dependencies { implementation "androidx.core:core-ktx:1.3.2" implementation "androidx.appcompat:appcompat:1.2.0" implementation "androidx.fragment:fragment-ktx:1.2.5" - implementation "androidx.browser:browser:1.2.0" + implementation "androidx.browser:browser:1.3.0" implementation "androidx.swiperefreshlayout:swiperefreshlayout:1.1.0" implementation "androidx.recyclerview:recyclerview:1.1.0" - implementation "androidx.exifinterface:exifinterface:1.3.1" + implementation "androidx.exifinterface:exifinterface:1.3.2" implementation "androidx.cardview:cardview:1.0.0" implementation "androidx.preference:preference-ktx:1.1.1" implementation "androidx.sharetarget:sharetarget:1.0.0" @@ -139,8 +139,9 @@ dependencies { implementation "com.squareup.okhttp3:okhttp:$okhttpVersion" implementation "com.squareup.okhttp3:logging-interceptor:$okhttpVersion" + implementation "com.squareup.okhttp3:okhttp-tls:$okhttpVersion" - implementation "org.conscrypt:conscrypt-android:2.4.0" + implementation "org.conscrypt:conscrypt-android:2.5.1" implementation "com.github.bumptech.glide:glide:$glideVersion" implementation "com.github.bumptech.glide:okhttp3-integration:$glideVersion" @@ -158,7 +159,7 @@ dependencies { implementation "com.google.dagger:dagger-android-support:$daggerVersion" kapt "com.google.dagger:dagger-android-processor:$daggerVersion" - implementation "com.github.connyduck:sparkbutton:4.0.0" + implementation "com.github.connyduck:sparkbutton:4.1.0" implementation "com.github.chrisbanes:PhotoView:2.3.0" @@ -172,7 +173,7 @@ dependencies { testImplementation "androidx.test.ext:junit:1.1.2" testImplementation "org.robolectric:robolectric:4.4" - testImplementation "org.mockito:mockito-inline:3.6.0" + testImplementation "org.mockito:mockito-inline:3.6.28" testImplementation "com.nhaarman.mockitokotlin2:mockito-kotlin:2.2.0" androidTestImplementation "androidx.test.espresso:espresso-core:3.3.0" diff --git a/app/src/main/java/com/keylesspalace/tusky/MainActivity.kt b/app/src/main/java/com/keylesspalace/tusky/MainActivity.kt index 58cd3a02..31a4e80c 100644 --- a/app/src/main/java/com/keylesspalace/tusky/MainActivity.kt +++ b/app/src/main/java/com/keylesspalace/tusky/MainActivity.kt @@ -139,11 +139,8 @@ class MainActivity : BottomSheetActivity(), ActionButtonActivity, HasAndroidInje } } val accountRequested = accountId != -1L - if (accountRequested) { - val account = accountManager.activeAccount - if (account == null || accountId != account.id) { - accountManager.setActiveAccount(accountId) - } + if (accountRequested && accountId != activeAccount.id) { + accountManager.setActiveAccount(accountId) } if (canHandleMimeType(intent.type)) { // Sharing to Tusky from an external app @@ -155,8 +152,7 @@ class MainActivity : BottomSheetActivity(), ActionButtonActivity, HasAndroidInje showAccountChooserDialog(getString(R.string.action_share_as), true, object : AccountSelectionListener { override fun onAccountSelected(account: AccountEntity) { val requestedId = account.id - val activeAccount = accountManager.activeAccount - if (activeAccount != null && requestedId == activeAccount.id) { + if (requestedId == activeAccount.id) { // The correct account is already active forwardShare(intent) } else { diff --git a/app/src/main/java/com/keylesspalace/tusky/adapter/ListSelectionAdapter.kt b/app/src/main/java/com/keylesspalace/tusky/adapter/ListSelectionAdapter.kt index e5470df6..f9b19c69 100644 --- a/app/src/main/java/com/keylesspalace/tusky/adapter/ListSelectionAdapter.kt +++ b/app/src/main/java/com/keylesspalace/tusky/adapter/ListSelectionAdapter.kt @@ -22,7 +22,6 @@ import android.view.ViewGroup import android.widget.ArrayAdapter import com.keylesspalace.tusky.R import com.keylesspalace.tusky.entity.MastoList -import com.keylesspalace.tusky.util.ThemeUtils import kotlinx.android.synthetic.main.item_picker_list.view.* class ListSelectionAdapter(context: Context) : ArrayAdapter(context, R.layout.item_autocomplete_hashtag) { @@ -34,10 +33,7 @@ class ListSelectionAdapter(context: Context) : ArrayAdapter(context, ?: layoutInflater.inflate(R.layout.item_picker_list, parent, false) getItem(position)?.let { list -> - val title = view.title - title.text = list.title - val icon = ThemeUtils.getTintedDrawable(context, R.drawable.ic_list, R.attr.iconColor) - title.setCompoundDrawablesRelativeWithIntrinsicBounds(icon, null, null, null) + view.title.text = list.title } return view diff --git a/app/src/main/java/com/keylesspalace/tusky/adapter/PreviewPollOptionsAdapter.kt b/app/src/main/java/com/keylesspalace/tusky/adapter/PreviewPollOptionsAdapter.kt index bb77cd27..328e9626 100644 --- a/app/src/main/java/com/keylesspalace/tusky/adapter/PreviewPollOptionsAdapter.kt +++ b/app/src/main/java/com/keylesspalace/tusky/adapter/PreviewPollOptionsAdapter.kt @@ -22,7 +22,6 @@ import android.widget.TextView import androidx.core.widget.TextViewCompat import androidx.recyclerview.widget.RecyclerView import com.keylesspalace.tusky.R -import com.keylesspalace.tusky.util.ThemeUtils class PreviewPollOptionsAdapter: RecyclerView.Adapter() { @@ -55,9 +54,7 @@ class PreviewPollOptionsAdapter: RecyclerView.Adapter() { R.drawable.ic_radio_button_unchecked_18dp } - val iconDrawable = ThemeUtils.getTintedDrawable(textView.context, iconId, android.R.attr.textColorTertiary) - - TextViewCompat.setCompoundDrawablesRelativeWithIntrinsicBounds(textView, iconDrawable, null, null, null) + TextViewCompat.setCompoundDrawablesRelativeWithIntrinsicBounds(textView, iconId, 0, 0, 0) textView.text = options[position] diff --git a/app/src/main/java/com/keylesspalace/tusky/adapter/StatusBaseViewHolder.java b/app/src/main/java/com/keylesspalace/tusky/adapter/StatusBaseViewHolder.java index 3869ca02..046ab9cf 100644 --- a/app/src/main/java/com/keylesspalace/tusky/adapter/StatusBaseViewHolder.java +++ b/app/src/main/java/com/keylesspalace/tusky/adapter/StatusBaseViewHolder.java @@ -57,7 +57,6 @@ import java.text.SimpleDateFormat; import java.util.Date; import java.util.List; import java.util.Locale; -import java.util.Objects; import at.connyduck.sparkbutton.SparkButton; import at.connyduck.sparkbutton.helpers.Utils; @@ -566,9 +565,7 @@ public abstract class StatusBaseViewHolder extends RecyclerView.ViewHolder { // Set the icon next to the label. int drawableId = getLabelIcon(attachments.get(0).getType()); - Drawable drawable = Objects.requireNonNull(context.getDrawable(drawableId)); - ThemeUtils.setDrawableTint(context, drawable, android.R.attr.textColorTertiary); - mediaLabel.setCompoundDrawablesWithIntrinsicBounds(drawable, null, null, null); + mediaLabel.setCompoundDrawablesWithIntrinsicBounds(drawableId, 0, 0, 0); setAttachmentClickListener(mediaLabel, listener, i, attachment, false); } else { diff --git a/app/src/main/java/com/keylesspalace/tusky/adapter/TabAdapter.kt b/app/src/main/java/com/keylesspalace/tusky/adapter/TabAdapter.kt index cd877a15..b4517dc6 100644 --- a/app/src/main/java/com/keylesspalace/tusky/adapter/TabAdapter.kt +++ b/app/src/main/java/com/keylesspalace/tusky/adapter/TabAdapter.kt @@ -15,6 +15,7 @@ package com.keylesspalace.tusky.adapter +import android.content.res.ColorStateList import android.view.LayoutInflater import android.view.MotionEvent import android.view.View @@ -68,8 +69,7 @@ class TabAdapter(private var data: List, } else { holder.itemView.textView.setText(tab.text) } - val iconDrawable = ThemeUtils.getTintedDrawable(context, tab.icon, android.R.attr.textColorSecondary) - holder.itemView.textView.setCompoundDrawablesRelativeWithIntrinsicBounds(iconDrawable, null, null, null) + holder.itemView.textView.setCompoundDrawablesRelativeWithIntrinsicBounds(tab.icon, 0, 0, 0) if (small) { holder.itemView.textView.setOnClickListener { listener.onTabAdded(tab) @@ -110,6 +110,7 @@ class TabAdapter(private var data: List, val chip = holder.itemView.chipGroup.getChildAt(i).takeUnless { it.id == R.id.actionChip } as Chip? ?: Chip(context).apply { holder.itemView.chipGroup.addView(this, holder.itemView.chipGroup.size - 1) + chipIconTint = ColorStateList.valueOf(ThemeUtils.getColor(context, android.R.attr.textColorPrimary)) } chip.text = arg @@ -118,8 +119,7 @@ class TabAdapter(private var data: List, chip.chipIcon = null chip.setOnClickListener(null) } else { - val cancelIcon = ThemeUtils.getTintedDrawable(context, R.drawable.ic_cancel_24dp, android.R.attr.textColorPrimary) - chip.chipIcon = cancelIcon + chip.setChipIconResource(R.drawable.ic_cancel_24dp) chip.setOnClickListener { listener.onChipClicked(tab, holder.adapterPosition, i) } diff --git a/app/src/main/java/com/keylesspalace/tusky/components/compose/ComposeActivity.kt b/app/src/main/java/com/keylesspalace/tusky/components/compose/ComposeActivity.kt index 4eba7e32..e9615d33 100644 --- a/app/src/main/java/com/keylesspalace/tusky/components/compose/ComposeActivity.kt +++ b/app/src/main/java/com/keylesspalace/tusky/components/compose/ComposeActivity.kt @@ -534,8 +534,7 @@ class ComposeActivity : BaseActivity(), Status.Visibility.UNLISTED -> R.drawable.ic_lock_open_24dp else -> R.drawable.ic_lock_open_24dp } - val drawable = ThemeUtils.getTintedDrawable(this, iconRes, android.R.attr.textColorTertiary) - composeToggleVisibilityButton.setImageDrawable(drawable) + composeToggleVisibilityButton.setImageResource(iconRes) } private fun showComposeOptions() { diff --git a/app/src/main/java/com/keylesspalace/tusky/components/compose/view/ComposeScheduleView.java b/app/src/main/java/com/keylesspalace/tusky/components/compose/view/ComposeScheduleView.java index ca663936..a1a99a7d 100644 --- a/app/src/main/java/com/keylesspalace/tusky/components/compose/view/ComposeScheduleView.java +++ b/app/src/main/java/com/keylesspalace/tusky/components/compose/view/ComposeScheduleView.java @@ -26,13 +26,13 @@ import androidx.annotation.NonNull; import androidx.annotation.Nullable; import androidx.appcompat.app.AppCompatActivity; import androidx.constraintlayout.widget.ConstraintLayout; +import androidx.core.content.ContextCompat; import com.google.android.material.datepicker.CalendarConstraints; import com.google.android.material.datepicker.DateValidatorPointForward; import com.google.android.material.datepicker.MaterialDatePicker; import com.keylesspalace.tusky.R; import com.keylesspalace.tusky.fragment.TimePickerFragment; -import com.keylesspalace.tusky.util.ThemeUtils; import java.text.DateFormat; import java.text.ParseException; @@ -106,7 +106,7 @@ public class ComposeScheduleView extends ConstraintLayout { } private void setEditIcons() { - Drawable icon = ThemeUtils.getTintedDrawable(getContext(), R.drawable.ic_create_24dp, android.R.attr.textColorTertiary); + Drawable icon = ContextCompat.getDrawable(getContext(), R.drawable.ic_create_24dp); if (icon == null) { return; } diff --git a/app/src/main/java/com/keylesspalace/tusky/components/preference/AccountPreferencesFragment.kt b/app/src/main/java/com/keylesspalace/tusky/components/preference/AccountPreferencesFragment.kt index af882977..286b49b5 100644 --- a/app/src/main/java/com/keylesspalace/tusky/components/preference/AccountPreferencesFragment.kt +++ b/app/src/main/java/com/keylesspalace/tusky/components/preference/AccountPreferencesFragment.kt @@ -16,10 +16,10 @@ package com.keylesspalace.tusky.components.preference import android.content.Intent -import android.graphics.drawable.Drawable import android.os.Build import android.os.Bundle import android.util.Log +import androidx.annotation.DrawableRes import androidx.preference.PreferenceFragmentCompat import com.google.android.material.snackbar.Snackbar import com.keylesspalace.tusky.* @@ -71,7 +71,7 @@ class AccountPreferencesFragment : PreferenceFragmentCompat(), Injectable { preference { setTitle(R.string.title_tab_preferences) - icon = getTintedIcon(R.drawable.ic_tabs) + setIcon(R.drawable.ic_tabs) setOnPreferenceClickListener { val intent = Intent(context, TabPreferenceActivity::class.java) activity?.startActivity(intent) @@ -83,7 +83,7 @@ class AccountPreferencesFragment : PreferenceFragmentCompat(), Injectable { preference { setTitle(R.string.action_view_mutes) - icon = getTintedIcon(R.drawable.ic_mute_24dp) + setIcon(R.drawable.ic_mute_24dp) setOnPreferenceClickListener { val intent = Intent(context, AccountListActivity::class.java) intent.putExtra("type", AccountListActivity.Type.MUTES) @@ -112,7 +112,7 @@ class AccountPreferencesFragment : PreferenceFragmentCompat(), Injectable { preference { setTitle(R.string.title_domain_mutes) - icon = getTintedIcon(R.drawable.ic_mute_24dp) + setIcon(R.drawable.ic_mute_24dp) setOnPreferenceClickListener { val intent = Intent(context, InstanceListActivity::class.java) activity?.startActivity(intent) @@ -132,11 +132,9 @@ class AccountPreferencesFragment : PreferenceFragmentCompat(), Injectable { val visibility = accountManager.activeAccount?.defaultPostPrivacy ?: Status.Visibility.PUBLIC value = visibility.serverString() - icon = getIconForVisibility(visibility) + setIcon(getIconForVisibility(visibility)) setOnPreferenceChangeListener { _, newValue -> - icon = getIconForVisibility( - Status.Visibility.byString(newValue as String) - ) + setIcon(getIconForVisibility(Status.Visibility.byString(newValue as String))) syncWithServer(visibility = newValue) eventHub.dispatch(PreferenceChangedEvent(key)) true @@ -151,9 +149,9 @@ class AccountPreferencesFragment : PreferenceFragmentCompat(), Injectable { val sensitivity = accountManager.activeAccount?.defaultMediaSensitivity ?: false setDefaultValue(sensitivity) - icon = getIconForSensitivity(sensitivity) + setIcon(getIconForSensitivity(sensitivity)) setOnPreferenceChangeListener { _, newValue -> - icon = getIconForSensitivity(newValue as Boolean) + setIcon(getIconForSensitivity(newValue as Boolean)) syncWithServer(sensitive = newValue) eventHub.dispatch(PreferenceChangedEvent(key)) true @@ -303,30 +301,24 @@ class AccountPreferencesFragment : PreferenceFragmentCompat(), Injectable { } } - private fun getIconForVisibility(visibility: Status.Visibility): Drawable? { - val drawableId = when (visibility) { + @DrawableRes + private fun getIconForVisibility(visibility: Status.Visibility): Int { + return when (visibility) { Status.Visibility.PRIVATE -> R.drawable.ic_lock_outline_24dp Status.Visibility.UNLISTED -> R.drawable.ic_lock_open_24dp else -> R.drawable.ic_public_24dp } - - return getTintedIcon(drawableId) } - private fun getIconForSensitivity(sensitive: Boolean): Drawable? { - val drawableId = if (sensitive) { + @DrawableRes + private fun getIconForSensitivity(sensitive: Boolean): Int { + return if (sensitive) { R.drawable.ic_hide_media_24dp } else { R.drawable.ic_eye_24dp } - - return getTintedIcon(drawableId) - } - - private fun getTintedIcon(iconId: Int): Drawable? { - return ThemeUtils.getTintedDrawable(requireContext(), iconId, R.attr.iconColor) } private fun launchFilterActivity(filterContext: String, titleResource: Int) { diff --git a/app/src/main/java/com/keylesspalace/tusky/components/preference/PreferencesFragment.kt b/app/src/main/java/com/keylesspalace/tusky/components/preference/PreferencesFragment.kt index edddffca..5e61e2fa 100644 --- a/app/src/main/java/com/keylesspalace/tusky/components/preference/PreferencesFragment.kt +++ b/app/src/main/java/com/keylesspalace/tusky/components/preference/PreferencesFragment.kt @@ -39,7 +39,6 @@ class PreferencesFragment : PreferenceFragmentCompat(), Injectable { private var httpProxyPref: Preference? = null override fun onCreatePreferences(savedInstanceState: Bundle?, rootKey: String?) { - val context = requireContext() makePreferenceScreen { preferenceCategory(R.string.pref_title_appearance_settings) { listPreference { @@ -115,11 +114,8 @@ class PreferencesFragment : PreferenceFragmentCompat(), Injectable { key = PrefKeys.SHOW_BOT_OVERLAY setTitle(R.string.pref_title_bot_overlay) isSingleLineTitle = false - icon = ThemeUtils.getTintedDrawable( - context, - R.drawable.ic_bot_24dp, - R.attr.iconColor - ) + setIcon(R.drawable.ic_bot_24dp) + } switchPreference { diff --git a/app/src/main/java/com/keylesspalace/tusky/di/NetworkModule.kt b/app/src/main/java/com/keylesspalace/tusky/di/NetworkModule.kt index b349d50d..ca60bac8 100644 --- a/app/src/main/java/com/keylesspalace/tusky/di/NetworkModule.kt +++ b/app/src/main/java/com/keylesspalace/tusky/di/NetworkModule.kt @@ -24,7 +24,7 @@ import com.keylesspalace.tusky.db.AccountManager import com.keylesspalace.tusky.json.SpannedTypeAdapter import com.keylesspalace.tusky.network.InstanceSwitchAuthInterceptor import com.keylesspalace.tusky.network.MastodonApi -import com.keylesspalace.tusky.util.OkHttpUtils +import com.keylesspalace.tusky.util.okhttpClient import dagger.Module import dagger.Provides import okhttp3.OkHttpClient @@ -32,6 +32,7 @@ import okhttp3.logging.HttpLoggingInterceptor import retrofit2.Retrofit import retrofit2.adapter.rxjava2.RxJava2CallAdapterFactory import retrofit2.converter.gson.GsonConverterFactory +import retrofit2.create import javax.inject.Singleton /** @@ -55,7 +56,7 @@ class NetworkModule { accountManager: AccountManager, context: Context ): OkHttpClient { - return OkHttpUtils.getCompatibleClientBuilder(context) + return okhttpClient(context) .apply { addInterceptor(InstanceSwitchAuthInterceptor(accountManager)) if (BuildConfig.DEBUG) { @@ -81,5 +82,5 @@ class NetworkModule { @Provides @Singleton - fun providesApi(retrofit: Retrofit): MastodonApi = retrofit.create(MastodonApi::class.java) + fun providesApi(retrofit: Retrofit): MastodonApi = retrofit.create() } \ No newline at end of file diff --git a/app/src/main/java/com/keylesspalace/tusky/util/OkHttpUtils.java b/app/src/main/java/com/keylesspalace/tusky/util/OkHttpUtils.java deleted file mode 100644 index 22e13e5e..00000000 --- a/app/src/main/java/com/keylesspalace/tusky/util/OkHttpUtils.java +++ /dev/null @@ -1,87 +0,0 @@ -/* Copyright 2017 Andrew Dawson - * - * This file is part of Tusky. - * - * Tusky is free software: you can redistribute it and/or modify it under the terms of the GNU - * Lesser General Public License as published by the Free Software Foundation, either version 3 of - * the License, or (at your option) any later version. - * - * Tusky is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even - * the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser - * General Public License for more details. - * - * You should have received a copy of the GNU Lesser General Public License along with Tusky. If - * not, see . */ - -package com.keylesspalace.tusky.util; - -import android.content.Context; -import android.content.SharedPreferences; -import android.os.Build; - -import androidx.annotation.NonNull; -import androidx.preference.PreferenceManager; - -import com.keylesspalace.tusky.BuildConfig; - -import java.net.InetSocketAddress; -import java.net.Proxy; -import java.util.concurrent.TimeUnit; - -import okhttp3.Cache; -import okhttp3.Interceptor; -import okhttp3.OkHttpClient; -import okhttp3.Request; - -public class OkHttpUtils { - - @NonNull - public static OkHttpClient.Builder getCompatibleClientBuilder(@NonNull Context context) { - - SharedPreferences preferences = PreferenceManager.getDefaultSharedPreferences(context); - - boolean httpProxyEnabled = preferences.getBoolean("httpProxyEnabled", false); - String httpServer = preferences.getString("httpProxyServer", ""); - int httpPort; - try { - httpPort = Integer.parseInt(preferences.getString("httpProxyPort", "-1")); - } catch (NumberFormatException e) { - // user has entered wrong port, fall back to no proxy - httpPort = -1; - } - - int cacheSize = 25*1024*1024; // 25 MiB - - OkHttpClient.Builder builder = new OkHttpClient.Builder() - .addInterceptor(getUserAgentInterceptor()) - .readTimeout(30, TimeUnit.SECONDS) - .writeTimeout(30, TimeUnit.SECONDS) - .cache(new Cache(context.getCacheDir(), cacheSize)); - - if (httpProxyEnabled && !httpServer.isEmpty() && (httpPort > 0) && (httpPort < 65535)) { - InetSocketAddress address = InetSocketAddress.createUnresolved(httpServer, httpPort); - builder.proxy(new Proxy(Proxy.Type.HTTP, address)); - } - - return builder; - } - - /** - * Add a custom User-Agent that contains Tusky & Android Version to all requests - * Example: - * User-Agent: Tusky/1.1.2 Android/5.0.2 - */ - @NonNull - private static Interceptor getUserAgentInterceptor() { - return chain -> { - Request originalRequest = chain.request(); - Request requestWithUserAgent = originalRequest.newBuilder() - .header("User-Agent", "Tusky/"+ BuildConfig.VERSION_NAME+" Android/"+Build.VERSION.RELEASE) - .build(); - return chain.proceed(requestWithUserAgent); - }; - } - -} - - diff --git a/app/src/main/java/com/keylesspalace/tusky/util/OkHttpUtils.kt b/app/src/main/java/com/keylesspalace/tusky/util/OkHttpUtils.kt new file mode 100644 index 00000000..3e1b89c6 --- /dev/null +++ b/app/src/main/java/com/keylesspalace/tusky/util/OkHttpUtils.kt @@ -0,0 +1,115 @@ +/* Copyright 2020 Tusky Contributors + * + * This file is part of Tusky. + * + * Tusky is free software: you can redistribute it and/or modify it under the terms of the GNU + * Lesser General Public License as published by the Free Software Foundation, either version 3 of + * the License, or (at your option) any later version. + * + * Tusky is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even + * the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser + * General Public License for more details. + * + * You should have received a copy of the GNU Lesser General Public License along with Tusky. If + * not, see . */ + +package com.keylesspalace.tusky.util + +import android.content.Context +import android.os.Build +import androidx.preference.PreferenceManager +import com.keylesspalace.tusky.BuildConfig +import okhttp3.Cache +import okhttp3.OkHttp +import okhttp3.OkHttpClient +import okhttp3.tls.HandshakeCertificates +import java.io.ByteArrayInputStream +import java.net.InetSocketAddress +import java.net.Proxy +import java.security.cert.CertificateFactory +import java.security.cert.X509Certificate +import java.util.concurrent.TimeUnit + +fun okhttpClient(context: Context): OkHttpClient.Builder { + val preferences = PreferenceManager.getDefaultSharedPreferences(context) + + val httpProxyEnabled = preferences.getBoolean("httpProxyEnabled", false) + val httpServer = preferences.getNonNullString("httpProxyServer", "") + val httpPort = preferences.getNonNullString("httpProxyPort", "-1").toIntOrNull() ?: -1 + + val cacheSize = 25 * 1024 * 1024 // 25 MiB + val builder = OkHttpClient.Builder() + .addInterceptor { chain -> + /** + * Add a custom User-Agent that contains Tusky, Android and Okhttp Version to all requests + * Example: + * User-Agent: Tusky/1.1.2 Android/5.0.2 + * */ + val requestWithUserAgent = chain.request().newBuilder() + .header( + "User-Agent", + "Tusky/${BuildConfig.VERSION_NAME} Android/${Build.VERSION.RELEASE} OkHttp/${OkHttp.VERSION}" + ) + .build() + chain.proceed(requestWithUserAgent) + } + .readTimeout(30, TimeUnit.SECONDS) + .writeTimeout(30, TimeUnit.SECONDS) + .cache(Cache(context.cacheDir, cacheSize.toLong())) + + if (httpProxyEnabled && httpServer.isNotEmpty() && httpPort > 0 && httpPort < 65535) { + val address = InetSocketAddress.createUnresolved(httpServer, httpPort) + builder.proxy(Proxy(Proxy.Type.HTTP, address)) + } + + // trust the new Let's Encrypt root certificate that is not available on Android < 7.1.1 + // new cert https://letsencrypt.org/certs/isrgrootx1.pem + // see https://letsencrypt.org/2020/11/06/own-two-feet.html + // see https://stackoverflow.com/questions/64844311/certpathvalidatorexception-connecting-to-a-lets-encrypt-host-on-android-m-or-ea + if (Build.VERSION.SDK_INT < Build.VERSION_CODES.O) { + val isgCert = """ + -----BEGIN CERTIFICATE----- + MIIFazCCA1OgAwIBAgIRAIIQz7DSQONZRGPgu2OCiwAwDQYJKoZIhvcNAQELBQAw + TzELMAkGA1UEBhMCVVMxKTAnBgNVBAoTIEludGVybmV0IFNlY3VyaXR5IFJlc2Vh + cmNoIEdyb3VwMRUwEwYDVQQDEwxJU1JHIFJvb3QgWDEwHhcNMTUwNjA0MTEwNDM4 + WhcNMzUwNjA0MTEwNDM4WjBPMQswCQYDVQQGEwJVUzEpMCcGA1UEChMgSW50ZXJu + ZXQgU2VjdXJpdHkgUmVzZWFyY2ggR3JvdXAxFTATBgNVBAMTDElTUkcgUm9vdCBY + MTCCAiIwDQYJKoZIhvcNAQEBBQADggIPADCCAgoCggIBAK3oJHP0FDfzm54rVygc + h77ct984kIxuPOZXoHj3dcKi/vVqbvYATyjb3miGbESTtrFj/RQSa78f0uoxmyF+ + 0TM8ukj13Xnfs7j/EvEhmkvBioZxaUpmZmyPfjxwv60pIgbz5MDmgK7iS4+3mX6U + A5/TR5d8mUgjU+g4rk8Kb4Mu0UlXjIB0ttov0DiNewNwIRt18jA8+o+u3dpjq+sW + T8KOEUt+zwvo/7V3LvSye0rgTBIlDHCNAymg4VMk7BPZ7hm/ELNKjD+Jo2FR3qyH + B5T0Y3HsLuJvW5iB4YlcNHlsdu87kGJ55tukmi8mxdAQ4Q7e2RCOFvu396j3x+UC + B5iPNgiV5+I3lg02dZ77DnKxHZu8A/lJBdiB3QW0KtZB6awBdpUKD9jf1b0SHzUv + KBds0pjBqAlkd25HN7rOrFleaJ1/ctaJxQZBKT5ZPt0m9STJEadao0xAH0ahmbWn + OlFuhjuefXKnEgV4We0+UXgVCwOPjdAvBbI+e0ocS3MFEvzG6uBQE3xDk3SzynTn + jh8BCNAw1FtxNrQHusEwMFxIt4I7mKZ9YIqioymCzLq9gwQbooMDQaHWBfEbwrbw + qHyGO0aoSCqI3Haadr8faqU9GY/rOPNk3sgrDQoo//fb4hVC1CLQJ13hef4Y53CI + rU7m2Ys6xt0nUW7/vGT1M0NPAgMBAAGjQjBAMA4GA1UdDwEB/wQEAwIBBjAPBgNV + HRMBAf8EBTADAQH/MB0GA1UdDgQWBBR5tFnme7bl5AFzgAiIyBpY9umbbjANBgkq + hkiG9w0BAQsFAAOCAgEAVR9YqbyyqFDQDLHYGmkgJykIrGF1XIpu+ILlaS/V9lZL + ubhzEFnTIZd+50xx+7LSYK05qAvqFyFWhfFQDlnrzuBZ6brJFe+GnY+EgPbk6ZGQ + 3BebYhtF8GaV0nxvwuo77x/Py9auJ/GpsMiu/X1+mvoiBOv/2X/qkSsisRcOj/KK + NFtY2PwByVS5uCbMiogziUwthDyC3+6WVwW6LLv3xLfHTjuCvjHIInNzktHCgKQ5 + ORAzI4JMPJ+GslWYHb4phowim57iaztXOoJwTdwJx4nLCgdNbOhdjsnvzqvHu7Ur + TkXWStAmzOVyyghqpZXjFaH3pO3JLF+l+/+sKAIuvtd7u+Nxe5AW0wdeRlN8NwdC + jNPElpzVmbUq4JUagEiuTDkHzsxHpFKVK7q4+63SM1N95R1NbdWhscdCb+ZAJzVc + oyi3B43njTOQ5yOf+1CceWxG1bQVs5ZufpsMljq4Ui0/1lvh+wjChP4kqKOJ2qxq + 4RgqsahDYVvTH9w7jXbyLeiNdd8XM2w9U/t7y0Ff/9yi0GE44Za4rF2LN9d11TPA + mRGunUHBcnWEvgJBQl9nJEiU0Zsnvgc/ubhPgXRR4Xq37Z0j4r7g1SgEEzwxA57d + emyPxgcYxn/eR44/KJ4EBs+lVDR3veyJm+kXQ99b21/+jh5Xos1AnX5iItreGCc= + -----END CERTIFICATE----- + """.trimIndent() + val cf = CertificateFactory.getInstance("X.509") + val isgCertificate = cf.generateCertificate(ByteArrayInputStream(isgCert.toByteArray(charset("UTF-8")))) + val certificates = HandshakeCertificates.Builder() + .addTrustedCertificate(isgCertificate as X509Certificate) + .addPlatformTrustedCertificates() + .build() + builder.sslSocketFactory( + certificates.sslSocketFactory(), + certificates.trustManager + ) + } + return builder +} diff --git a/app/src/main/java/com/keylesspalace/tusky/util/StatusViewHelper.kt b/app/src/main/java/com/keylesspalace/tusky/util/StatusViewHelper.kt index cb4651fd..2fb9ad42 100644 --- a/app/src/main/java/com/keylesspalace/tusky/util/StatusViewHelper.kt +++ b/app/src/main/java/com/keylesspalace/tusky/util/StatusViewHelper.kt @@ -23,7 +23,6 @@ import android.view.View import android.widget.ImageView import android.widget.TextView import androidx.annotation.DrawableRes -import androidx.appcompat.content.res.AppCompatResources import com.bumptech.glide.Glide import com.keylesspalace.tusky.R import com.keylesspalace.tusky.entity.Attachment @@ -220,9 +219,7 @@ class StatusViewHelper(private val itemView: View) { // Set the icon next to the label. val drawableId = getLabelIcon(attachments[0].type) - val drawable = AppCompatResources.getDrawable(context, drawableId) - ThemeUtils.setDrawableTint(context, drawable!!, android.R.attr.textColorTertiary) - mediaLabel.setCompoundDrawablesWithIntrinsicBounds(drawable, null, null, null) + mediaLabel.setCompoundDrawablesWithIntrinsicBounds(drawableId, 0, 0, 0) mediaLabel.setOnClickListener { listener.onViewMedia(null, 0) } } diff --git a/app/src/main/java/com/keylesspalace/tusky/util/ThemeUtils.java b/app/src/main/java/com/keylesspalace/tusky/util/ThemeUtils.java index 9f7be621..d01775dd 100644 --- a/app/src/main/java/com/keylesspalace/tusky/util/ThemeUtils.java +++ b/app/src/main/java/com/keylesspalace/tusky/util/ThemeUtils.java @@ -22,9 +22,7 @@ import android.graphics.PorterDuff; import android.graphics.drawable.Drawable; import androidx.annotation.AttrRes; import androidx.annotation.ColorInt; -import androidx.annotation.DrawableRes; import androidx.annotation.NonNull; -import androidx.annotation.Nullable; import androidx.appcompat.app.AppCompatDelegate; import android.util.TypedValue; @@ -59,17 +57,6 @@ public class ThemeUtils { return dimen; } - /** this can be replaced with drawableTint in xml once minSdkVersion >= 23 */ - @Nullable - public static Drawable getTintedDrawable(@NonNull Context context, @DrawableRes int drawableId, @AttrRes int colorAttr) { - Drawable drawable = context.getDrawable(drawableId); - if(drawable == null) { - return null; - } - setDrawableTint(context, drawable, colorAttr); - return drawable; - } - public static void setDrawableTint(Context context, Drawable drawable, @AttrRes int attribute) { drawable.setColorFilter(getColor(context, attribute), PorterDuff.Mode.SRC_IN); } diff --git a/app/src/main/res/layout/activity_compose.xml b/app/src/main/res/layout/activity_compose.xml index 5f8d6ffd..4a92ff11 100644 --- a/app/src/main/res/layout/activity_compose.xml +++ b/app/src/main/res/layout/activity_compose.xml @@ -136,10 +136,10 @@ + android:scrollbars="none" + android:visibility="gone" /> + app:srcCompat="@drawable/ic_attach_file_24dp" + app:tooltipText="@string/action_add_media" /> + app:srcCompat="@drawable/ic_cw_24dp" + app:tooltipText="@string/action_content_warning" /> + app:srcCompat="@drawable/ic_emoji_24dp" + app:tooltipText="@string/action_emoji_keyboard" /> + app:srcCompat="@drawable/ic_access_time" + app:tooltipText="@string/action_schedule_toot" /> + app:layout_scrollFlags="scroll|enterAlways" + app:navigationContentDescription="@string/action_open_drawer" /> + android:textStyle="normal|bold" + app:drawableStartCompat="@drawable/ic_list" + app:drawableTint="?attr/iconColor" /> diff --git a/app/src/main/res/layout/item_conversation.xml b/app/src/main/res/layout/item_conversation.xml index a2dd4e3d..d746f99e 100644 --- a/app/src/main/res/layout/item_conversation.xml +++ b/app/src/main/res/layout/item_conversation.xml @@ -340,6 +340,7 @@ android:importantForAccessibility="no" android:textSize="?attr/status_text_medium" android:visibility="gone" + app:drawableTint="?android:attr/textColorTertiary" app:layout_constraintStart_toStartOf="parent" app:layout_constraintTop_toTopOf="parent" /> @@ -353,6 +354,7 @@ android:importantForAccessibility="no" android:textSize="?attr/status_text_medium" android:visibility="gone" + app:drawableTint="?android:attr/textColorTertiary" app:layout_constraintStart_toStartOf="parent" app:layout_constraintTop_toBottomOf="@id/status_media_label_0" /> @@ -366,6 +368,7 @@ android:importantForAccessibility="no" android:textSize="?attr/status_text_medium" android:visibility="gone" + app:drawableTint="?android:attr/textColorTertiary" app:layout_constraintStart_toStartOf="parent" app:layout_constraintTop_toBottomOf="@id/status_media_label_1" /> @@ -379,6 +382,7 @@ android:importantForAccessibility="no" android:textSize="?attr/status_text_medium" android:visibility="gone" + app:drawableTint="?android:attr/textColorTertiary" app:layout_constraintStart_toStartOf="parent" app:layout_constraintTop_toBottomOf="@id/status_media_label_2" /> diff --git a/app/src/main/res/layout/item_emoji_pref.xml b/app/src/main/res/layout/item_emoji_pref.xml index 539677f1..d8755a3d 100644 --- a/app/src/main/res/layout/item_emoji_pref.xml +++ b/app/src/main/res/layout/item_emoji_pref.xml @@ -6,8 +6,8 @@ android:layout_width="match_parent" android:layout_height="wrap_content" android:background="?attr/selectableItemBackground" - android:paddingBottom="8dp" - android:paddingTop="8dp"> + android:paddingTop="8dp" + android:paddingBottom="8dp"> + app:srcCompat="@drawable/ic_emoji_24dp" + app:tint="#0000" /> @@ -58,8 +60,8 @@ style="?android:attr/progressBarStyleHorizontal" android:layout_width="0dp" android:layout_height="wrap_content" - android:layout_marginEnd="72dp" android:layout_marginTop="8dp" + android:layout_marginEnd="72dp" android:indeterminate="false" android:visibility="gone" app:layout_constraintEnd_toEndOf="parent" diff --git a/app/src/main/res/layout/item_poll_preview_option.xml b/app/src/main/res/layout/item_poll_preview_option.xml index d7f5887a..e8fa9849 100644 --- a/app/src/main/res/layout/item_poll_preview_option.xml +++ b/app/src/main/res/layout/item_poll_preview_option.xml @@ -1,5 +1,6 @@ \ No newline at end of file + android:maxEms="20" + app:drawableTint="?android:attr/textColorTertiary" /> \ No newline at end of file diff --git a/app/src/main/res/layout/item_report_status.xml b/app/src/main/res/layout/item_report_status.xml index b7ed0555..56a2dea9 100644 --- a/app/src/main/res/layout/item_report_status.xml +++ b/app/src/main/res/layout/item_report_status.xml @@ -198,8 +198,8 @@ app:layout_constraintLeft_toLeftOf="@+id/status_media_preview_container" app:layout_constraintTop_toTopOf="@+id/status_media_preview_container" app:srcCompat="@drawable/ic_eye_24dp" - tools:visibility="visible" - app:tint="@color/white" /> + app:tint="@color/white" + tools:visibility="visible" /> diff --git a/app/src/main/res/layout/item_status.xml b/app/src/main/res/layout/item_status.xml index 8d831757..b6c59725 100644 --- a/app/src/main/res/layout/item_status.xml +++ b/app/src/main/res/layout/item_status.xml @@ -167,9 +167,9 @@ android:foreground="?attr/selectableItemBackground" android:minHeight="80dp" android:orientation="vertical" + app:layout_constraintEnd_toEndOf="parent" app:layout_constraintStart_toStartOf="@id/status_display_name" app:layout_constraintTop_toBottomOf="@+id/button_toggle_content" - app:layout_constraintEnd_toEndOf="parent" tools:visibility="gone"> @@ -411,6 +412,7 @@ android:importantForAccessibility="no" android:textSize="?attr/status_text_medium" android:visibility="gone" + app:drawableTint="?android:attr/textColorTertiary" app:layout_constraintStart_toStartOf="parent" app:layout_constraintTop_toBottomOf="@id/status_media_label_0" /> @@ -424,6 +426,7 @@ android:importantForAccessibility="no" android:textSize="?attr/status_text_medium" android:visibility="gone" + app:drawableTint="?android:attr/textColorTertiary" app:layout_constraintStart_toStartOf="parent" app:layout_constraintTop_toBottomOf="@id/status_media_label_1" /> @@ -437,6 +440,7 @@ android:importantForAccessibility="no" android:textSize="?attr/status_text_medium" android:visibility="gone" + app:drawableTint="?android:attr/textColorTertiary" app:layout_constraintStart_toStartOf="parent" app:layout_constraintTop_toBottomOf="@id/status_media_label_2" /> diff --git a/app/src/main/res/layout/item_status_detailed.xml b/app/src/main/res/layout/item_status_detailed.xml index 019ab8bd..f3ad6ed5 100644 --- a/app/src/main/res/layout/item_status_detailed.xml +++ b/app/src/main/res/layout/item_status_detailed.xml @@ -344,6 +344,7 @@ android:importantForAccessibility="no" android:textSize="?attr/status_text_medium" android:visibility="gone" + app:drawableTint="?android:attr/textColorTertiary" app:layout_constraintStart_toStartOf="parent" app:layout_constraintTop_toTopOf="parent" /> @@ -357,6 +358,7 @@ android:importantForAccessibility="no" android:textSize="?attr/status_text_medium" android:visibility="gone" + app:drawableTint="?android:attr/textColorTertiary" app:layout_constraintStart_toStartOf="parent" app:layout_constraintTop_toBottomOf="@id/status_media_label_0" /> @@ -370,6 +372,7 @@ android:importantForAccessibility="no" android:textSize="?attr/status_text_medium" android:visibility="gone" + app:drawableTint="?android:attr/textColorTertiary" app:layout_constraintStart_toStartOf="parent" app:layout_constraintTop_toBottomOf="@id/status_media_label_1" /> @@ -383,6 +386,7 @@ android:importantForAccessibility="no" android:textSize="?attr/status_text_medium" android:visibility="gone" + app:drawableTint="?android:attr/textColorTertiary" app:layout_constraintStart_toStartOf="parent" app:layout_constraintTop_toBottomOf="@id/status_media_label_2" /> diff --git a/app/src/main/res/layout/item_tab_preference.xml b/app/src/main/res/layout/item_tab_preference.xml index b0926cea..9eb164c3 100644 --- a/app/src/main/res/layout/item_tab_preference.xml +++ b/app/src/main/res/layout/item_tab_preference.xml @@ -32,6 +32,7 @@ android:paddingBottom="8dp" android:textColor="?android:attr/textColorSecondary" android:textSize="?attr/status_text_large" + app:drawableTint="?android:attr/textColorSecondary" app:layout_constraintBottom_toTopOf="@id/chipGroup" app:layout_constraintEnd_toEndOf="parent" app:layout_constraintStart_toEndOf="@id/imageView" diff --git a/app/src/main/res/layout/item_tab_preference_small.xml b/app/src/main/res/layout/item_tab_preference_small.xml index bee49eb2..15daafe0 100644 --- a/app/src/main/res/layout/item_tab_preference_small.xml +++ b/app/src/main/res/layout/item_tab_preference_small.xml @@ -1,17 +1,19 @@ + android:textSize="?attr/status_text_large" + app:drawableStartCompat="@drawable/ic_home_24dp" + app:drawableTint="?android:attr/textColorSecondary" /> diff --git a/app/src/main/res/layout/view_compose_schedule.xml b/app/src/main/res/layout/view_compose_schedule.xml index b07270f6..7ae003c4 100644 --- a/app/src/main/res/layout/view_compose_schedule.xml +++ b/app/src/main/res/layout/view_compose_schedule.xml @@ -23,6 +23,7 @@ android:paddingBottom="16dp" android:textColor="?android:textColorTertiary" android:textSize="?attr/status_text_medium" + app:drawableTint="?android:attr/textColorTertiary" app:layout_constraintBottom_toTopOf="@id/invalidScheduleWarning" app:layout_constraintEnd_toEndOf="parent" app:layout_constraintHorizontal_bias="1" @@ -39,11 +40,11 @@ android:paddingBottom="16dp" android:textColor="?android:textColorTertiary" android:textSize="?attr/status_text_medium" + android:visibility="gone" app:layout_constraintBottom_toBottomOf="parent" app:layout_constraintEnd_toEndOf="parent" app:layout_constraintHorizontal_bias="1" app:layout_constraintStart_toStartOf="parent" - tools:text="@string/warning_scheduling_interval" - android:visibility="gone" /> + tools:text="@string/warning_scheduling_interval" /> \ No newline at end of file diff --git a/app/src/main/res/values-bn-rBD/strings.xml b/app/src/main/res/values-bn-rBD/strings.xml index e14d254e..2fb78dd8 100644 --- a/app/src/main/res/values-bn-rBD/strings.xml +++ b/app/src/main/res/values-bn-rBD/strings.xml @@ -381,7 +381,7 @@ ভোট বন্ধ \'%s এ শেষ হবে\' - " <!-- ১৫ ভোট • ১ ঘন্টা বাকি --> %1$s • %2$s" + %1$s • %2$s ছবি %s এর জন্য ক্রিয়া আপনি কি আপনার সমস্ত বিজ্ঞপ্তি স্থায়ীভাবে মুছে ফেলতে চান\? diff --git a/app/src/main/res/values-cs/strings.xml b/app/src/main/res/values-cs/strings.xml index d7a5463e..42c5ce26 100644 --- a/app/src/main/res/values-cs/strings.xml +++ b/app/src/main/res/values-cs/strings.xml @@ -475,11 +475,7 @@ Odkrýt oznámení od %s Odkrýt %s Ztišit @%s\? - - - - - + %s požádal/a aby vás mohl/a sledovat Zobrazit dialogové okno s potvrzením při boostování \ No newline at end of file diff --git a/app/src/main/res/values-eo/strings.xml b/app/src/main/res/values-eo/strings.xml index 13a06597..82988898 100644 --- a/app/src/main/res/values-eo/strings.xml +++ b/app/src/main/res/values-eo/strings.xml @@ -474,4 +474,12 @@ iu petas sekvi min Malsupro Supro + Konservita! + Via privata noto pri ĉi tiu konto + Kaŝi la titolon de la supra ilobreto + Montri antaŭvidojn de ligiloj en tempolinioj + Montri konfirman fenestron antaŭ ol diskonigi + Estas neniu anonco. + Ebligi ŝovumadon por ŝanĝi inter la langetoj + Mastodon havas minimuman intervalon de planado de 5 minutoj. \ No newline at end of file diff --git a/app/src/main/res/values-eu/strings.xml b/app/src/main/res/values-eu/strings.xml index 511b0957..6dabede9 100644 --- a/app/src/main/res/values-eu/strings.xml +++ b/app/src/main/res/values-eu/strings.xml @@ -450,10 +450,7 @@ Traolak Ez erakutsi jakinarazpenak Desmututu %s - - Pertsona %1 - %2 pertsona - + Ezkutatu goiko tresna-barraren izenburua Erakutsi berrespen-abisua tuta bultzatu aurretik Erakutsi esteken aurrebista denbora-lerroetan diff --git a/app/src/main/res/values-fa/strings.xml b/app/src/main/res/values-fa/strings.xml index 4d54af2e..a4284406 100644 --- a/app/src/main/res/values-fa/strings.xml +++ b/app/src/main/res/values-fa/strings.xml @@ -150,8 +150,8 @@ ظاهر زمینهٔ کاره خط‌ زمانی‌ها - روشن - سیاه + تاریک + روشن سیاه خودکار در غروب مرورگر diff --git a/app/src/main/res/values-fr/strings.xml b/app/src/main/res/values-fr/strings.xml index f2554340..732f65a2 100644 --- a/app/src/main/res/values-fr/strings.xml +++ b/app/src/main/res/values-fr/strings.xml @@ -452,18 +452,18 @@ Les fichiers audio doivent avoir moins de 40 Mo. Vous n’avez aucun brouillon. Vous n’avez aucun pouet planifié. - L’intervalle minimum de planification sur Mastodon est de5 minutes. + L’intervalle minimum de planification sur Mastodon est de 5 minutes. Demandes d\'abonnement Bloquer @%s \? Afficher une fenêtre de confirmation avant de partager - Afficher des aperçus des liens dans les fils + Afficher les aperçus des liens dans les fils %s a demandé à vous suivre Notifications à propos des demandes d’abonnement on demande à me suivre Mettre en sourdine @%s \? Enlever la sourdine à la conversation Masquer la conversation - Activer les gestes de glissement pour passer d’un onglet à l’autre + Activer le glissement pour changer d’onglet Hashtags Ajouter un hashtag Afficher des dégradés en couleur pour les médias cachés @@ -486,6 +486,6 @@ Sauvegardé ! Votre note privée sur ce compte - Il n’y a pas d’annonces. + Il n’y a pas d’annonce. Annonces \ No newline at end of file diff --git a/app/src/main/res/values-hu/strings.xml b/app/src/main/res/values-hu/strings.xml index 56081443..df5cd610 100644 --- a/app/src/main/res/values-hu/strings.xml +++ b/app/src/main/res/values-hu/strings.xml @@ -3,30 +3,30 @@ Hiba történt. Hálózati hiba történt! Kérjük, ellenőrizd a kapcsolatot, és próbálja meg újra! Ez nem lehet üres. - Helytelen domén - Sikertelen bejelentkezés ezen a szerveren. + Helytelen domain + Sikertelen hitelesítés ezen a példányon. Nem található használható böngésző. Azonosítatlan engedélyezési hiba történt. Engedély megtagadva. Bejelentkezési token megszerzése sikertelen. Túl hosszú a tülkölés! - A fájlnak kisebbnek kell lennie, mint 8MB. - A video fájlnak kisebbnek kell lennie, mint 40MB. + A fájlnak kisebbnek kell lennie, mint 8 MB. + A videofájloknak kisebbnek kell lenniük, mint 40 MB. Ilyen típusú fájlt nem lehet feltölteni. Fájl megnyitása sikertelen. Média olvasási engedély szükséges. Média tárolási engedély szükséges. Képek és videók egyszerre nem csatolhatók ugyanazon tülköléshez. Feltöltés sikertelen. - Nem sikerült elküldeni a tülköt.. + Nem sikerült elküldeni a tülköt. Kezdőlap Értesítések Helyi - Föderáció + Föderációs Közvetlen üzenetek Fülek Tülk - Posztok + Tülkök Válaszokkal Rögzített Követett @@ -65,8 +65,8 @@ Biztosan ki szeretnél jelentkezni a következőből: %1$s? Követés Követés vége - Letiltás - Letiltás feloldása + Blokkolás + Blokkolás feloldása Megtolások elrejtése Megtolások mutatása Bejelentés @@ -80,7 +80,7 @@ Fiókbeállítások Kedvencek Némított felhasználók - Letiltott felhasználók + Blokkolt felhasználók Követési kérelmek Média Megnyitás böngészőben @@ -118,11 +118,11 @@ Tülk URL megosztása… Tülk megosztása… Elküldve! - Felhasználó letiltása feloldva + Felhasználó blokkolása feloldva Felhasználó némítása feloldva Elküldve! Válasz sikeresen elküldve. - Melyik szerver\? + Melyik példány\? Mi jár a fejedben\? Tartalom figyelmeztetés Megjelenítési név @@ -134,11 +134,11 @@ Fejléc Mi az a szerver\? Csatlakozás… - Bármely szerver címét beírhatod ide, mint mastodon.social, icosahedron.website, social.tchncs.de, és mások! + Bármely példány címét vagy domain nevét beírhatod ide, mint a mastodon.social, az icosahedron.website, a social.tchncs.de és mások! \n -\nHa még nincs fiókod, beírhatod a címét ide annak a szervernek amelyhez csatlakoznál, majd azon létrehozhatsz egy fiókot. +\nHa még nincs fiókod, beírhatod annak a példánynak a címét, amelyhez csatlakoznál, majd azon létrehozhatsz egy fiókot. \n -\nA szerver az a hely ahol a fiókadataidat tárolják, de ettől még ugyanúgy kommunikálhatsz más szervereken lévő emberekkel, mintha ugyanazon az oldalon lennétek. +\nA példány az a hely, ahol a fiókadataidat tárolják, de ettől még ugyanúgy kommunikálhatsz más példányokon lévő emberekkel, mintha ugyanazon az oldalon lennétek. \n \nTöbb információt találhatsz itt: joinmastodon.org. Média feltöltés befejezése @@ -198,7 +198,7 @@ Új követők Értesítések új követőkről Megtolások - Értesítések posztjaid megtolása esetén + Értesítések tülkjeid megtolása esetén Kedvencek Értesítések mikor tülkjeidet kedvencnek jelölik %s megemlített téged @@ -236,7 +236,7 @@ Listák Listák Törlés - Fiók lezárása + Fiók zárolása Elmented a vázlatot? Tülk elküldése… A tülk elküldése nem sikerült @@ -433,7 +433,7 @@ Időzített tülkök Tülk Időzítése Visszaállítás - Nem találjuk ezt a posztot %s + Nem találjuk ezt a tülköt %s Könyvjelzők Könyvjelzőzés Könyvjelzők @@ -441,7 +441,7 @@ Könyvjelzőzve Lista kiválasztása Lista - A hangfájlok mérete 40MB-nál kisebb kell legyen. + A hangfájloknak kisebbnek kell lenniük, mint 40 MB. Nincs egy vázlatod sem. Nincs egy ütemezett tülköd sem. A Mastodonban a legrövidebb ütemezhető időintervallum 5 perc. @@ -462,7 +462,7 @@ Színes homály mutatása rejtett médiánál követni szeretnének Értesítések elrejtése - Letiltsuk @%s -t\? + Blokkolod: @%s\? Elnémítsuk @%s fiókot\? Beszélgetés némításának feloldása Beszélgetés némítása diff --git a/app/src/main/res/values-is/strings.xml b/app/src/main/res/values-is/strings.xml index 9ce6c6cc..4e27ac52 100644 --- a/app/src/main/res/values-is/strings.xml +++ b/app/src/main/res/values-is/strings.xml @@ -415,8 +415,8 @@ Fylgjendabeiðnir Myllumerki - %1$s Eftirlæti - %1$s Eftirlæti + %1$s eftirlæti + %1$s eftirlæti %s Endurbirting @@ -438,4 +438,33 @@ %d dagur eftir %d dagar eftir + Vistað! + Þí eigin einkaathugasemd um þennan aðgang + Fela titil á verkfærastikunni efst + Birta staðfestingarglugga áður en endurbirting fer fram + Birta forskoðun tengla á tímalínum + Það eru engar tilkynningar. + Virkja strokuhreyfingu til að skipta milli flipa + + %s aðili + %s aðilar + + Bæta við myllumerki + Tilkynningar um fylgjendabeiðnir + Neðst + Efst + Aðalstaða leiðsagnar + Birta litstigla í stað falins myndefnis + beiðni um að fylgja + Fela tilkynningar + Þagga niður í @%s\? + Loka á @%s\? + Hætta að þagga niður í samtölum + Þagga niður í samtölum + Afþagga %s + Þagga tilkynningar frá %s + Afþagga tilkynningar frá %s + Afþagga %s + %s bað um að fylgjast með þér + Tilkynningar \ No newline at end of file diff --git a/app/src/main/res/values-it/strings.xml b/app/src/main/res/values-it/strings.xml index 2cc0cfb2..a704c110 100644 --- a/app/src/main/res/values-it/strings.xml +++ b/app/src/main/res/values-it/strings.xml @@ -482,4 +482,5 @@ Disattiva le notifiche da %s Riattiva le notifiche da %s Annunci + Richieste di seguirti \ No newline at end of file diff --git a/app/src/main/res/values-sv/strings.xml b/app/src/main/res/values-sv/strings.xml index de4b4409..8e3d5fb7 100644 --- a/app/src/main/res/values-sv/strings.xml +++ b/app/src/main/res/values-sv/strings.xml @@ -480,4 +480,8 @@ Dölj aviseringar Tysta aviseringar från %s Aktivera aviseringar från %s + Sparat! + Din privata notering om detta kontot + Det finns inga meddelanden. + Meddelanden \ No newline at end of file diff --git a/app/src/main/res/values-vi/strings.xml b/app/src/main/res/values-vi/strings.xml index 1730919e..e6a93e82 100644 --- a/app/src/main/res/values-vi/strings.xml +++ b/app/src/main/res/values-vi/strings.xml @@ -48,7 +48,7 @@ Làm tươi Tìm kiếm Trang cá nhân - Riêng bạn + Tài khoản Cài đặt Đăng xuất Xong @@ -97,7 +97,7 @@ Tải về Chia sẻ với tư cách … Mở với tư cách %s - Sao chép URL + Chép URL Đang tải %1$s Mở tập tin #%d Links @@ -131,7 +131,7 @@ Ẩn Chia sẻ Chụp hình - Tạo vău + Tạo bình chọn Thêm tệp Mở trong trình duyệt Bộ sưu tập @@ -221,7 +221,7 @@ Bảng tin Chủ đề Giao diện - vău đã kết thúc + cuộc bình chọn kết thúc tút được thích tút được chia sẻ yêu cầu theo dõi @@ -236,7 +236,7 @@ Thông báo Nhắn tin: Chỉ người được nhắc tới mới thấy Người theo dõi: Ai đã theo dõi mới xem được - Mở: Công khai, không hiện trên bảng tin + Riêng tư: Không hiện trên bảng tin Công khai: Mọi người đều có thể thấy Ẩn @%s\? Chặn @%s\? @@ -253,20 +253,20 @@ Nhỏ Kích thức phông chữ Người theo dõi - Mở + Riêng tư Công khai Dưới màn hình Trên màn hình Vị trí menu Đồng bộ hoá thất bại Đăng (đồng bộ với máy chủ) - Luôn đánh dấu nội dung là nhạy cảm + Tài khoản nhạy cảm Trạng thái tút mặc định - HTTP proxy server - HTTP proxy port - Bật HTTP proxy - HTTP proxy - Proxy + Máy chủ proxy + Cổng + Bật proxy + Dùng proxy + Vượt tường lửa Thông báo khi của bạn được chia sẻ Chia sẻ Thông báo về lượt yêu cầu theo dõi @@ -278,8 +278,8 @@ Powered by Tusky Tusky %s Tài khoản bị khóa - Thông báo khi những vău kết thúc - Vău + Thông báo khi một cuộc bình chọn kết thúc + Bình chọn Thông báo khi ai đó thích tút của bạn Lượt thích Toàn bộ câu @@ -315,9 +315,9 @@ Bạn không có tút đã lên lịch. Bạn không có bản nháp nào. Sửa - Bình chọn %d - Cho phép vău nhiều bình chọn - Thêm bình chọn + Lựa chọn %d + Cho phép chọn nhiều lựa chọn + Thêm lựa chọn 7 ngày 3 ngày 1 ngày @@ -325,8 +325,8 @@ 1 giờ 30 phút 5 phút - Vău - Vuốt để chuyển qua lại giữa các tab + Bình chọn + Vuốt qua lại giữa các tab Hiện bộ lọc thông báo Không thể tìm thấy Người @@ -349,18 +349,18 @@ %d ngày nữa kết thúc - Vău bạn tạo đã kết thúc - Vău mà bạn tham gia đã kết thúc - Vău + Cuộc bình chọn bạn tạo đã kết thúc + Cuộc bình chọn của bạn đã kết thúc + Bình chọn Kết thúc kết thúc lúc %s %s người - %s vău + %s người - %1$s • %2$s + %1$s • %2$s Mô tả cho hình %s Viết Viết tút @@ -376,7 +376,7 @@ Lượt bình chọn: %1$s, %2$s, %3$s, %4$s; %5$s Tin nhắn Người theo dõi - Mở + Riêng tư Công khai Đã lưu Đã thích @@ -456,7 +456,7 @@ Bỏ ẩn %s Ẩn tiêu đề tab Đã lưu! - Chú thích của bạn về người này + Ghi chú của bạn Chưa có thông báo. - Thông báo + Tin tức \ No newline at end of file diff --git a/app/src/main/res/values-zh-rCN/strings.xml b/app/src/main/res/values-zh-rCN/strings.xml index 8ce9eb19..ccd20b0b 100644 --- a/app/src/main/res/values-zh-rCN/strings.xml +++ b/app/src/main/res/values-zh-rCN/strings.xml @@ -477,8 +477,8 @@ %s 请求关注你 导航栏位置 隐藏顶部工具栏标题 - - %s 人 - - + 本站暂无公告。 + 公告 + 已保存 + 此账号的备注 \ No newline at end of file diff --git a/app/src/main/res/values/styles.xml b/app/src/main/res/values/styles.xml index 50da2622..693c8427 100644 --- a/app/src/main/res/values/styles.xml +++ b/app/src/main/res/values/styles.xml @@ -80,6 +80,8 @@ ?attr/colorSurface @style/Widget.MaterialComponents.Chip.Choice + + @style/TuskyPreferenceTheme + +