Change debug text in menu

This commit is contained in:
Adolfo Santiago 2021-10-02 08:08:39 +02:00
parent 300e19a9c5
commit 5022b7f256
No known key found for this signature in database
GPG key ID: 244D6F9A317B4A65
2 changed files with 338 additions and 276 deletions

View file

@ -1,24 +1,28 @@
/* Copyright 2020 Tusky Contributors /*
* Husky -- A Pleroma client for Android
* *
* This file is a part of Tusky. * Copyright (C) 2021 The Husky Developers
* Copyright (C) 2020 Tusky Contributors
* *
* This program is free software; you can redistribute it and/or modify it under the terms of the * This program is free software: you can redistribute it and/or modify
* GNU General Public License as published by the Free Software Foundation; either version 3 of the * it under the terms of the GNU General Public License as published by
* License, or (at your option) any later version. * 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 * This program is distributed in the hope that it will be useful,
* the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General * but WITHOUT ANY WARRANTY; without even the implied warranty of
* Public License for more details. * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
* *
* You should have received a copy of the GNU General Public License along with Tusky; if not, * You should have received a copy of the GNU General Public License
* see <http://www.gnu.org/licenses>. */ * along with this program. If not, see <https://www.gnu.org/licenses/>.
*/
package com.keylesspalace.tusky package com.keylesspalace.tusky
import android.content.Context import android.content.Context
import android.content.DialogInterface import android.content.DialogInterface
import android.content.Intent import android.content.Intent
import android.content.res.ColorStateList
import android.graphics.Color import android.graphics.Color
import android.graphics.drawable.Drawable import android.graphics.drawable.Drawable
import android.net.Uri import android.net.Uri
@ -59,10 +63,10 @@ import com.keylesspalace.tusky.components.notifications.NotificationHelper
import com.keylesspalace.tusky.components.preference.PreferencesActivity import com.keylesspalace.tusky.components.preference.PreferencesActivity
import com.keylesspalace.tusky.components.scheduled.ScheduledTootActivity import com.keylesspalace.tusky.components.scheduled.ScheduledTootActivity
import com.keylesspalace.tusky.components.search.SearchActivity import com.keylesspalace.tusky.components.search.SearchActivity
import com.keylesspalace.tusky.core.utils.ApplicationUtils
import com.keylesspalace.tusky.db.AccountEntity import com.keylesspalace.tusky.db.AccountEntity
import com.keylesspalace.tusky.db.AppDatabase import com.keylesspalace.tusky.db.AppDatabase
import com.keylesspalace.tusky.entity.Account import com.keylesspalace.tusky.entity.Account
import com.keylesspalace.tusky.entity.Notification
import com.keylesspalace.tusky.fragment.SFragment import com.keylesspalace.tusky.fragment.SFragment
import com.keylesspalace.tusky.interfaces.AccountSelectionListener import com.keylesspalace.tusky.interfaces.AccountSelectionListener
import com.keylesspalace.tusky.interfaces.ActionButtonActivity import com.keylesspalace.tusky.interfaces.ActionButtonActivity
@ -88,14 +92,12 @@ import dagger.android.DispatchingAndroidInjector
import dagger.android.HasAndroidInjector import dagger.android.HasAndroidInjector
import io.reactivex.android.schedulers.AndroidSchedulers import io.reactivex.android.schedulers.AndroidSchedulers
import io.reactivex.schedulers.Schedulers import io.reactivex.schedulers.Schedulers
import kotlinx.android.synthetic.main.activity_main.*
import retrofit2.Call
import retrofit2.Callback
import retrofit2.Response
import java.io.IOException
import javax.inject.Inject import javax.inject.Inject
import kotlinx.android.synthetic.main.activity_main.*
import timber.log.Timber
class MainActivity : BottomSheetActivity(), ActionButtonActivity, HasAndroidInjector { class MainActivity : BottomSheetActivity(), ActionButtonActivity, HasAndroidInjector {
@Inject @Inject
lateinit var androidInjector: DispatchingAndroidInjector<Any> lateinit var androidInjector: DispatchingAndroidInjector<Any>
@ -124,7 +126,7 @@ class MainActivity : BottomSheetActivity(), ActionButtonActivity, HasAndroidInje
private val emojiInitCallback = object : InitCallback() { private val emojiInitCallback = object : InitCallback() {
override fun onInitialized() { override fun onInitialized() {
if (!isDestroyed) { if(!isDestroyed) {
updateProfiles() updateProfiles()
} }
} }
@ -134,54 +136,58 @@ class MainActivity : BottomSheetActivity(), ActionButtonActivity, HasAndroidInje
super.onCreate(savedInstanceState) super.onCreate(savedInstanceState)
val activeAccount = accountManager.activeAccount val activeAccount = accountManager.activeAccount
if (activeAccount == null) { if(activeAccount == null) {
// will be redirected to LoginActivity by BaseActivity // will be redirected to LoginActivity by BaseActivity
return return
} }
var showNotificationTab = false var showNotificationTab = false
if (intent != null) { if(intent != null) {
/** there are two possibilities the accountId can be passed to MainActivity: /** there are two possibilities the accountId can be passed to MainActivity:
* - from our code as long 'account_id' * - from our code as long 'account_id'
* - from share shortcuts as String 'android.intent.extra.shortcut.ID' * - from share shortcuts as String 'android.intent.extra.shortcut.ID'
*/ */
var accountId = intent.getLongExtra(NotificationHelper.ACCOUNT_ID, -1) var accountId = intent.getLongExtra(NotificationHelper.ACCOUNT_ID, -1)
if (accountId == -1L) { if(accountId == -1L) {
val accountIdString = intent.getStringExtra(ShortcutManagerCompat.EXTRA_SHORTCUT_ID) val accountIdString = intent.getStringExtra(ShortcutManagerCompat.EXTRA_SHORTCUT_ID)
if (accountIdString != null) { if(accountIdString != null) {
accountId = accountIdString.toLong() accountId = accountIdString.toLong()
} }
} }
val accountRequested = accountId != -1L val accountRequested = accountId != -1L
if (accountRequested && accountId != activeAccount.id) { if(accountRequested && accountId != activeAccount.id) {
accountManager.setActiveAccount(accountId) accountManager.setActiveAccount(accountId)
} }
if (canHandleMimeType(intent.type)) { if(canHandleMimeType(intent.type)) {
// Sharing to Tusky from an external app // Sharing to Tusky from an external app
if (accountRequested) { if(accountRequested) {
// The correct account is already active // The correct account is already active
forwardShare(intent) forwardShare(intent)
} else { } else {
// No account was provided, show the chooser // No account was provided, show the chooser
showAccountChooserDialog(getString(R.string.action_share_as), true, object : AccountSelectionListener { showAccountChooserDialog(
override fun onAccountSelected(account: AccountEntity) { getString(R.string.action_share_as),
val requestedId = account.id true,
if (requestedId == activeAccount.id) { object : AccountSelectionListener {
// The correct account is already active override fun onAccountSelected(account: AccountEntity) {
forwardShare(intent) val requestedId = account.id
} else { if(requestedId == activeAccount.id) {
// A different account was requested, restart the activity // The correct account is already active
intent.putExtra(NotificationHelper.ACCOUNT_ID, requestedId) forwardShare(intent)
changeAccount(requestedId, intent) } else {
// A different account was requested, restart the activity
intent.putExtra(NotificationHelper.ACCOUNT_ID, requestedId)
changeAccount(requestedId, intent)
}
} }
} })
})
} }
} else if (accountRequested) { } else if(accountRequested) {
// user clicked a notification, show notification tab and switch user if necessary // user clicked a notification, show notification tab and switch user if necessary
showNotificationTab = true showNotificationTab = true
} }
} }
window.statusBarColor = Color.TRANSPARENT // don't draw a status bar, the DrawerLayout and the MaterialDrawerLayout have their own window.statusBarColor =
Color.TRANSPARENT // don't draw a status bar, the DrawerLayout and the MaterialDrawerLayout have their own
setContentView(R.layout.activity_main) setContentView(R.layout.activity_main)
ViewPager2Fix.reduceVelocity(viewPager, 2.0f); ViewPager2Fix.reduceVelocity(viewPager, 2.0f);
@ -220,25 +226,25 @@ class MainActivity : BottomSheetActivity(), ActionButtonActivity, HasAndroidInje
setupTabs(showNotificationTab) setupTabs(showNotificationTab)
eventHub.events eventHub.events
.observeOn(AndroidSchedulers.mainThread()) .observeOn(AndroidSchedulers.mainThread())
.autoDispose(this, Lifecycle.Event.ON_DESTROY) .autoDispose(this, Lifecycle.Event.ON_DESTROY)
.subscribe { event: Event? -> .subscribe { event: Event? ->
when (event) { when(event) {
is ProfileEditedEvent -> onFetchUserInfoSuccess(event.newProfileData) is ProfileEditedEvent -> onFetchUserInfoSuccess(event.newProfileData)
is MainTabsChangedEvent -> setupTabs(false) is MainTabsChangedEvent -> setupTabs(false)
is PreferenceChangedEvent -> { is PreferenceChangedEvent -> {
when (event.preferenceKey) { when(event.preferenceKey) {
PrefKeys.LIVE_NOTIFICATIONS -> { PrefKeys.LIVE_NOTIFICATIONS -> {
initPullNotifications() initPullNotifications()
}
} }
} }
is AnnouncementReadEvent -> { }
unreadAnnouncementsCount-- is AnnouncementReadEvent -> {
updateAnnouncementsBadge() unreadAnnouncementsCount--
} updateAnnouncementsBadge()
} }
} }
}
Schedulers.io().scheduleDirect { Schedulers.io().scheduleDirect {
// Flush old media that was cached for sharing // Flush old media that was cached for sharing
@ -247,7 +253,7 @@ class MainActivity : BottomSheetActivity(), ActionButtonActivity, HasAndroidInje
} }
private fun initPullNotifications() { private fun initPullNotifications() {
if (NotificationHelper.areNotificationsEnabled(this, accountManager)) { if(NotificationHelper.areNotificationsEnabled(this, accountManager)) {
if(accountManager.areNotificationsStreamingEnabled()) { if(accountManager.areNotificationsStreamingEnabled()) {
StreamingService.startStreaming(this) StreamingService.startStreaming(this)
NotificationHelper.disablePullNotifications(this) NotificationHelper.disablePullNotifications(this)
@ -282,9 +288,9 @@ class MainActivity : BottomSheetActivity(), ActionButtonActivity, HasAndroidInje
} }
override fun onKeyDown(keyCode: Int, event: KeyEvent): Boolean { override fun onKeyDown(keyCode: Int, event: KeyEvent): Boolean {
when (keyCode) { when(keyCode) {
KeyEvent.KEYCODE_MENU -> { KeyEvent.KEYCODE_MENU -> {
if (mainDrawerLayout.isOpen) { if(mainDrawerLayout.isOpen) {
mainDrawerLayout.close() mainDrawerLayout.close()
} else { } else {
mainDrawerLayout.open() mainDrawerLayout.open()
@ -296,9 +302,9 @@ class MainActivity : BottomSheetActivity(), ActionButtonActivity, HasAndroidInje
return true return true
} }
} }
if (event.isCtrlPressed || event.isShiftPressed) { if(event.isCtrlPressed || event.isShiftPressed) {
// FIXME: blackberry keyONE raises SHIFT key event even CTRL IS PRESSED // FIXME: blackberry keyONE raises SHIFT key event even CTRL IS PRESSED
when (keyCode) { when(keyCode) {
KeyEvent.KEYCODE_N -> { KeyEvent.KEYCODE_N -> {
// open compose activity by pressing SHIFT + N (or CTRL + N) // open compose activity by pressing SHIFT + N (or CTRL + N)
@ -314,9 +320,9 @@ class MainActivity : BottomSheetActivity(), ActionButtonActivity, HasAndroidInje
public override fun onPostCreate(savedInstanceState: Bundle?) { public override fun onPostCreate(savedInstanceState: Bundle?) {
super.onPostCreate(savedInstanceState) super.onPostCreate(savedInstanceState)
if (intent != null) { if(intent != null) {
val statusUrl = intent.getStringExtra(STATUS_URL) val statusUrl = intent.getStringExtra(STATUS_URL)
if (statusUrl != null) { if(statusUrl != null) {
viewUrl(statusUrl, PostLookupFallbackBehavior.DISPLAY_ERROR) viewUrl(statusUrl, PostLookupFallbackBehavior.DISPLAY_ERROR)
} }
} }
@ -346,7 +352,12 @@ class MainActivity : BottomSheetActivity(), ActionButtonActivity, HasAndroidInje
header = AccountHeaderView(this).apply { header = AccountHeaderView(this).apply {
headerBackgroundScaleType = ImageView.ScaleType.CENTER_CROP headerBackgroundScaleType = ImageView.ScaleType.CENTER_CROP
currentHiddenInList = true currentHiddenInList = true
onAccountHeaderListener = { _: View?, profile: IProfile, current: Boolean -> handleProfileClick(profile, current) } onAccountHeaderListener = { _: View?, profile: IProfile, current: Boolean ->
handleProfileClick(
profile,
current
)
}
addProfile(ProfileSettingDrawerItem().apply { addProfile(ProfileSettingDrawerItem().apply {
identifier = DRAWER_ITEM_ADD_ACCOUNT identifier = DRAWER_ITEM_ADD_ACCOUNT
nameRes = R.string.add_account_name nameRes = R.string.add_account_name
@ -358,21 +369,31 @@ class MainActivity : BottomSheetActivity(), ActionButtonActivity, HasAndroidInje
closeDrawerOnProfileListClick = true closeDrawerOnProfileListClick = true
} }
header.accountHeaderBackground.setColorFilter(ContextCompat.getColor(this, R.color.headerBackgroundFilter)) header.accountHeaderBackground.setColorFilter(
header.accountHeaderBackground.setBackgroundColor(ThemeUtils.getColor(this, R.attr.colorBackgroundAccent)) ContextCompat.getColor(
this,
R.color.headerBackgroundFilter
)
)
header.accountHeaderBackground.setBackgroundColor(
ThemeUtils.getColor(
this,
R.attr.colorBackgroundAccent
)
)
val animateAvatars = preferences.getBoolean("animateGifAvatars", false) val animateAvatars = preferences.getBoolean("animateGifAvatars", false)
DrawerImageLoader.init(object : AbstractDrawerImageLoader() { DrawerImageLoader.init(object : AbstractDrawerImageLoader() {
override fun set(imageView: ImageView, uri: Uri, placeholder: Drawable, tag: String?) { override fun set(imageView: ImageView, uri: Uri, placeholder: Drawable, tag: String?) {
if (animateAvatars) { if(animateAvatars) {
glide.load(uri) glide.load(uri)
.placeholder(placeholder) .placeholder(placeholder)
.into(imageView) .into(imageView)
} else { } else {
glide.asBitmap() glide.asBitmap()
.load(uri) .load(uri)
.placeholder(placeholder) .placeholder(placeholder)
.into(imageView) .into(imageView)
} }
} }
@ -381,7 +402,7 @@ class MainActivity : BottomSheetActivity(), ActionButtonActivity, HasAndroidInje
} }
override fun placeholder(ctx: Context, tag: String?): Drawable { override fun placeholder(ctx: Context, tag: String?): Drawable {
if (tag == DrawerImageLoader.Tags.PROFILE.name || tag == DrawerImageLoader.Tags.PROFILE_DRAWER_ITEM.name) { if(tag == DrawerImageLoader.Tags.PROFILE.name || tag == DrawerImageLoader.Tags.PROFILE_DRAWER_ITEM.name) {
return ctx.getDrawable(R.drawable.avatar_default)!! return ctx.getDrawable(R.drawable.avatar_default)!!
} }
@ -392,118 +413,135 @@ class MainActivity : BottomSheetActivity(), ActionButtonActivity, HasAndroidInje
mainDrawer.apply { mainDrawer.apply {
tintStatusBar = true tintStatusBar = true
addItems( addItems(
primaryDrawerItem { primaryDrawerItem {
nameRes = R.string.action_edit_profile nameRes = R.string.action_edit_profile
iconicsIcon = GoogleMaterial.Icon.gmd_person iconicsIcon = GoogleMaterial.Icon.gmd_person
onClick = { onClick = {
val intent = Intent(context, EditProfileActivity::class.java) val intent = Intent(context, EditProfileActivity::class.java)
startActivityWithSlideInAnimation(intent) startActivityWithSlideInAnimation(intent)
}
},
primaryDrawerItem {
nameRes = R.string.action_view_favourites
isSelectable = false
iconicsIcon = GoogleMaterial.Icon.gmd_star
onClick = {
val intent = StatusListActivity.newFavouritesIntent(context)
startActivityWithSlideInAnimation(intent)
}
},
primaryDrawerItem {
nameRes = R.string.action_view_bookmarks
iconicsIcon = GoogleMaterial.Icon.gmd_bookmark
onClick = {
val intent = StatusListActivity.newBookmarksIntent(context)
startActivityWithSlideInAnimation(intent)
}
},
primaryDrawerItem {
nameRes = R.string.action_lists
iconicsIcon = GoogleMaterial.Icon.gmd_list
onClick = {
startActivityWithSlideInAnimation(ListsActivity.newIntent(context))
}
},
primaryDrawerItem {
nameRes = R.string.action_access_saved_toot
iconRes = R.drawable.ic_notebook
onClick = {
val intent = DraftsActivity.newIntent(context)
startActivityWithSlideInAnimation(intent)
}
},
primaryDrawerItem {
nameRes = R.string.action_access_scheduled_toot
iconRes = R.drawable.ic_access_time
onClick = {
startActivityWithSlideInAnimation(ScheduledTootActivity.newIntent(context))
}
},
primaryDrawerItem {
identifier = DRAWER_ITEM_ANNOUNCEMENTS
nameRes = R.string.title_announcements
iconRes = R.drawable.ic_bullhorn_24dp
onClick = {
startActivityWithSlideInAnimation(AnnouncementsActivity.newIntent(context))
}
badgeStyle = BadgeStyle().apply {
textColor = ColorHolder.fromColor(ThemeUtils.getColor(this@MainActivity, R.attr.colorOnPrimary))
color = ColorHolder.fromColor(ThemeUtils.getColor(this@MainActivity, R.attr.colorPrimary))
}
},
DividerDrawerItem(),
secondaryDrawerItem {
nameRes = R.string.action_view_account_preferences
iconRes = R.drawable.ic_account_settings
onClick = {
val intent = PreferencesActivity.newIntent(context, PreferencesActivity.ACCOUNT_PREFERENCES)
startActivityWithSlideInAnimation(intent)
}
},
secondaryDrawerItem {
nameRes = R.string.action_view_preferences
iconicsIcon = GoogleMaterial.Icon.gmd_settings
onClick = {
val intent = PreferencesActivity.newIntent(context, PreferencesActivity.GENERAL_PREFERENCES)
startActivityWithSlideInAnimation(intent)
}
},
secondaryDrawerItem {
nameRes = R.string.about_title_activity
iconicsIcon = GoogleMaterial.Icon.gmd_info
onClick = {
val intent = Intent(context, AboutActivity::class.java)
startActivityWithSlideInAnimation(intent)
}
},
secondaryDrawerItem {
nameRes = R.string.action_logout
iconRes = R.drawable.ic_logout
onClick = ::logout
} }
},
primaryDrawerItem {
nameRes = R.string.action_view_favourites
isSelectable = false
iconicsIcon = GoogleMaterial.Icon.gmd_star
onClick = {
val intent = StatusListActivity.newFavouritesIntent(context)
startActivityWithSlideInAnimation(intent)
}
},
primaryDrawerItem {
nameRes = R.string.action_view_bookmarks
iconicsIcon = GoogleMaterial.Icon.gmd_bookmark
onClick = {
val intent = StatusListActivity.newBookmarksIntent(context)
startActivityWithSlideInAnimation(intent)
}
},
primaryDrawerItem {
nameRes = R.string.action_lists
iconicsIcon = GoogleMaterial.Icon.gmd_list
onClick = {
startActivityWithSlideInAnimation(ListsActivity.newIntent(context))
}
},
primaryDrawerItem {
nameRes = R.string.action_access_saved_toot
iconRes = R.drawable.ic_notebook
onClick = {
val intent = DraftsActivity.newIntent(context)
startActivityWithSlideInAnimation(intent)
}
},
primaryDrawerItem {
nameRes = R.string.action_access_scheduled_toot
iconRes = R.drawable.ic_access_time
onClick = {
startActivityWithSlideInAnimation(ScheduledTootActivity.newIntent(context))
}
},
primaryDrawerItem {
identifier = DRAWER_ITEM_ANNOUNCEMENTS
nameRes = R.string.title_announcements
iconRes = R.drawable.ic_bullhorn_24dp
onClick = {
startActivityWithSlideInAnimation(AnnouncementsActivity.newIntent(context))
}
badgeStyle = BadgeStyle().apply {
textColor = ColorHolder.fromColor(
ThemeUtils.getColor(
this@MainActivity,
R.attr.colorOnPrimary
)
)
color = ColorHolder.fromColor(
ThemeUtils.getColor(
this@MainActivity,
R.attr.colorPrimary
)
)
}
},
DividerDrawerItem(),
secondaryDrawerItem {
nameRes = R.string.action_view_account_preferences
iconRes = R.drawable.ic_account_settings
onClick = {
val intent = PreferencesActivity.newIntent(
context,
PreferencesActivity.ACCOUNT_PREFERENCES
)
startActivityWithSlideInAnimation(intent)
}
},
secondaryDrawerItem {
nameRes = R.string.action_view_preferences
iconicsIcon = GoogleMaterial.Icon.gmd_settings
onClick = {
val intent = PreferencesActivity.newIntent(
context,
PreferencesActivity.GENERAL_PREFERENCES
)
startActivityWithSlideInAnimation(intent)
}
},
secondaryDrawerItem {
nameRes = R.string.about_title_activity
iconicsIcon = GoogleMaterial.Icon.gmd_info
onClick = {
val intent = Intent(context, AboutActivity::class.java)
startActivityWithSlideInAnimation(intent)
}
},
secondaryDrawerItem {
nameRes = R.string.action_logout
iconRes = R.drawable.ic_logout
onClick = ::logout
}
) )
if (addSearchButton) { if(addSearchButton) {
mainDrawer.addItemsAtPosition(4, mainDrawer.addItemsAtPosition(4,
primaryDrawerItem { primaryDrawerItem {
nameRes = R.string.action_search nameRes = R.string.action_search
iconicsIcon = GoogleMaterial.Icon.gmd_search iconicsIcon = GoogleMaterial.Icon.gmd_search
onClick = { onClick = {
startActivityWithSlideInAnimation(SearchActivity.getIntent(context)) startActivityWithSlideInAnimation(SearchActivity.getIntent(context))
} }
}) })
} }
setSavedInstance(savedInstanceState) setSavedInstance(savedInstanceState)
} }
if (BuildConfig.DEBUG) { if(ApplicationUtils.isDebug()) {
Timber.d("Flavor: ${BuildConfig.FLAVOR}")
mainDrawer.addItems( mainDrawer.addItems(
secondaryDrawerItem { secondaryDrawerItem {
nameText = "debug" nameText = getString(R.string.debug_status)
isEnabled = false isEnabled = false
textColor = ColorStateList.valueOf(Color.GREEN) }
}
) )
} }
EmojiCompat.get().registerInitCallback(emojiInitCallback) EmojiCompat.get().registerInitCallback(emojiInitCallback)
@ -514,11 +552,11 @@ class MainActivity : BottomSheetActivity(), ActionButtonActivity, HasAndroidInje
} }
private fun setupTabs(selectNotificationTab: Boolean) { private fun setupTabs(selectNotificationTab: Boolean) {
val activeTabLayout = if(preferences.getString("mainNavPosition", "top") == "bottom") {
val activeTabLayout = if (preferences.getString("mainNavPosition", "top") == "bottom") {
val actionBarSize = ThemeUtils.getDimension(this, R.attr.actionBarSize) val actionBarSize = ThemeUtils.getDimension(this, R.attr.actionBarSize)
val fabMargin = resources.getDimensionPixelSize(R.dimen.fabMargin) val fabMargin = resources.getDimensionPixelSize(R.dimen.fabMargin)
(composeButton.layoutParams as CoordinatorLayout.LayoutParams).bottomMargin = actionBarSize + fabMargin (composeButton.layoutParams as CoordinatorLayout.LayoutParams).bottomMargin =
actionBarSize + fabMargin
tabLayout.hide() tabLayout.hide()
bottomTabLayout bottomTabLayout
} else { } else {
@ -532,21 +570,24 @@ class MainActivity : BottomSheetActivity(), ActionButtonActivity, HasAndroidInje
val adapter = MainPagerAdapter(tabs, this) val adapter = MainPagerAdapter(tabs, this)
viewPager.adapter = adapter viewPager.adapter = adapter
TabLayoutMediator(activeTabLayout, viewPager, TabConfigurationStrategy { _: TabLayout.Tab?, _: Int -> }).attach() TabLayoutMediator(
activeTabLayout,
viewPager,
TabConfigurationStrategy { _: TabLayout.Tab?, _: Int -> }).attach()
activeTabLayout.removeAllTabs() activeTabLayout.removeAllTabs()
for (i in tabs.indices) { for(i in tabs.indices) {
val tab = activeTabLayout.newTab() val tab = activeTabLayout.newTab()
.setIcon(tabs[i].icon) .setIcon(tabs[i].icon)
if (tabs[i].id == LIST) { if(tabs[i].id == LIST) {
tab.contentDescription = tabs[i].arguments[1] tab.contentDescription = tabs[i].arguments[1]
} else { } else {
tab.setContentDescription(tabs[i].text) tab.setContentDescription(tabs[i].text)
} }
activeTabLayout.addTab(tab) activeTabLayout.addTab(tab)
if (tabs[i].id == NOTIFICATIONS) { if(tabs[i].id == NOTIFICATIONS) {
notificationTabPosition = i notificationTabPosition = i
if (selectNotificationTab) { if(selectNotificationTab) {
tab.select() tab.select()
} }
} }
@ -564,8 +605,11 @@ class MainActivity : BottomSheetActivity(), ActionButtonActivity, HasAndroidInje
onTabSelectedListener = object : OnTabSelectedListener { onTabSelectedListener = object : OnTabSelectedListener {
override fun onTabSelected(tab: TabLayout.Tab) { override fun onTabSelected(tab: TabLayout.Tab) {
if (tab.position == notificationTabPosition) { if(tab.position == notificationTabPosition) {
NotificationHelper.clearNotificationsForActiveAccount(this@MainActivity, accountManager) NotificationHelper.clearNotificationsForActiveAccount(
this@MainActivity,
accountManager
)
} }
mainToolbar.title = tabs[tab.position].title(this@MainActivity) mainToolbar.title = tabs[tab.position].title(this@MainActivity)
@ -575,7 +619,7 @@ class MainActivity : BottomSheetActivity(), ActionButtonActivity, HasAndroidInje
override fun onTabReselected(tab: TabLayout.Tab) { override fun onTabReselected(tab: TabLayout.Tab) {
val fragment = adapter.getFragment(tab.position) val fragment = adapter.getFragment(tab.position)
if (fragment is ReselectableFragment) { if(fragment is ReselectableFragment) {
(fragment as ReselectableFragment).onReselect() (fragment as ReselectableFragment).onReselect()
} }
} }
@ -583,7 +627,7 @@ class MainActivity : BottomSheetActivity(), ActionButtonActivity, HasAndroidInje
activeTabLayout.addOnTabSelectedListener(it) activeTabLayout.addOnTabSelectedListener(it)
} }
val activeTabPosition = if (selectNotificationTab) notificationTabPosition else 0 val activeTabPosition = if(selectNotificationTab) notificationTabPosition else 0
mainToolbar.title = tabs[activeTabPosition].title(this@MainActivity) mainToolbar.title = tabs[activeTabPosition].title(this@MainActivity)
mainToolbar.setOnClickListener { mainToolbar.setOnClickListener {
(adapter.getFragment(activeTabLayout.selectedTabPosition) as? ReselectableFragment)?.onReselect() (adapter.getFragment(activeTabLayout.selectedTabPosition) as? ReselectableFragment)?.onReselect()
@ -595,13 +639,13 @@ class MainActivity : BottomSheetActivity(), ActionButtonActivity, HasAndroidInje
val activeAccount = accountManager.activeAccount val activeAccount = accountManager.activeAccount
//open profile when active image was clicked //open profile when active image was clicked
if (current && activeAccount != null) { if(current && activeAccount != null) {
val intent = AccountActivity.getIntent(this, activeAccount.accountId) val intent = AccountActivity.getIntent(this, activeAccount.accountId)
startActivityWithSlideInAnimation(intent) startActivityWithSlideInAnimation(intent)
return false return false
} }
//open LoginActivity to add new account //open LoginActivity to add new account
if (profile.identifier == DRAWER_ITEM_ADD_ACCOUNT) { if(profile.identifier == DRAWER_ITEM_ADD_ACCOUNT) {
startActivityWithSlideInAnimation(LoginActivity.getIntent(this, true)) startActivityWithSlideInAnimation(LoginActivity.getIntent(this, true))
return false return false
} }
@ -616,7 +660,7 @@ class MainActivity : BottomSheetActivity(), ActionButtonActivity, HasAndroidInje
accountManager.setActiveAccount(newSelectedId) accountManager.setActiveAccount(newSelectedId)
val intent = Intent(this, MainActivity::class.java) val intent = Intent(this, MainActivity::class.java)
intent.flags = Intent.FLAG_ACTIVITY_NEW_TASK or Intent.FLAG_ACTIVITY_CLEAR_TASK intent.flags = Intent.FLAG_ACTIVITY_NEW_TASK or Intent.FLAG_ACTIVITY_CLEAR_TASK
if (forward != null) { if(forward != null) {
intent.type = forward.type intent.type = forward.type
intent.action = forward.action intent.action = forward.action
intent.putExtras(forward) intent.putExtras(forward)
@ -629,56 +673,59 @@ class MainActivity : BottomSheetActivity(), ActionButtonActivity, HasAndroidInje
private fun logout() { private fun logout() {
accountManager.activeAccount?.let { activeAccount -> accountManager.activeAccount?.let { activeAccount ->
AlertDialog.Builder(this) AlertDialog.Builder(this)
.setTitle(R.string.action_logout) .setTitle(R.string.action_logout)
.setMessage(getString(R.string.action_logout_confirm, activeAccount.fullName)) .setMessage(getString(R.string.action_logout_confirm, activeAccount.fullName))
.setPositiveButton(android.R.string.yes) { _: DialogInterface?, _: Int -> .setPositiveButton(android.R.string.yes) { _: DialogInterface?, _: Int ->
NotificationHelper.deleteNotificationChannelsForAccount(activeAccount, this) NotificationHelper.deleteNotificationChannelsForAccount(activeAccount, this)
cacheUpdater.clearForUser(activeAccount.id) cacheUpdater.clearForUser(activeAccount.id)
conversationRepository.deleteCacheForAccount(activeAccount.id) conversationRepository.deleteCacheForAccount(activeAccount.id)
removeShortcut(this, activeAccount) removeShortcut(this, activeAccount)
val newAccount = accountManager.logActiveAccountOut() val newAccount = accountManager.logActiveAccountOut()
initPullNotifications() initPullNotifications()
val intent = if (newAccount == null) { val intent = if(newAccount == null) {
LoginActivity.getIntent(this, false) LoginActivity.getIntent(this, false)
} else { } else {
Intent(this, MainActivity::class.java) Intent(this, MainActivity::class.java)
}
startActivity(intent)
finishWithoutSlideOutAnimation()
} }
.setNegativeButton(android.R.string.no, null) startActivity(intent)
.show() finishWithoutSlideOutAnimation()
}
.setNegativeButton(android.R.string.no, null)
.show()
} }
} }
private fun fetchUserInfo() { private fun fetchUserInfo() {
mastodonApi.accountVerifyCredentials() mastodonApi.accountVerifyCredentials()
.observeOn(AndroidSchedulers.mainThread()) .observeOn(AndroidSchedulers.mainThread())
.autoDispose(this, Lifecycle.Event.ON_DESTROY) .autoDispose(this, Lifecycle.Event.ON_DESTROY)
.subscribe( .subscribe(
{ userInfo -> { userInfo ->
onFetchUserInfoSuccess(userInfo) onFetchUserInfoSuccess(userInfo)
}, },
{ throwable -> { throwable ->
Log.e(TAG, "Failed to fetch user info. " + throwable.message) Log.e(TAG, "Failed to fetch user info. " + throwable.message)
} }
) )
} }
private fun onFetchUserInfoSuccess(me: Account) { private fun onFetchUserInfoSuccess(me: Account) {
glide.asBitmap() glide.asBitmap()
.load(me.header) .load(me.header)
.into(header.accountHeaderBackground) .into(header.accountHeaderBackground)
loadDrawerAvatar(me.avatar, false) loadDrawerAvatar(me.avatar, false)
accountManager.updateActiveAccount(me) accountManager.updateActiveAccount(me)
NotificationHelper.createNotificationChannelsForAccount(accountManager.activeAccount!!, this) NotificationHelper.createNotificationChannelsForAccount(
accountManager.activeAccount!!,
this
)
initPullNotifications() initPullNotifications()
// Show follow requests in the menu, if this is a locked account. // Show follow requests in the menu, if this is a locked account.
if (me.locked && mainDrawer.getDrawerItem(DRAWER_ITEM_FOLLOW_REQUESTS) == null) { if(me.locked && mainDrawer.getDrawerItem(DRAWER_ITEM_FOLLOW_REQUESTS) == null) {
val followRequestsItem = primaryDrawerItem { val followRequestsItem = primaryDrawerItem {
identifier = DRAWER_ITEM_FOLLOW_REQUESTS identifier = DRAWER_ITEM_FOLLOW_REQUESTS
nameRes = R.string.action_view_follow_requests nameRes = R.string.action_view_follow_requests
@ -690,7 +737,7 @@ class MainActivity : BottomSheetActivity(), ActionButtonActivity, HasAndroidInje
} }
} }
mainDrawer.addItemAtPosition(4, followRequestsItem) mainDrawer.addItemAtPosition(4, followRequestsItem)
} else if (!me.locked) { } else if(!me.locked) {
mainDrawer.removeItems(DRAWER_ITEM_FOLLOW_REQUESTS) mainDrawer.removeItems(DRAWER_ITEM_FOLLOW_REQUESTS)
} }
updateProfiles() updateProfiles()
@ -706,7 +753,7 @@ class MainActivity : BottomSheetActivity(), ActionButtonActivity, HasAndroidInje
RoundedCorners(resources.getDimensionPixelSize(R.dimen.avatar_radius_36dp)) RoundedCorners(resources.getDimensionPixelSize(R.dimen.avatar_radius_36dp))
) )
.apply { .apply {
if (showPlaceholder) { if(showPlaceholder) {
placeholder(R.drawable.avatar_default) placeholder(R.drawable.avatar_default)
} }
} }
@ -714,10 +761,15 @@ class MainActivity : BottomSheetActivity(), ActionButtonActivity, HasAndroidInje
override fun onLoadStarted(placeholder: Drawable?) { override fun onLoadStarted(placeholder: Drawable?) {
if(placeholder != null) { if(placeholder != null) {
mainToolbar.navigationIcon = FixedSizeDrawable(placeholder, navIconSize, navIconSize) mainToolbar.navigationIcon =
FixedSizeDrawable(placeholder, navIconSize, navIconSize)
} }
} }
override fun onResourceReady(resource: Drawable, transition: Transition<in Drawable>?) {
override fun onResourceReady(
resource: Drawable,
transition: Transition<in Drawable>?
) {
mainToolbar.navigationIcon = resource mainToolbar.navigationIcon = resource
} }
@ -729,40 +781,45 @@ class MainActivity : BottomSheetActivity(), ActionButtonActivity, HasAndroidInje
private fun fetchAnnouncements() { private fun fetchAnnouncements() {
mastodonApi.listAnnouncements(false) mastodonApi.listAnnouncements(false)
.observeOn(AndroidSchedulers.mainThread()) .observeOn(AndroidSchedulers.mainThread())
.autoDispose(this, Lifecycle.Event.ON_DESTROY) .autoDispose(this, Lifecycle.Event.ON_DESTROY)
.subscribe( .subscribe(
{ announcements -> { announcements ->
unreadAnnouncementsCount = announcements.count { !it.read } unreadAnnouncementsCount = announcements.count { !it.read }
updateAnnouncementsBadge() updateAnnouncementsBadge()
}, },
{ {
Log.w(TAG, "Failed to fetch announcements.", it) Log.w(TAG, "Failed to fetch announcements.", it)
} }
) )
} }
private fun updateAnnouncementsBadge() { private fun updateAnnouncementsBadge() {
mainDrawer.updateBadge(DRAWER_ITEM_ANNOUNCEMENTS, StringHolder(if (unreadAnnouncementsCount <= 0) null else unreadAnnouncementsCount.toString())) mainDrawer.updateBadge(
DRAWER_ITEM_ANNOUNCEMENTS,
StringHolder(if(unreadAnnouncementsCount <= 0) null else unreadAnnouncementsCount.toString())
)
} }
private fun updateProfiles() { private fun updateProfiles() {
val profiles: MutableList<IProfile> = accountManager.getAllAccountsOrderedByActive().map { acc -> val profiles: MutableList<IProfile> =
val emojifiedName = EmojiCompat.get().process(acc.displayName.emojify(acc.emojis, header, true)) accountManager.getAllAccountsOrderedByActive().map { acc ->
val emojifiedName =
EmojiCompat.get().process(acc.displayName.emojify(acc.emojis, header, true))
ProfileDrawerItem().apply { ProfileDrawerItem().apply {
isSelected = acc.isActive isSelected = acc.isActive
nameText = emojifiedName nameText = emojifiedName
iconUrl = acc.profilePictureUrl iconUrl = acc.profilePictureUrl
isNameShown = true isNameShown = true
identifier = acc.id identifier = acc.id
descriptionText = acc.fullName descriptionText = acc.fullName
} }
}.toMutableList() }.toMutableList()
// reuse the already existing "add account" item // reuse the already existing "add account" item
for (profile in header.profiles.orEmpty()) { for(profile in header.profiles.orEmpty()) {
if (profile.identifier == DRAWER_ITEM_ADD_ACCOUNT) { if(profile.identifier == DRAWER_ITEM_ADD_ACCOUNT) {
profiles.add(profile) profiles.add(profile)
break break
} }
@ -775,23 +832,23 @@ class MainActivity : BottomSheetActivity(), ActionButtonActivity, HasAndroidInje
private fun draftWarning() { private fun draftWarning() {
val sharedPrefsKey = "show_draft_warning" val sharedPrefsKey = "show_draft_warning"
appDb.tootDao().savedTootCount() appDb.tootDao().savedTootCount()
.subscribeOn(Schedulers.io()) .subscribeOn(Schedulers.io())
.observeOn(AndroidSchedulers.mainThread()) .observeOn(AndroidSchedulers.mainThread())
.autoDispose(this, Lifecycle.Event.ON_DESTROY) .autoDispose(this, Lifecycle.Event.ON_DESTROY)
.subscribe { draftCount -> .subscribe { draftCount ->
val showDraftWarning = preferences.getBoolean(sharedPrefsKey, true) val showDraftWarning = preferences.getBoolean(sharedPrefsKey, true)
if (draftCount > 0 && showDraftWarning) { if(draftCount > 0 && showDraftWarning) {
AlertDialog.Builder(this) AlertDialog.Builder(this)
.setMessage(R.string.new_drafts_warning) .setMessage(R.string.new_drafts_warning)
.setNegativeButton("Don't show again") { _, _ -> .setNegativeButton("Don't show again") { _, _ ->
preferences.edit(commit = true) { preferences.edit(commit = true) {
putBoolean(sharedPrefsKey, false) putBoolean(sharedPrefsKey, false)
} }
} }
.setPositiveButton(android.R.string.ok, null) .setPositiveButton(android.R.string.ok, null)
.show() .show()
}
} }
}
} }
@ -810,20 +867,20 @@ class MainActivity : BottomSheetActivity(), ActionButtonActivity, HasAndroidInje
private inline fun primaryDrawerItem(block: PrimaryDrawerItem.() -> Unit): PrimaryDrawerItem { private inline fun primaryDrawerItem(block: PrimaryDrawerItem.() -> Unit): PrimaryDrawerItem {
return PrimaryDrawerItem() return PrimaryDrawerItem()
.apply { .apply {
isSelectable = false isSelectable = false
isIconTinted = true isIconTinted = true
} }
.apply(block) .apply(block)
} }
private inline fun secondaryDrawerItem(block: SecondaryDrawerItem.() -> Unit): SecondaryDrawerItem { private inline fun secondaryDrawerItem(block: SecondaryDrawerItem.() -> Unit): SecondaryDrawerItem {
return SecondaryDrawerItem() return SecondaryDrawerItem()
.apply { .apply {
isSelectable = false isSelectable = false
isIconTinted = true isIconTinted = true
} }
.apply(block) .apply(block)
} }
private var AbstractDrawerItem<*, *>.onClick: () -> Unit private var AbstractDrawerItem<*, *>.onClick: () -> Unit

View file

@ -612,4 +612,9 @@
<string name="drafts_failed_loading_reply">Failed loading Reply information</string> <string name="drafts_failed_loading_reply">Failed loading Reply information</string>
<string name="draft_deleted">Draft deleted</string> <string name="draft_deleted">Draft deleted</string>
<string name="drafts_toot_reply_removed">The Toot you drafted a reply to has been removed</string> <string name="drafts_toot_reply_removed">The Toot you drafted a reply to has been removed</string>
<!-- Debug strings -->
<string name="debug_status">Debug build</string>
<string name="debug_status_message">A debug build has enabled logs and debugging information for the application. Information might leak. Please use it carefully.</string>
<string name="debug_status_message_close">Close</string>
</resources> </resources>